Ignore:
Timestamp:
Nov 14, 2012, 12:59:34 PM (13 years ago)
Author:
Silvan Scherrer
Message:

Samba Server: update vendor to 3.6.0

Location:
vendor/current/lib/util
Files:
19 added
12 deleted
55 edited

Legend:

Unmodified
Added
Removed
  • vendor/current/lib/util/asn1.c

    r597 r740  
    215215}
    216216
    217 bool ber_write_OID_String(DATA_BLOB *blob, const char *OID)
    218 {
    219         uint_t v, v2;
     217bool ber_write_OID_String(TALLOC_CTX *mem_ctx, DATA_BLOB *blob, const char *OID)
     218{
     219        unsigned int v, v2;
    220220        const char *p = (const char *)OID;
    221221        char *newp;
    222222        int i;
    223223
     224        if (!isdigit(*p)) return false;
    224225        v = strtoul(p, &newp, 10);
    225226        if (newp[0] != '.') return false;
    226227        p = newp + 1;
    227228
     229        if (!isdigit(*p)) return false;
    228230        v2 = strtoul(p, &newp, 10);
    229231        if (newp[0] != '.') return false;
     
    231233
    232234        /*the ber representation can't use more space then the string one */
    233         *blob = data_blob(NULL, strlen(OID));
     235        *blob = data_blob_talloc(mem_ctx, NULL, strlen(OID));
    234236        if (!blob->data) return false;
    235237
     
    238240        i = 1;
    239241        while (*p) {
     242                if (!isdigit(*p)) return false;
    240243                v = strtoul(p, &newp, 10);
    241244                if (newp[0] == '.') {
    242245                        p = newp + 1;
     246                        /* check for empty last component */
     247                        if (!*p) return false;
    243248                } else if (newp[0] == '\0') {
    244249                        p = newp;
     
    259264}
    260265
     266/**
     267 * Serialize partial OID string.
     268 * Partial OIDs are in the form:
     269 *   1:2.5.6:0x81
     270 *   1:2.5.6:0x8182
     271 */
     272bool ber_write_partial_OID_String(TALLOC_CTX *mem_ctx, DATA_BLOB *blob, const char *partial_oid)
     273{
     274        TALLOC_CTX *tmp_ctx = talloc_new(mem_ctx);
     275        char *oid = talloc_strdup(tmp_ctx, partial_oid);
     276        char *p;
     277
     278        /* truncate partial part so ber_write_OID_String() works */
     279        p = strchr(oid, ':');
     280        if (p) {
     281                *p = '\0';
     282                p++;
     283        }
     284
     285        if (!ber_write_OID_String(mem_ctx, blob, oid)) {
     286                talloc_free(tmp_ctx);
     287                return false;
     288        }
     289
     290        /* Add partially encoded sub-identifier */
     291        if (p) {
     292                DATA_BLOB tmp_blob = strhex_to_data_blob(tmp_ctx, p);
     293                if (!data_blob_append(mem_ctx, blob, tmp_blob.data,
     294                                      tmp_blob.length)) {
     295                        talloc_free(tmp_ctx);
     296                        return false;
     297                }
     298        }
     299
     300        talloc_free(tmp_ctx);
     301
     302        return true;
     303}
     304
    261305/* write an object ID to a ASN1 buffer */
    262306bool asn1_write_OID(struct asn1_data *data, const char *OID)
     
    266310        if (!asn1_push_tag(data, ASN1_OID)) return false;
    267311
    268         if (!ber_write_OID_String(&blob, OID)) {
     312        if (!ber_write_OID_String(NULL, &blob, OID)) {
    269313                data->has_error = true;
    270314                return false;
     
    453497
    454498        return (b == tag);
     499}
     500
     501/*
     502 * just get the needed size the tag would consume
     503 */
     504bool asn1_peek_tag_needed_size(struct asn1_data *data, uint8_t tag, size_t *size)
     505{
     506        off_t start_ofs = data->ofs;
     507        uint8_t b;
     508        size_t taglen = 0;
     509
     510        if (data->has_error) {
     511                return false;
     512        }
     513
     514        if (!asn1_read_uint8(data, &b)) {
     515                data->ofs = start_ofs;
     516                data->has_error = false;
     517                return false;
     518        }
     519
     520        if (b != tag) {
     521                data->ofs = start_ofs;
     522                data->has_error = false;
     523                return false;
     524        }
     525
     526        if (!asn1_read_uint8(data, &b)) {
     527                data->ofs = start_ofs;
     528                data->has_error = false;
     529                return false;
     530        }
     531
     532        if (b & 0x80) {
     533                int n = b & 0x7f;
     534                if (!asn1_read_uint8(data, &b)) {
     535                        data->ofs = start_ofs;
     536                        data->has_error = false;
     537                        return false;
     538                }
     539                if (n > 4) {
     540                        /*
     541                         * We should not allow more than 4 bytes
     542                         * for the encoding of the tag length.
     543                         *
     544                         * Otherwise we'd overflow the taglen
     545                         * variable on 32 bit systems.
     546                         */
     547                        data->ofs = start_ofs;
     548                        data->has_error = false;
     549                        return false;
     550                }
     551                taglen = b;
     552                while (n > 1) {
     553                        if (!asn1_read_uint8(data, &b)) {
     554                                data->ofs = start_ofs;
     555                                data->has_error = false;
     556                                return false;
     557                        }
     558                        taglen = (taglen << 8) | b;
     559                        n--;
     560                }
     561        } else {
     562                taglen = b;
     563        }
     564
     565        *size = (data->ofs - start_ofs) + taglen;
     566
     567        data->ofs = start_ofs;
     568        data->has_error = false;
     569        return true;
    455570}
    456571
     
    544659}
    545660
    546 /* read an object ID from a data blob */
    547 bool ber_read_OID_String(TALLOC_CTX *mem_ctx, DATA_BLOB blob, const char **OID)
     661/**
     662 * Internal implementation for reading binary OIDs
     663 * Reading is done as far in the buffer as valid OID
     664 * till buffer ends or not valid sub-identifier is found.
     665 */
     666static bool _ber_read_OID_String_impl(TALLOC_CTX *mem_ctx, DATA_BLOB blob,
     667                                      char **OID, size_t *bytes_eaten)
    548668{
    549669        int i;
    550670        uint8_t *b;
    551         uint_t v;
     671        unsigned int v;
    552672        char *tmp_oid = NULL;
    553673
     
    560680        tmp_oid = talloc_asprintf_append_buffer(tmp_oid, ".%u",  b[0]%40);
    561681        if (!tmp_oid) goto nomem;
     682
     683        if (bytes_eaten != NULL) {
     684                *bytes_eaten = 0;
     685        }
    562686
    563687        for(i = 1, v = 0; i < blob.length; i++) {
     
    566690                        tmp_oid = talloc_asprintf_append_buffer(tmp_oid, ".%u",  v);
    567691                        v = 0;
     692                        if (bytes_eaten)
     693                                *bytes_eaten = i+1;
    568694                }
    569695                if (!tmp_oid) goto nomem;
    570696        }
    571697
    572         if (v != 0) {
    573                 talloc_free(tmp_oid);
    574                 return false;
    575         }
    576 
    577698        *OID = tmp_oid;
    578699        return true;
    579700
    580 nomem: 
     701nomem:
    581702        return false;
    582703}
    583704
     705/* read an object ID from a data blob */
     706bool ber_read_OID_String(TALLOC_CTX *mem_ctx, DATA_BLOB blob, char **OID)
     707{
     708        size_t bytes_eaten;
     709
     710        if (!_ber_read_OID_String_impl(mem_ctx, blob, OID, &bytes_eaten))
     711                return false;
     712
     713        return (bytes_eaten == blob.length);
     714}
     715
     716/**
     717 * Deserialize partial OID string.
     718 * Partial OIDs are in the form:
     719 *   1:2.5.6:0x81
     720 *   1:2.5.6:0x8182
     721 */
     722bool ber_read_partial_OID_String(TALLOC_CTX *mem_ctx, DATA_BLOB blob,
     723                                 char **partial_oid)
     724{
     725        size_t bytes_left;
     726        size_t bytes_eaten;
     727        char *identifier = NULL;
     728        char *tmp_oid = NULL;
     729
     730        if (!_ber_read_OID_String_impl(mem_ctx, blob, &tmp_oid, &bytes_eaten))
     731                return false;
     732
     733        if (bytes_eaten < blob.length) {
     734                bytes_left = blob.length - bytes_eaten;
     735                identifier = hex_encode_talloc(mem_ctx, &blob.data[bytes_eaten], bytes_left);
     736                if (!identifier)        goto nomem;
     737
     738                *partial_oid = talloc_asprintf_append_buffer(tmp_oid, ":0x%s", identifier);
     739                if (!*partial_oid)      goto nomem;
     740                TALLOC_FREE(identifier);
     741        } else {
     742                *partial_oid = tmp_oid;
     743        }
     744
     745        return true;
     746
     747nomem:
     748        TALLOC_FREE(identifier);
     749        TALLOC_FREE(tmp_oid);
     750        return false;
     751}
     752
    584753/* read an object ID from a ASN1 buffer */
    585 bool asn1_read_OID(struct asn1_data *data, TALLOC_CTX *mem_ctx, const char **OID)
     754bool asn1_read_OID(struct asn1_data *data, TALLOC_CTX *mem_ctx, char **OID)
    586755{
    587756        DATA_BLOB blob;
     
    622791bool asn1_check_OID(struct asn1_data *data, const char *OID)
    623792{
    624         const char *id;
     793        char *id;
    625794
    626795        if (!asn1_read_OID(data, data, &id)) return false;
    627796
    628797        if (strcmp(id, OID) != 0) {
    629                 talloc_free(discard_const(id));
    630                 data->has_error = true;
    631                 return false;
    632         }
    633         talloc_free(discard_const(id));
     798                talloc_free(id);
     799                data->has_error = true;
     800                return false;
     801        }
     802        talloc_free(id);
    634803        return true;
    635804}
     
    8651034        if (size > blob.length) {
    8661035                return STATUS_MORE_ENTRIES;
    867         }               
     1036        }
    8681037
    8691038        *packet_size = size;
    8701039        return NT_STATUS_OK;
    8711040}
     1041
     1042NTSTATUS asn1_peek_full_tag(DATA_BLOB blob, uint8_t tag, size_t *packet_size)
     1043{
     1044        struct asn1_data asn1;
     1045        size_t size;
     1046        bool ok;
     1047
     1048        ZERO_STRUCT(asn1);
     1049        asn1.data = blob.data;
     1050        asn1.length = blob.length;
     1051
     1052        ok = asn1_peek_tag_needed_size(&asn1, tag, &size);
     1053        if (!ok) {
     1054                return NT_STATUS_INVALID_BUFFER_SIZE;
     1055        }
     1056
     1057        if (size > blob.length) {
     1058                *packet_size = size;
     1059                return STATUS_MORE_ENTRIES;
     1060        }               
     1061
     1062        *packet_size = size;
     1063        return NT_STATUS_OK;
     1064}
  • vendor/current/lib/util/asn1.h

    r414 r740  
    6262bool asn1_write_Integer(struct asn1_data *data, int i);
    6363bool asn1_write_BitString(struct asn1_data *data, const void *p, size_t length, uint8_t padding);
    64 bool ber_write_OID_String(DATA_BLOB *blob, const char *OID);
     64bool ber_write_OID_String(TALLOC_CTX *mem_ctx, DATA_BLOB *blob, const char *OID);
     65bool ber_write_partial_OID_String(TALLOC_CTX *mem_ctx, DATA_BLOB *blob, const char *partial_oid);
    6566bool asn1_write_OID(struct asn1_data *data, const char *OID);
    6667bool asn1_write_OctetString(struct asn1_data *data, const void *p, size_t length);
     
    7980bool asn1_read_uint8(struct asn1_data *data, uint8_t *v);
    8081bool asn1_peek_uint8(struct asn1_data *data, uint8_t *v);
     82bool asn1_peek_tag_needed_size(struct asn1_data *data, uint8_t tag, size_t *size);
    8183bool asn1_peek_tag(struct asn1_data *data, uint8_t tag);
    8284bool asn1_start_tag(struct asn1_data *data, uint8_t tag);
    8385bool asn1_end_tag(struct asn1_data *data);
    8486int asn1_tag_remaining(struct asn1_data *data);
    85 bool ber_read_OID_String(TALLOC_CTX *mem_ctx, DATA_BLOB blob, const char **OID);
    86 bool asn1_read_OID(struct asn1_data *data, TALLOC_CTX *mem_ctx, const char **OID);
     87bool ber_read_OID_String(TALLOC_CTX *mem_ctx, DATA_BLOB blob, char **OID);
     88bool ber_read_partial_OID_String(TALLOC_CTX *mem_ctx, DATA_BLOB blob, char **partial_oid);
     89bool asn1_read_OID(struct asn1_data *data, TALLOC_CTX *mem_ctx, char **OID);
    8790bool asn1_check_OID(struct asn1_data *data, const char *OID);
    8891bool asn1_read_LDAPString(struct asn1_data *data, TALLOC_CTX *mem_ctx, char **s);
     
    99102void asn1_load_nocopy(struct asn1_data *data, uint8_t *buf, size_t len);
    100103NTSTATUS asn1_full_tag(DATA_BLOB blob, uint8_t tag, size_t *packet_size);
     104NTSTATUS asn1_peek_full_tag(DATA_BLOB blob, uint8_t tag, size_t *packet_size);
    101105
    102106#endif /* _ASN_1_H */
  • vendor/current/lib/util/attr.h

    r414 r740  
    2828#  define UNUSED(param) param
    2929/** Feel free to add definitions for other compilers here. */
    30 #endif
    31 
    32 #ifdef HAVE_VISIBILITY_ATTR
    33 #  define _PUBLIC_ __attribute__((visibility("default")))
    34 #else
    35 #  define _PUBLIC_
    3630#endif
    3731
     
    8882#endif
    8983
     84#ifndef FORMAT_ATTRIBUTE
     85#if __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ >= 1)
     86/** Use gcc attribute to check printf fns.  a1 is argument to format()
     87 * in the above macro.  This is needed to support Heimdal's printf
     88 * decorations. Note that some gcc 2.x versions don't handle this
     89 * properly, and as such I've used the same minimum from heimdal: GCC 3.1 **/
     90#define FORMAT_ATTRIBUTE(a) __attribute__ ((format a))
     91#else
     92#define FORMAT_ATTRIBUTE(a)
     93#endif
     94#endif
     95
    9096#endif /* __UTIL_ATTR_H__ */
  • vendor/current/lib/util/become_daemon.c

    r414 r740  
    6767****************************************************************************/
    6868
    69 _PUBLIC_ void become_daemon(bool do_fork, bool no_process_group)
     69_PUBLIC_ void become_daemon(bool do_fork, bool no_process_group, bool log_stdout)
    7070{
    7171        if (do_fork) {
     
    8888#endif /* HAVE_SETSID */
    8989
    90         /* Close fd's 0,1,2. Needed if started by rsh */
    91         close_low_fds(false);  /* Don't close stderr, let the debug system
    92                                   attach it to the logfile */
     90        if (!log_stdout) {
     91                /* Close fd's 0,1,2. Needed if started by rsh */
     92                close_low_fds(false);  /* Don't close stderr, let the debug system
     93                                          attach it to the logfile */
     94        }
    9395}
  • vendor/current/lib/util/binsearch.h

    r414 r740  
    6666        }} } while (0)
    6767
     68/*
     69  like BINARY_ARRAY_SEARCH_P, but assumes that the array is an array
     70  of elements, rather than pointers to structures
     71
     72  result points to the found structure, or NULL
     73 */
     74#define BINARY_ARRAY_SEARCH_V(array, array_size, target, comparison_fn, result) do { \
     75        int32_t _b, _e; \
     76        (result) = NULL; \
     77        if (array_size) { for (_b = 0, _e = (array_size)-1; _b <= _e; ) {       \
     78                int32_t _i = (_b+_e)/2; \
     79                int _r = comparison_fn(target, array[_i]); \
     80                if (_r == 0) { (result) = &array[_i]; break; } \
     81                if (_r < 0) _e = _i - 1; else _b = _i + 1; \
     82        }} } while (0)
     83
    6884#endif
  • vendor/current/lib/util/byteorder.h

    r414 r740  
    5555
    5656#define CVAL(buf,pos) (((uint8_t *)(buf))[pos])
    57 #define PVAL(buf,pos) ((uint_t)CVAL(buf,pos))
     57#define PVAL(buf,pos) ((unsigned int)CVAL(buf,pos))
    5858#define SVAL(buf,pos) (PVAL(buf,pos)|PVAL(buf,(pos)+1)<<8)
    5959
     
    145145#endif
    146146
    147 #define CVAL(buf,pos) ((uint_t)(((const uint8_t *)(buf))[pos]))
     147#define CVAL(buf,pos) ((unsigned int)(((const uint8_t *)(buf))[pos]))
    148148#define CVAL_NC(buf,pos) (((uint8_t *)(buf))[pos]) /* Non-const version of CVAL */
    149149#define PVAL(buf,pos) (CVAL(buf,pos))
     
    186186/* get single value from an SMB buffer */
    187187#define SVAL(buf,pos) (*(const uint16_t *)((const char *)(buf) + (pos)))
    188 #define SVAL_NC(buf,pos) (*(uint16_t *)((char *)(buf) + (pos))) /* Non const version of above. */
     188#define SVAL_NC(buf,pos) (*(uint16_t *)((void *)((char *)(buf) + (pos)))) /* Non const version of above. */
    189189#define IVAL(buf,pos) (*(const uint32_t *)((const char *)(buf) + (pos)))
    190 #define IVAL_NC(buf,pos) (*(uint32_t *)((char *)(buf) + (pos))) /* Non const version of above. */
     190#define IVAL_NC(buf,pos) (*(uint32_t *)((void *)((char *)(buf) + (pos)))) /* Non const version of above. */
    191191#define SVALS(buf,pos) (*(const int16_t *)((const char *)(buf) + (pos)))
    192 #define SVALS_NC(buf,pos) (*(int16_t *)((char *)(buf) + (pos))) /* Non const version of above. */
     192#define SVALS_NC(buf,pos) (*(int16_t *)((void *)((char *)(buf) + (pos)))) /* Non const version of above. */
    193193#define IVALS(buf,pos) (*(const int32_t *)((const char *)(buf) + (pos)))
    194 #define IVALS_NC(buf,pos) (*(int32_t *)((char *)(buf) + (pos))) /* Non const version of above. */
     194#define IVALS_NC(buf,pos) (*(int32_t *)((void *)((char *)(buf) + (pos)))) /* Non const version of above. */
    195195
    196196/* store single value in an SMB buffer */
     
    202202#endif /* not CAREFUL_ALIGNMENT */
    203203
    204 /* now the reverse routines - these are used in nmb packets (mostly) */
    205 #define SREV(x) ((((x)&0xFF)<<8) | (((x)>>8)&0xFF))
    206 #define IREV(x) ((SREV(x)<<16) | (SREV((x)>>16)))
    207 
    208 #define RSVAL(buf,pos) SREV(SVAL(buf,pos))
    209 #define RSVALS(buf,pos) SREV(SVALS(buf,pos))
    210 #define RIVAL(buf,pos) IREV(IVAL(buf,pos))
    211 #define RIVALS(buf,pos) IREV(IVALS(buf,pos))
    212 #define RSSVAL(buf,pos,val) SSVAL(buf,pos,SREV(val))
    213 #define RSSVALS(buf,pos,val) SSVALS(buf,pos,SREV(val))
    214 #define RSIVAL(buf,pos,val) SIVAL(buf,pos,IREV(val))
    215 #define RSIVALS(buf,pos,val) SIVALS(buf,pos,IREV(val))
    216 
    217 /* Alignment macros. */
    218 #define ALIGN4(p,base) ((p) + ((4 - (PTR_DIFF((p), (base)) & 3)) & 3))
    219 #define ALIGN2(p,base) ((p) + ((2 - (PTR_DIFF((p), (base)) & 1)) & 1))
    220 
    221 
    222 /* macros for accessing SMB protocol elements */
    223 #define VWV(vwv) ((vwv)*2)
    224 
    225204/* 64 bit macros */
    226205#define BVAL(p, ofs) (IVAL(p,ofs) | (((uint64_t)IVAL(p,(ofs)+4)) << 32))
     
    229208#define SBVALS(p, ofs, v) (SBVAL(p,ofs,(uint64_t)v))
    230209
     210/* now the reverse routines - these are used in nmb packets (mostly) */
     211#define SREV(x) ((((x)&0xFF)<<8) | (((x)>>8)&0xFF))
     212#define IREV(x) ((SREV(x)<<16) | (SREV((x)>>16)))
     213#define BREV(x) ((IREV(x)<<32) | (IREV((x)>>32)))
     214
     215#define RSVAL(buf,pos) SREV(SVAL(buf,pos))
     216#define RSVALS(buf,pos) SREV(SVALS(buf,pos))
     217#define RIVAL(buf,pos) IREV(IVAL(buf,pos))
     218#define RIVALS(buf,pos) IREV(IVALS(buf,pos))
     219#define RBVAL(buf,pos) BREV(BVAL(buf,pos))
     220#define RBVALS(buf,pos) BREV(BVALS(buf,pos))
     221#define RSSVAL(buf,pos,val) SSVAL(buf,pos,SREV(val))
     222#define RSSVALS(buf,pos,val) SSVALS(buf,pos,SREV(val))
     223#define RSIVAL(buf,pos,val) SIVAL(buf,pos,IREV(val))
     224#define RSIVALS(buf,pos,val) SIVALS(buf,pos,IREV(val))
     225#define RSBVAL(buf,pos,val) SBVAL(buf,pos,BREV(val))
     226#define RSBVALS(buf,pos,val) SBVALS(buf,pos,BREV(val))
     227
     228/* Alignment macros. */
     229#define ALIGN4(p,base) ((p) + ((4 - (PTR_DIFF((p), (base)) & 3)) & 3))
     230#define ALIGN2(p,base) ((p) + ((2 - (PTR_DIFF((p), (base)) & 1)) & 1))
     231
     232
     233/* macros for accessing SMB protocol elements */
     234#define VWV(vwv) ((vwv)*2)
     235
    231236#endif /* _BYTEORDER_H */
  • vendor/current/lib/util/charset/charcnv.c

    r414 r740  
    3939 */
    4040
    41 struct smb_iconv_convenience {
    42         const char *unix_charset;
    43         const char *dos_charset;
    44         bool native_iconv;
    45         smb_iconv_t conv_handles[NUM_CHARSETS][NUM_CHARSETS];
    46 };
    47 
    48 
    49 /**
    50  * Return the name of a charset to give to iconv().
    51  **/
    52 static const char *charset_name(struct smb_iconv_convenience *ic, charset_t ch)
    53 {
    54         switch (ch) {
    55         case CH_UTF16: return "UTF-16LE";
    56         case CH_UNIX: return ic->unix_charset;
    57         case CH_DOS: return ic->dos_charset;
    58         case CH_UTF8: return "UTF8";
    59         case CH_UTF16BE: return "UTF-16BE";
    60         case CH_UTF16MUNGED: return "UTF16_MUNGED";
    61         default:
    62         return "ASCII";
    63         }
    64 }
    65 
    66 /**
    67  re-initialize iconv conversion descriptors
    68 **/
    69 static int close_iconv_convenience(struct smb_iconv_convenience *data)
    70 {
    71         unsigned c1, c2;
    72         for (c1=0;c1<NUM_CHARSETS;c1++) {
    73                 for (c2=0;c2<NUM_CHARSETS;c2++) {
    74                         if (data->conv_handles[c1][c2] != NULL) {
    75                                 if (data->conv_handles[c1][c2] != (smb_iconv_t)-1) {
    76                                         smb_iconv_close(data->conv_handles[c1][c2]);
    77                                 }
    78                                 data->conv_handles[c1][c2] = NULL;
    79                         }
    80                 }
    81         }
    82 
    83         return 0;
    84 }
    85 
    86 _PUBLIC_ struct smb_iconv_convenience *smb_iconv_convenience_init(TALLOC_CTX *mem_ctx,
    87                                                          const char *dos_charset,
    88                                                          const char *unix_charset,
    89                                                          bool native_iconv)
    90 {
    91         struct smb_iconv_convenience *ret = talloc_zero(mem_ctx,
    92                                         struct smb_iconv_convenience);
    93 
    94         if (ret == NULL) {
    95                 return NULL;
    96         }
    97 
    98         talloc_set_destructor(ret, close_iconv_convenience);
    99 
    100         ret->dos_charset = talloc_strdup(ret, dos_charset);
    101         ret->unix_charset = talloc_strdup(ret, unix_charset);
    102         ret->native_iconv = native_iconv;
    103 
    104         return ret;
    105 }
    106 
    107 /*
    108   on-demand initialisation of conversion handles
    109 */
    110 static smb_iconv_t get_conv_handle(struct smb_iconv_convenience *ic,
    111                                    charset_t from, charset_t to)
    112 {
    113         const char *n1, *n2;
    114         static bool initialised;
    115 
    116         if (initialised == false) {
    117                 initialised = true;
    118                
    119 #ifdef LC_ALL
    120                 /* we set back the locale to C to get ASCII-compatible
    121                    toupper/lower functions.  For now we do not need
    122                    any other POSIX localisations anyway. When we
    123                    should really need localized string functions one
    124                    day we need to write our own ascii_tolower etc.
    125                 */
    126                 setlocale(LC_ALL, "C");
    127 #endif
    128         }
    129 
    130         if (ic->conv_handles[from][to]) {
    131                 return ic->conv_handles[from][to];
    132         }
    133 
    134         n1 = charset_name(ic, from);
    135         n2 = charset_name(ic, to);
    136 
    137         ic->conv_handles[from][to] = smb_iconv_open_ex(ic, n2, n1,
    138                                                        ic->native_iconv);
    139        
    140         if (ic->conv_handles[from][to] == (smb_iconv_t)-1) {
    141                 if ((from == CH_DOS || to == CH_DOS) &&
    142                     strcasecmp(charset_name(ic, CH_DOS), "ASCII") != 0) {
    143                         DEBUG(0,("dos charset '%s' unavailable - using ASCII\n",
    144                                  charset_name(ic, CH_DOS)));
    145                         ic->dos_charset = "ASCII";
    146 
    147                         n1 = charset_name(ic, from);
    148                         n2 = charset_name(ic, to);
    149                        
    150                         ic->conv_handles[from][to] =
    151                                 smb_iconv_open_ex(ic, n2, n1, ic->native_iconv);
    152                 }
    153         }
    154 
    155         return ic->conv_handles[from][to];
    156 }
    157 
    15841/**
    15942 * Convert string from one encoding to another, making error checking etc
     
    21497                                break;
    21598                }
    216                 DEBUG(0,("Conversion error: %s(%s)\n",reason,inbuf));
     99                DEBUG(0,("Conversion error: %s - ",reason));
     100                dump_data(0, (const uint8_t *) inbuf, i_len);
    217101                talloc_free(ob);
    218102                return (size_t)-1;
     
    349233}
    350234
    351 /*
    352   return the unicode codepoint for the next multi-byte CH_UNIX character
    353   in the string
    354 
    355   also return the number of bytes consumed (which tells the caller
    356   how many bytes to skip to get to the next CH_UNIX character)
    357 
    358   return INVALID_CODEPOINT if the next character cannot be converted
    359 */
    360 _PUBLIC_ codepoint_t next_codepoint_convenience(struct smb_iconv_convenience *ic,
    361                                     const char *str, size_t *size)
    362 {
    363         /* it cannot occupy more than 4 bytes in UTF16 format */
    364         uint8_t buf[4];
    365         smb_iconv_t descriptor;
    366         size_t ilen_orig;
    367         size_t ilen;
    368         size_t olen;
    369         char *outbuf;
    370 
    371         if ((str[0] & 0x80) == 0) {
    372                 *size = 1;
    373                 return (codepoint_t)str[0];
    374         }
    375 
    376         /* we assume that no multi-byte character can take
    377            more than 5 bytes. This is OK as we only
    378            support codepoints up to 1M */
    379         ilen_orig = strnlen(str, 5);
    380         ilen = ilen_orig;
    381 
    382         descriptor = get_conv_handle(ic, CH_UNIX, CH_UTF16);
    383         if (descriptor == (smb_iconv_t)-1) {
    384                 *size = 1;
    385                 return INVALID_CODEPOINT;
    386         }
    387 
    388         /* this looks a little strange, but it is needed to cope
    389            with codepoints above 64k */
    390         olen = 2;
    391         outbuf = (char *)buf;
    392         smb_iconv(descriptor, &str, &ilen, &outbuf, &olen);
    393         if (olen == 2) {
    394                 olen = 4;
    395                 outbuf = (char *)buf;
    396                 smb_iconv(descriptor,  &str, &ilen, &outbuf, &olen);
    397                 if (olen == 4) {
    398                         /* we didn't convert any bytes */
    399                         *size = 1;
    400                         return INVALID_CODEPOINT;
    401                 }
    402                 olen = 4 - olen;
    403         } else {
    404                 olen = 2 - olen;
    405         }
    406 
    407         *size = ilen_orig - ilen;
    408 
    409         if (olen == 2) {
    410                 return (codepoint_t)SVAL(buf, 0);
    411         }
    412         if (olen == 4) {
    413                 /* decode a 4 byte UTF16 character manually */
    414                 return (codepoint_t)0x10000 +
    415                         (buf[2] | ((buf[3] & 0x3)<<8) |
    416                          (buf[0]<<10) | ((buf[1] & 0x3)<<18));
    417         }
    418 
    419         /* no other length is valid */
    420         return INVALID_CODEPOINT;
    421 }
    422 
    423 /*
    424   push a single codepoint into a CH_UNIX string the target string must
    425   be able to hold the full character, which is guaranteed if it is at
    426   least 5 bytes in size. The caller may pass less than 5 bytes if they
    427   are sure the character will fit (for example, you can assume that
    428   uppercase/lowercase of a character will not add more than 1 byte)
    429 
    430   return the number of bytes occupied by the CH_UNIX character, or
    431   -1 on failure
    432 */
    433 _PUBLIC_ ssize_t push_codepoint_convenience(struct smb_iconv_convenience *ic,
    434                                 char *str, codepoint_t c)
    435 {
    436         smb_iconv_t descriptor;
    437         uint8_t buf[4];
    438         size_t ilen, olen;
    439         const char *inbuf;
    440        
    441         if (c < 128) {
    442                 *str = c;
    443                 return 1;
    444         }
    445 
    446         descriptor = get_conv_handle(ic,
    447                                      CH_UTF16, CH_UNIX);
    448         if (descriptor == (smb_iconv_t)-1) {
    449                 return -1;
    450         }
    451 
    452         if (c < 0x10000) {
    453                 ilen = 2;
    454                 olen = 5;
    455                 inbuf = (char *)buf;
    456                 SSVAL(buf, 0, c);
    457                 smb_iconv(descriptor, &inbuf, &ilen, &str, &olen);
    458                 if (ilen != 0) {
    459                         return -1;
    460                 }
    461                 return 5 - olen;
    462         }
    463 
    464         c -= 0x10000;
    465 
    466         buf[0] = (c>>10) & 0xFF;
    467         buf[1] = (c>>18) | 0xd8;
    468         buf[2] = c & 0xFF;
    469         buf[3] = ((c>>8) & 0x3) | 0xdc;
    470 
    471         ilen = 4;
    472         olen = 5;
    473         inbuf = (char *)buf;
    474 
    475         smb_iconv(descriptor, &inbuf, &ilen, &str, &olen);
    476         if (ilen != 0) {
    477                 return -1;
    478         }
    479         return 5 - olen;
    480 }
    481 
    482 
  • vendor/current/lib/util/charset/charset.h

    r587 r740  
    4040typedef uint16_t smb_ucs2_t;
    4141
     42#ifdef WORDS_BIGENDIAN
     43#define UCS2_SHIFT 8
     44#else
     45#define UCS2_SHIFT 0
     46#endif
     47
     48/* turn a 7 bit character into a ucs2 character */
     49#define UCS2_CHAR(c) ((c) << UCS2_SHIFT)
     50
     51/* return an ascii version of a ucs2 character */
     52#define UCS2_TO_CHAR(c) (((c) >> UCS2_SHIFT) & 0xff)
     53
     54/* Copy into a smb_ucs2_t from a possibly unaligned buffer. Return the copied smb_ucs2_t */
     55#define COPY_UCS2_CHAR(dest,src) (((unsigned char *)(dest))[0] = ((unsigned char *)(src))[0],\
     56                                ((unsigned char *)(dest))[1] = ((unsigned char *)(src))[1], (dest))
     57
     58
     59
    4260/*
    4361 *   for each charset we have a function that pulls from that charset to
     
    103121
    104122char *strchr_m(const char *s, char c);
     123size_t strlen_m_ext(const char *s, charset_t src_charset, charset_t dst_charset);
     124size_t strlen_m_ext_term(const char *s, charset_t src_charset,
     125                         charset_t dst_charset);
    105126size_t strlen_m_term(const char *s);
    106127size_t strlen_m_term_null(const char *s);
     
    150171
    151172extern struct smb_iconv_convenience *global_iconv_convenience;
    152 
     173struct smb_iconv_convenience *get_iconv_convenience(void);
     174smb_iconv_t get_conv_handle(struct smb_iconv_convenience *ic,
     175                            charset_t from, charset_t to);
     176const char *charset_name(struct smb_iconv_convenience *ic, charset_t ch);
     177
     178codepoint_t next_codepoint_ext(const char *str, charset_t src_charset,
     179                               size_t *size);
    153180codepoint_t next_codepoint(const char *str, size_t *size);
    154181ssize_t push_codepoint(char *str, codepoint_t c);
    155182
    156183/* codepoints */
     184codepoint_t next_codepoint_convenience_ext(struct smb_iconv_convenience *ic,
     185                            const char *str, charset_t src_charset,
     186                            size_t *size);
    157187codepoint_t next_codepoint_convenience(struct smb_iconv_convenience *ic,
    158188                            const char *str, size_t *size);
    159189ssize_t push_codepoint_convenience(struct smb_iconv_convenience *ic,
    160190                                char *str, codepoint_t c);
     191
    161192codepoint_t toupper_m(codepoint_t val);
    162193codepoint_t tolower_m(codepoint_t val);
     194bool islower_m(codepoint_t val);
     195bool isupper_m(codepoint_t val);
    163196int codepoint_cmpi(codepoint_t c1, codepoint_t c2);
    164197
    165198/* Iconv convenience functions */
    166 struct smb_iconv_convenience *smb_iconv_convenience_init(TALLOC_CTX *mem_ctx,
    167                                                          const char *dos_charset,
    168                                                          const char *unix_charset,
    169                                                          bool native_iconv);
     199struct smb_iconv_convenience *smb_iconv_convenience_reinit(TALLOC_CTX *mem_ctx,
     200                                                           const char *dos_charset,
     201                                                           const char *unix_charset,
     202                                                           const char *display_charset,
     203                                                           bool native_iconv,
     204                                                           struct smb_iconv_convenience *old_ic);
    170205
    171206bool convert_string_convenience(struct smb_iconv_convenience *ic,
     
    189224
    190225void load_case_tables(void);
    191 bool charset_register_backend(const void *_funcs);
     226void load_case_tables_library(void);
     227bool smb_register_charset(const struct charset_functions *funcs_in);
    192228
    193229/*
     
    264300NTSTATUS charset_ ## CHARSETNAME ## _init(void)                                                 \
    265301{                                                                                               \
    266         return smb_register_charset(& CHARSETNAME ## _functions);                               \
    267 }                                                                                               \
     302        if (!smb_register_charset(& CHARSETNAME ## _functions)) {       \
     303                return NT_STATUS_INTERNAL_ERROR;                        \
     304        }                                                               \
     305        return NT_STATUS_OK; \
     306}                                               \
    268307
    269308
  • vendor/current/lib/util/charset/codepoints.c

    r414 r740  
    11/*
    22   Unix SMB/CIFS implementation.
    3    Samba utility functions
    4    Copyright (C) Andrew Tridgell 1992-2001
     3   Character set conversion Extensions
     4   Copyright (C) Igor Vergeichik <iverg@mail.ru> 2001
     5   Copyright (C) Andrew Tridgell 2001
    56   Copyright (C) Simo Sorce 2001
     7   Copyright (C) Jelmer Vernooij 2007
    68   
    79   This program is free software; you can redistribute it and/or modify
     
    1719   You should have received a copy of the GNU General Public License
    1820   along with this program.  If not, see <http://www.gnu.org/licenses/>.
     21
    1922*/
    20 
    2123#include "includes.h"
     24#include "lib/util/charset/charset.h"
    2225#include "system/locale.h"
    23 #include "dynconfig/dynconfig.h"
     26#include "dynconfig.h"
     27
     28#ifdef strcasecmp
     29#undef strcasecmp
     30#endif
    2431
    2532/**
     
    3643/*******************************************************************
    3744load the case handling tables
     45
     46This is the function that should be called from library code.
    3847********************************************************************/
    39 void load_case_tables(void)
     48void load_case_tables_library(void)
    4049{
    4150        TALLOC_CTX *mem_ctx;
     
    4554                smb_panic("No memory for case_tables");
    4655        }
    47         upcase_table = map_file(talloc_asprintf(mem_ctx, "%s/upcase.dat", dyn_DATADIR), 0x20000);
    48         lowcase_table = map_file(talloc_asprintf(mem_ctx, "%s/lowcase.dat", dyn_DATADIR), 0x20000);
     56        upcase_table = map_file(talloc_asprintf(mem_ctx, "%s/upcase.dat", get_dyn_CODEPAGEDIR()), 0x20000);
     57        lowcase_table = map_file(talloc_asprintf(mem_ctx, "%s/lowcase.dat", get_dyn_CODEPAGEDIR()), 0x20000);
    4958        talloc_free(mem_ctx);
    5059        if (upcase_table == NULL) {
    51                 /* try also under codepages for testing purposes */
    52                 upcase_table = map_file("codepages/upcase.dat", 0x20000);
    53                 if (upcase_table == NULL) {
    54                         upcase_table = (void *)-1;
    55                 }
     60                DEBUG(1, ("Failed to load upcase.dat, will use lame ASCII-only case sensitivity rules\n"));
     61                upcase_table = (void *)-1;
    5662        }
    5763        if (lowcase_table == NULL) {
    58                 /* try also under codepages for testing purposes */
    59                 lowcase_table = map_file("codepages/lowcase.dat", 0x20000);
    60                 if (lowcase_table == NULL) {
    61                         lowcase_table = (void *)-1;
    62                 }
    63         }
     64                DEBUG(1, ("Failed to load lowcase.dat, will use lame ASCII-only case sensitivity rules\n"));
     65                lowcase_table = (void *)-1;
     66        }
     67}
     68
     69/*******************************************************************
     70load the case handling tables
     71
     72This MUST only be called from main() in application code, never from a
     73library.  We don't know if the calling program has already done
     74setlocale() to another value, and can't tell if they have.
     75********************************************************************/
     76void load_case_tables(void)
     77{
     78        /* This is a useful global hook where we can ensure that the
     79         * locale is set from the environment.  This is needed so that
     80         * we can use LOCALE as a codepage */
     81#ifdef HAVE_SETLOCALE
     82        setlocale(LC_ALL, "");
     83#endif
     84        load_case_tables_library();
    6485}
    6586
     
    7394        }
    7495        if (upcase_table == NULL) {
    75                 load_case_tables();
     96                load_case_tables_library();
    7697        }
    7798        if (upcase_table == (void *)-1) {
     
    93114        }
    94115        if (lowcase_table == NULL) {
    95                 load_case_tables();
     116                load_case_tables_library();
    96117        }
    97118        if (lowcase_table == (void *)-1) {
     
    102123        }
    103124        return SVAL(lowcase_table, val*2);
     125}
     126
     127/**
     128 If we upper cased this character, would we get the same character?
     129**/
     130_PUBLIC_ bool islower_m(codepoint_t val)
     131{
     132        return (toupper_m(val) != val);
     133}
     134
     135/**
     136 If we lower cased this character, would we get the same character?
     137**/
     138_PUBLIC_ bool isupper_m(codepoint_t val)
     139{
     140        return (tolower_m(val) != val);
    104141}
    105142
     
    117154
    118155
     156struct smb_iconv_convenience {
     157        TALLOC_CTX *child_ctx;
     158        const char *unix_charset;
     159        const char *dos_charset;
     160        const char *display_charset;
     161        bool native_iconv;
     162        smb_iconv_t conv_handles[NUM_CHARSETS][NUM_CHARSETS];
     163};
     164
     165struct smb_iconv_convenience *global_iconv_convenience = NULL;
     166
     167struct smb_iconv_convenience *get_iconv_convenience(void)
     168{
     169        if (global_iconv_convenience == NULL)
     170                global_iconv_convenience = smb_iconv_convenience_reinit(talloc_autofree_context(),
     171                                                                        "ASCII", "UTF-8", "ASCII", true, NULL);
     172        return global_iconv_convenience;
     173}
     174
     175/**
     176 * Return the name of a charset to give to iconv().
     177 **/
     178const char *charset_name(struct smb_iconv_convenience *ic, charset_t ch)
     179{
     180        switch (ch) {
     181        case CH_UTF16: return "UTF-16LE";
     182        case CH_UNIX: return ic->unix_charset;
     183        case CH_DOS: return ic->dos_charset;
     184        case CH_DISPLAY: return ic->display_charset;
     185        case CH_UTF8: return "UTF8";
     186        case CH_UTF16BE: return "UTF-16BE";
     187        case CH_UTF16MUNGED: return "UTF16_MUNGED";
     188        default:
     189        return "ASCII";
     190        }
     191}
     192
     193/**
     194 re-initialize iconv conversion descriptors
     195**/
     196static int close_iconv_convenience(struct smb_iconv_convenience *data)
     197{
     198        unsigned c1, c2;
     199        for (c1=0;c1<NUM_CHARSETS;c1++) {
     200                for (c2=0;c2<NUM_CHARSETS;c2++) {
     201                        if (data->conv_handles[c1][c2] != NULL) {
     202                                if (data->conv_handles[c1][c2] != (smb_iconv_t)-1) {
     203                                        smb_iconv_close(data->conv_handles[c1][c2]);
     204                                }
     205                                data->conv_handles[c1][c2] = NULL;
     206                        }
     207                }
     208        }
     209
     210        return 0;
     211}
     212
     213static const char *map_locale(const char *charset)
     214{
     215        if (strcmp(charset, "LOCALE") != 0) {
     216                return charset;
     217        }
     218#if defined(HAVE_NL_LANGINFO) && defined(CODESET)
     219        {
     220                const char *ln;
     221                smb_iconv_t handle;
     222
     223                ln = nl_langinfo(CODESET);
     224                if (ln == NULL) {
     225                        DEBUG(1,("Unable to determine charset for LOCALE - using ASCII\n"));
     226                        return "ASCII";
     227                }
     228                /* Check whether the charset name is supported
     229                   by iconv */
     230                handle = smb_iconv_open(ln, "UCS-2LE");
     231                if (handle == (smb_iconv_t) -1) {
     232                        DEBUG(5,("Locale charset '%s' unsupported, using ASCII instead\n", ln));
     233                        return "ASCII";
     234                } else {
     235                        DEBUG(5,("Substituting charset '%s' for LOCALE\n", ln));
     236                        smb_iconv_close(handle);
     237                }
     238                return ln;
     239        }
     240#endif
     241        return "ASCII";
     242}
     243
     244/*
     245  the old_ic is passed in here as the smb_iconv_convenience structure
     246  is used as a global pointer in some places (eg. python modules). We
     247  don't want to invalidate those global pointers, but we do want to
     248  update them with the right charset information when loadparm
     249  runs. To do that we need to re-use the structure pointer, but
     250  re-fill the elements in the structure with the updated values
     251 */
     252_PUBLIC_ struct smb_iconv_convenience *smb_iconv_convenience_reinit(TALLOC_CTX *mem_ctx,
     253                                                                    const char *dos_charset,
     254                                                                    const char *unix_charset,
     255                                                                    const char *display_charset,
     256                                                                    bool native_iconv,
     257                                                                    struct smb_iconv_convenience *old_ic)
     258{
     259        struct smb_iconv_convenience *ret;
     260
     261        display_charset = map_locale(display_charset);
     262
     263        if (old_ic != NULL) {
     264                ret = old_ic;
     265                close_iconv_convenience(ret);
     266                talloc_free(ret->child_ctx);
     267                ZERO_STRUCTP(ret);
     268        } else {
     269                ret = talloc_zero(mem_ctx, struct smb_iconv_convenience);
     270        }
     271        if (ret == NULL) {
     272                return NULL;
     273        }
     274
     275        /* we use a child context to allow us to free all ptrs without
     276           freeing the structure itself */
     277        ret->child_ctx = talloc_new(ret);
     278        if (ret->child_ctx == NULL) {
     279                return NULL;
     280        }
     281
     282        talloc_set_destructor(ret, close_iconv_convenience);
     283
     284        ret->dos_charset = talloc_strdup(ret->child_ctx, dos_charset);
     285        ret->unix_charset = talloc_strdup(ret->child_ctx, unix_charset);
     286        ret->display_charset = talloc_strdup(ret->child_ctx, display_charset);
     287        ret->native_iconv = native_iconv;
     288
     289        return ret;
     290}
     291
     292/*
     293  on-demand initialisation of conversion handles
     294*/
     295smb_iconv_t get_conv_handle(struct smb_iconv_convenience *ic,
     296                            charset_t from, charset_t to)
     297{
     298        const char *n1, *n2;
     299        static bool initialised;
     300
     301        if (initialised == false) {
     302                initialised = true;
     303        }
     304
     305        if (ic->conv_handles[from][to]) {
     306                return ic->conv_handles[from][to];
     307        }
     308
     309        n1 = charset_name(ic, from);
     310        n2 = charset_name(ic, to);
     311
     312        ic->conv_handles[from][to] = smb_iconv_open_ex(ic, n2, n1,
     313                                                       ic->native_iconv);
     314
     315        if (ic->conv_handles[from][to] == (smb_iconv_t)-1) {
     316                if ((from == CH_DOS || to == CH_DOS) &&
     317                    strcasecmp(charset_name(ic, CH_DOS), "ASCII") != 0) {
     318                        DEBUG(0,("dos charset '%s' unavailable - using ASCII\n",
     319                                 charset_name(ic, CH_DOS)));
     320                        ic->dos_charset = "ASCII";
     321
     322                        n1 = charset_name(ic, from);
     323                        n2 = charset_name(ic, to);
     324
     325                        ic->conv_handles[from][to] =
     326                                smb_iconv_open_ex(ic, n2, n1, ic->native_iconv);
     327                }
     328        }
     329
     330        return ic->conv_handles[from][to];
     331}
     332
     333/**
     334 * Return the unicode codepoint for the next character in the input
     335 * string in the given src_charset.
     336 * The unicode codepoint (codepoint_t) is an unsinged 32 bit value.
     337 *
     338 * Also return the number of bytes consumed (which tells the caller
     339 * how many bytes to skip to get to the next src_charset-character).
     340 *
     341 * This is implemented (in the non-ascii-case) by first converting the
     342 * next character in the input string to UTF16_LE and then calculating
     343 * the unicode codepoint from that.
     344 *
     345 * Return INVALID_CODEPOINT if the next character cannot be converted.
     346 */
     347_PUBLIC_ codepoint_t next_codepoint_convenience_ext(
     348                        struct smb_iconv_convenience *ic,
     349                        const char *str, charset_t src_charset,
     350                        size_t *bytes_consumed)
     351{
     352        /* it cannot occupy more than 4 bytes in UTF16 format */
     353        uint8_t buf[4];
     354        smb_iconv_t descriptor;
     355        size_t ilen_orig;
     356        size_t ilen;
     357        size_t olen;
     358        char *outbuf;
     359
     360        if ((str[0] & 0x80) == 0) {
     361                *bytes_consumed = 1;
     362                return (codepoint_t)str[0];
     363        }
     364
     365        /*
     366         * we assume that no multi-byte character can take more than 5 bytes.
     367         * This is OK as we only support codepoints up to 1M (U+100000)
     368         */
     369        ilen_orig = strnlen(str, 5);
     370        ilen = ilen_orig;
     371
     372        descriptor = get_conv_handle(ic, src_charset, CH_UTF16);
     373        if (descriptor == (smb_iconv_t)-1) {
     374                *bytes_consumed = 1;
     375                return INVALID_CODEPOINT;
     376        }
     377
     378        /*
     379         * this looks a little strange, but it is needed to cope with
     380         * codepoints above 64k (U+1000) which are encoded as per RFC2781.
     381         */
     382        olen = 2;
     383        outbuf = (char *)buf;
     384        smb_iconv(descriptor, &str, &ilen, &outbuf, &olen);
     385        if (olen == 2) {
     386                olen = 4;
     387                outbuf = (char *)buf;
     388                smb_iconv(descriptor,  &str, &ilen, &outbuf, &olen);
     389                if (olen == 4) {
     390                        /* we didn't convert any bytes */
     391                        *bytes_consumed = 1;
     392                        return INVALID_CODEPOINT;
     393                }
     394                olen = 4 - olen;
     395        } else {
     396                olen = 2 - olen;
     397        }
     398
     399        *bytes_consumed = ilen_orig - ilen;
     400
     401        if (olen == 2) {
     402                return (codepoint_t)SVAL(buf, 0);
     403        }
     404        if (olen == 4) {
     405                /* decode a 4 byte UTF16 character manually */
     406                return (codepoint_t)0x10000 +
     407                        (buf[2] | ((buf[3] & 0x3)<<8) |
     408                         (buf[0]<<10) | ((buf[1] & 0x3)<<18));
     409        }
     410
     411        /* no other length is valid */
     412        return INVALID_CODEPOINT;
     413}
     414
     415/*
     416  return the unicode codepoint for the next multi-byte CH_UNIX character
     417  in the string
     418
     419  also return the number of bytes consumed (which tells the caller
     420  how many bytes to skip to get to the next CH_UNIX character)
     421
     422  return INVALID_CODEPOINT if the next character cannot be converted
     423*/
     424_PUBLIC_ codepoint_t next_codepoint_convenience(struct smb_iconv_convenience *ic,
     425                                    const char *str, size_t *size)
     426{
     427        return next_codepoint_convenience_ext(ic, str, CH_UNIX, size);
     428}
     429
     430/*
     431  push a single codepoint into a CH_UNIX string the target string must
     432  be able to hold the full character, which is guaranteed if it is at
     433  least 5 bytes in size. The caller may pass less than 5 bytes if they
     434  are sure the character will fit (for example, you can assume that
     435  uppercase/lowercase of a character will not add more than 1 byte)
     436
     437  return the number of bytes occupied by the CH_UNIX character, or
     438  -1 on failure
     439*/
     440_PUBLIC_ ssize_t push_codepoint_convenience(struct smb_iconv_convenience *ic,
     441                                char *str, codepoint_t c)
     442{
     443        smb_iconv_t descriptor;
     444        uint8_t buf[4];
     445        size_t ilen, olen;
     446        const char *inbuf;
     447
     448        if (c < 128) {
     449                *str = c;
     450                return 1;
     451        }
     452
     453        descriptor = get_conv_handle(ic,
     454                                     CH_UTF16, CH_UNIX);
     455        if (descriptor == (smb_iconv_t)-1) {
     456                return -1;
     457        }
     458
     459        if (c < 0x10000) {
     460                ilen = 2;
     461                olen = 5;
     462                inbuf = (char *)buf;
     463                SSVAL(buf, 0, c);
     464                smb_iconv(descriptor, &inbuf, &ilen, &str, &olen);
     465                if (ilen != 0) {
     466                        return -1;
     467                }
     468                return 5 - olen;
     469        }
     470
     471        c -= 0x10000;
     472
     473        buf[0] = (c>>10) & 0xFF;
     474        buf[1] = (c>>18) | 0xd8;
     475        buf[2] = c & 0xFF;
     476        buf[3] = ((c>>8) & 0x3) | 0xdc;
     477
     478        ilen = 4;
     479        olen = 5;
     480        inbuf = (char *)buf;
     481
     482        smb_iconv(descriptor, &inbuf, &ilen, &str, &olen);
     483        if (ilen != 0) {
     484                return -1;
     485        }
     486        return 5 - olen;
     487}
     488
     489_PUBLIC_ codepoint_t next_codepoint_ext(const char *str, charset_t src_charset,
     490                                        size_t *size)
     491{
     492        return next_codepoint_convenience_ext(get_iconv_convenience(), str,
     493                                              src_charset, size);
     494}
     495
     496_PUBLIC_ codepoint_t next_codepoint(const char *str, size_t *size)
     497{
     498        return next_codepoint_convenience(get_iconv_convenience(), str, size);
     499}
     500
     501_PUBLIC_ ssize_t push_codepoint(char *str, codepoint_t c)
     502{
     503        return push_codepoint_convenience(get_iconv_convenience(), str, c);
     504}
  • vendor/current/lib/util/charset/iconv.c

    r414 r740  
    2424#include "system/filesys.h"
    2525
     26#ifdef strcasecmp
     27#undef strcasecmp
     28#endif
     29
     30#ifdef static_decl_charset
     31static_decl_charset;
     32#endif
    2633
    2734/**
     
    5057static size_t ascii_pull  (void *,const char **, size_t *, char **, size_t *);
    5158static size_t ascii_push  (void *,const char **, size_t *, char **, size_t *);
     59static size_t latin1_push(void *,const char **, size_t *, char **, size_t *);
    5260static size_t utf8_pull   (void *,const char **, size_t *, char **, size_t *);
    5361static size_t utf8_push   (void *,const char **, size_t *, char **, size_t *);
     
    7381
    7482        {"ASCII", ascii_pull, ascii_push},
     83        {"646", ascii_pull, ascii_push},
     84        {"ISO-8859-1", ascii_pull, latin1_push},
    7585        {"UCS2-HEX", ucs2hex_pull, ucs2hex_push}
    7686};
     
    7888static struct charset_functions *charsets = NULL;
    7989
    80 bool charset_register_backend(const void *_funcs)
    81 {
    82         struct charset_functions *funcs = (struct charset_functions *)memdup(_funcs,sizeof(struct charset_functions));
     90static struct charset_functions *find_charset_functions(const char *name)
     91{
    8392        struct charset_functions *c;
    8493
    8594        /* Check whether we already have this charset... */
    8695        for (c = charsets; c != NULL; c = c->next) {
    87                 if(!strcasecmp(c->name, funcs->name)) {
    88                         DEBUG(2, ("Duplicate charset %s, not registering\n", funcs->name));
    89                         return false;
    90                 }
    91         }
     96                if(strcasecmp(c->name, name) == 0) {
     97                        return c;
     98                }
     99                c = c->next;
     100        }
     101
     102        return NULL;
     103}
     104
     105bool smb_register_charset(const struct charset_functions *funcs_in)
     106{
     107        struct charset_functions *funcs;
     108
     109        DEBUG(5, ("Attempting to register new charset %s\n", funcs_in->name));
     110        /* Check whether we already have this charset... */
     111        if (find_charset_functions(funcs_in->name)) {
     112                DEBUG(0, ("Duplicate charset %s, not registering\n", funcs_in->name));
     113                return false;
     114        }
     115
     116        funcs = talloc(NULL, struct charset_functions);
     117        if (!funcs) {
     118                DEBUG(0, ("Out of memory duplicating charset %s\n", funcs_in->name));
     119                return false;
     120        }
     121        *funcs = *funcs_in;
    92122
    93123        funcs->next = funcs->prev = NULL;
     124        DEBUG(5, ("Registered charset %s\n", funcs->name));
    94125        DLIST_ADD(charsets, funcs);
    95126        return true;
     127}
     128
     129static void lazy_initialize_iconv(void)
     130{
     131        static bool initialized;
     132
     133#ifdef static_init_charset
     134        if (!initialized) {
     135                static_init_charset;
     136                initialized = true;
     137        }
     138#endif
    96139}
    97140
     
    159202}
    160203
    161 int smb_iconv_t_destructor(smb_iconv_t hwd)
    162 { 
     204static int smb_iconv_t_destructor(smb_iconv_t hwd)
     205{
    163206#ifdef HAVE_NATIVE_ICONV
    164207        if (hwd->cd_pull != NULL && hwd->cd_pull != (iconv_t)-1)
     
    180223        int i;
    181224
     225        lazy_initialize_iconv();
     226
    182227        ret = (smb_iconv_t)talloc_named(mem_ctx,
    183228                                        sizeof(*ret),
     
    261306        if (is_utf16(tocode)) {
    262307                ret->direct = sys_iconv;
    263                 /* could be set just above - so we need to close iconv */
    264                 if (ret->cd_direct != NULL && ret->cd_direct != (iconv_t)-1)
    265                         iconv_close(ret->cd_direct);
    266308                ret->cd_direct = ret->cd_pull;
    267309                ret->cd_pull = NULL;
     
    286328_PUBLIC_ smb_iconv_t smb_iconv_open(const char *tocode, const char *fromcode)
    287329{
    288         return smb_iconv_open_ex(talloc_autofree_context(), tocode, fromcode, true);
     330        return smb_iconv_open_ex(NULL, tocode, fromcode, true);
    289331}
    290332
     
    351393}
    352394
     395static size_t latin1_push(void *cd, const char **inbuf, size_t *inbytesleft,
     396                         char **outbuf, size_t *outbytesleft)
     397{
     398        int ir_count=0;
     399
     400        while (*inbytesleft >= 2 && *outbytesleft >= 1) {
     401                (*outbuf)[0] = (*inbuf)[0];
     402                if ((*inbuf)[1]) ir_count++;
     403                (*inbytesleft)  -= 2;
     404                (*outbytesleft) -= 1;
     405                (*inbuf)  += 2;
     406                (*outbuf) += 1;
     407        }
     408
     409        if (*inbytesleft == 1) {
     410                errno = EINVAL;
     411                return -1;
     412        }
     413
     414        if (*inbytesleft > 1) {
     415                errno = E2BIG;
     416                return -1;
     417        }
     418
     419        return ir_count;
     420}
    353421
    354422static size_t ucs2hex_pull(void *cd, const char **inbuf, size_t *inbytesleft,
     
    356424{
    357425        while (*inbytesleft >= 1 && *outbytesleft >= 2) {
    358                 uint_t v;
     426                unsigned int v;
    359427
    360428                if ((*inbuf)[0] != '@') {
  • vendor/current/lib/util/charset/tests/charset.c

    r414 r740  
    247247struct torture_suite *torture_local_charset(TALLOC_CTX *mem_ctx)
    248248{
    249         struct torture_suite *suite = torture_suite_create(mem_ctx, "CHARSET");
     249        struct torture_suite *suite = torture_suite_create(mem_ctx, "charset");
    250250
    251251        torture_suite_add_simple_test(suite, "toupper_m", test_toupper_m);
  • vendor/current/lib/util/charset/tests/iconv.c

    r414 r740  
    3636        iconv_t cd;
    3737
    38         if (!lp_parm_bool(tctx->lp_ctx, NULL, "iconv", "native", true))
     38        if (!lpcfg_parm_bool(tctx->lp_ctx, NULL, "iconv", "native", true))
    3939                torture_skip(tctx, "system iconv disabled - skipping test");
    4040
     
    135135        uint8_t buf1[1000], buf2[1000], buf3[1000];
    136136        size_t outsize1, outsize2, outsize3;
    137         const char *ptr_in;
     137        char *ptr_in;
    138138        char *ptr_out;
    139139        size_t size_in1, size_in2, size_in3;
     
    159159                                                     charset));
    160160                }
    161                 cd2 = smb_iconv_open_ex(test, charset, "UTF-16LE", lp_parm_bool(test->lp_ctx, NULL, "iconv", "native", true));
    162                 cd3 = smb_iconv_open_ex(test, "UTF-16LE", charset, lp_parm_bool(test->lp_ctx, NULL, "iconv", "native", true));
     161                cd2 = smb_iconv_open_ex(test, charset, "UTF-16LE", lpcfg_parm_bool(test->lp_ctx, NULL, "iconv", "native", true));
     162                cd3 = smb_iconv_open_ex(test, "UTF-16LE", charset, lpcfg_parm_bool(test->lp_ctx, NULL, "iconv", "native", true));
    163163                last_charset = charset;
    164164        }
    165165
    166166        /* internal convert to charset - placing result in buf1 */
    167         ptr_in = (const char *)inbuf;
     167        ptr_in = (char *)inbuf;
    168168        ptr_out = (char *)buf1;
    169169        size_in1 = size;
     
    172172        memset(ptr_out, 0, outsize1);
    173173        errno = 0;
    174         ret1 = smb_iconv(cd2, &ptr_in, &size_in1, &ptr_out, &outsize1);
     174        ret1 = smb_iconv(cd2, (const char **) &ptr_in, &size_in1, &ptr_out, &outsize1);
    175175        errno1 = errno;
    176176
    177177        /* system convert to charset - placing result in buf2 */
    178         ptr_in = (const char *)inbuf;
     178        ptr_in = (char *)inbuf;
    179179        ptr_out = (char *)buf2;
    180180        size_in2 = size;
     
    183183        memset(ptr_out, 0, outsize2);
    184184        errno = 0;
    185         ret2 = iconv(cd, discard_const_p(char *, &ptr_in), &size_in2, &ptr_out, &outsize2);
     185        ret2 = iconv(cd, &ptr_in, &size_in2, &ptr_out, &outsize2);
    186186        errno2 = errno;
    187187
     
    237237        /* convert back to UTF-16, putting result in buf3 */
    238238        size = size - size_in1;
    239         ptr_in = (const char *)buf1;
     239        ptr_in = (char *)buf1;
    240240        ptr_out = (char *)buf3;
    241241        size_in3 = len1;
     
    243243
    244244        memset(ptr_out, 0, outsize3);
    245         ret3 = smb_iconv(cd3, &ptr_in, &size_in3, &ptr_out, &outsize3);
     245        ret3 = smb_iconv(cd3, (const char **) &ptr_in, &size_in3, &ptr_out, &outsize3);
    246246
    247247        /* we only internally support the first 1M codepoints */
     
    290290        codepoint_t c;
    291291
    292         size = push_codepoint_convenience(lp_iconv_convenience(tctx->lp_ctx), (char *)buf, codepoint);
     292        size = push_codepoint_convenience(lpcfg_iconv_convenience(tctx->lp_ctx), (char *)buf, codepoint);
    293293        torture_assert(tctx, size != -1 || (codepoint >= 0xd800 && codepoint <= 0x10000),
    294294                       "Invalid Codepoint range");
     
    301301        buf[size+3] = random();
    302302
    303         c = next_codepoint_convenience(lp_iconv_convenience(tctx->lp_ctx), (char *)buf, &size2);
     303        c = next_codepoint_convenience(lpcfg_iconv_convenience(tctx->lp_ctx), (char *)buf, &size2);
    304304
    305305        torture_assert(tctx, c == codepoint,
     
    452452struct torture_suite *torture_local_iconv(TALLOC_CTX *mem_ctx)
    453453{
    454         struct torture_suite *suite = torture_suite_create(mem_ctx, "ICONV");
     454        struct torture_suite *suite = torture_suite_create(mem_ctx, "iconv");
    455455
    456456        torture_suite_add_simple_test(suite, "string2key",
  • vendor/current/lib/util/charset/util_unistr.c

    r414 r740  
    2222#include "system/locale.h"
    2323
    24 struct smb_iconv_convenience *global_iconv_convenience = NULL;
    25 
    26 static inline struct smb_iconv_convenience *get_iconv_convenience(void)
    27 {
    28         if (global_iconv_convenience == NULL)
    29                 global_iconv_convenience = smb_iconv_convenience_init(talloc_autofree_context(), "ASCII", "UTF-8", true);
    30         return global_iconv_convenience;
    31 }
    32 
    3324/**
    3425 Case insensitive string compararison
     
    6859
    6960        return *s1 - *s2;
    70 }
    71 
    72 /**
    73  * Get the next token from a string, return False if none found.
    74  * Handles double-quotes.
    75  *
    76  * Based on a routine by GJC@VILLAGE.COM.
    77  * Extensively modified by Andrew.Tridgell@anu.edu.au
    78  **/
    79 _PUBLIC_ bool next_token(const char **ptr,char *buff, const char *sep, size_t bufsize)
    80 {
    81         const char *s;
    82         bool quoted;
    83         size_t len=1;
    84 
    85         if (!ptr)
    86                 return false;
    87 
    88         s = *ptr;
    89 
    90         /* default to simple separators */
    91         if (!sep)
    92                 sep = " \t\n\r";
    93 
    94         /* find the first non sep char */
    95         while (*s && strchr_m(sep,*s))
    96                 s++;
    97        
    98         /* nothing left? */
    99         if (!*s)
    100                 return false;
    101        
    102         /* copy over the token */
    103         for (quoted = false; len < bufsize && *s && (quoted || !strchr_m(sep,*s)); s++) {
    104                 if (*s == '\"') {
    105                         quoted = !quoted;
    106                 } else {
    107                         len++;
    108                         *buff++ = *s;
    109                 }
    110         }
    111        
    112         *ptr = (*s) ? s+1 : s; 
    113         *buff = 0;
    114        
    115         return true;
    11661}
    11762
     
    249194
    250195/**
    251  Count the number of UCS2 characters in a string. Normally this will
    252  be the same as the number of bytes in a string for single byte strings,
    253  but will be different for multibyte.
    254 **/
    255 _PUBLIC_ size_t strlen_m(const char *s)
     196 * Calculate the number of units (8 or 16-bit, depending on the
     197 * destination charset), that would be needed to convert the input
     198 * string which is expected to be in in src_charset encoding to the
     199 * destination charset (which should be a unicode charset).
     200 */
     201_PUBLIC_ size_t strlen_m_ext(const char *s, charset_t src_charset, charset_t dst_charset)
    256202{
    257203        size_t count = 0;
     
    273219        while (*s) {
    274220                size_t c_size;
    275                 codepoint_t c = next_codepoint_convenience(ic, s, &c_size);
    276                 if (c < 0x10000) {
     221                codepoint_t c = next_codepoint_convenience_ext(ic, s, src_charset, &c_size);
     222                s += c_size;
     223
     224                switch (dst_charset) {
     225                case CH_UTF16LE:
     226                case CH_UTF16BE:
     227                case CH_UTF16MUNGED:
     228                        if (c < 0x10000) {
     229                                count += 1;
     230                        } else {
     231                                count += 2;
     232                        }
     233                        break;
     234                case CH_UTF8:
     235                        /*
     236                         * this only checks ranges, and does not
     237                         * check for invalid codepoints
     238                         */
     239                        if (c < 0x80) {
     240                                count += 1;
     241                        } else if (c < 0x800) {
     242                                count += 2;
     243                        } else if (c < 0x1000) {
     244                                count += 3;
     245                        } else {
     246                                count += 4;
     247                        }
     248                        break;
     249                default:
     250                        /*
     251                         * non-unicode encoding:
     252                         * assume that each codepoint fits into
     253                         * one unit in the destination encoding.
     254                         */
    277255                        count += 1;
    278                 } else {
    279                         count += 2;
    280                 }
    281                 s += c_size;
     256                }
    282257        }
    283258
    284259        return count;
     260}
     261
     262_PUBLIC_ size_t strlen_m_ext_term(const char *s, const charset_t src_charset,
     263                                  const charset_t dst_charset)
     264{
     265        if (!s) {
     266                return 0;
     267        }
     268        return strlen_m_ext(s, src_charset, dst_charset) + 1;
     269}
     270
     271/**
     272 * Calculate the number of 16-bit units that would be needed to convert
     273 * the input string which is expected to be in CH_UNIX encoding to UTF16.
     274 *
     275 * This will be the same as the number of bytes in a string for single
     276 * byte strings, but will be different for multibyte.
     277 */
     278_PUBLIC_ size_t strlen_m(const char *s)
     279{
     280        return strlen_m_ext(s, CH_UNIX, CH_UTF16LE);
    285281}
    286282
     
    430426        char *dest;
    431427        struct smb_iconv_convenience *iconv_convenience = get_iconv_convenience();
     428
     429        if(src == NULL) {
     430                return NULL;
     431        }
    432432
    433433        /* this takes advantage of the fact that upper/lower can't
     
    988988}
    989989
    990 
    991 _PUBLIC_ codepoint_t next_codepoint(const char *str, size_t *size)
    992 {
    993         return next_codepoint_convenience(get_iconv_convenience(), str, size);
    994 }
    995 
    996 _PUBLIC_ ssize_t push_codepoint(char *str, codepoint_t c)
    997 {
    998         return push_codepoint_convenience(get_iconv_convenience(), str, c);
    999 }
  • vendor/current/lib/util/data_blob.c

    r414 r740  
    3434_PUBLIC_ DATA_BLOB data_blob_named(const void *p, size_t length, const char *name)
    3535{
     36        return data_blob_talloc_named(NULL, p, length, name);
     37}
     38
     39/**
     40 construct a data blob, using supplied TALLOC_CTX
     41**/
     42_PUBLIC_ DATA_BLOB data_blob_talloc_named(TALLOC_CTX *mem_ctx, const void *p, size_t length, const char *name)
     43{
    3644        DATA_BLOB ret;
    3745
     
    4250
    4351        if (p) {
    44                 ret.data = (uint8_t *)talloc_memdup(NULL, p, length);
     52                ret.data = (uint8_t *)talloc_memdup(mem_ctx, p, length);
    4553        } else {
    46                 ret.data = talloc_array(NULL, uint8_t, length);
     54                ret.data = talloc_array(mem_ctx, uint8_t, length);
    4755        }
    4856        if (ret.data == NULL) {
     
    5260        talloc_set_name_const(ret.data, name);
    5361        ret.length = length;
    54         return ret;
    55 }
    56 
    57 /**
    58  construct a data blob, using supplied TALLOC_CTX
    59 **/
    60 _PUBLIC_ DATA_BLOB data_blob_talloc_named(TALLOC_CTX *mem_ctx, const void *p, size_t length, const char *name)
    61 {
    62         DATA_BLOB ret = data_blob_named(p, length, name);
    63 
    64         if (ret.data) {
    65                 talloc_steal(mem_ctx, ret.data);
    66         }
    67         return ret;
    68 }
    69 
    70 
    71 /**
    72  reference a data blob, to the supplied TALLOC_CTX. 
    73  Returns a NULL DATA_BLOB on failure
    74 **/
    75 _PUBLIC_ DATA_BLOB data_blob_talloc_reference(TALLOC_CTX *mem_ctx, DATA_BLOB *blob)
    76 {
    77         DATA_BLOB ret = *blob;
    78 
    79         ret.data = talloc_reference(mem_ctx, blob->data);
    80 
    81         if (!ret.data) {
    82                 return data_blob(NULL, 0);
    83         }
    8462        return ret;
    8563}
     
    154132print the data_blob as hex string
    155133**/
    156 _PUBLIC_ char *data_blob_hex_string(TALLOC_CTX *mem_ctx, const DATA_BLOB *blob)
     134_PUBLIC_ char *data_blob_hex_string_lower(TALLOC_CTX *mem_ctx, const DATA_BLOB *blob)
    157135{
    158136        int i;
     
    174152}
    175153
     154_PUBLIC_ char *data_blob_hex_string_upper(TALLOC_CTX *mem_ctx, const DATA_BLOB *blob)
     155{
     156        int i;
     157        char *hex_string;
     158
     159        hex_string = talloc_array(mem_ctx, char, (blob->length*2)+1);
     160        if (!hex_string) {
     161                return NULL;
     162        }
     163
     164        for (i = 0; i < blob->length; i++)
     165                slprintf(&hex_string[i*2], 3, "%02X", blob->data[i]);
     166
     167        hex_string[(blob->length*2)] = '\0';
     168        return hex_string;
     169}
     170
    176171/**
    177172  useful for constructing data blobs in test suites, while
  • vendor/current/lib/util/data_blob.h

    r414 r740  
    22   Unix SMB/CIFS implementation.
    33   DATA BLOB
    4    
     4
     5   Copyright (C) Andrew Tridgell 2001
     6   Copyright (C) Andrew Bartlett 2001
     7
    58   This program is free software; you can redistribute it and/or modify
    69   it under the terms of the GNU General Public License as published by
     
    6265
    6366/**
    64  reference a data blob, to the supplied TALLOC_CTX. 
    65  Returns a NULL DATA_BLOB on failure
    66 **/
    67 _PUBLIC_ DATA_BLOB data_blob_talloc_reference(TALLOC_CTX *mem_ctx, DATA_BLOB *blob);
    68 
    69 /**
    7067 construct a zero data blob, using supplied TALLOC_CTX.
    7168 use this sparingly as it initialises data - better to initialise
     
    9794print the data_blob as hex string
    9895**/
    99 _PUBLIC_ char *data_blob_hex_string(TALLOC_CTX *mem_ctx, const DATA_BLOB *blob);
     96_PUBLIC_ char *data_blob_hex_string_upper(TALLOC_CTX *mem_ctx, const DATA_BLOB *blob);
     97
     98/**
     99print the data_blob as hex string
     100**/
     101_PUBLIC_ char *data_blob_hex_string_lower(TALLOC_CTX *mem_ctx, const DATA_BLOB *blob);
    100102
    101103/**
  • vendor/current/lib/util/debug.c

    r414 r740  
    11/*
    22   Unix SMB/CIFS implementation.
    3    Samba debug functions
    4    Copyright (C) Andrew Tridgell 2003
    5    Copyright (C) James J Myers   2003
     3   Samba utility functions
     4   Copyright (C) Andrew Tridgell 1992-1998
     5   Copyright (C) Elrond               2002
     6   Copyright (C) Simo Sorce           2002
    67
    78   This program is free software; you can redistribute it and/or modify
     
    2122#include "includes.h"
    2223#include "system/filesys.h"
    23 #include "system/time.h"
    24 #include "dynconfig/dynconfig.h"
     24#include "system/syslog.h"
     25#include "lib/util/time.h"
     26
     27/* define what facility to use for syslog */
     28#ifndef SYSLOG_FACILITY
     29#define SYSLOG_FACILITY LOG_DAEMON
     30#endif
     31
     32/* -------------------------------------------------------------------------- **
     33 * Defines...
     34 *
     35 *  FORMAT_BUFR_MAX - Index of the last byte of the format buffer;
     36 *                    format_bufr[FORMAT_BUFR_MAX] should always be reserved
     37 *                    for a terminating null byte.
     38 */
     39
     40#define FORMAT_BUFR_SIZE 1024
     41#define FORMAT_BUFR_MAX (FORMAT_BUFR_SIZE - 1)
     42
     43/* -------------------------------------------------------------------------- **
     44 * This module implements Samba's debugging utility.
     45 *
     46 * The syntax of a debugging log file is represented as:
     47 *
     48 *  <debugfile> :== { <debugmsg> }
     49 *
     50 *  <debugmsg>  :== <debughdr> '\n' <debugtext>
     51 *
     52 *  <debughdr>  :== '[' TIME ',' LEVEL ']' [ [FILENAME ':'] [FUNCTION '()'] ]
     53 *
     54 *  <debugtext> :== { <debugline> }
     55 *
     56 *  <debugline> :== TEXT '\n'
     57 *
     58 * TEXT     is a string of characters excluding the newline character.
     59 * LEVEL    is the DEBUG level of the message (an integer in the range 0..10).
     60 * TIME     is a timestamp.
     61 * FILENAME is the name of the file from which the debug message was generated.
     62 * FUNCTION is the function from which the debug message was generated.
     63 *
     64 * Basically, what that all means is:
     65 *
     66 * - A debugging log file is made up of debug messages.
     67 *
     68 * - Each debug message is made up of a header and text.  The header is
     69 *   separated from the text by a newline.
     70 *
     71 * - The header begins with the timestamp and debug level of the message
     72 *   enclosed in brackets.  The filename and function from which the
     73 *   message was generated may follow.  The filename is terminated by a
     74 *   colon, and the function name is terminated by parenthesis.
     75 *
     76 * - The message text is made up of zero or more lines, each terminated by
     77 *   a newline.
     78 */
     79
     80/* state variables for the debug system */
     81static struct {
     82        bool initialized;
     83        int fd;   /* The log file handle */
     84        enum debug_logtype logtype; /* The type of logging we are doing: eg stdout, file, stderr */
     85        const char *prog_name;
     86        bool reopening_logs;
     87        bool schedule_reopen_logs;
     88
     89        struct debug_settings settings;
     90        char *debugf;
     91} state = {
     92        .settings = {
     93                .timestamp_logs = true
     94        }
     95};
     96
     97/* -------------------------------------------------------------------------- **
     98 * External variables.
     99 *
     100 *  debugf        - Debug file name.
     101 *  DEBUGLEVEL    - System-wide debug message limit.  Messages with message-
     102 *                  levels higher than DEBUGLEVEL will not be processed.
     103 */
     104
     105/*
     106   used to check if the user specified a
     107   logfile on the command line
     108*/
     109bool    override_logfile;
     110
     111/*
     112 * This is to allow reading of DEBUGLEVEL_CLASS before the debug
     113 * system has been initialized.
     114 */
     115static const int debug_class_list_initial[DBGC_MAX_FIXED + 1];
     116
     117static int debug_num_classes = 0;
     118int     *DEBUGLEVEL_CLASS = discard_const_p(int, debug_class_list_initial);
     119
     120
     121/* -------------------------------------------------------------------------- **
     122 * Internal variables.
     123 *
     124 *  debug_count     - Number of debug messages that have been output.
     125 *                    Used to check log size.
     126 *
     127 *  syslog_level    - Internal copy of the message debug level.  Written by
     128 *                    dbghdr() and read by Debug1().
     129 *
     130 *  format_bufr     - Used to format debug messages.  The dbgtext() function
     131 *                    prints debug messages to a string, and then passes the
     132 *                    string to format_debug_text(), which uses format_bufr
     133 *                    to build the formatted output.
     134 *
     135 *  format_pos      - Marks the first free byte of the format_bufr.
     136 *
     137 *
     138 *  log_overflow    - When this variable is true, never attempt to check the
     139 *                    size of the log. This is a hack, so that we can write
     140 *                    a message using DEBUG, from open_logs() when we
     141 *                    are unable to open a new log file for some reason.
     142 */
     143
     144static int     debug_count    = 0;
     145#ifdef WITH_SYSLOG
     146static int     syslog_level   = 0;
     147#endif
     148static char *format_bufr = NULL;
     149static size_t     format_pos     = 0;
     150static bool    log_overflow   = false;
     151
     152/*
     153 * Define all the debug class selection names here. Names *MUST NOT* contain
     154 * white space. There must be one name for each DBGC_<class name>, and they
     155 * must be in the table in the order of DBGC_<class name>..
     156 */
     157static const char *default_classname_table[] = {
     158        "all",               /* DBGC_ALL; index refs traditional DEBUGLEVEL */
     159        "tdb",               /* DBGC_TDB          */
     160        "printdrivers",      /* DBGC_PRINTDRIVERS */
     161        "lanman",            /* DBGC_LANMAN       */
     162        "smb",               /* DBGC_SMB          */
     163        "rpc_parse",         /* DBGC_RPC_PARSE    */
     164        "rpc_srv",           /* DBGC_RPC_SRV      */
     165        "rpc_cli",           /* DBGC_RPC_CLI      */
     166        "passdb",            /* DBGC_PASSDB       */
     167        "sam",               /* DBGC_SAM          */
     168        "auth",              /* DBGC_AUTH         */
     169        "winbind",           /* DBGC_WINBIND      */
     170        "vfs",               /* DBGC_VFS          */
     171        "idmap",             /* DBGC_IDMAP        */
     172        "quota",             /* DBGC_QUOTA        */
     173        "acls",              /* DBGC_ACLS         */
     174        "locking",           /* DBGC_LOCKING      */
     175        "msdfs",             /* DBGC_MSDFS        */
     176        "dmapi",             /* DBGC_DMAPI        */
     177        "registry",          /* DBGC_REGISTRY     */
     178        NULL
     179};
     180
     181static char **classname_table = NULL;
     182
     183
     184/* -------------------------------------------------------------------------- **
     185 * Functions...
     186 */
     187
     188static void debug_init(void);
     189
     190/***************************************************************************
     191 Free memory pointed to by global pointers.
     192****************************************************************************/
     193
     194void gfree_debugsyms(void)
     195{
     196        TALLOC_FREE(classname_table);
     197
     198        if ( DEBUGLEVEL_CLASS != debug_class_list_initial ) {
     199                TALLOC_FREE( DEBUGLEVEL_CLASS );
     200                DEBUGLEVEL_CLASS = discard_const_p(int, debug_class_list_initial);
     201        }
     202
     203        TALLOC_FREE(format_bufr);
     204
     205        debug_num_classes = DBGC_MAX_FIXED;
     206
     207        state.initialized = false;
     208}
     209
     210/****************************************************************************
     211utility lists registered debug class names's
     212****************************************************************************/
     213
     214char *debug_list_class_names_and_levels(void)
     215{
     216        char *buf = NULL;
     217        unsigned int i;
     218        /* prepare strings */
     219        for (i = 0; i < debug_num_classes; i++) {
     220                buf = talloc_asprintf_append(buf,
     221                                             "%s:%d%s",
     222                                             classname_table[i],
     223                                             DEBUGLEVEL_CLASS[i],
     224                                             i == (debug_num_classes - 1) ? "\n" : " ");
     225                if (buf == NULL) {
     226                        return NULL;
     227                }
     228        }
     229        return buf;
     230}
     231
     232/****************************************************************************
     233 Utility to translate names to debug class index's (internal version).
     234****************************************************************************/
     235
     236static int debug_lookup_classname_int(const char* classname)
     237{
     238        int i;
     239
     240        if (!classname) return -1;
     241
     242        for (i=0; i < debug_num_classes; i++) {
     243                if (strcmp(classname, classname_table[i])==0)
     244                        return i;
     245        }
     246        return -1;
     247}
     248
     249/****************************************************************************
     250 Add a new debug class to the system.
     251****************************************************************************/
     252
     253int debug_add_class(const char *classname)
     254{
     255        int ndx;
     256        int *new_class_list;
     257        char **new_name_list;
     258        int default_level;
     259
     260        if (!classname)
     261                return -1;
     262
     263        /* check the init has yet been called */
     264        debug_init();
     265
     266        ndx = debug_lookup_classname_int(classname);
     267        if (ndx >= 0)
     268                return ndx;
     269        ndx = debug_num_classes;
     270
     271        if (DEBUGLEVEL_CLASS == debug_class_list_initial) {
     272                /* Initial loading... */
     273                new_class_list = NULL;
     274        } else {
     275                new_class_list = DEBUGLEVEL_CLASS;
     276        }
     277
     278        default_level = DEBUGLEVEL_CLASS[DBGC_ALL];
     279
     280        new_class_list = talloc_realloc(NULL, new_class_list, int, ndx + 1);
     281        if (!new_class_list)
     282                return -1;
     283        DEBUGLEVEL_CLASS = new_class_list;
     284
     285        DEBUGLEVEL_CLASS[ndx] = default_level;
     286
     287        new_name_list = talloc_realloc(NULL, classname_table, char *, ndx + 1);
     288        if (!new_name_list)
     289                return -1;
     290        classname_table = new_name_list;
     291
     292        classname_table[ndx] = talloc_strdup(classname_table, classname);
     293        if (! classname_table[ndx])
     294                return -1;
     295
     296        debug_num_classes = ndx + 1;
     297
     298        return ndx;
     299}
     300
     301/****************************************************************************
     302 Utility to translate names to debug class index's (public version).
     303****************************************************************************/
     304
     305int debug_lookup_classname(const char *classname)
     306{
     307        int ndx;
     308
     309        if (!classname || !*classname)
     310                return -1;
     311
     312        ndx = debug_lookup_classname_int(classname);
     313
     314        if (ndx != -1)
     315                return ndx;
     316
     317        DEBUG(0, ("debug_lookup_classname(%s): Unknown class\n",
     318                  classname));
     319        return debug_add_class(classname);
     320}
     321
     322/****************************************************************************
     323 Dump the current registered debug levels.
     324****************************************************************************/
     325
     326static void debug_dump_status(int level)
     327{
     328        int q;
     329
     330        DEBUG(level, ("INFO: Current debug levels:\n"));
     331        for (q = 0; q < debug_num_classes; q++) {
     332                const char *classname = classname_table[q];
     333                DEBUGADD(level, ("  %s: %d\n",
     334                                 classname,
     335                                 DEBUGLEVEL_CLASS[q]));
     336        }
     337}
     338
     339/****************************************************************************
     340 parse the debug levels from smbcontrol. Example debug level parameter:
     341 printdrivers:7
     342****************************************************************************/
     343
     344static bool debug_parse_params(char **params)
     345{
     346        int   i, ndx;
     347        char *class_name;
     348        char *class_level;
     349
     350        if (!params)
     351                return false;
     352
     353        /* Allow DBGC_ALL to be specified w/o requiring its class name e.g."10"
     354         * v.s. "all:10", this is the traditional way to set DEBUGLEVEL
     355         */
     356        if (isdigit((int)params[0][0])) {
     357                DEBUGLEVEL_CLASS[DBGC_ALL] = atoi(params[0]);
     358                i = 1; /* start processing at the next params */
     359        } else {
     360                DEBUGLEVEL_CLASS[DBGC_ALL] = 0;
     361                i = 0; /* DBGC_ALL not specified OR class name was included */
     362        }
     363
     364        /* Array is debug_num_classes long */
     365        for (ndx = DBGC_ALL; ndx < debug_num_classes; ndx++) {
     366                DEBUGLEVEL_CLASS[ndx] = DEBUGLEVEL_CLASS[DBGC_ALL];
     367        }
     368               
     369        /* Fill in new debug class levels */
     370        for (; i < debug_num_classes && params[i]; i++) {
     371                char *saveptr;
     372                if ((class_name = strtok_r(params[i],":", &saveptr)) &&
     373                        (class_level = strtok_r(NULL, "\0", &saveptr)) &&
     374            ((ndx = debug_lookup_classname(class_name)) != -1)) {
     375                                DEBUGLEVEL_CLASS[ndx] = atoi(class_level);
     376                } else {
     377                        DEBUG(0,("debug_parse_params: unrecognized debug class name or format [%s]\n", params[i]));
     378                        return false;
     379                }
     380        }
     381
     382        return true;
     383}
     384
     385/****************************************************************************
     386 Parse the debug levels from smb.conf. Example debug level string:
     387  3 tdb:5 printdrivers:7
     388 Note: the 1st param has no "name:" preceeding it.
     389****************************************************************************/
     390
     391bool debug_parse_levels(const char *params_str)
     392{
     393        char **params;
     394
     395        /* Just in case */
     396        debug_init();
     397
     398        params = str_list_make(NULL, params_str, NULL);
     399
     400        if (debug_parse_params(params)) {
     401                debug_dump_status(5);
     402                TALLOC_FREE(params);
     403                return true;
     404        } else {
     405                TALLOC_FREE(params);
     406                return false;
     407        }
     408}
     409
     410/* setup for logging of talloc warnings */
     411static void talloc_log_fn(const char *msg)
     412{
     413        DEBUG(0,("%s", msg));
     414}
     415
     416void debug_setup_talloc_log(void)
     417{
     418        talloc_set_log_fn(talloc_log_fn);
     419}
     420
     421
     422/****************************************************************************
     423Init debugging (one time stuff)
     424****************************************************************************/
     425
     426static void debug_init(void)
     427{
     428        const char **p;
     429
     430        if (state.initialized)
     431                return;
     432
     433        state.initialized = true;
     434
     435        debug_setup_talloc_log();
     436
     437        for(p = default_classname_table; *p; p++) {
     438                debug_add_class(*p);
     439        }
     440        format_bufr = talloc_array(NULL, char, FORMAT_BUFR_SIZE);
     441        if (!format_bufr) {
     442                smb_panic("debug_init: unable to create buffer");
     443        }
     444}
     445
     446/* This forces in some smb.conf derived values into the debug system.
     447 * There are no pointers in this structure, so we can just
     448 * structure-assign it in */
     449void debug_set_settings(struct debug_settings *settings)
     450{
     451        state.settings = *settings;
     452}
    25453
    26454/**
    27  * @file
    28  * @brief Debug logging
    29  **/
    30 
    31 /**
    32  * this global variable determines what messages are printed
    33  */
    34 int _debug_level = 0;
    35 _PUBLIC_ int *debug_level = &_debug_level;
    36 static int debug_all_class_hack = 1;
    37 int *DEBUGLEVEL_CLASS = &debug_all_class_hack; /* For samba 3 */
    38 static bool debug_all_class_isset_hack = true;
    39 bool    *DEBUGLEVEL_CLASS_ISSET = &debug_all_class_isset_hack; /* For samba 3 */
    40 XFILE *dbf = NULL; /* For Samba 3*/
     455  control the name of the logfile and whether logging will be to stdout, stderr
     456  or a file, and set up syslog
     457
     458  new_log indicates the destination for the debug log (an enum in
     459  order of precedence - once set to DEBUG_FILE, it is not possible to
     460  reset to DEBUG_STDOUT for example.  This makes it easy to override
     461  for debug to stderr on the command line, as the smb.conf cannot
     462  reset it back to file-based logging
     463*/
     464void setup_logging(const char *prog_name, enum debug_logtype new_logtype)
     465{
     466        debug_init();
     467        if (state.logtype < new_logtype) {
     468                state.logtype = new_logtype;
     469        }
     470        if (prog_name) {
     471                state.prog_name = prog_name;
     472        }
     473        reopen_logs_internal();
     474
     475        if (state.logtype == DEBUG_FILE) {
     476#ifdef WITH_SYSLOG
     477                const char *p = strrchr_m( prog_name,'/' );
     478                if (p)
     479                        prog_name = p + 1;
     480#ifdef LOG_DAEMON
     481                openlog( prog_name, LOG_PID, SYSLOG_FACILITY );
     482#else
     483                /* for old systems that have no facility codes. */
     484                openlog( prog_name, LOG_PID );
     485#endif
     486#endif
     487        }
     488}
     489
     490/***************************************************************************
     491 Set the logfile name.
     492**************************************************************************/
     493
     494void debug_set_logfile(const char *name)
     495{
     496        if (name == NULL || *name == 0) {
     497                /* this copes with calls when smb.conf is not loaded yet */
     498                return;
     499        }
     500        TALLOC_FREE(state.debugf);
     501        state.debugf = talloc_strdup(NULL, name);
     502}
     503
     504static void debug_close_fd(int fd)
     505{
     506        if (fd > 2) {
     507                close(fd);
     508        }
     509}
     510
     511bool debug_get_output_is_stderr(void)
     512{
     513        return (state.logtype == DEBUG_DEFAULT_STDERR) || (state.logtype == DEBUG_STDERR);
     514}
     515
     516/**************************************************************************
     517 reopen the log files
     518 note that we now do this unconditionally
     519 We attempt to open the new debug fp before closing the old. This means
     520 if we run out of fd's we just keep using the old fd rather than aborting.
     521 Fix from dgibson@linuxcare.com.
     522**************************************************************************/
     523
     524/**
     525  reopen the log file (usually called because the log file name might have changed)
     526*/
     527bool reopen_logs_internal(void)
     528{
     529        mode_t oldumask;
     530        int new_fd = 0;
     531        int old_fd = 0;
     532        bool ret = true;
     533
     534        char *fname = NULL;
     535        if (state.reopening_logs) {
     536                return true;
     537        }
     538
     539        /* Now clear the SIGHUP induced flag */
     540        state.schedule_reopen_logs = false;
     541
     542        switch (state.logtype) {
     543        case DEBUG_STDOUT:
     544                debug_close_fd(state.fd);
     545                state.fd = 1;
     546                return true;
     547
     548        case DEBUG_DEFAULT_STDERR:
     549        case DEBUG_STDERR:
     550                debug_close_fd(state.fd);
     551                state.fd = 2;
     552                return true;
     553
     554        case DEBUG_FILE:
     555                break;
     556        }
     557
     558        oldumask = umask( 022 );
     559
     560        fname = state.debugf;
     561        if (!fname) {
     562                return false;
     563        }
     564
     565        state.reopening_logs = true;
     566
     567        new_fd = open( state.debugf, O_WRONLY|O_APPEND|O_CREAT, 0644);
     568
     569        if (new_fd == -1) {
     570                log_overflow = true;
     571                DEBUG(0, ("Unable to open new log file '%s': %s\n", state.debugf, strerror(errno)));
     572                log_overflow = false;
     573                ret = false;
     574        } else {
     575                old_fd = state.fd;
     576                state.fd = new_fd;
     577                debug_close_fd(old_fd);
     578        }
     579
     580        /* Fix from klausr@ITAP.Physik.Uni-Stuttgart.De
     581         * to fix problem where smbd's that generate less
     582         * than 100 messages keep growing the log.
     583         */
     584        force_check_log_size();
     585        (void)umask(oldumask);
     586
     587        /* Take over stderr to catch output into logs */
     588        if (state.fd > 0 && dup2(state.fd, 2) == -1) {
     589                close_low_fds(true); /* Close stderr too, if dup2 can't point it
     590                                        at the logfile */
     591        }
     592
     593        state.reopening_logs = false;
     594
     595        return ret;
     596}
     597
     598/**************************************************************************
     599 Force a check of the log size.
     600 ***************************************************************************/
     601
     602void force_check_log_size( void )
     603{
     604        debug_count = 100;
     605}
     606
     607_PUBLIC_ void debug_schedule_reopen_logs(void)
     608{
     609        state.schedule_reopen_logs = true;
     610}
     611
     612
     613/***************************************************************************
     614 Check to see if there is any need to check if the logfile has grown too big.
     615**************************************************************************/
     616
     617bool need_to_check_log_size( void )
     618{
     619        int maxlog;
     620
     621        if( debug_count < 100)
     622                return( false );
     623
     624        maxlog = state.settings.max_log_size * 1024;
     625        if ( state.fd <=2 || maxlog <= 0 ) {
     626                debug_count = 0;
     627                return(false);
     628        }
     629        return( true );
     630}
     631
     632/**************************************************************************
     633 Check to see if the log has grown to be too big.
     634 **************************************************************************/
     635
     636void check_log_size( void )
     637{
     638        int         maxlog;
     639        struct stat st;
     640
     641        /*
     642         *  We need to be root to check/change log-file, skip this and let the main
     643         *  loop check do a new check as root.
     644         */
     645
     646        if( geteuid() != 0) {
     647                /* We don't check sec_initial_uid() here as it isn't
     648                 * available in common code and we don't generally
     649                 * want to rotate and the possibly lose logs in
     650                 * make test or the build farm */
     651                return;
     652        }
     653
     654        if(log_overflow || (!state.schedule_reopen_logs && !need_to_check_log_size())) {
     655                return;
     656        }
     657
     658        maxlog = state.settings.max_log_size * 1024;
     659
     660        if (state.schedule_reopen_logs ||
     661           (fstat(state.fd, &st) == 0
     662            && st.st_size > maxlog )) {
     663                (void)reopen_logs_internal();
     664                if (state.fd > 0 && fstat(state.fd, &st) == 0) {
     665                        if (st.st_size > maxlog) {
     666                                char *name = NULL;
     667
     668                                if (asprintf(&name, "%s.old", state.debugf ) < 0) {
     669                                        return;
     670                                }
     671                                (void)rename(state.debugf, name);
     672
     673                                if (!reopen_logs_internal()) {
     674                                        /* We failed to reopen a log - continue using the old name. */
     675                                        (void)rename(name, state.debugf);
     676                                }
     677                                SAFE_FREE(name);
     678                        }
     679                }
     680        }
     681
     682        /*
     683         * Here's where we need to panic if state.fd == 0 or -1 (invalid values)
     684         */
     685
     686        if (state.fd <= 0) {
     687                /* This code should only be reached in very strange
     688                 * circumstances. If we merely fail to open the new log we
     689                 * should stick with the old one. ergo this should only be
     690                 * reached when opening the logs for the first time: at
     691                 * startup or when the log level is increased from zero.
     692                 * -dwg 6 June 2000
     693                 */
     694                int fd = open( "/dev/console", O_WRONLY, 0);
     695                if (fd != -1) {
     696                        state.fd = fd;
     697                        DEBUG(0,("check_log_size: open of debug file %s failed - using console.\n",
     698                                        state.debugf ));
     699                } else {
     700                        /*
     701                         * We cannot continue without a debug file handle.
     702                         */
     703                        abort();
     704                }
     705        }
     706        debug_count = 0;
     707}
     708
     709/*************************************************************************
     710 Write an debug message on the debugfile.
     711 This is called by dbghdr() and format_debug_text().
     712************************************************************************/
     713
     714 int Debug1( const char *format_str, ... )
     715{
     716        va_list ap;
     717        int old_errno = errno;
     718
     719        debug_count++;
     720
     721        if ( state.logtype != DEBUG_FILE ) {
     722                va_start( ap, format_str );
     723                if (state.fd > 0)
     724                        (void)vdprintf( state.fd, format_str, ap );
     725                va_end( ap );
     726                errno = old_errno;
     727                goto done;
     728        }
     729
     730#ifdef WITH_SYSLOG
     731        if( !state.settings.syslog_only)
     732#endif
     733        {
     734                if( state.fd <= 0 ) {
     735                        mode_t oldumask = umask( 022 );
     736                        int fd = open( state.debugf, O_WRONLY|O_APPEND|O_CREAT, 0644 );
     737                        (void)umask( oldumask );
     738                        if(fd == -1) {
     739                                errno = old_errno;
     740                                goto done;
     741                        }
     742                        state.fd = fd;
     743                }
     744        }
     745
     746#ifdef WITH_SYSLOG
     747        if( syslog_level < state.settings.syslog ) {
     748                /* map debug levels to syslog() priorities
     749                 * note that not all DEBUG(0, ...) calls are
     750                 * necessarily errors */
     751                static const int priority_map[4] = {
     752                        LOG_ERR,     /* 0 */
     753                        LOG_WARNING, /* 1 */
     754                        LOG_NOTICE,  /* 2 */
     755                        LOG_INFO,    /* 3 */
     756                };
     757                int     priority;
     758                char *msgbuf = NULL;
     759                int ret;
     760
     761                if( syslog_level >= ARRAY_SIZE(priority_map) || syslog_level < 0)
     762                        priority = LOG_DEBUG;
     763                else
     764                        priority = priority_map[syslog_level];
     765
     766                /*
     767                 * Specify the facility to interoperate with other syslog
     768                 * callers (vfs_full_audit for example).
     769                 */
     770                priority |= SYSLOG_FACILITY;
     771
     772                va_start(ap, format_str);
     773                ret = vasprintf(&msgbuf, format_str, ap);
     774                va_end(ap);
     775
     776                if (ret != -1) {
     777                        syslog(priority, "%s", msgbuf);
     778                }
     779                SAFE_FREE(msgbuf);
     780        }
     781#endif
     782
     783        check_log_size();
     784
     785#ifdef WITH_SYSLOG
     786        if( !state.settings.syslog_only)
     787#endif
     788        {
     789                va_start( ap, format_str );
     790                if (state.fd > 0)
     791                        (void)vdprintf( state.fd, format_str, ap );
     792                va_end( ap );
     793        }
     794
     795 done:
     796        errno = old_errno;
     797
     798        return( 0 );
     799}
     800
     801
     802/**************************************************************************
     803 Print the buffer content via Debug1(), then reset the buffer.
     804 Input:  none
     805 Output: none
     806****************************************************************************/
     807
     808static void bufr_print( void )
     809{
     810        format_bufr[format_pos] = '\0';
     811        (void)Debug1( "%s", format_bufr );
     812        format_pos = 0;
     813}
     814
     815/***************************************************************************
     816 Format the debug message text.
     817
     818 Input:  msg - Text to be added to the "current" debug message text.
     819
     820 Output: none.
     821
     822 Notes:  The purpose of this is two-fold.  First, each call to syslog()
     823         (used by Debug1(), see above) generates a new line of syslog
     824         output.  This is fixed by storing the partial lines until the
     825         newline character is encountered.  Second, printing the debug
     826         message lines when a newline is encountered allows us to add
     827         spaces, thus indenting the body of the message and making it
     828         more readable.
     829**************************************************************************/
     830
     831static void format_debug_text( const char *msg )
     832{
     833        size_t i;
     834        bool timestamp = (state.logtype == DEBUG_FILE && (state.settings.timestamp_logs));
     835
     836        if (!format_bufr) {
     837                debug_init();
     838        }
     839
     840        for( i = 0; msg[i]; i++ ) {
     841                /* Indent two spaces at each new line. */
     842                if(timestamp && 0 == format_pos) {
     843                        format_bufr[0] = format_bufr[1] = ' ';
     844                        format_pos = 2;
     845                }
     846
     847                /* If there's room, copy the character to the format buffer. */
     848                if( format_pos < FORMAT_BUFR_MAX )
     849                        format_bufr[format_pos++] = msg[i];
     850
     851                /* If a newline is encountered, print & restart. */
     852                if( '\n' == msg[i] )
     853                        bufr_print();
     854
     855                /* If the buffer is full dump it out, reset it, and put out a line
     856                 * continuation indicator.
     857                 */
     858                if( format_pos >= FORMAT_BUFR_MAX ) {
     859                        bufr_print();
     860                        (void)Debug1( " +>\n" );
     861                }
     862        }
     863
     864        /* Just to be safe... */
     865        format_bufr[format_pos] = '\0';
     866}
     867
     868/***************************************************************************
     869 Flush debug output, including the format buffer content.
     870
     871 Input:  none
     872 Output: none
     873***************************************************************************/
     874
     875void dbgflush( void )
     876{
     877        bufr_print();
     878}
     879
     880/***************************************************************************
     881 Print a Debug Header.
     882
     883 Input:  level - Debug level of the message (not the system-wide debug
     884                  level. )
     885          cls   - Debuglevel class of the calling module.
     886          file  - Pointer to a string containing the name of the file
     887                  from which this function was called, or an empty string
     888                  if the __FILE__ macro is not implemented.
     889          func  - Pointer to a string containing the name of the function
     890                  from which this function was called, or an empty string
     891                  if the __FUNCTION__ macro is not implemented.
     892         line  - line number of the call to dbghdr, assuming __LINE__
     893                 works.
     894
     895  Output: Always true.  This makes it easy to fudge a call to dbghdr()
     896          in a macro, since the function can be called as part of a test.
     897          Eg: ( (level <= DEBUGLEVEL) && (dbghdr(level,"",line)) )
     898
     899  Notes:  This function takes care of setting syslog_level.
     900
     901****************************************************************************/
     902
     903bool dbghdrclass(int level, int cls, const char *location, const char *func)
     904{
     905        /* Ensure we don't lose any real errno value. */
     906        int old_errno = errno;
     907
     908        if( format_pos ) {
     909                /* This is a fudge.  If there is stuff sitting in the format_bufr, then
     910                 * the *right* thing to do is to call
     911                 *   format_debug_text( "\n" );
     912                 * to write the remainder, and then proceed with the new header.
     913                 * Unfortunately, there are several places in the code at which
     914                 * the DEBUG() macro is used to build partial lines.  That in mind,
     915                 * we'll work under the assumption that an incomplete line indicates
     916                 * that a new header is *not* desired.
     917                 */
     918                return( true );
     919        }
     920
     921#ifdef WITH_SYSLOG
     922        /* Set syslog_level. */
     923        syslog_level = level;
     924#endif
     925
     926        /* Don't print a header if we're logging to stdout. */
     927        if ( state.logtype != DEBUG_FILE ) {
     928                return( true );
     929        }
     930
     931        /* Print the header if timestamps are turned on.  If parameters are
     932         * not yet loaded, then default to timestamps on.
     933         */
     934        if( state.settings.timestamp_logs || state.settings.debug_prefix_timestamp) {
     935                char header_str[200];
     936
     937                header_str[0] = '\0';
     938
     939                if( state.settings.debug_pid)
     940                        slprintf(header_str,sizeof(header_str)-1,", pid=%u",(unsigned int)getpid());
     941
     942                if( state.settings.debug_uid) {
     943                        size_t hs_len = strlen(header_str);
     944                        slprintf(header_str + hs_len,
     945                        sizeof(header_str) - 1 - hs_len,
     946                                ", effective(%u, %u), real(%u, %u)",
     947                                (unsigned int)geteuid(), (unsigned int)getegid(),
     948                                (unsigned int)getuid(), (unsigned int)getgid());
     949                }
     950
     951                if (state.settings.debug_class && (cls != DBGC_ALL)) {
     952                        size_t hs_len = strlen(header_str);
     953                        slprintf(header_str + hs_len,
     954                                 sizeof(header_str) -1 - hs_len,
     955                                 ", class=%s",
     956                                 default_classname_table[cls]);
     957                }
     958
     959                /* Print it all out at once to prevent split syslog output. */
     960                if( state.settings.debug_prefix_timestamp ) {
     961                        char *time_str = current_timestring(NULL,
     962                                                            state.settings.debug_hires_timestamp);
     963                        (void)Debug1( "[%s, %2d%s] ",
     964                                      time_str,
     965                                      level, header_str);
     966                        talloc_free(time_str);
     967                } else {
     968                        char *time_str = current_timestring(NULL,
     969                                                            state.settings.debug_hires_timestamp);
     970                        (void)Debug1( "[%s, %2d%s] %s(%s)\n",
     971                                      time_str,
     972                                      level, header_str, location, func );
     973                        talloc_free(time_str);
     974                }
     975        }
     976
     977        errno = old_errno;
     978        return( true );
     979}
     980
     981/***************************************************************************
     982 Add text to the body of the "current" debug message via the format buffer.
     983
     984  Input:  format_str  - Format string, as used in printf(), et. al.
     985          ...         - Variable argument list.
     986
     987  ..or..  va_alist    - Old style variable parameter list starting point.
     988
     989  Output: Always true.  See dbghdr() for more info, though this is not
     990          likely to be used in the same way.
     991
     992***************************************************************************/
     993
     994 bool dbgtext( const char *format_str, ... )
     995{
     996        va_list ap;
     997        char *msgbuf = NULL;
     998        bool ret = true;
     999        int res;
     1000
     1001        va_start(ap, format_str);
     1002        res = vasprintf(&msgbuf, format_str, ap);
     1003        va_end(ap);
     1004
     1005        if (res != -1) {
     1006                format_debug_text(msgbuf);
     1007        } else {
     1008                ret = false;
     1009        }
     1010        SAFE_FREE(msgbuf);
     1011        return ret;
     1012}
     1013
    411014
    421015/* the registered mutex handlers */
     
    461019} debug_handlers;
    471020
    48 /* state variables for the debug system */
    49 static struct {
    50         int fd;
    51         enum debug_logtype logtype;
    52         const char *prog_name;
    53         bool reopening_logs;
    54 } state;
    55 
    56 static bool reopen_logs_scheduled;
    57 static bool check_reopen_logs(void)
    58 {
    59         if (state.fd == 0 || reopen_logs_scheduled) {
    60                 reopen_logs_scheduled = false;
    61                 reopen_logs();
    62         }
    63 
    64         if (state.fd <= 0)
    65                 return false;
    66 
    67         return true;
    68 }
    69 
    70 _PUBLIC_ void debug_schedule_reopen_logs(void)
    71 {
    72         reopen_logs_scheduled = true;
    73 }
    74 
    75 static void log_timestring(int level, const char *location, const char *func)
    76 {
    77         char *t = NULL;
    78         char *s = NULL;
    79 
    80         if (!check_reopen_logs()) return;
    81 
    82         if (state.logtype != DEBUG_FILE) return;
    83 
    84         t = timestring(NULL, time(NULL));
    85         if (!t) return;
    86 
    87         asprintf(&s, "[%s, %d %s:%s()]\n", t, level, location, func);
    88         talloc_free(t);
    89         if (!s) return;
    90 
    91         write(state.fd, s, strlen(s));
    92         free(s);
    93 }
    94 
    95 /**
    96   the backend for debug messages. Note that the DEBUG() macro has already
    97   ensured that the log level has been met before this is called
    98 */
    99 _PUBLIC_ void dbghdr(int level, const char *location, const char *func)
    100 {
    101         log_timestring(level, location, func);
    102         log_task_id();
    103 }
    104 
    105 
    106 _PUBLIC_ void dbghdrclass(int level, int dclass, const char *location, const char *func)
    107 {
    108         /* Simple wrapper, Samba 4 doesn't do debug classes */
    109         dbghdr(level, location, func);
    110 }
    111 
    112 /**
    113   the backend for debug messages. Note that the DEBUG() macro has already
    114   ensured that the log level has been met before this is called
    115 
    116   @note You should never have to call this function directly. Call the DEBUG()
    117   macro instead.
    118 */
    119 _PUBLIC_ void dbgtext(const char *format, ...)
    120 {
    121         va_list ap;
    122         char *s = NULL;
    123 
    124         if (!check_reopen_logs()) return;
    125 
    126         va_start(ap, format);
    127         vasprintf(&s, format, ap);
    128         va_end(ap);
    129 
    130         write(state.fd, s, strlen(s));
    131         free(s);
    132 }
    133 
    134 _PUBLIC_ const char *logfile = NULL;
    135 
    136 /**
    137   reopen the log file (usually called because the log file name might have changed)
    138 */
    139 _PUBLIC_ void reopen_logs(void)
    140 {
    141         char *fname = NULL;
    142         int old_fd = state.fd;
    143         if (state.reopening_logs) {
    144                 return;
    145         }
    146 
    147         switch (state.logtype) {
    148         case DEBUG_STDOUT:
    149                 state.fd = 1;
    150                 break;
    151 
    152         case DEBUG_STDERR:
    153                 state.fd = 2;
    154                 break;
    155 
    156         case DEBUG_FILE:
    157                 state.reopening_logs = true;
    158                 if (logfile && (*logfile) == '/') {
    159                         fname = strdup(logfile);
    160                 } else {
    161                         asprintf(&fname, "%s/%s.log", dyn_LOGFILEBASE, state.prog_name);
    162                 }
    163                 if (fname) {
    164                         int newfd = open(fname, O_CREAT|O_APPEND|O_WRONLY, 0600);
    165                         if (newfd == -1) {
    166                                 DEBUG(1, ("Failed to open new logfile: %s\n", fname));
    167                                 old_fd = -1;
    168                         } else {
    169                                 state.fd = newfd;
    170                         }
    171                         free(fname);
    172                 } else {
    173                         DEBUG(1, ("Failed to find name for file-based logfile!\n"));
    174                 }
    175                 state.reopening_logs = false;
    176 
    177                 break;
    178         }
    179 
    180         if (old_fd > 2) {
    181                 close(old_fd);
    182         }
    183 }
    184 
    185 /**
    186   control the name of the logfile and whether logging will be to stdout, stderr
    187   or a file
    188 */
    189 _PUBLIC_ void setup_logging(const char *prog_name, enum debug_logtype new_logtype)
    190 {
    191         if (state.logtype < new_logtype) {
    192                 state.logtype = new_logtype;
    193         }
    194         if (prog_name) {
    195                 state.prog_name = prog_name;
    196         }
    197         reopen_logs();
    198 }
    199 
    200 /**
    201    Just run logging to stdout for this program
    202 */
    203 _PUBLIC_ void setup_logging_stdout(void)
    204 {
    205         setup_logging(NULL, DEBUG_STDOUT);
    206 }
    207 
    208 /**
    209   return a string constant containing n tabs
    210   no more than 10 tabs are returned
    211 */
    212 _PUBLIC_ const char *do_debug_tab(int n)
    213 {
    214         const char *tabs[] = {"", "\t", "\t\t", "\t\t\t", "\t\t\t\t", "\t\t\t\t\t",
    215                               "\t\t\t\t\t\t", "\t\t\t\t\t\t\t", "\t\t\t\t\t\t\t\t",
    216                               "\t\t\t\t\t\t\t\t\t", "\t\t\t\t\t\t\t\t\t\t"};
    217         return tabs[MIN(n, 10)];
    218 }
    219 
    220 
    2211021/**
    2221022  log suspicious usage - print comments and backtrace
     
    2521052        if (!debug_handlers.ops.log_task_id) return;
    2531053
    254         if (!check_reopen_logs()) return;
     1054        if (!reopen_logs_internal()) return;
    2551055
    2561056        debug_handlers.ops.log_task_id(state.fd);
  • vendor/current/lib/util/debug.h

    r414 r740  
    11/*
    22   Unix SMB/CIFS implementation.
    3    Samba debug defines
    4    Copyright (C) Andrew Tridgell 2003
     3   SMB debug stuff
     4   Copyright (C) Andrew Tridgell 1992-1998
     5   Copyright (C) John H Terpstra 1996-1998
     6   Copyright (C) Luke Kenneth Casson Leighton 1996-1998
     7   Copyright (C) Paul Ashton 1998
    58
    69   This program is free software; you can redistribute it and/or modify
     
    811   the Free Software Foundation; either version 3 of the License, or
    912   (at your option) any later version.
    10    
     13
    1114   This program is distributed in the hope that it will be useful,
    1215   but WITHOUT ANY WARRANTY; without even the implied warranty of
    1316   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    1417   GNU General Public License for more details.
    15    
     18
    1619   You should have received a copy of the GNU General Public License
    1720   along with this program.  If not, see <http://www.gnu.org/licenses/>.
    1821*/
    1922
    20 #ifndef _SAMBA_DEBUG_H_
    21 #define _SAMBA_DEBUG_H_
    22 
    23 /**
    24  * @file
    25  * @brief Debugging macros
    26  */
    27 
    28 /* the debug operations structure - contains function pointers to
    29    various debug implementations of each operation */
    30 struct debug_ops {
    31         /* function to log (using DEBUG) suspicious usage of data structure */
    32         void (*log_suspicious_usage)(const char* from, const char* info);
    33                                
    34         /* function to log (using printf) suspicious usage of data structure.
    35          * To be used in circumstances when using DEBUG would cause loop. */
    36         void (*print_suspicious_usage)(const char* from, const char* info);
    37        
    38         /* function to return process/thread id */
    39         uint32_t (*get_task_id)(void);
    40        
    41         /* function to log process/thread id */
    42         void (*log_task_id)(int fd);
    43 };
    44 
    45 #define DEBUGLEVEL *debug_level
    46 extern int DEBUGLEVEL;
    47 
    48 #define debug_ctx() (_debug_ctx?_debug_ctx:(_debug_ctx=talloc_new(NULL)))
    49 
    50 #define DEBUGLVL(level) ((level) <= DEBUGLEVEL)
    51 #define _DEBUG(level, body, header) do { \
    52         if (DEBUGLVL(level)) { \
    53                 void* _debug_ctx=NULL; \
    54                 if (header) { \
    55                         dbghdr(level, __location__, __FUNCTION__); \
    56                 } \
    57                 dbgtext body; \
    58                 talloc_free(_debug_ctx); \
    59         } \
    60 } while (0)
    61 /**
    62  * Write to the debug log.
    63  */
    64 #define DEBUG(level, body) _DEBUG(level, body, true)
    65 /**
    66  * Add data to an existing debug log entry.
    67  */
    68 #define DEBUGADD(level, body) _DEBUG(level, body, false)
    69 
    70 /**
    71  * Obtain indentation string for the debug log.
    72  *
    73  * Level specified by n.
    74  */
    75 #define DEBUGTAB(n) do_debug_tab(n)
     23#ifndef _DEBUG_H
     24#define _DEBUG_H
     25
     26/* -------------------------------------------------------------------------- **
     27 * Debugging code.  See also debug.c
     28 */
     29
     30/* the maximum debug level to compile into the code. This assumes a good
     31   optimising compiler that can remove unused code
     32   for embedded or low-memory systems set this to a value like 2 to get
     33   only important messages. This gives *much* smaller binaries
     34*/
     35#ifndef MAX_DEBUG_LEVEL
     36#define MAX_DEBUG_LEVEL 1000
     37#endif
     38
     39int  Debug1( const char *, ... ) PRINTF_ATTRIBUTE(1,2);
     40bool dbgtext( const char *, ... ) PRINTF_ATTRIBUTE(1,2);
     41bool dbghdrclass( int level, int cls, const char *location, const char *func);
     42bool dbghdr( int level, const char *location, const char *func);
     43
     44/*
     45 * Redefine DEBUGLEVEL because so we don't have to change every source file
     46 * that *unnecessarily* references it.
     47 */
     48#define DEBUGLEVEL DEBUGLEVEL_CLASS[DBGC_ALL]
     49
     50/*
     51 * Define all new debug classes here. A class is represented by an entry in
     52 * the DEBUGLEVEL_CLASS array. Index zero of this arrray is equivalent to the
     53 * old DEBUGLEVEL. Any source file that does NOT add the following lines:
     54 *
     55 *   #undef  DBGC_CLASS
     56 *   #define DBGC_CLASS DBGC_<your class name here>
     57 *
     58 * at the start of the file (after #include "includes.h") will default to
     59 * using index zero, so it will behaive just like it always has.
     60 */
     61#define DBGC_ALL                0 /* index equivalent to DEBUGLEVEL */
     62
     63#define DBGC_TDB                1
     64#define DBGC_PRINTDRIVERS       2
     65#define DBGC_LANMAN             3
     66#define DBGC_SMB                4
     67#define DBGC_RPC_PARSE          5
     68#define DBGC_RPC_SRV            6
     69#define DBGC_RPC_CLI            7
     70#define DBGC_PASSDB             8
     71#define DBGC_SAM                9
     72#define DBGC_AUTH               10
     73#define DBGC_WINBIND            11
     74#define DBGC_VFS                12
     75#define DBGC_IDMAP              13
     76#define DBGC_QUOTA              14
     77#define DBGC_ACLS               15
     78#define DBGC_LOCKING            16
     79#define DBGC_MSDFS              17
     80#define DBGC_DMAPI              18
     81#define DBGC_REGISTRY           19
     82
     83/* Always ensure this is updated when new fixed classes area added, to ensure the array in debug.c is the right size */
     84#define DBGC_MAX_FIXED          19
     85
     86/* So you can define DBGC_CLASS before including debug.h */
     87#ifndef DBGC_CLASS
     88#define DBGC_CLASS            0     /* override as shown above */
     89#endif
     90
     91extern int  *DEBUGLEVEL_CLASS;
     92
     93/* Debugging macros
     94 *
     95 * DEBUGLVL()
     96 *   If the 'file specific' debug class level >= level OR the system-wide
     97 *   DEBUGLEVEL (synomym for DEBUGLEVEL_CLASS[ DBGC_ALL ]) >= level then
     98 *   generate a header using the default macros for file, line, and
     99 *   function name. Returns True if the debug level was <= DEBUGLEVEL.
     100 *
     101 *   Example: if( DEBUGLVL( 2 ) ) dbgtext( "Some text.\n" );
     102 *
     103 * DEBUG()
     104 *   If the 'file specific' debug class level >= level OR the system-wide
     105 *   DEBUGLEVEL (synomym for DEBUGLEVEL_CLASS[ DBGC_ALL ]) >= level then
     106 *   generate a header using the default macros for file, line, and
     107 *   function name. Each call to DEBUG() generates a new header *unless* the
     108 *   previous debug output was unterminated (i.e. no '\n').
     109 *   See debug.c:dbghdr() for more info.
     110 *
     111 *   Example: DEBUG( 2, ("Some text and a value %d.\n", value) );
     112 *
     113 * DEBUGC()
     114 *   If the 'macro specified' debug class level >= level OR the system-wide
     115 *   DEBUGLEVEL (synomym for DEBUGLEVEL_CLASS[ DBGC_ALL ]) >= level then
     116 *   generate a header using the default macros for file, line, and
     117 *   function name. Each call to DEBUG() generates a new header *unless* the
     118 *   previous debug output was unterminated (i.e. no '\n').
     119 *   See debug.c:dbghdr() for more info.
     120 *
     121 *   Example: DEBUGC( DBGC_TDB, 2, ("Some text and a value %d.\n", value) );
     122 *
     123 *  DEBUGADD(), DEBUGADDC()
     124 *    Same as DEBUG() and DEBUGC() except the text is appended to the previous
     125 *    DEBUG(), DEBUGC(), DEBUGADD(), DEBUGADDC() with out another interviening
     126 *    header.
     127 *
     128 *    Example: DEBUGADD( 2, ("Some text and a value %d.\n", value) );
     129 *             DEBUGADDC( DBGC_TDB, 2, ("Some text and a value %d.\n", value) );
     130 *
     131 * Note: If the debug class has not be redeined (see above) then the optimizer
     132 * will remove the extra conditional test.
     133 */
     134
     135/*
     136 * From talloc.c:
     137 */
     138
     139/* these macros gain us a few percent of speed on gcc */
     140#if (__GNUC__ >= 3)
     141/* the strange !! is to ensure that __builtin_expect() takes either 0 or 1
     142   as its first argument */
     143#ifndef likely
     144#define likely(x)   __builtin_expect(!!(x), 1)
     145#endif
     146#ifndef unlikely
     147#define unlikely(x) __builtin_expect(!!(x), 0)
     148#endif
     149#else
     150#ifndef likely
     151#define likely(x) (x)
     152#endif
     153#ifndef unlikely
     154#define unlikely(x) (x)
     155#endif
     156#endif
     157
     158#define CHECK_DEBUGLVL( level ) \
     159  ( ((level) <= MAX_DEBUG_LEVEL) && \
     160    unlikely(DEBUGLEVEL_CLASS[ DBGC_CLASS ] >= (level)))
     161
     162#define DEBUGLVL( level ) \
     163  ( CHECK_DEBUGLVL(level) \
     164   && dbghdrclass( level, DBGC_CLASS, __location__, __FUNCTION__ ) )
     165
     166
     167#define DEBUG( level, body ) \
     168  (void)( ((level) <= MAX_DEBUG_LEVEL) && \
     169          unlikely(DEBUGLEVEL_CLASS[ DBGC_CLASS ] >= (level))           \
     170       && (dbghdrclass( level, DBGC_CLASS, __location__, __FUNCTION__ )) \
     171       && (dbgtext body) )
     172
     173#define DEBUGC( dbgc_class, level, body ) \
     174  (void)( ((level) <= MAX_DEBUG_LEVEL) && \
     175          unlikely(DEBUGLEVEL_CLASS[ dbgc_class ] >= (level))           \
     176       && (dbghdrclass( level, DBGC_CLASS, __location__, __FUNCTION__ )) \
     177       && (dbgtext body) )
     178
     179#define DEBUGADD( level, body ) \
     180  (void)( ((level) <= MAX_DEBUG_LEVEL) && \
     181          unlikely(DEBUGLEVEL_CLASS[ DBGC_CLASS ] >= (level))   \
     182       && (dbgtext body) )
     183
     184#define DEBUGADDC( dbgc_class, level, body ) \
     185  (void)( ((level) <= MAX_DEBUG_LEVEL) && \
     186          unlikely((DEBUGLEVEL_CLASS[ dbgc_class ] >= (level))) \
     187       && (dbgtext body) )
     188
     189/* Print a separator to the debug log. */
     190#define DEBUGSEP(level)\
     191        DEBUG((level),("===============================================================\n"))
     192
     193/* The following definitions come from lib/debug.c  */
    76194
    77195/** Possible destinations for the debug log (in order of precedence -
     
    80198 * the command line, as the smb.conf cannot reset it back to
    81199 * file-based logging */
    82 enum debug_logtype {DEBUG_STDOUT = 0, DEBUG_FILE = 1, DEBUG_STDERR = 2};
    83 
    84 /**
    85   the backend for debug messages. Note that the DEBUG() macro has already
    86   ensured that the log level has been met before this is called
    87 */
    88 _PUBLIC_ void dbghdr(int level, const char *location, const char *func);
    89 
    90 _PUBLIC_ void dbghdrclass(int level, int cls, const char *location, const char *func);
    91 
    92 /**
    93   reopen the log file (usually called because the log file name might have changed)
    94 */
    95 _PUBLIC_ void reopen_logs(void);
    96 
    97 /**
    98  * this global variable determines what messages are printed
    99  */
    100 _PUBLIC_ void debug_schedule_reopen_logs(void);
    101 
    102 /**
    103   control the name of the logfile and whether logging will be to stdout, stderr
    104   or a file
    105 */
    106 _PUBLIC_ void setup_logging(const char *prog_name, enum debug_logtype new_logtype);
    107 
    108 /**
    109    Just run logging to stdout for this program
    110 */
    111 _PUBLIC_ void setup_logging_stdout(void);
    112 
    113 /**
    114   return a string constant containing n tabs
    115   no more than 10 tabs are returned
    116 */
    117 _PUBLIC_ const char *do_debug_tab(int n);
     200enum debug_logtype {DEBUG_DEFAULT_STDERR = 0, DEBUG_STDOUT = 1, DEBUG_FILE = 2, DEBUG_STDERR = 3};
     201
     202struct debug_settings {
     203        size_t max_log_size;
     204        bool syslog;
     205        bool syslog_only;
     206        bool timestamp_logs;
     207        bool debug_prefix_timestamp;
     208        bool debug_hires_timestamp;
     209        bool debug_pid;
     210        bool debug_uid;
     211        bool debug_class;
     212};
     213
     214void setup_logging(const char *prog_name, enum debug_logtype new_logtype);
     215
     216void debug_close_dbf(void);
     217void gfree_debugsyms(void);
     218int debug_add_class(const char *classname);
     219int debug_lookup_classname(const char *classname);
     220bool debug_parse_levels(const char *params_str);
     221void debug_setup_talloc_log(void);
     222void debug_set_logfile(const char *name);
     223void debug_set_settings(struct debug_settings *settings);
     224bool reopen_logs_internal( void );
     225void force_check_log_size( void );
     226bool need_to_check_log_size( void );
     227void check_log_size( void );
     228void dbgflush( void );
     229bool dbghdrclass(int level, int cls, const char *location, const char *func);
     230bool dbghdr(int level, const char *location, const char *func);
     231bool debug_get_output_is_stderr(void);
     232void debug_schedule_reopen_logs(void);
     233char *debug_list_class_names_and_levels(void);
    118234
    119235/**
     
    129245_PUBLIC_ void log_task_id(void);
    130246
     247/* the debug operations structure - contains function pointers to
     248   various debug implementations of each operation */
     249struct debug_ops {
     250        /* function to log (using DEBUG) suspicious usage of data structure */
     251        void (*log_suspicious_usage)(const char* from, const char* info);
     252
     253        /* function to log (using printf) suspicious usage of data structure.
     254         * To be used in circumstances when using DEBUG would cause loop. */
     255        void (*print_suspicious_usage)(const char* from, const char* info);
     256
     257        /* function to return process/thread id */
     258        uint32_t (*get_task_id)(void);
     259
     260        /* function to log process/thread id */
     261        void (*log_task_id)(int fd);
     262};
     263
    131264/**
    132265  register a set of debug handlers.
     
    134267_PUBLIC_ void register_debug_handlers(const char *name, struct debug_ops *ops);
    135268
    136 /**
    137   the backend for debug messages. Note that the DEBUG() macro has already
    138   ensured that the log level has been met before this is called
    139 
    140   @note You should never have to call this function directly. Call the DEBUG()
    141   macro instead.
    142 */
    143 _PUBLIC_ void dbgtext(const char *format, ...) PRINTF_ATTRIBUTE(1,2);
    144 
    145 struct _XFILE;
    146 extern struct _XFILE *dbf;
    147 
    148 #endif
     269#endif
  • vendor/current/lib/util/dlinklist.h

    r414 r740  
    22   Unix SMB/CIFS implementation.
    33   some simple double linked list macros
    4    Copyright (C) Andrew Tridgell 1998
     4
     5   Copyright (C) Andrew Tridgell 1998-2010
    56   
    67   This program is free software; you can redistribute it and/or modify
     
    2425#define _DLINKLIST_H
    2526
     27/*
     28  February 2010 - changed list format to have a prev pointer from the
     29  list head. This makes DLIST_ADD_END() O(1) even though we only have
     30  one list pointer.
    2631
    27 /* hook into the front of the list */
     32  The scheme is as follows:
     33
     34     1) with no entries in the list:
     35          list_head == NULL
     36
     37     2) with 1 entry in the list:
     38          list_head->next == NULL
     39          list_head->prev == list_head
     40
     41     3) with 2 entries in the list:
     42          list_head->next == element2
     43          list_head->prev == element2
     44          element2->prev == list_head
     45          element2->next == NULL
     46
     47     4) with N entries in the list:
     48          list_head->next == element2
     49          list_head->prev == elementN
     50          elementN->prev == element{N-1}
     51          elementN->next == NULL
     52
     53  This allows us to find the tail of the list by using
     54  list_head->prev, which means we can add to the end of the list in
     55  O(1) time
     56
     57
     58  Note that the 'type' arguments below are no longer needed, but
     59  are kept for now to prevent an incompatible argument change
     60 */
     61
     62
     63/*
     64   add an element at the front of a list
     65*/
    2866#define DLIST_ADD(list, p) \
    2967do { \
    3068        if (!(list)) { \
    31                 (list) = (p); \
    32                 (p)->next = (p)->prev = NULL; \
     69                (p)->prev = (list) = (p); \
     70                (p)->next = NULL; \
    3371        } else { \
     72                (p)->prev = (list)->prev; \
    3473                (list)->prev = (p); \
    3574                (p)->next = (list); \
    36                 (p)->prev = NULL; \
    3775                (list) = (p); \
    38         }\
     76        } \
    3977} while (0)
    4078
    41 /* remove an element from a list - element doesn't have to be in list. */
     79/*
     80   remove an element from a list
     81   Note that the element doesn't have to be in the list. If it
     82   isn't then this is a no-op
     83*/
    4284#define DLIST_REMOVE(list, p) \
    4385do { \
    4486        if ((p) == (list)) { \
     87                if ((p)->next) (p)->next->prev = (p)->prev; \
    4588                (list) = (p)->next; \
    46                 if (list) (list)->prev = NULL; \
     89        } else if ((list) && (p) == (list)->prev) {     \
     90                (p)->prev->next = NULL; \
     91                (list)->prev = (p)->prev; \
    4792        } else { \
    4893                if ((p)->prev) (p)->prev->next = (p)->next; \
    4994                if ((p)->next) (p)->next->prev = (p)->prev; \
    5095        } \
    51         if ((p) != (list)) (p)->next = (p)->prev = NULL; \
     96        if ((p) != (list)) (p)->next = (p)->prev = NULL;        \
    5297} while (0)
    5398
    54 /* promote an element to the top of the list */
    55 #define DLIST_PROMOTE(list, p) \
     99/*
     100   find the head of the list given any element in it.
     101   Note that this costs O(N), so you should avoid this macro
     102   if at all possible!
     103*/
     104#define DLIST_HEAD(p, result_head) \
    56105do { \
    57           DLIST_REMOVE(list, p); \
    58           DLIST_ADD(list, p); \
    59 } while (0)
     106       (result_head) = (p); \
     107       while (DLIST_PREV(result_head)) (result_head) = (result_head)->prev; \
     108} while(0)
    60109
    61 /* hook into the end of the list - needs the entry type */
    62 #define DLIST_ADD_END(list, p, type) \
    63 do { \
    64                 if (!(list)) { \
    65                         (list) = (p); \
    66                         (p)->next = (p)->prev = NULL; \
    67                 } else { \
    68                         type tmp; \
    69                         for (tmp = (list); tmp->next; tmp = tmp->next) ; \
    70                         tmp->next = (p); \
    71                         (p)->next = NULL; \
    72                         (p)->prev = tmp; \
    73                 } \
    74 } while (0)
     110/* return the last element in the list */
     111#define DLIST_TAIL(list) ((list)?(list)->prev:NULL)
     112
     113/* return the previous element in the list. */
     114#define DLIST_PREV(p) (((p)->prev && (p)->prev->next != NULL)?(p)->prev:NULL)
    75115
    76116/* insert 'p' after the given element 'el' in a list. If el is NULL then
     
    81121                DLIST_ADD(list, p); \
    82122        } else { \
    83                 p->prev = el; \
    84                 p->next = el->next; \
    85                 el->next = p; \
    86                 if (p->next) p->next->prev = p; \
     123                (p)->prev = (el);   \
     124                (p)->next = (el)->next;         \
     125                (el)->next = (p);               \
     126                if ((p)->next) (p)->next->prev = (p);   \
     127                if ((list)->prev == (el)) (list)->prev = (p); \
    87128        }\
    88129} while (0)
    89130
    90 /* demote an element to the end of the list, needs the entry type */
    91 #define DLIST_DEMOTE(list, p, type) \
     131
     132/*
     133   add to the end of a list.
     134   Note that 'type' is ignored
     135*/
     136#define DLIST_ADD_END(list, p, type)                    \
    92137do { \
    93                 DLIST_REMOVE(list, p); \
    94                 DLIST_ADD_END(list, p, type); \
     138        if (!(list)) { \
     139                DLIST_ADD(list, p); \
     140        } else { \
     141                DLIST_ADD_AFTER(list, p, (list)->prev); \
     142        } \
    95143} while (0)
    96144
    97 /* concatenate two lists - putting all elements of the 2nd list at the
    98    end of the first list */
    99 #define DLIST_CONCATENATE(list1, list2, type) \
     145/* promote an element to the from of a list */
     146#define DLIST_PROMOTE(list, p) \
    100147do { \
    101                 if (!(list1)) { \
    102                         (list1) = (list2); \
    103                 } else { \
    104                         type tmp; \
    105                         for (tmp = (list1); tmp->next; tmp = tmp->next) ; \
    106                         tmp->next = (list2); \
    107                         if (list2) { \
    108                                 (list2)->prev = tmp;    \
    109                         } \
     148          DLIST_REMOVE(list, p); \
     149          DLIST_ADD(list, p); \
     150} while (0)
     151
     152/*
     153   demote an element to the end of a list.
     154   Note that 'type' is ignored
     155*/
     156#define DLIST_DEMOTE(list, p, type)                     \
     157do { \
     158        DLIST_REMOVE(list, p); \
     159        DLIST_ADD_END(list, p, NULL);           \
     160} while (0)
     161
     162/*
     163   concatenate two lists - putting all elements of the 2nd list at the
     164   end of the first list.
     165   Note that 'type' is ignored
     166*/
     167#define DLIST_CONCATENATE(list1, list2, type)   \
     168do { \
     169        if (!(list1)) { \
     170                (list1) = (list2); \
     171        } else { \
     172                (list1)->prev->next = (list2); \
     173                if (list2) { \
     174                        void *_tmplist = (void *)(list1)->prev; \
     175                        (list1)->prev = (list2)->prev; \
     176                        (list2)->prev = _tmplist; \
    110177                } \
     178        } \
    111179} while (0)
    112180
  • vendor/current/lib/util/fault.c

    r414 r740  
    5252#endif
    5353        void *backtrace_stack[BACKTRACE_STACK_SIZE];
    54         size_t backtrace_size;
     54        int backtrace_size;
    5555        char **backtrace_strings;
    5656
     
    126126                char cmdstring[200];
    127127                safe_strcpy(cmdstring, panic_action, sizeof(cmdstring));
    128                 snprintf(pidstr, sizeof(pidstr), "%u", getpid());
     128                snprintf(pidstr, sizeof(pidstr), "%d", (int) getpid());
    129129                all_string_sub(cmdstring, "%PID%", pidstr, sizeof(cmdstring));
    130130                if (progname) {
     
    146146
    147147#ifdef SIGABRT
    148         CatchSignal(SIGABRT,SIGNAL_CAST SIG_DFL);
     148        CatchSignal(SIGABRT, SIG_DFL);
    149149#endif
    150150        abort();
     
    188188_PUBLIC_ void fault_setup(const char *pname)
    189189{
    190         if (progname == NULL) {
    191                 progname = pname;
    192         }
     190        if (progname != NULL) {
     191                return;
     192        }
     193        progname = pname;
    193194#ifdef SIGSEGV
    194         CatchSignal(SIGSEGV,SIGNAL_CAST sig_fault);
     195        CatchSignal(SIGSEGV, sig_fault);
    195196#endif
    196197#ifdef SIGBUS
    197         CatchSignal(SIGBUS,SIGNAL_CAST sig_fault);
     198        CatchSignal(SIGBUS, sig_fault);
    198199#endif
    199200#ifdef SIGABRT
    200         CatchSignal(SIGABRT,SIGNAL_CAST sig_fault);
     201        CatchSignal(SIGABRT, sig_fault);
    201202#endif
    202203#ifdef SIGFPE
    203         CatchSignal(SIGFPE,SIGNAL_CAST sig_fault);
    204 #endif
    205 }
     204        CatchSignal(SIGFPE, sig_fault);
     205#endif
     206}
     207
     208/**
     209   disable setting up fault handlers
     210**/
     211_PUBLIC_ void fault_setup_disable(void)
     212{
     213        progname = "fault disabled";
     214}
     215
    206216
    207217/**
  • vendor/current/lib/util/genrand.c

    r414 r740  
    363363
    364364/**
     365 * Generate a random text password.
     366 */
     367
     368_PUBLIC_ char *generate_random_password(TALLOC_CTX *mem_ctx, size_t min, size_t max)
     369{
     370        char *retstr;
     371        /* This list does not include { or } because they cause
     372         * problems for our provision (it can create a substring
     373         * ${...}, and for Fedora DS (which treats {...} at the start
     374         * of a stored password as special
     375         *  -- Andrew Bartlett 2010-03-11
     376         */
     377        const char *c_list = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+_-#.,@$%&!?:;<=>()[]~";
     378        size_t len = max;
     379        size_t diff;
     380
     381        if (min > max) {
     382                errno = EINVAL;
     383                return NULL;
     384        }
     385
     386        diff = max - min;
     387
     388        if (diff > 0 ) {
     389                size_t tmp;
     390
     391                generate_random_buffer((uint8_t *)&tmp, sizeof(tmp));
     392
     393                tmp %= diff;
     394
     395                len = min + tmp;
     396        }
     397
     398again:
     399        retstr = generate_random_str_list(mem_ctx, len, c_list);
     400        if (!retstr) return NULL;
     401
     402        /* we need to make sure the random string passes basic quality tests
     403           or it might be rejected by windows as a password */
     404        if (len >= 7 && !check_password_quality(retstr)) {
     405                talloc_free(retstr);
     406                goto again;
     407        }
     408
     409        return retstr;
     410}
     411
     412/**
    365413 * Generate an array of unique text strings all of the same length.
    366414 * The returned string will be allocated.
  • vendor/current/lib/util/idtree.c

    r414 r740  
    105105        int n, m, sh;
    106106        struct idr_layer *p, *pn;
    107         struct idr_layer *pa[MAX_LEVEL];
    108         int l, id, oid;
     107        struct idr_layer *pa[MAX_LEVEL+1];
     108        unsigned int l, id, oid;
    109109        uint32_t bm;
    110110
     
    241241{
    242242        struct idr_layer *p = idp->top;
    243         struct idr_layer **pa[MAX_LEVEL];
     243        struct idr_layer **pa[1+MAX_LEVEL];
    244244        struct idr_layer ***paa = &pa[0];
    245245        int n;
     
    281281         * present.  If so, tain't one of ours!
    282282         */
    283         if ((id & ~(~0 << MAX_ID_SHIFT)) >> (n + IDR_BITS))
    284              return NULL;
     283        if (n + IDR_BITS < 31 &&
     284            ((id & ~(~0 << MAX_ID_SHIFT)) >> (n + IDR_BITS))) {
     285                return NULL;
     286        }
    285287
    286288        /* Mask off upper bits we don't use for the search. */
  • vendor/current/lib/util/memory.h

    r414 r740  
    2929 * always be ignored.
    3030 **/
    31 #define SAFE_FREE(x) do { if ((x) != NULL) {free(discard_const_p(void *, (x))); (x)=NULL;} } while(0)
     31#define SAFE_FREE(x) do { if ((x) != NULL) {free(x); (x)=NULL;} } while(0)
    3232#endif
    3333
  • vendor/current/lib/util/params.c

    r594 r740  
    489489  } /* Parse */
    490490
    491 static myFILE *OpenConfFile( const char *FileName )
     491static myFILE *OpenConfFile(TALLOC_CTX *mem_ctx, const char *FileName )
    492492  /* ------------------------------------------------------------------------ **
    493493   * Open a configuration file.
     
    503503  myFILE *ret;
    504504
    505   ret = talloc(talloc_autofree_context(), myFILE);
     505  ret = talloc(mem_ctx, myFILE);
    506506  if (!ret) return NULL;
    507507
     
    544544  const char *func = "params.c:pm_process() -";
    545545
    546   InFile = OpenConfFile( FileName );          /* Open the config file. */
     546  InFile = OpenConfFile(NULL, FileName); /* Open the config file. */
    547547  if( NULL == InFile )
    548548    return( false );
  • vendor/current/lib/util/system.c

    r414 r740  
    118118        return mypid;
    119119}
     120
     121
     122_PUBLIC_ int sys_getpeereid( int s, uid_t *uid)
     123{
     124#if defined(HAVE_PEERCRED)
     125        struct ucred cred;
     126        socklen_t cred_len = sizeof(struct ucred);
     127        int ret;
     128
     129        ret = getsockopt(s, SOL_SOCKET, SO_PEERCRED, (void *)&cred, &cred_len);
     130        if (ret != 0) {
     131                return -1;
     132        }
     133
     134        if (cred_len != sizeof(struct ucred)) {
     135                errno = EINVAL;
     136                return -1;
     137        }
     138
     139        *uid = cred.uid;
     140        return 0;
     141#else
     142#if defined(HAVE_GETPEEREID)
     143        gid_t gid;
     144        return getpeereid(s, uid, &gid);
     145#endif
     146        errno = ENOSYS;
     147        return -1;
     148#endif
     149}
     150
     151_PUBLIC_ int sys_getnameinfo(const struct sockaddr *psa,
     152                             int salen,
     153                             char *host,
     154                             size_t hostlen,
     155                             char *service,
     156                             size_t servlen,
     157                             int flags)
     158{
     159        /*
     160         * For Solaris we must make sure salen is the
     161         * correct length for the incoming sa_family.
     162         */
     163
     164        if (salen == sizeof(struct sockaddr_storage)) {
     165                salen = sizeof(struct sockaddr_in);
     166#if defined(HAVE_IPV6)
     167                if (psa->sa_family == AF_INET6) {
     168                        salen = sizeof(struct sockaddr_in6);
     169                }
     170#endif
     171        }
     172        return getnameinfo(psa, salen, host, hostlen, service, servlen, flags);
     173}
     174
     175_PUBLIC_ int sys_connect(int fd, const struct sockaddr * addr)
     176{
     177        socklen_t salen = (socklen_t)-1;
     178
     179        if (addr->sa_family == AF_INET) {
     180            salen = sizeof(struct sockaddr_in);
     181        } else if (addr->sa_family == AF_UNIX) {
     182            salen = sizeof(struct sockaddr_un);
     183        }
     184#if defined(HAVE_IPV6)
     185        else if (addr->sa_family == AF_INET6) {
     186            salen = sizeof(struct sockaddr_in6);
     187        }
     188#endif
     189
     190        return connect(fd, addr, salen);
     191}
  • vendor/current/lib/util/talloc_stack.c

    r427 r740  
    6969{
    7070#if defined(PARANOID_MALLOC_CHECKER)
    71 #ifdef malloc
    72 #undef malloc
     71#ifdef calloc
     72#undef calloc
    7373#endif
    7474#endif
    75         struct talloc_stackframe *ts =
    76                 (struct talloc_stackframe *)malloc(sizeof(struct talloc_stackframe));
     75        struct talloc_stackframe *ts = (struct talloc_stackframe *)calloc(
     76                1, sizeof(struct talloc_stackframe));
    7777#if defined(PARANOID_MALLOC_CHECKER)
    78 #define malloc(s) __ERROR_DONT_USE_MALLOC_DIRECTLY
     78#define calloc(n, s) __ERROR_DONT_USE_MALLOC_DIRECTLY
    7979#endif
    8080
     
    8282                smb_panic("talloc_stackframe_init malloc failed");
    8383        }
    84 
    85         ZERO_STRUCTP(ts);
    8684
    8785        SMB_THREAD_ONCE(&ts_initialized, talloc_stackframe_init, NULL);
     
    103101                        break;
    104102                }
    105                 talloc_free(ts->talloc_stack[i]);
    106                 ts->talloc_stack[i] = NULL;
     103                TALLOC_FREE(ts->talloc_stack[i]);
    107104        }
    108105
  • vendor/current/lib/util/talloc_stack.h

    r414 r740  
    3636#define _TALLOC_STACK_H
    3737
    38 #include "talloc.h"
     38#include <talloc.h>
    3939
    4040/*
  • vendor/current/lib/util/tests/data_blob.c

    r414 r740  
    7979{
    8080        DATA_BLOB a = data_blob_string_const("\xC\xA\xF\xE");
    81         torture_assert_str_equal(tctx, data_blob_hex_string(tctx, &a), "0C0A0F0E", "hex string");
     81        torture_assert_str_equal(tctx, data_blob_hex_string_lower(tctx, &a), "0c0a0f0e", "hex string");
     82        torture_assert_str_equal(tctx, data_blob_hex_string_upper(tctx, &a), "0C0A0F0E", "hex string");
    8283        return true;
    8384}
     
    8586struct torture_suite *torture_local_util_data_blob(TALLOC_CTX *mem_ctx)
    8687{
    87         struct torture_suite *suite = torture_suite_create(mem_ctx, "DATABLOB");
     88        struct torture_suite *suite = torture_suite_create(mem_ctx, "datablob");
    8889
    8990        torture_suite_add_simple_test(suite, "string", test_string);
  • vendor/current/lib/util/tests/file.c

    r414 r740  
    9292struct torture_suite *torture_local_util_file(TALLOC_CTX *mem_ctx)
    9393{
    94         struct torture_suite *suite = torture_suite_create(mem_ctx, "FILE");
     94        struct torture_suite *suite = torture_suite_create(mem_ctx, "file");
    9595
    9696        torture_suite_add_simple_test(suite, "file_load_save",
    9797                                      test_file_load_save);
    9898
    99         torture_suite_add_simple_test(suite, "afdgets",
    100                                       test_afdgets);
     99        torture_suite_add_simple_test(suite, "afdgets", test_afdgets);
    101100
    102101        return suite;
  • vendor/current/lib/util/tests/genrand.c

    r414 r740  
    6060struct torture_suite *torture_local_genrand(TALLOC_CTX *mem_ctx)
    6161{
    62         struct torture_suite *suite = torture_suite_create(mem_ctx, "GENRAND");
     62        struct torture_suite *suite = torture_suite_create(mem_ctx, "genrand");
    6363        torture_suite_add_simple_test(suite, "reseed_callback", test_reseed_callback);
    6464        torture_suite_add_simple_test(suite, "check_password_quality", test_check_password_quality);
  • vendor/current/lib/util/tests/idtree.c

    r414 r740  
    116116struct torture_suite *torture_local_idtree(TALLOC_CTX *mem_ctx)
    117117{
    118         struct torture_suite *suite = torture_suite_create(mem_ctx, "IDTREE");
     118        struct torture_suite *suite = torture_suite_create(mem_ctx, "idtree");
    119119        torture_suite_add_simple_test(suite, "idtree", torture_local_idtree_simple);
    120120        return suite;
  • vendor/current/lib/util/tests/parmlist.c

    r414 r740  
    6060        torture_assert_str_equal(tctx, e->value, "mystring", "value");
    6161
    62         e = parmlist_get(pctx, "nonexistant");
    63         torture_assert(tctx, e == NULL, "nonexistant");
     62        e = parmlist_get(pctx, "non-existent");
     63        torture_assert(tctx, e == NULL, "non-existent");
    6464        return true;
    6565}
     
    8888        torture_assert_str_equal(tctx, "true", ret[0], "ret[0]");
    8989        torture_assert_str_equal(tctx, "false", ret[1], "ret[1]");
    90         torture_assert(tctx, NULL == parmlist_get_string_list(pctx, "nonexistant", NULL), "nonexistant");
     90        torture_assert(tctx, NULL == parmlist_get_string_list(pctx, "non-existent", NULL), "non-existent");
    9191
    9292        return true;
     
    9595struct torture_suite *torture_local_util_parmlist(TALLOC_CTX *mem_ctx)
    9696{
    97         struct torture_suite *suite = torture_suite_create(mem_ctx, "PARMLIST");
     97        struct torture_suite *suite = torture_suite_create(mem_ctx, "parmlist");
    9898
    9999        torture_suite_add_simple_test(suite, "get_int", test_get_int);
  • vendor/current/lib/util/tests/str.c

    r414 r740  
    9595struct torture_suite *torture_local_util_str(TALLOC_CTX *mem_ctx)
    9696{
    97         struct torture_suite *suite = torture_suite_create(mem_ctx, "STR");
     97        struct torture_suite *suite = torture_suite_create(mem_ctx, "str");
    9898
    9999        torture_suite_add_simple_test(suite, "string_sub_simple",
  • vendor/current/lib/util/tests/strlist.c

    r414 r740  
    2727struct test_list_element {
    2828        const char *list_as_string;
    29         const char *seperators;
     29        const char *separators;
    3030        const char *list[5];
    3131};
    3232
    33 struct test_list_element test_lists_strings[] = {
     33const struct test_list_element test_lists_strings[] = {
    3434        {
    3535                .list_as_string = "",
     
    4747                .list_as_string = "foo bar",
    4848                .list = { "foo bar", NULL },
    49                 .seperators = ";"
     49                .separators = ";"
    5050        },
    5151        {
     
    6060                .list_as_string = "\"foo bar\",comma;semicolon",
    6161                .list = { "\"foo bar\",comma", "semicolon", NULL },
    62                 .seperators = ";"
     62                .separators = ";"
    6363        }
    6464};
    6565
    66 struct test_list_element test_lists_shell_strings[] = {
     66const struct test_list_element test_lists_shell_strings[] = {
    6767        {
    6868                .list_as_string = "",
     
    8080                .list_as_string = "foo bar",
    8181                .list = { "foo bar", NULL },
    82                 .seperators = ";"
     82                .separators = ";"
    8383        },
    8484        {
     
    100100};
    101101
    102 static bool test_lists_shell(struct torture_context *tctx,
    103                              const void *data)
     102static bool test_lists_shell(struct torture_context *tctx, const void *data)
    104103{
    105104        const struct test_list_element *element = data;
    106         const char **ret1, **ret2, *tmp;
     105
     106        char **ret1, **ret2, *tmp;
    107107        bool match = true;
    108108        TALLOC_CTX *mem_ctx = tctx;
    109109
    110         ret1 = str_list_make_shell(mem_ctx, element->list_as_string, element->seperators);
     110        ret1 = str_list_make_shell(mem_ctx, element->list_as_string, element->separators);
    111111       
    112112        torture_assert(tctx, ret1, "str_list_make_shell() must not return NULL");
    113         tmp = str_list_join_shell(mem_ctx, ret1, element->seperators ? *element->seperators : ' ');
    114         ret2 = str_list_make_shell(mem_ctx, tmp, element->seperators);
     113        tmp = str_list_join_shell(mem_ctx, (const char **) ret1, element->separators ? *element->separators : ' ');
     114        ret2 = str_list_make_shell(mem_ctx, tmp, element->separators);
    115115
    116116        if ((ret1 == NULL || ret2 == NULL) && ret2 != ret1) {
     
    131131        torture_assert(tctx, match, talloc_asprintf(tctx,
    132132                "str_list_{make,join}_shell: Error double parsing, first run:\n%s\nSecond run: \n%s", element->list_as_string, tmp));
    133         torture_assert(tctx, str_list_equal(ret1, element->list),
     133        torture_assert(tctx, str_list_equal((const char * const *) ret1,
     134                                            element->list),
    134135                       talloc_asprintf(tctx,
    135136                                       "str_list_make_shell(%s) failed to create correct list",
     
    142143{
    143144        const struct test_list_element *element = data;
     145
    144146        char **result;
    145         result = str_list_make(tctx, element->list_as_string, element->seperators);
     147        result = str_list_make(tctx, element->list_as_string, element->separators);
    146148        torture_assert(tctx, result, "str_list_make() must not return NULL");
    147         torture_assert(tctx, str_list_equal((const char **)result, element->list),
     149        torture_assert(tctx, str_list_equal((const char * const *) result,
     150                                            element->list),
    148151                       talloc_asprintf(tctx,
    149152                                       "str_list_make(%s) failed to create correct list",
     
    251254static bool test_list_add(struct torture_context *tctx)
    252255{
    253         char **result, **result2;
     256        const char **result, **result2;
    254257        const char *list[] = {
    255258                "element_0",
     
    259262                NULL
    260263        };
    261         result = str_list_make(tctx, "element_0, element_1, element_2", NULL);
     264        result = (const char **) str_list_make(tctx, "element_0, element_1, element_2", NULL);
    262265        torture_assert(tctx, result, "str_list_make() must not return NULL");
    263         result2 = str_list_add(result, "element_3");
     266        result2 = str_list_add((const char **) result, "element_3");
    264267        torture_assert(tctx, result2, "str_list_add() must not return NULL");
    265268        torture_assert(tctx, str_list_equal(result2, list),
     
    271274static bool test_list_add_const(struct torture_context *tctx)
    272275{
    273         char **result, **result2;
     276        const char **result, **result2;
    274277        const char *list[] = {
    275278                "element_0",
     
    279282                NULL
    280283        };
    281         result = str_list_make(tctx, "element_0, element_1, element_2", NULL);
     284        result = (const char **) str_list_make(tctx, "element_0, element_1, element_2", NULL);
    282285        torture_assert(tctx, result, "str_list_make() must not return NULL");
    283286        result2 = str_list_add_const(result, "element_3");
     
    291294static bool test_list_remove(struct torture_context *tctx)
    292295{
    293         char **result;
     296        const char **result;
    294297        const char *list[] = {
    295298                "element_0",
     
    298301                NULL
    299302        };
    300         result = str_list_make(tctx, "element_0, element_1, element_2, element_3", NULL);
     303        result = (const char **) str_list_make(tctx, "element_0, element_1, element_2, element_3", NULL);
    301304        torture_assert(tctx, result, "str_list_make() must not return NULL");
    302305        str_list_remove(result, "element_2");
     
    337340static bool test_list_unique(struct torture_context *tctx)
    338341{
    339         char **result;
     342        const char **result;
    340343        const char *list[] = {
    341344                "element_0",
     
    355358                NULL
    356359        };
    357         result = str_list_copy(tctx, list_dup);
     360        result = (const char **) str_list_copy(tctx, list_dup);
    358361        /* We must copy the list, as str_list_unique does a talloc_realloc() on it's parameter */
    359362        result = str_list_unique(result);
     
    374377        const char **list_dup = (const char **)str_list_make_empty(tctx);
    375378
    376         count = lp_parm_int(tctx->lp_ctx, NULL, "list_unique", "count", 9);
    377         num_dups = lp_parm_int(tctx->lp_ctx, NULL, "list_unique", "dups", 7);
     379        count = lpcfg_parm_int(tctx->lp_ctx, NULL, "list_unique", "count", 9);
     380        num_dups = lpcfg_parm_int(tctx->lp_ctx, NULL, "list_unique", "dups", 7);
    378381        torture_comment(tctx, "test_list_unique_2() with %d elements and %d dups\n", count, num_dups);
    379382
     
    399402static bool test_list_append(struct torture_context *tctx)
    400403{
    401         char **result;
     404        const char **result;
    402405        const char *list[] = {
    403406                "element_0",
     
    421424                NULL
    422425        };
    423         result = str_list_copy(tctx, list);
     426        result = (const char **) str_list_copy(tctx, list);
    424427        torture_assert(tctx, result, "str_list_copy() must not return NULL");
    425428        result = str_list_append(result, list2);
     
    433436static bool test_list_append_const(struct torture_context *tctx)
    434437{
    435         char **result;
     438        const char **result;
    436439        const char *list[] = {
    437440                "element_0",
     
    455458                NULL
    456459        };
    457         result = str_list_copy(tctx, list);
     460        result = (const char **) str_list_copy(tctx, list);
    458461        torture_assert(tctx, result, "str_list_copy() must not return NULL");
    459462        result = str_list_append_const(result, list2);
     
    467470struct torture_suite *torture_local_util_strlist(TALLOC_CTX *mem_ctx)
    468471{
    469         struct torture_suite *suite = torture_suite_create(mem_ctx, "STRLIST");
     472        struct torture_suite *suite = torture_suite_create(mem_ctx, "strlist");
    470473        int i;
    471474
    472475        for (i = 0; i < ARRAY_SIZE(test_lists_shell_strings); i++) {
    473                 torture_suite_add_simple_tcase_const(suite, "lists_shell",
    474                                 test_lists_shell, &test_lists_shell_strings[i]);
     476                char *name;
     477                name = talloc_asprintf(suite, "lists_shell(%s)",
     478                                                           test_lists_shell_strings[i].list_as_string);
     479                torture_suite_add_simple_tcase_const(suite, name,
     480                        test_lists_shell,  &test_lists_shell_strings[i]);
    475481        }
    476482
    477483        for (i = 0; i < ARRAY_SIZE(test_lists_strings); i++) {
    478                 torture_suite_add_simple_tcase_const(suite, "lists",
    479                                                      test_list_make, &test_lists_strings[i]);
     484                char *name;
     485                name = talloc_asprintf(suite, "list_make(%s)",
     486                                                           test_lists_strings[i].list_as_string);
     487                torture_suite_add_simple_tcase_const(suite, name,
     488                        test_list_make, &test_lists_strings[i]);
    480489        }
    481490
  • vendor/current/lib/util/tests/time.c

    r414 r740  
    7878
    7979        result = timestring(tctx, 42 - (utc_offset < 0 ? utc_offset : 0));
    80         torture_assert(tctx, !strncmp(start, result, strlen(start)),
    81                                    result);
     80        torture_assert(tctx, !strncmp(start, result, strlen(start)), result);
    8281        return true;
    8382}
     
    102101struct torture_suite *torture_local_util_time(TALLOC_CTX *mem_ctx)
    103102{
    104         struct torture_suite *suite = torture_suite_create(mem_ctx, "TIME");
     103        struct torture_suite *suite = torture_suite_create(mem_ctx, "time");
    105104
    106105        torture_suite_add_simple_test(suite, "null_time", test_null_time);
  • vendor/current/lib/util/tevent_ntstatus.c

    r414 r740  
    2121#include "tevent_ntstatus.h"
    2222
    23 bool tevent_req_nterror(struct tevent_req *req, NTSTATUS status)
     23#define TEVENT_NTERROR_MAGIC (0x917b5acd)
     24
     25bool _tevent_req_nterror(struct tevent_req *req,
     26                         NTSTATUS status,
     27                         const char *location)
    2428{
    25         return tevent_req_error(req, NT_STATUS_V(status));
     29        uint64_t err;
     30
     31        if (NT_STATUS_IS_OK(status)) {
     32                return false;
     33        }
     34
     35        /*
     36         * I've put this variable here, because I'm not 100% certain
     37         * how to correctly assign a 64-bit constant and left-shift it
     38         * by 32 bits in a single expression. If anyone knows, feel
     39         * free :-)
     40         */
     41        err = TEVENT_NTERROR_MAGIC;
     42        err <<= 32;
     43        err |= NT_STATUS_V(status);
     44
     45        return _tevent_req_error(req, err, location);
    2646}
    2747
     
    4262                break;
    4363        case TEVENT_REQ_USER_ERROR:
    44                 *status = NT_STATUS(err);
     64                if ((err >> 32) != TEVENT_NTERROR_MAGIC) {
     65                        abort();
     66                }
     67                *status = NT_STATUS(err & 0xffffffff);
    4568                break;
    4669        default:
     
    6083        return NT_STATUS_OK;
    6184}
     85
     86void tevent_req_simple_finish_ntstatus(struct tevent_req *subreq,
     87                                       NTSTATUS subreq_status)
     88{
     89        struct tevent_req *req = tevent_req_callback_data(
     90                subreq, struct tevent_req);
     91
     92        TALLOC_FREE(subreq);
     93
     94        if (!NT_STATUS_IS_OK(subreq_status)) {
     95                tevent_req_nterror(req, subreq_status);
     96                return;
     97        }
     98        tevent_req_done(req);
     99}
  • vendor/current/lib/util/tevent_ntstatus.h

    r414 r740  
    2424#include <stdbool.h>
    2525#include "../libcli/util/ntstatus.h"
    26 #include "../tevent/tevent.h"
     26#include <tevent.h>
    2727
    28 bool tevent_req_nterror(struct tevent_req *req, NTSTATUS status);
     28bool _tevent_req_nterror(struct tevent_req *req,
     29                         NTSTATUS status,
     30                         const char *location);
     31#define tevent_req_nterror(req, status) \
     32        _tevent_req_nterror(req, status, __location__)
    2933bool tevent_req_is_nterror(struct tevent_req *req, NTSTATUS *pstatus);
    3034NTSTATUS tevent_req_simple_recv_ntstatus(struct tevent_req *req);
    3135
     36/*
     37 * Helper routine to pass the subreq_ntstatus to the req embedded in
     38 * tevent_req_callback_data(subreq), which will be freed.
     39 */
     40void tevent_req_simple_finish_ntstatus(struct tevent_req *subreq,
     41                                       NTSTATUS subreq_status);
     42
    3243#endif
  • vendor/current/lib/util/tevent_unix.c

    r414 r740  
    2222*/
    2323
     24#include "../replace/replace.h"
    2425#include "tevent_unix.h"
    25 #include "../replace/replace.h"
    2626
    2727bool tevent_req_is_unix_error(struct tevent_req *req, int *perrno)
  • vendor/current/lib/util/tevent_unix.h

    r414 r740  
    2525#define _TEVENT_UNIX_H
    2626
    27 #include "../tevent/tevent.h"
     27#include <tevent.h>
    2828
    2929bool tevent_req_is_unix_error(struct tevent_req *req, int *perrno);
  • vendor/current/lib/util/time.c

    r478 r740  
    55   Copyright (C) Andrew Tridgell                1992-2004
    66   Copyright (C) Stefan (metze) Metzmacher      2002   
     7   Copyright (C) Jeremy Allison                 2007
     8   Copyright (C) Andrew Bartlett                2011
    79
    810   This program is free software; you can redistribute it and/or modify
     
    5658}
    5759
     60/**
     61a wrapper to preferably get the monotonic time
     62**/
     63_PUBLIC_ void clock_gettime_mono(struct timespec *tp)
     64{
     65        if (clock_gettime(CUSTOM_CLOCK_MONOTONIC,tp) != 0) {
     66                clock_gettime(CLOCK_REALTIME,tp);
     67        }
     68}
     69
     70/**
     71a wrapper to preferably get the monotonic time in seconds
     72as this is only second resolution we can use the cached
     73(and much faster) COARSE clock variant
     74**/
     75_PUBLIC_ time_t time_mono(time_t *t)
     76{
     77        struct timespec tp;
     78        int rc = -1;
     79#ifdef CLOCK_MONOTONIC_COARSE
     80        rc = clock_gettime(CLOCK_MONOTONIC_COARSE,&tp);
     81#endif
     82        if (rc != 0) {
     83                clock_gettime_mono(&tp);
     84        }
     85        if (t != NULL) {
     86                *t = tp.tv_sec;
     87        }
     88        return tp.tv_sec;
     89}
     90
    5891
    5992#define TIME_FIXUP_CONSTANT 11644473600LL
     
    6194time_t convert_timespec_to_time_t(struct timespec ts)
    6295{
     96        /* Ensure tv_nsec is less than 1sec. */
     97        while (ts.tv_nsec > 1000000000) {
     98                ts.tv_sec += 1;
     99                ts.tv_nsec -= 1000000000;
     100        }
     101
    63102        /* 1 ns == 1,000,000,000 - one thousand millionths of a second.
    64103           increment if it's greater than 500 millionth of a second. */
     104
    65105        if (ts.tv_nsec > 500000000) {
    66106                return ts.tv_sec + 1;
     
    300340
    301341
     342/****************************************************************************
     343 Return the date and time as a string
     344****************************************************************************/
     345
     346char *timeval_string(TALLOC_CTX *ctx, const struct timeval *tp, bool hires)
     347{
     348        time_t t;
     349        struct tm *tm;
     350
     351        t = (time_t)tp->tv_sec;
     352        tm = localtime(&t);
     353        if (!tm) {
     354                if (hires) {
     355                        return talloc_asprintf(ctx,
     356                                               "%ld.%06ld seconds since the Epoch",
     357                                               (long)tp->tv_sec,
     358                                               (long)tp->tv_usec);
     359                } else {
     360                        return talloc_asprintf(ctx,
     361                                               "%ld seconds since the Epoch",
     362                                               (long)t);
     363                }
     364        } else {
     365#ifdef HAVE_STRFTIME
     366                char TimeBuf[60];
     367                if (hires) {
     368                        strftime(TimeBuf,sizeof(TimeBuf)-1,"%Y/%m/%d %H:%M:%S",tm);
     369                        return talloc_asprintf(ctx,
     370                                               "%s.%06ld", TimeBuf,
     371                                               (long)tp->tv_usec);
     372                } else {
     373                        strftime(TimeBuf,sizeof(TimeBuf)-1,"%Y/%m/%d %H:%M:%S",tm);
     374                        return talloc_strdup(ctx, TimeBuf);
     375                }
     376#else
     377                if (hires) {
     378                        const char *asct = asctime(tm);
     379                        return talloc_asprintf(ctx, "%s.%06ld",
     380                                        asct ? asct : "unknown",
     381                                        (long)tp->tv_usec);
     382                } else {
     383                        const char *asct = asctime(tm);
     384                        return talloc_asprintf(ctx, asct ? asct : "unknown");
     385                }
     386#endif
     387        }
     388}
     389
     390char *current_timestring(TALLOC_CTX *ctx, bool hires)
     391{
     392        struct timeval tv;
     393
     394        GetTimeOfDay(&tv);
     395        return timeval_string(ctx, &tv, hires);
     396}
     397
     398
    302399/**
    303400return a HTTP/1.0 time string
     
    347444
    348445#ifdef HAVE_STRFTIME
    349         /* some versions of gcc complain about using %c. This is a bug
    350            in the gcc warning, not a bug in this code. See a recent
    351            strftime() manual page for details.
    352          */
    353         strftime(tempTime,sizeof(tempTime)-1,"%c %Z",tm);
     446        /* Some versions of gcc complain about using some special format
     447         * specifiers. This is a bug in gcc, not a bug in this code. See a
     448         * recent strftime() manual page for details. */
     449        strftime(tempTime,sizeof(tempTime)-1,"%a %b %e %X %Y %Z",tm);
    354450        TimeBuf = talloc_strdup(mem_ctx, tempTime);
    355451#else
     
    398494        int64_t sec_diff = tv1->tv_sec - tv2->tv_sec;
    399495        return (sec_diff * 1000000) + (int64_t)(tv1->tv_usec - tv2->tv_usec);
     496}
     497
     498/**
     499  return (tp1 - tp2) in microseconds
     500*/
     501_PUBLIC_ int64_t nsec_time_diff(const struct timespec *tp1, const struct timespec *tp2)
     502{
     503        int64_t sec_diff = tp1->tv_sec - tp2->tv_sec;
     504        return (sec_diff * 1000000000) + (int64_t)(tp1->tv_nsec - tp2->tv_nsec);
    400505}
    401506
  • vendor/current/lib/util/time.h

    r478 r740  
    22   Unix SMB/CIFS implementation.
    33   time utility functions
    4    
     4
     5   Copyright (C) Andrew Tridgell                1992-2004
     6   Copyright (C) Stefan (metze) Metzmacher      2002
     7   Copyright (C) Jeremy Allison                 2007
     8   Copyright (C) Andrew Bartlett                2011
     9
    510   This program is free software; you can redistribute it and/or modify
    611   it under the terms of the GNU General Public License as published by
     
    5257
    5358/**
     59a wrapper to preferably get the monotonic time
     60**/
     61_PUBLIC_ void clock_gettime_mono(struct timespec *tp);
     62
     63/**
     64a wrapper to preferably get the monotonic time in s
     65**/
     66_PUBLIC_ time_t time_mono(time_t *t);
     67
     68/**
    5469interpret an 8 byte "filetime" structure to a time_t
    5570It's originally in "100ns units since jan 1st 1601"
     
    110125
    111126/**
     127 Return a date and time as a string (optionally with microseconds)
     128
     129 format is %Y/%m/%d %H:%M:%S if strftime is available
     130**/
     131
     132char *timeval_string(TALLOC_CTX *ctx, const struct timeval *tp, bool hires);
     133
     134/**
     135 Return the current date and time as a string (optionally with microseconds)
     136
     137 format is %Y/%m/%d %H:%M:%S if strftime is available
     138**/
     139char *current_timestring(TALLOC_CTX *ctx, bool hires);
     140
     141/**
    112142return a HTTP/1.0 time string
    113143**/
     
    116146/**
    117147 Return the date and time as a string
     148
     149 format is %a %b %e %X %Y %Z
    118150**/
    119151_PUBLIC_ char *timestring(TALLOC_CTX *mem_ctx, time_t t);
     
    143175*/
    144176_PUBLIC_ int64_t usec_time_diff(const struct timeval *tv1, const struct timeval *tv2);
     177
     178/**
     179  return (tp1 - tp2) in nanoseconds
     180*/
     181_PUBLIC_ int64_t nsec_time_diff(const struct timespec *tp1, const struct timespec *tp2);
    145182
    146183/**
  • vendor/current/lib/util/unix_privs.c

    r414 r740  
    2121
    2222#include "includes.h"
    23 #include "system/filesys.h"
     23#include "system/passwd.h"
    2424#include "../lib/util/unix_privs.h"
     25
     26#if defined(UID_WRAPPER)
     27#if !defined(UID_WRAPPER_REPLACE) && !defined(UID_WRAPPER_NOT_REPLACE)
     28#define UID_WRAPPER_REPLACE
     29#include "../uid_wrapper/uid_wrapper.h"
     30#endif
     31#else
     32#define uwrap_enabled() 0
     33#endif
    2534
    2635/**
     
    7786        return s;
    7887}
     88
     89uid_t root_privileges_original_uid(void *s)
     90{
     91        struct saved_state *saved = talloc_get_type_abort(s, struct saved_state);
     92        return saved->uid;
     93}
  • vendor/current/lib/util/util.c

    r414 r740  
    2626#include "system/filesys.h"
    2727#include "system/locale.h"
     28#include "system/shmem.h"
     29
    2830#undef malloc
    2931#undef strcasecmp
     
    3133#undef strdup
    3234#undef realloc
     35
     36#if defined(UID_WRAPPER)
     37#if !defined(UID_WRAPPER_REPLACE) && !defined(UID_WRAPPER_NOT_REPLACE)
     38#define UID_WRAPPER_REPLACE
     39#include "../uid_wrapper/uid_wrapper.h"
     40#endif
     41#else
     42#define uwrap_enabled() 0
     43#endif
    3344
    3445/**
     
    155166**/
    156167
    157 _PUBLIC_ void msleep(unsigned int t)
    158 {
    159         struct timeval tval; 
    160 
    161         tval.tv_sec = t/1000;
    162         tval.tv_usec = 1000*(t%1000);
    163         /* this should be the real select - do NOT replace
    164            with sys_select() */
    165         select(0,NULL,NULL,NULL,&tval);
     168_PUBLIC_ void smb_msleep(unsigned int t)
     169{
     170#if defined(HAVE_NANOSLEEP)
     171        struct timespec ts;
     172        int ret;
     173
     174        ts.tv_sec = t/1000;
     175        ts.tv_nsec = 1000000*(t%1000);
     176
     177        do {
     178                errno = 0;
     179                ret = nanosleep(&ts, &ts);
     180        } while (ret < 0 && errno == EINTR && (ts.tv_sec > 0 || ts.tv_nsec > 0));
     181#else
     182        unsigned int tdiff=0;
     183        struct timeval tval,t1,t2;
     184        fd_set fds;
     185
     186        GetTimeOfDay(&t1);
     187        t2 = t1;
     188
     189        while (tdiff < t) {
     190                tval.tv_sec = (t-tdiff)/1000;
     191                tval.tv_usec = 1000*((t-tdiff)%1000);
     192
     193                /* Never wait for more than 1 sec. */
     194                if (tval.tv_sec > 1) {
     195                        tval.tv_sec = 1;
     196                        tval.tv_usec = 0;
     197                }
     198
     199                FD_ZERO(&fds);
     200                errno = 0;
     201                select(0,&fds,NULL,NULL,&tval);
     202
     203                GetTimeOfDay(&t2);
     204                if (t2.tv_sec < t1.tv_sec) {
     205                        /* Someone adjusted time... */
     206                        t1 = t2;
     207                }
     208
     209                tdiff = usec_time_diff(&t2,&t1)/1000;
     210        }
     211#endif
    166212}
    167213
     
    255301}
    256302
     303static void debugadd_cb(const char *buf, void *private_data)
     304{
     305        int *plevel = (int *)private_data;
     306        DEBUGADD(*plevel, ("%s", buf));
     307}
     308
     309void print_asc_cb(const uint8_t *buf, int len,
     310                  void (*cb)(const char *buf, void *private_data),
     311                  void *private_data)
     312{
     313        int i;
     314        char s[2];
     315        s[1] = 0;
     316
     317        for (i=0; i<len; i++) {
     318                s[0] = isprint(buf[i]) ? buf[i] : '.';
     319                cb(s, private_data);
     320        }
     321}
     322
    257323void print_asc(int level, const uint8_t *buf,int len)
    258324{
    259         int i;
    260         for (i=0;i<len;i++)
    261                 DEBUGADD(level,("%c", isprint(buf[i])?buf[i]:'.'));
    262 }
    263 
    264 /**
    265  * Write dump of binary data to the log file.
    266  *
    267  * The data is only written if the log level is at least level.
     325        print_asc_cb(buf, len, debugadd_cb, &level);
     326}
     327
     328/**
     329 * Write dump of binary data to a callback
    268330 */
    269 static void _dump_data(int level, const uint8_t *buf, int len,
    270                        bool omit_zero_bytes)
     331void dump_data_cb(const uint8_t *buf, int len,
     332                  bool omit_zero_bytes,
     333                  void (*cb)(const char *buf, void *private_data),
     334                  void *private_data)
    271335{
    272336        int i=0;
    273337        static const uint8_t empty[16] = { 0, };
    274338        bool skipped = false;
     339        char tmp[16];
    275340
    276341        if (len<=0) return;
    277 
    278         if (!DEBUGLVL(level)) return;
    279342
    280343        for (i=0;i<len;) {
     
    291354
    292355                        if (i<len)  {
    293                                 DEBUGADD(level,("[%04X] ",i));
     356                                snprintf(tmp, sizeof(tmp), "[%04X] ", i);
     357                                cb(tmp, private_data);
    294358                        }
    295359                }
    296360
    297                 DEBUGADD(level,("%02X ",(int)buf[i]));
     361                snprintf(tmp, sizeof(tmp), "%02X ", (int)buf[i]);
     362                cb(tmp, private_data);
    298363                i++;
    299                 if (i%8 == 0) DEBUGADD(level,("  "));
     364                if (i%8 == 0) {
     365                        cb("  ", private_data);
     366                }
    300367                if (i%16 == 0) {
    301368
    302                         print_asc(level,&buf[i-16],8); DEBUGADD(level,(" "));
    303                         print_asc(level,&buf[i-8],8); DEBUGADD(level,("\n"));
     369                        print_asc_cb(&buf[i-16], 8, cb, private_data);
     370                        cb(" ", private_data);
     371                        print_asc_cb(&buf[i-8], 8, cb, private_data);
     372                        cb("\n", private_data);
    304373
    305374                        if ((omit_zero_bytes == true) &&
     
    307376                            (memcmp(&buf[i], &empty, 16) == 0)) {
    308377                                if (!skipped) {
    309                                         DEBUGADD(level,("skipping zero buffer bytes\n"));
     378                                        cb("skipping zero buffer bytes\n",
     379                                           private_data);
    310380                                        skipped = true;
    311381                                }
     
    317387                int n;
    318388                n = 16 - (i%16);
    319                 DEBUGADD(level,(" "));
    320                 if (n>8) DEBUGADD(level,(" "));
    321                 while (n--) DEBUGADD(level,("   "));
     389                cb(" ", private_data);
     390                if (n>8) {
     391                        cb(" ", private_data);
     392                }
     393                while (n--) {
     394                        cb("   ", private_data);
     395                }
    322396                n = MIN(8,i%16);
    323                 print_asc(level,&buf[i-(i%16)],n); DEBUGADD(level,( " " ));
     397                print_asc_cb(&buf[i-(i%16)], n, cb, private_data);
     398                cb(" ", private_data);
    324399                n = (i%16) - n;
    325                 if (n>0) print_asc(level,&buf[i-n],n);
    326                 DEBUGADD(level,("\n"));
     400                if (n>0) {
     401                        print_asc_cb(&buf[i-n], n, cb, private_data);
     402                }
     403                cb("\n", private_data);
    327404        }
    328405
     
    336413_PUBLIC_ void dump_data(int level, const uint8_t *buf, int len)
    337414{
    338         _dump_data(level, buf, len, false);
     415        if (!DEBUGLVL(level)) {
     416                return;
     417        }
     418        dump_data_cb(buf, len, false, debugadd_cb, &level);
    339419}
    340420
     
    343423 *
    344424 * The data is only written if the log level is at least level.
    345  * 16 zero bytes in a row are ommited
     425 * 16 zero bytes in a row are omitted
    346426 */
    347427_PUBLIC_ void dump_data_skip_zeros(int level, const uint8_t *buf, int len)
    348428{
    349         _dump_data(level, buf, len, true);
     429        if (!DEBUGLVL(level)) {
     430                return;
     431        }
     432        dump_data_cb(buf, len, true, debugadd_cb, &level);
    350433}
    351434
     
    580663_PUBLIC_ size_t strhex_to_str(char *p, size_t p_len, const char *strhex, size_t strhex_len)
    581664{
    582         size_t i;
     665        size_t i = 0;
    583666        size_t num_chars = 0;
    584667        uint8_t   lonybble, hinybble;
     
    586669        char           *p1 = NULL, *p2 = NULL;
    587670
    588         for (i = 0; i < strhex_len && strhex[i] != 0; i++) {
    589                 if (strncasecmp(hexchars, "0x", 2) == 0) {
    590                         i++; /* skip two chars */
    591                         continue;
    592                 }
    593 
     671        /* skip leading 0x prefix */
     672        if (strncasecmp(strhex, "0x", 2) == 0) {
     673                i += 2; /* skip two chars */
     674        }
     675
     676        for (; i < strhex_len && strhex[i] != 0; i++) {
    594677                if (!(p1 = strchr(hexchars, toupper((unsigned char)strhex[i]))))
    595678                        break;
     
    765848                                bool ltrim)
    766849{
    767         char *s;
    768         char *saved_s;
     850        const char *s;
     851        const char *saved_s;
    769852        char *pbuf;
    770853        bool quoted;
     
    776859        }
    777860
    778         s = (char *)*ptr;
     861        s = *ptr;
    779862
    780863        /* default to simple separators */
     
    854937}
    855938
    856 
     939/**
     940 * Get the next token from a string, return False if none found.
     941 * Handles double-quotes.
     942 *
     943 * Based on a routine by GJC@VILLAGE.COM.
     944 * Extensively modified by Andrew.Tridgell@anu.edu.au
     945 **/
     946_PUBLIC_ bool next_token(const char **ptr,char *buff, const char *sep, size_t bufsize)
     947{
     948        const char *s;
     949        bool quoted;
     950        size_t len=1;
     951
     952        if (!ptr)
     953                return false;
     954
     955        s = *ptr;
     956
     957        /* default to simple separators */
     958        if (!sep)
     959                sep = " \t\n\r";
     960
     961        /* find the first non sep char */
     962        while (*s && strchr_m(sep,*s))
     963                s++;
     964
     965        /* nothing left? */
     966        if (!*s)
     967                return false;
     968
     969        /* copy over the token */
     970        for (quoted = false; len < bufsize && *s && (quoted || !strchr_m(sep,*s)); s++) {
     971                if (*s == '\"') {
     972                        quoted = !quoted;
     973                } else {
     974                        len++;
     975                        *buff++ = *s;
     976                }
     977        }
     978
     979        *ptr = (*s) ? s+1 : s;
     980        *buff = 0;
     981
     982        return true;
     983}
     984
     985struct anonymous_shared_header {
     986        union {
     987                size_t length;
     988                uint8_t pad[16];
     989        } u;
     990};
     991
     992/* Map a shared memory buffer of at least nelem counters. */
     993void *anonymous_shared_allocate(size_t orig_bufsz)
     994{
     995        void *ptr;
     996        void *buf;
     997        size_t pagesz = getpagesize();
     998        size_t pagecnt;
     999        size_t bufsz = orig_bufsz;
     1000        struct anonymous_shared_header *hdr;
     1001
     1002        bufsz += sizeof(*hdr);
     1003
     1004        /* round up to full pages */
     1005        pagecnt = bufsz / pagesz;
     1006        if (bufsz % pagesz) {
     1007                pagecnt += 1;
     1008        }
     1009        bufsz = pagesz * pagecnt;
     1010
     1011        if (orig_bufsz >= bufsz) {
     1012                /* integer wrap */
     1013                errno = ENOMEM;
     1014                return NULL;
     1015        }
     1016
     1017#ifdef MAP_ANON
     1018        /* BSD */
     1019        buf = mmap(NULL, bufsz, PROT_READ|PROT_WRITE, MAP_ANON|MAP_SHARED,
     1020                        -1 /* fd */, 0 /* offset */);
     1021#else
     1022        buf = mmap(NULL, bufsz, PROT_READ|PROT_WRITE, MAP_FILE|MAP_SHARED,
     1023                        open("/dev/zero", O_RDWR), 0 /* offset */);
     1024#endif
     1025
     1026        if (buf == MAP_FAILED) {
     1027                return NULL;
     1028        }
     1029
     1030        hdr = (struct anonymous_shared_header *)buf;
     1031        hdr->u.length = bufsz;
     1032
     1033        ptr = (void *)(&hdr[1]);
     1034
     1035        return ptr;
     1036}
     1037
     1038void anonymous_shared_free(void *ptr)
     1039{
     1040        struct anonymous_shared_header *hdr;
     1041
     1042        if (ptr == NULL) {
     1043                return;
     1044        }
     1045
     1046        hdr = (struct anonymous_shared_header *)ptr;
     1047
     1048        hdr--;
     1049
     1050        munmap(hdr, hdr->u.length);
     1051}
     1052
     1053#ifdef DEVELOPER
     1054/* used when you want a debugger started at a particular point in the
     1055   code. Mostly useful in code that runs as a child process, where
     1056   normal gdb attach is harder to organise.
     1057*/
     1058void samba_start_debugger(void)
     1059{
     1060        char *cmd = NULL;
     1061        if (asprintf(&cmd, "xterm -e \"gdb --pid %u\"&", getpid()) == -1) {
     1062                return;
     1063        }
     1064        if (system(cmd) == -1) {
     1065                free(cmd);
     1066                return;
     1067        }
     1068        free(cmd);
     1069        sleep(2);
     1070}
     1071#endif
  • vendor/current/lib/util/util.h

    r414 r740  
    2222#define _SAMBA_UTIL_H_
    2323
    24 #if _SAMBA_BUILD_ == 4
    25 #include "../lib/util/charset/charset.h"
    26 #endif
    27 #include "../lib/util/attr.h"
     24#include "lib/util/charset/charset.h"
     25#include "lib/util/attr.h"
    2826
    2927/* for TALLOC_CTX */
     
    4038extern const char *panic_action;
    4139
    42 #include "../lib/util/time.h"
    43 #include "../lib/util/data_blob.h"
    44 #include "../lib/util/xfile.h"
    45 #include "../lib/util/mutex.h"
    46 #include "../lib/util/byteorder.h"
    47 #include "../lib/util/talloc_stack.h"
     40#include "lib/util/time.h"
     41#include "lib/util/data_blob.h"
     42#include "lib/util/xfile.h"
     43#include "lib/util/byteorder.h"
     44#include "lib/util/talloc_stack.h"
    4845
    4946/**
     
    6158#endif
    6259
    63 #if _SAMBA_BUILD_ == 4
    64 #ifdef VALGRIND
    65 #define strlen(x) valgrind_strlen(x)
    66 size_t valgrind_strlen(const char *s);
    67 #endif
    68 #endif
    69 
    7060#ifndef ABS
    7161#define ABS(a) ((a)>0?(a):(-(a)))
    7262#endif
    7363
    74 #include "../lib/util/memory.h"
     64#include "lib/util/memory.h"
    7565
    7666/**
     
    8979**/
    9080_PUBLIC_ void fault_setup(const char *pname);
     81_PUBLIC_ void fault_setup_disable(void);
    9182#endif
    9283
     
    143134_PUBLIC_ pid_t sys_getpid(void);
    144135
     136_PUBLIC_ int sys_getpeereid( int s, uid_t *uid);
     137
     138struct sockaddr;
     139
     140_PUBLIC_ int sys_getnameinfo(const struct sockaddr *psa,
     141                             int salen,
     142                             char *host,
     143                             size_t hostlen,
     144                             char *service,
     145                             size_t servlen,
     146                             int flags);
     147_PUBLIC_ int sys_connect(int fd, const struct sockaddr * addr);
     148
    145149/* The following definitions come from lib/util/genrand.c  */
    146 
    147150/**
    148151 Copy any user given reseed data.
     
    177180**/
    178181_PUBLIC_ bool check_password_quality(const char *s);
     182
     183/**
     184 * Generate a random text password.
     185 */
     186_PUBLIC_ char *generate_random_password(TALLOC_CTX *mem_ctx, size_t min, size_t max);
    179187
    180188/**
     
    451459/**
    452460 * build a null terminated list of strings from an argv-like input string
    453  * Entries are seperated by spaces and can be enclosed by quotes.
     461 * Entries are separated by spaces and can be enclosed by quotes.
    454462 * Does NOT support escaping
    455463 */
     
    459467 * join a list back to one string
    460468 */
    461 _PUBLIC_ char *str_list_join(TALLOC_CTX *mem_ctx, const char **list, char seperator);
     469_PUBLIC_ char *str_list_join(TALLOC_CTX *mem_ctx, const char **list, char separator);
    462470
    463471/** join a list back to one (shell-like) string; entries
    464  * seperated by spaces, using quotes where necessary */
     472 * separated by spaces, using quotes where necessary */
    465473_PUBLIC_ char *str_list_join_shell(TALLOC_CTX *mem_ctx, const char **list, char sep);
    466474
     
    478486   Return true if all the elements of the list match exactly.
    479487 */
    480 _PUBLIC_ bool str_list_equal(const char **list1, const char **list2);
     488_PUBLIC_ bool str_list_equal(const char * const *list1, const char * const *list2);
    481489
    482490/**
     
    535543_PUBLIC_ const char **str_list_copy_const(TALLOC_CTX *mem_ctx,
    536544                                          const char **list);
     545
     546/**
     547 * Needed for making an "unconst" list "const"
     548 */
     549_PUBLIC_ const char **const_str_list(char **list);
    537550
    538551
     
    597610_PUBLIC_ bool large_file_support(const char *path);
    598611
     612/*
     613  compare two files, return true if the two files have the same content
     614 */
     615bool file_compare(const char *path1, const char *path2);
     616
    599617/* The following definitions come from lib/util/util.c  */
    600618
     
    641659 Sleep for a specified number of milliseconds.
    642660**/
    643 _PUBLIC_ void msleep(unsigned int t);
     661_PUBLIC_ void smb_msleep(unsigned int t);
    644662
    645663/**
     
    647665**/
    648666_PUBLIC_ char* get_myname(TALLOC_CTX *mem_ctx);
    649 
    650 /**
    651  Return true if a string could be a pure IP address.
    652 **/
    653 _PUBLIC_ bool is_ipaddress(const char *str);
    654 
    655 /**
    656  Interpret an internet address or name into an IP address in 4 byte form.
    657 **/
    658 _PUBLIC_ uint32_t interpret_addr(const char *str);
    659 
    660 /**
    661  A convenient addition to interpret_addr().
    662 **/
    663 _PUBLIC_ struct in_addr interpret_addr2(const char *str);
    664 
    665 /**
    666  Check if an IP is the 0.0.0.0.
    667 **/
    668 _PUBLIC_ bool is_zero_ip_v4(struct in_addr ip);
    669 
    670 /**
    671  Are two IPs on the same subnet?
    672 **/
    673 _PUBLIC_ bool same_net_v4(struct in_addr ip1,struct in_addr ip2,struct in_addr mask);
    674 
    675 _PUBLIC_ bool is_ipaddress_v4(const char *str);
    676667
    677668/**
     
    687678
    688679/**
     680 * Write dump of binary data to a callback
     681 */
     682void dump_data_cb(const uint8_t *buf, int len,
     683                  bool omit_zero_bytes,
     684                  void (*cb)(const char *buf, void *private_data),
     685                  void *private_data);
     686
     687/**
    689688 * Write dump of binary data to the log file.
    690689 *
     
    697696 *
    698697 * The data is only written if the log level is at least level.
    699  * 16 zero bytes in a row are ommited
     698 * 16 zero bytes in a row are omitted
    700699 */
    701700_PUBLIC_ void dump_data_skip_zeros(int level, const uint8_t *buf, int len);
     
    784783#endif
    785784
    786 /* The following definitions come from lib/util/mutex.c  */
    787 
    788 
    789 /**
    790   register a set of mutex/rwlock handlers.
    791   Should only be called once in the execution of smbd.
    792 */
    793 _PUBLIC_ bool register_mutex_handlers(const char *name, struct mutex_ops *ops);
    794 
    795785/* The following definitions come from lib/util/idtree.c  */
    796786
     
    840830 Become a daemon, discarding the controlling terminal.
    841831**/
    842 _PUBLIC_ void become_daemon(bool do_fork, bool no_process_group);
     832_PUBLIC_ void become_daemon(bool do_fork, bool no_process_group, bool log_stdout);
    843833
    844834/**
     
    853843
    854844void print_asc(int level, const uint8_t *buf,int len);
     845void print_asc_cb(const uint8_t *buf, int len,
     846                  void (*cb)(const char *buf, void *private_data),
     847                  void *private_data);
    855848
    856849/**
     
    862855
    863856bool add_uid_to_array_unique(TALLOC_CTX *mem_ctx, uid_t uid,
    864                              uid_t **uids, size_t *num_uids);
     857                             uid_t **uids, uint32_t *num_uids);
    865858bool add_gid_to_array_unique(TALLOC_CTX *mem_ctx, gid_t gid,
    866                              gid_t **gids, size_t *num_gids);
    867 
     859                             gid_t **gids, uint32_t *num_gids);
     860
     861/**
     862 * Allocate anonymous shared memory of the given size
     863 */
     864void *anonymous_shared_allocate(size_t bufsz);
     865void anonymous_shared_free(void *ptr);
     866
     867/*
     868  run a command as a child process, with a timeout.
     869
     870  any stdout/stderr from the child will appear in the Samba logs with
     871  the specified log levels
     872
     873  If callback is set then the callback is called on completion
     874  with the return code from the command
     875 */
     876struct tevent_context;
     877struct tevent_req;
     878struct tevent_req *samba_runcmd_send(TALLOC_CTX *mem_ctx,
     879                                     struct tevent_context *ev,
     880                                     struct timeval endtime,
     881                                     int stdout_log_level,
     882                                     int stderr_log_level,
     883                                     const char * const *argv0, ...);
     884int samba_runcmd_recv(struct tevent_req *req, int *perrno);
     885
     886#ifdef DEVELOPER
     887void samba_start_debugger(void);
     888#endif
    868889
    869890#endif /* _SAMBA_UTIL_H_ */
  • vendor/current/lib/util/util_file.c

    r414 r740  
    236236#endif
    237237        if (!p) {
    238                 p = file_load(fname, &s2, 0, talloc_autofree_context());
     238                p = file_load(fname, &s2, 0, NULL);
    239239                if (!p) return NULL;
    240240                if (s2 != size) {
     
    436436
    437437
     438/*
     439  compare two files, return true if the two files have the same content
     440 */
     441bool file_compare(const char *path1, const char *path2)
     442{
     443        size_t size1, size2;
     444        char *p1, *p2;
     445        TALLOC_CTX *mem_ctx = talloc_new(NULL);
     446
     447        p1 = file_load(path1, &size1, 0, mem_ctx);
     448        p2 = file_load(path2, &size2, 0, mem_ctx);
     449        if (!p1 || !p2 || size1 != size2) {
     450                talloc_free(mem_ctx);
     451                return false;
     452        }
     453        if (memcmp(p1, p2, size1) != 0) {
     454                talloc_free(mem_ctx);
     455                return false;
     456        }
     457        talloc_free(mem_ctx);
     458        return true;
     459}
  • vendor/current/lib/util/util_id.c

    r414 r740  
    2727
    2828bool add_gid_to_array_unique(TALLOC_CTX *mem_ctx, gid_t gid,
    29                              gid_t **gids, size_t *num_gids)
     29                             gid_t **gids, uint32_t *num_gids)
    3030{
    3131        int i;
     
    6060
    6161bool add_uid_to_array_unique(TALLOC_CTX *mem_ctx, uid_t uid,
    62                              uid_t **uids, size_t *num_uids)
     62                             uid_t **uids, uint32_t *num_uids)
    6363{
    6464        int i;
  • vendor/current/lib/util/util_ldb.c

    r414 r740  
    2222
    2323#include "includes.h"
    24 #include "lib/ldb/include/ldb.h"
     24#include <ldb.h>
    2525#include "../lib/util/util_ldb.h"
     26
    2627/*
    27   search the sam for the specified attributes - va_list variant
    28 */
     28 * search the LDB for the specified attributes - va_list variant
     29 */
    2930int gendb_search_v(struct ldb_context *ldb,
    3031                   TALLOC_CTX *mem_ctx,
     
    3334                   const char * const *attrs,
    3435                   const char *format,
    35                    va_list ap) 
     36                   va_list ap)
    3637{
    3738        enum ldb_scope scope = LDB_SCOPE_SUBTREE;
     
    5556
    5657        if (ret == LDB_SUCCESS) {
    57                 talloc_steal(mem_ctx, res->msgs);
    58 
    5958                DEBUG(6,("gendb_search_v: %s %s -> %d\n",
    6059                         basedn?ldb_dn_get_linearized(basedn):"NULL",
     
    6261
    6362                ret = res->count;
    64                 *msgs = res->msgs;
     63                if (msgs != NULL) {
     64                        *msgs = talloc_steal(mem_ctx, res->msgs);
     65                }
    6566                talloc_free(res);
    6667        } else if (scope == LDB_SCOPE_BASE && ret == LDB_ERR_NO_SUCH_OBJECT) {
    6768                ret = 0;
    68                 *msgs = NULL;
     69                if (msgs != NULL) *msgs = NULL;
    6970        } else {
    7071                DEBUG(4,("gendb_search_v: search failed: %s\n",
    7172                                        ldb_errstring(ldb)));
    7273                ret = -1;
     74                if (msgs != NULL) *msgs = NULL;
    7375        }
    7476
     
    7981
    8082/*
    81   search the LDB for the specified attributes - varargs variant
    82 */
     83 * search the LDB for the specified attributes - varargs variant
     84 */
    8385int gendb_search(struct ldb_context *ldb,
    8486                 TALLOC_CTX *mem_ctx,
     
    8688                 struct ldb_message ***res,
    8789                 const char * const *attrs,
    88                  const char *format, ...) 
     90                 const char *format, ...)
    8991{
    9092        va_list ap;
     
    99101
    100102/*
    101   search the LDB for a specified record (by DN)
    102 */
    103 
     103 * search the LDB for a specified record (by DN)
     104 */
    104105int gendb_search_dn(struct ldb_context *ldb,
    105106                 TALLOC_CTX *mem_ctx,
     
    111112}
    112113
    113 /*
    114   setup some initial ldif in a ldb
    115 */
    116 int gendb_add_ldif(struct ldb_context *ldb, const char *ldif_string)
    117 {
    118         struct ldb_ldif *ldif;
    119         int ret;
    120         ldif = ldb_ldif_read_string(ldb, &ldif_string);
    121         if (ldif == NULL) return -1;
    122         ret = ldb_add(ldb, ldif->msg);
    123         talloc_free(ldif);
    124         return ret;
    125 }
    126 
    127 char *wrap_casefold(void *context, void *mem_ctx, const char *s, size_t n)
    128 {
    129         return strupper_talloc_n(mem_ctx, s, n);
    130 }
    131 
    132 
    133 
    134 /*
    135   search the LDB for a single record, with the extended_dn control
    136   return LDB_SUCCESS on success, or an ldb error code on error
    137 
    138   if the search returns 0 entries, return LDB_ERR_NO_SUCH_OBJECT
    139   if the search returns more than 1 entry, return LDB_ERR_CONSTRAINT_VIOLATION
    140 */
    141 int gendb_search_single_extended_dn(struct ldb_context *ldb,
    142                                     TALLOC_CTX *mem_ctx,
    143                                     struct ldb_dn *basedn,
    144                                     enum ldb_scope scope,
    145                                     struct ldb_message **msg,
    146                                     const char * const *attrs,
    147                                     const char *format, ...)
    148 {
    149         va_list ap;
    150         int ret;
    151         struct ldb_request *req;
    152         char *filter;
    153         TALLOC_CTX *tmp_ctx;
    154         struct ldb_result *res;
    155         struct ldb_extended_dn_control *ctrl;
    156 
    157         tmp_ctx = talloc_new(mem_ctx);
    158 
    159         res = talloc_zero(tmp_ctx, struct ldb_result);
    160         if (!res) {
    161                 return LDB_ERR_OPERATIONS_ERROR;
    162         }
    163 
    164         va_start(ap, format);
    165         filter = talloc_vasprintf(tmp_ctx, format, ap);
    166         va_end(ap);
    167 
    168         if (filter == NULL) {
    169                 talloc_free(tmp_ctx);
    170                 return LDB_ERR_OPERATIONS_ERROR;
    171         }
    172 
    173         ret = ldb_build_search_req(&req, ldb, tmp_ctx,
    174                                    basedn,
    175                                    scope,
    176                                    filter,
    177                                    attrs,
    178                                    NULL,
    179                                    res,
    180                                    ldb_search_default_callback,
    181                                    NULL);
    182         if (ret != LDB_SUCCESS) {
    183                 talloc_free(tmp_ctx);
    184                 return ret;
    185         }
    186 
    187         ctrl = talloc(tmp_ctx, struct ldb_extended_dn_control);
    188         if (ctrl == NULL) {
    189                 talloc_free(tmp_ctx);
    190                 return LDB_ERR_OPERATIONS_ERROR;               
    191         }
    192 
    193         ctrl->type = 1;
    194 
    195         ret = ldb_request_add_control(req, LDB_CONTROL_EXTENDED_DN_OID, true, ctrl);
    196         if (ret != LDB_SUCCESS) {
    197                 return ret;
    198         }
    199 
    200         ret = ldb_request(ldb, req);
    201         if (ret == LDB_SUCCESS) {
    202                 ret = ldb_wait(req->handle, LDB_WAIT_ALL);
    203         }
    204 
    205         if (ret != LDB_SUCCESS) {
    206                 talloc_free(tmp_ctx);
    207                 return ret;
    208         }
    209 
    210         if (res->count == 0) {
    211                 talloc_free(tmp_ctx);
    212                 return LDB_ERR_NO_SUCH_OBJECT;
    213         }
    214 
    215         if (res->count > 1) {
    216                 /* the function is only supposed to return a single entry */
    217                 DEBUG(0,(__location__ ": More than one return for baseDN %s  filter %s\n",
    218                          ldb_dn_get_linearized(basedn), filter));
    219                 talloc_free(tmp_ctx);
    220                 return LDB_ERR_CONSTRAINT_VIOLATION;
    221         }
    222 
    223         *msg = talloc_steal(mem_ctx, res->msgs[0]);
    224 
    225         talloc_free(tmp_ctx);
    226 
    227         return LDB_SUCCESS;
    228 }
  • vendor/current/lib/util/util_ldb.h

    r414 r740  
     1/*
     2   Unix SMB/CIFS implementation.
     3
     4   common share info functions
     5
     6   Copyright (C) Andrew Tridgell 2004
     7   Copyright (C) Tim Potter 2004
     8
     9   This program is free software; you can redistribute it and/or modify
     10   it under the terms of the GNU General Public License as published by
     11   the Free Software Foundation; either version 3 of the License, or
     12   (at your option) any later version.
     13
     14   This program is distributed in the hope that it will be useful,
     15   but WITHOUT ANY WARRANTY; without even the implied warranty of
     16   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     17   GNU General Public License for more details.
     18
     19   You should have received a copy of the GNU General Public License
     20   along with this program.  If not, see <http://www.gnu.org/licenses/>.
     21*/
     22
     23
    124#ifndef __LIB_UTIL_UTIL_LDB_H__
    225#define __LIB_UTIL_UTIL_LDB_H__
     
    2447                 struct ldb_message ***res,
    2548                 const char * const *attrs);
    26 int gendb_add_ldif(struct ldb_context *ldb, const char *ldif_string);
    27 char *wrap_casefold(void *context, void *mem_ctx, const char *s, size_t n);
    28 
    29 int gendb_search_single_extended_dn(struct ldb_context *ldb,
    30                                     TALLOC_CTX *mem_ctx,
    31                                     struct ldb_dn *basedn,
    32                                     enum ldb_scope scope,
    33                                     struct ldb_message **msg,
    34                                     const char * const *attrs,
    35                                     const char *format, ...)  PRINTF_ATTRIBUTE(7,8);
    3649
    3750#endif /* __LIB_UTIL_UTIL_LDB_H__ */
  • vendor/current/lib/util/util_net.c

    r414 r740  
    2828#include "system/locale.h"
    2929#include "system/filesys.h"
     30#include "lib/util/util_net.h"
    3031#undef strcasecmp
    3132
     
    3637void zero_sockaddr(struct sockaddr_storage *pss)
    3738{
    38         memset(pss, '\0', sizeof(*pss));
     39        ZERO_STRUCTP(pss);
    3940        /* Ensure we're at least a valid sockaddr-storage. */
    4041        pss->ss_family = AF_INET;
     
    5051        struct addrinfo hints;
    5152
    52         memset(&hints, '\0', sizeof(hints));
     53        ZERO_STRUCT(hints);
     54
    5355        /* By default make sure it supports TCP. */
    5456        hints.ai_socktype = SOCK_STREAM;
    5557        hints.ai_flags = flags;
    5658
    57         /* Linux man page on getaddinfo() says port will be
    58            uninitialized when service string in NULL */
     59        /* Linux man page on getaddrinfo() says port will be
     60           uninitialized when service string is NULL */
    5961
    6062        ret = getaddrinfo(str, NULL,
     
    383385 * Check if a struct sockaddr has an unspecified address.
    384386 */
    385 bool is_zero_addr(const struct sockaddr *pss)
    386 {
    387 #if defined(HAVE_IPV6)
    388         if (pss->sa_family == AF_INET6) {
     387bool is_zero_addr(const struct sockaddr_storage *pss)
     388{
     389#if defined(HAVE_IPV6)
     390        if (pss->ss_family == AF_INET6) {
    389391                const struct in6_addr *pin6 =
    390392                        &((const struct sockaddr_in6 *)pss)->sin6_addr;
     
    392394        }
    393395#endif
    394         if (pss->sa_family == AF_INET) {
     396        if (pss->ss_family == AF_INET) {
    395397                const struct in_addr *pin = &((const struct sockaddr_in *)pss)->sin_addr;
    396398                return is_zero_ip_v4(*pin);
     
    539541
    540542
     543/****************************************************************************
     544 Get a port number in host byte order from a sockaddr_storage.
     545****************************************************************************/
     546
     547uint16_t get_sockaddr_port(const struct sockaddr_storage *pss)
     548{
     549        uint16_t port = 0;
     550
     551        if (pss->ss_family != AF_INET) {
     552#if defined(HAVE_IPV6)
     553                /* IPv6 */
     554                const struct sockaddr_in6 *sa6 =
     555                        (const struct sockaddr_in6 *)pss;
     556                port = ntohs(sa6->sin6_port);
     557#endif
     558        } else {
     559                const struct sockaddr_in *sa =
     560                        (const struct sockaddr_in *)pss;
     561                port = ntohs(sa->sin_port);
     562        }
     563        return port;
     564}
     565
     566/****************************************************************************
     567 Print out an IPv4 or IPv6 address from a struct sockaddr_storage.
     568****************************************************************************/
     569
     570char *print_sockaddr_len(char *dest,
     571                         size_t destlen,
     572                        const struct sockaddr *psa,
     573                        socklen_t psalen)
     574{
     575        if (destlen > 0) {
     576                dest[0] = '\0';
     577        }
     578        (void)sys_getnameinfo(psa,
     579                        psalen,
     580                        dest, destlen,
     581                        NULL, 0,
     582                        NI_NUMERICHOST);
     583        return dest;
     584}
     585
     586/****************************************************************************
     587 Print out an IPv4 or IPv6 address from a struct sockaddr_storage.
     588****************************************************************************/
     589
     590char *print_sockaddr(char *dest,
     591                        size_t destlen,
     592                        const struct sockaddr_storage *psa)
     593{
     594        return print_sockaddr_len(dest, destlen, (struct sockaddr *)psa,
     595                        sizeof(struct sockaddr_storage));
     596}
     597
     598/****************************************************************************
     599 Print out a canonical IPv4 or IPv6 address from a struct sockaddr_storage.
     600****************************************************************************/
     601
     602char *print_canonical_sockaddr(TALLOC_CTX *ctx,
     603                        const struct sockaddr_storage *pss)
     604{
     605        char addr[INET6_ADDRSTRLEN];
     606        char *dest = NULL;
     607        int ret;
     608
     609        /* Linux getnameinfo() man pages says port is unitialized if
     610           service name is NULL. */
     611
     612        ret = sys_getnameinfo((const struct sockaddr *)pss,
     613                        sizeof(struct sockaddr_storage),
     614                        addr, sizeof(addr),
     615                        NULL, 0,
     616                        NI_NUMERICHOST);
     617        if (ret != 0) {
     618                return NULL;
     619        }
     620
     621        if (pss->ss_family != AF_INET) {
     622#if defined(HAVE_IPV6)
     623                dest = talloc_asprintf(ctx, "[%s]", addr);
     624#else
     625                return NULL;
     626#endif
     627        } else {
     628                dest = talloc_asprintf(ctx, "%s", addr);
     629        }
     630
     631        return dest;
     632}
     633
     634/****************************************************************************
     635 Return the port number we've bound to on a socket.
     636****************************************************************************/
     637
     638int get_socket_port(int fd)
     639{
     640        struct sockaddr_storage sa;
     641        socklen_t length = sizeof(sa);
     642
     643        if (fd == -1) {
     644                return -1;
     645        }
     646
     647        if (getsockname(fd, (struct sockaddr *)&sa, &length) < 0) {
     648                int level = (errno == ENOTCONN) ? 2 : 0;
     649                DEBUG(level, ("getsockname failed. Error was %s\n",
     650                               strerror(errno)));
     651                return -1;
     652        }
     653
     654#if defined(HAVE_IPV6)
     655        if (sa.ss_family == AF_INET6) {
     656                return ntohs(((struct sockaddr_in6 *)&sa)->sin6_port);
     657        }
     658#endif
     659        if (sa.ss_family == AF_INET) {
     660                return ntohs(((struct sockaddr_in *)&sa)->sin_port);
     661        }
     662        return -1;
     663}
     664
     665/****************************************************************************
     666 Return the string of an IP address (IPv4 or IPv6).
     667****************************************************************************/
     668
     669static const char *get_socket_addr(int fd, char *addr_buf, size_t addr_len)
     670{
     671        struct sockaddr_storage sa;
     672        socklen_t length = sizeof(sa);
     673
     674        /* Ok, returning a hard coded IPv4 address
     675         * is bogus, but it's just as bogus as a
     676         * zero IPv6 address. No good choice here.
     677         */
     678
     679        strlcpy(addr_buf, "0.0.0.0", addr_len);
     680
     681        if (fd == -1) {
     682                return addr_buf;
     683        }
     684
     685        if (getsockname(fd, (struct sockaddr *)&sa, &length) < 0) {
     686                DEBUG(0,("getsockname failed. Error was %s\n",
     687                        strerror(errno) ));
     688                return addr_buf;
     689        }
     690
     691        return print_sockaddr_len(addr_buf, addr_len, (struct sockaddr *)&sa, length);
     692}
     693
     694const char *client_socket_addr(int fd, char *addr, size_t addr_len)
     695{
     696        return get_socket_addr(fd, addr, addr_len);
     697}
  • vendor/current/lib/util/util_net.h

    r414 r740  
    4444                                       int flags);
    4545
     46void set_sockaddr_port(struct sockaddr *psa, uint16_t port);
     47
     48/**
     49 Check if an IP is the 0.0.0.0.
     50**/
     51_PUBLIC_ bool is_zero_ip_v4(struct in_addr ip);
     52
     53void in_addr_to_sockaddr_storage(struct sockaddr_storage *ss,
     54                                 struct in_addr ip);
     55#if defined(HAVE_IPV6)
     56/**
     57 * Convert an IPv6 struct in_addr to a struct sockaddr_storage.
     58 */
     59void in6_addr_to_sockaddr_storage(struct sockaddr_storage *ss,
     60                                  struct in6_addr ip);
     61#endif
     62/**
     63 Are two IPs on the same subnet?
     64**/
     65_PUBLIC_ bool same_net_v4(struct in_addr ip1,struct in_addr ip2,struct in_addr mask);
     66
     67/**
     68 Return true if a string could be a pure IP address.
     69**/
     70_PUBLIC_ bool is_ipaddress(const char *str);
     71
     72bool is_broadcast_addr(const struct sockaddr *pss);
     73bool is_loopback_ip_v4(struct in_addr ip);
     74bool is_loopback_addr(const struct sockaddr *pss);
     75bool is_zero_addr(const struct sockaddr_storage *pss);
     76void zero_ip_v4(struct in_addr *ip);
     77/**
     78 Interpret an internet address or name into an IP address in 4 byte form.
     79**/
     80_PUBLIC_ uint32_t interpret_addr(const char *str);
     81
     82/**
     83 A convenient addition to interpret_addr().
     84**/
     85_PUBLIC_ struct in_addr interpret_addr2(const char *str);
     86
     87_PUBLIC_ bool is_ipaddress_v4(const char *str);
     88
     89bool is_address_any(const struct sockaddr *psa);
     90bool same_net(const struct sockaddr *ip1,
     91              const struct sockaddr *ip2,
     92              const struct sockaddr *mask);
     93bool sockaddr_equal(const struct sockaddr *ip1,
     94                    const struct sockaddr *ip2);
     95
     96bool is_address_any(const struct sockaddr *psa);
     97uint16_t get_sockaddr_port(const struct sockaddr_storage *pss);
     98char *print_sockaddr_len(char *dest,
     99                         size_t destlen,
     100                         const struct sockaddr *psa,
     101                         socklen_t psalen);
     102char *print_sockaddr(char *dest,
     103                        size_t destlen,
     104                        const struct sockaddr_storage *psa);
     105char *print_canonical_sockaddr(TALLOC_CTX *ctx,
     106                        const struct sockaddr_storage *pss);
     107const char *client_name(int fd);
     108int get_socket_port(int fd);
     109const char *client_socket_addr(int fd, char *addr, size_t addr_len);
     110
    46111#endif /* _SAMBA_UTIL_NET_H_ */
  • vendor/current/lib/util/util_pw.c

    r414 r740  
    44   Safe versions of getpw* calls
    55
     6   Copyright (C) Andrew Tridgell 1992-1998
     7   Copyright (C) Jeremy Allison  1998-2005
    68   Copyright (C) Andrew Bartlett 2002
     9   Copyright (C) Timur Bakeyev        2005
     10   Copyright (C) Bjoern Jacke    2006-2007
     11
    712   
    813   This program is free software; you can redistribute it and/or modify
     
    2126
    2227#include "includes.h"
     28#include "system/passwd.h"
     29#include "lib/util/util_pw.h"
    2330
    24 static struct passwd *alloc_copy_passwd(TALLOC_CTX *mem_ctx,
    25                                         const struct passwd *from)
     31/**************************************************************************
     32 Wrappers for setpwent(), getpwent() and endpwent()
     33****************************************************************************/
     34
     35void sys_setpwent(void)
     36{
     37        setpwent();
     38}
     39
     40struct passwd *sys_getpwent(void)
     41{
     42        return getpwent();
     43}
     44
     45void sys_endpwent(void)
     46{
     47        endpwent();
     48}
     49
     50/**************************************************************************
     51 Wrappers for getpwnam(), getpwuid(), getgrnam(), getgrgid()
     52****************************************************************************/
     53
     54struct passwd *sys_getpwnam(const char *name)
     55{
     56        return getpwnam(name);
     57}
     58
     59struct passwd *sys_getpwuid(uid_t uid)
     60{
     61        return getpwuid(uid);
     62}
     63
     64struct group *sys_getgrnam(const char *name)
     65{
     66        return getgrnam(name);
     67}
     68
     69struct group *sys_getgrgid(gid_t gid)
     70{
     71        return getgrgid(gid);
     72}
     73
     74struct passwd *tcopy_passwd(TALLOC_CTX *mem_ctx,
     75                            const struct passwd *from)
    2676{
    2777        struct passwd *ret = talloc_zero(mem_ctx, struct passwd);
     
    4191}
    4292
    43 struct passwd *getpwnam_alloc(TALLOC_CTX *mem_ctx, const char *name) 
     93struct passwd *getpwnam_alloc(TALLOC_CTX *mem_ctx, const char *name)
    4494{
    4595        struct passwd *temp;
     
    56106        }
    57107
    58         return alloc_copy_passwd(mem_ctx, temp);
     108        return tcopy_passwd(mem_ctx, temp);
    59109}
    60110
    61 struct passwd *getpwuid_alloc(TALLOC_CTX *mem_ctx, uid_t uid)
     111/****************************************************************************
     112 talloc'ed version of getpwuid.
     113****************************************************************************/
     114
     115struct passwd *getpwuid_alloc(TALLOC_CTX *mem_ctx, uid_t uid)
    62116{
    63117        struct passwd *temp;
     
    74128        }
    75129
    76         return alloc_copy_passwd(mem_ctx, temp);
     130        return tcopy_passwd(mem_ctx, temp);
    77131}
  • vendor/current/lib/util/util_str.c

    r414 r740  
    6565        if (len > maxlength) {
    6666                DEBUG(0,("ERROR: string overflow by %u (%u - %u) in safe_strcpy [%.50s]\n",
    67                          (uint_t)(len-maxlength), (unsigned)len, (unsigned)maxlength, src));
     67                         (unsigned int)(len-maxlength), (unsigned)len, (unsigned)maxlength, src));
    6868                len = maxlength;
    6969        }
     
    112112        return dest;
    113113}
    114 
    115 #ifdef VALGRIND
    116 size_t valgrind_strlen(const char *s)
    117 {
    118         size_t count;
    119         for(count = 0; *s++; count++)
    120                 ;
    121         return count;
    122 }
    123 #endif
    124 
    125114
    126115/**
  • vendor/current/lib/util/util_strlist.c

    r414 r740  
    2121#include "includes.h"
    2222#include "system/locale.h"
     23#include "lib/util/tsort.h"
    2324
    2425#undef strcasecmp
     
    121122/**
    122123 * build a null terminated list of strings from an argv-like input string
    123  * Entries are seperated by spaces and can be enclosed by quotes.
     124 * Entries are separated by spaces and can be enclosed by quotes.
    124125 * Does NOT support escaping
    125126 */
     
    183184 * join a list back to one string
    184185 */
    185 _PUBLIC_ char *str_list_join(TALLOC_CTX *mem_ctx, const char **list, char seperator)
     186_PUBLIC_ char *str_list_join(TALLOC_CTX *mem_ctx, const char **list, char separator)
    186187{
    187188        char *ret = NULL;
     
    194195
    195196        for (i = 1; list[i]; i++) {
    196                 ret = talloc_asprintf_append_buffer(ret, "%c%s", seperator, list[i]);
     197                ret = talloc_asprintf_append_buffer(ret, "%c%s", separator, list[i]);
    197198        }
    198199
     
    201202
    202203/** join a list back to one (shell-like) string; entries
    203  * seperated by spaces, using quotes where necessary */
     204 * separated by spaces, using quotes where necessary */
    204205_PUBLIC_ char *str_list_join_shell(TALLOC_CTX *mem_ctx, const char **list, char sep)
    205206{
     
    265266   Return true if all the elements of the list match exactly.
    266267 */
    267 _PUBLIC_ bool str_list_equal(const char **list1, const char **list2)
     268_PUBLIC_ bool str_list_equal(const char * const *list1,
     269                             const char * const *list2)
    268270{
    269271        int i;
     
    393395        list2 = (const char **)talloc_memdup(list, list,
    394396                                             sizeof(list[0])*(len+1));
    395         qsort(list2, len, sizeof(list2[0]), QSORT_CAST list_cmp);
     397        TYPESAFE_QSORT(list2, len, list_cmp);
    396398        list[0] = list2[0];
    397399        for (i=j=1;i<len;i++) {
     
    486488        return ret;
    487489}
     490
     491/**
     492 * Needed for making an "unconst" list "const"
     493 */
     494_PUBLIC_ const char **const_str_list(char **list)
     495{
     496        return (const char **)list;
     497}
     498
  • vendor/current/lib/util/util_tdb.c

    r427 r740  
    2121
    2222#include "includes.h"
    23 #include "tdb.h"
     23#include <tdb.h>
    2424#include "../lib/util/util_tdb.h"
    2525
     
    134134
    135135/****************************************************************************
    136  Store a int32_t value by an arbitary blob key, return 0 on success, -1 on failure.
     136 Store a int32_t value by an arbitrary blob key, return 0 on success, -1 on failure.
    137137 Input is int32_t in native byte order. Output in tdb is in little-endian.
    138138****************************************************************************/
     
    191191
    192192/****************************************************************************
    193  Store a uint32_t value by an arbitary blob key, return 0 on success, -1 on failure.
     193 Store a uint32_t value by an arbitrary blob key, return 0 on success, -1 on failure.
    194194 Input is uint32_t in native byte order. Output in tdb is in little-endian.
    195195****************************************************************************/
  • vendor/current/lib/util/util_tdb.h

    r427 r740  
     1/*
     2   Unix SMB/CIFS implementation.
     3
     4   tdb utility functions
     5
     6   Copyright (C) Andrew Tridgell 1992-2006
     7
     8   This program is free software; you can redistribute it and/or modify
     9   it under the terms of the GNU General Public License as published by
     10   the Free Software Foundation; either version 3 of the License, or
     11   (at your option) any later version.
     12
     13   This program is distributed in the hope that it will be useful,
     14   but WITHOUT ANY WARRANTY; without even the implied warranty of
     15   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     16   GNU General Public License for more details.
     17
     18   You should have received a copy of the GNU General Public License
     19   along with this program.  If not, see <http://www.gnu.org/licenses/>.
     20*/
     21
    122#ifndef _____LIB_UTIL_UTIL_TDB_H__
    223#define _____LIB_UTIL_UTIL_TDB_H__
    3 
    424
    525/***************************************************************
     
    4464
    4565/****************************************************************************
    46  Store a int32_t value by an arbitary blob key, return 0 on success, -1 on failure.
     66 Store a int32_t value by an arbitrary blob key, return 0 on success, -1 on failure.
    4767 Input is int32_t in native byte order. Output in tdb is in little-endian.
    4868****************************************************************************/
     
    6888
    6989/****************************************************************************
    70  Store a uint32_t value by an arbitary blob key, return 0 on success, -1 on failure.
     90 Store a uint32_t value by an arbitrary blob key, return 0 on success, -1 on failure.
    7191 Input is uint32_t in native byte order. Output in tdb is in little-endian.
    7292****************************************************************************/
  • vendor/current/lib/util/wrap_xattr.h

    r414 r740  
     1/*
     2   Unix SMB/CIFS implementation.
     3
     4   POSIX NTVFS backend - xattr support using filesystem xattrs
     5
     6   Copyright (C) Andrew Tridgell 2004
     7
     8   This program is free software; you can redistribute it and/or modify
     9   it under the terms of the GNU General Public License as published by
     10   the Free Software Foundation; either version 3 of the License, or
     11   (at your option) any later version.
     12
     13   This program is distributed in the hope that it will be useful,
     14   but WITHOUT ANY WARRANTY; without even the implied warranty of
     15   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     16   GNU General Public License for more details.
     17
     18   You should have received a copy of the GNU General Public License
     19   along with this program.  If not, see <http://www.gnu.org/licenses/>.
     20*/
     21
    122#ifndef __LIB_UTIL_WRAP_XATTR_H__
    223#define __LIB_UTIL_WRAP_XATTR_H__
Note: See TracChangeset for help on using the changeset viewer.