From 8b7d72e8aae5e684eef93020432af4955df236bc Mon Sep 17 00:00:00 2001 From: Frank Lahm Date: Fri, 22 Jun 2012 11:44:56 +0200 Subject: [PATCH] First working packing --- etc/afpd/spotlight.c | 133 ++++++++++++++++++++++++++++++++++---- etc/afpd/spotlight.h | 4 +- include/atalk/byteorder.h | 10 +-- 3 files changed, 126 insertions(+), 21 deletions(-) diff --git a/etc/afpd/spotlight.c b/etc/afpd/spotlight.c index 8240d5c7..f37e226e 100644 --- a/etc/afpd/spotlight.c +++ b/etc/afpd/spotlight.c @@ -125,7 +125,7 @@ static int dd_dump(DALLOC_CTX *dd, int nestinglevel) sl_cnids_t cnids; memcpy(&cnids, dd->dd_talloc_array[n], sizeof(sl_cnids_t)); LOG(log_debug, logtype_sl, "%s%d:\tunkn1: %" PRIu16 ", unkn2: %" PRIu32, - neststrings[nestinglevel + 1], n + 1, cnids.ca_unkn1, cnids.ca_unkn2); + neststrings[nestinglevel + 1], n + 1, cnids.ca_unkn1, cnids.ca_context); if (cnids.ca_cnids) dd_dump(cnids.ca_cnids, nestinglevel + 1); } @@ -193,6 +193,20 @@ static int sl_pack_uint64(uint64_t u, char *buf, int offset) return offset + 2 * sizeof(uint64_t); } +static int sl_pack_bool(sl_bool_t bl, char *buf, int offset) +{ + SLVAL(buf, offset, sl_pack_tag(SQ_TYPE_BOOL, 1, bl ? 1 : 0)); + + return offset + sizeof(uint64_t); +} + +static int sl_pack_nil(char *buf, int offset) +{ + SLVAL(buf, offset, sl_pack_tag(SQ_TYPE_NULL, 1, 1)); + + return offset + sizeof(uint64_t); +} + static int sl_pack_date(sl_time_t t, char *buf, int offset) { uint64_t data = 0; @@ -205,33 +219,35 @@ static int sl_pack_date(sl_time_t t, char *buf, int offset) return offset + 2 * sizeof(uint64_t); } -static int sl_pack_uuid(sl_uuid_t uuid, char *buf, int offset) +static int sl_pack_uuid(sl_uuid_t *uuid, char *buf, int offset) { SLVAL(buf, offset, sl_pack_tag(SQ_TYPE_UUID, 3, 1)); - memcpy(buf + offset + 8, &uuid, 16); + memcpy(buf + offset + 8, uuid, 16); return offset + sizeof(uint64_t) + 16; } -static int sl_pack_CNID(sl_cnids_t *cnids, uint32_t context, char *buf, int offset, char *toc_buf, int *toc_idx) +static int sl_pack_CNID(sl_cnids_t *cnids, char *buf, int offset, char *toc_buf, int *toc_idx) { int len = 0, off = 0; int cnid_count = talloc_array_length(cnids->ca_cnids); SLVAL(toc_buf, *toc_idx * 8, sl_pack_tag(SQ_CPX_TYPE_CNIDS, (offset + SL_OFFSET_DELTA) / 8, cnid_count)); SLVAL(buf, offset, sl_pack_tag(SQ_TYPE_COMPLEX, 1, *toc_idx)); - *toc_idx++; + *toc_idx += 1; offset += 8; SLVAL(buf, offset, sl_pack_tag(SQ_TYPE_CNIDS, 2 + cnid_count, 8 /* unknown meaning, but always 8 */)); offset += 8; - SLVAL(buf, offset, sl_pack_tag(0x0add, cnid_count, context)); - offset += 8; - - for (int i = 0; i < cnid_count; i++) { - SLVAL(buf, offset, cnids->ca_cnids->dd_talloc_array[i]); + if (cnid_count > 0) { + SLVAL(buf, offset, sl_pack_tag(0x0add, cnid_count, cnids->ca_context)); offset += 8; + + for (int i = 0; i < cnid_count; i++) { + SLVAL(buf, offset, cnids->ca_cnids->dd_talloc_array[i]); + offset += 8; + } } return offset; @@ -241,7 +257,7 @@ static int sl_pack_array(sl_array_t *array, char *buf, int offset, char *toc_buf { SLVAL(toc_buf, *toc_idx * 8, sl_pack_tag(SQ_CPX_TYPE_ARRAY, (offset + SL_OFFSET_DELTA) / 8, talloc_array_length(array->dd_talloc_array))); SLVAL(buf, offset, sl_pack_tag(SQ_TYPE_COMPLEX, 1, *toc_idx)); - *toc_idx++; + *toc_idx += 1; offset += 8; offset = sl_pack_loop(array, buf, offset, toc_buf, toc_idx); @@ -253,7 +269,7 @@ static int sl_pack_dict(sl_array_t *dict, char *buf, int offset, char *toc_buf, { SLVAL(toc_buf, *toc_idx * 8, sl_pack_tag(SQ_CPX_TYPE_DICT, (offset + SL_OFFSET_DELTA) / 8, talloc_array_length(dict->dd_talloc_array))); SLVAL(buf, offset, sl_pack_tag(SQ_TYPE_COMPLEX, 1, *toc_idx)); - *toc_idx++; + *toc_idx += 1; offset += 8; offset = sl_pack_loop(dict, buf, offset, toc_buf, toc_idx); @@ -270,7 +286,7 @@ static int sl_pack_string(char *s, char *buf, int offset, char *toc_buf, int *to SLVAL(toc_buf, *toc_idx * 8, sl_pack_tag(SQ_CPX_TYPE_DICT, (offset + SL_OFFSET_DELTA) / 8, used_in_last_octet)); SLVAL(buf, offset, sl_pack_tag(SQ_TYPE_COMPLEX, 1, *toc_idx)); - *toc_idx++; + *toc_idx += 1; offset += 8; SLVAL(buf, offset, sl_pack_tag(SQ_TYPE_DATA, octets + 1, used_in_last_octet)); @@ -285,9 +301,72 @@ static int sl_pack_string(char *s, char *buf, int offset, char *toc_buf, int *to static int sl_pack_loop(DALLOC_CTX *query, char *buf, int offset, char *toc_buf, int *toc_idx) { + const char *type; + + for (int n = 0; n < talloc_array_length(query->dd_talloc_array); n++) { + + type = talloc_get_name(query->dd_talloc_array[n]); + + if (STRCMP(type, ==, "sl_array_t")) { + offset = sl_pack_array(query->dd_talloc_array[n], buf, offset, toc_buf, toc_idx); + } else if (STRCMP(type, ==, "sl_dict_t")) { + offset = sl_pack_dict(query->dd_talloc_array[n], buf, offset, toc_buf, toc_idx); + } else if (STRCMP(type, ==, "uint64_t")) { + uint64_t i; + memcpy(&i, query->dd_talloc_array[n], sizeof(uint64_t)); + offset = sl_pack_uint64(i, buf, offset); + } else if (STRCMP(type, ==, "char *")) { + offset = sl_pack_string(query->dd_talloc_array[n], buf, offset, toc_buf, toc_idx); + } else if (STRCMP(type, ==, "sl_bool_t")) { + sl_bool_t bl; + memcpy(&bl, query->dd_talloc_array[n], sizeof(sl_bool_t)); + offset = sl_pack_bool(bl, buf, offset); + } else if (STRCMP(type, ==, "double")) { + double d; + memcpy(&d, query->dd_talloc_array[n], sizeof(double)); + offset = sl_pack_float(d, buf, offset); + } else if (STRCMP(type, ==, "sl_nil_t")) { + offset = sl_pack_nil(buf, offset); + } else if (STRCMP(type, ==, "sl_time_t")) { + sl_time_t t; + memcpy(&t, query->dd_talloc_array[n], sizeof(sl_time_t)); + offset = sl_pack_date(t, buf, offset); + } else if (STRCMP(type, ==, "sl_uuid_t")) { + offset = sl_pack_uuid(query->dd_talloc_array[n], buf, offset); + } else if (STRCMP(type, ==, "sl_cnids_t")) { + offset = sl_pack_CNID(query->dd_talloc_array[n], buf, offset, toc_buf, toc_idx); + } + } + return offset; } +#define MAX_SLQ_DAT 65000 +#define MAX_SLQ_TOC 2048 + +static int sl_pack(DALLOC_CTX *query, char *buf) +{ + EC_INIT; + char toc_buf[MAX_SLQ_TOC]; + int toc_index = 0; + int len = 0; + + memcpy(buf, "432130dm", 8); + EC_NEG1_LOG( len = sl_pack_loop(query, buf + 16, 0, toc_buf, &toc_index) ); + SIVAL(buf, 8, len / 8 + toc_index + 1); + SIVAL(buf, 12, toc_index + 1); + + SLVAL(toc_buf, 0, sl_pack_tag(SQ_TYPE_TOC, toc_index + 1, 0)); + memcpy(buf + 16 + len, toc_buf, (toc_index + 1 ) * 8); + + len += 16 + (toc_index + 1 ) * 8; + +EC_CLEANUP: + if (ret != 0) + len = -1; + return len; +} + /************************************************************************************************** * unmarshalling functions **************************************************************************************************/ @@ -417,7 +496,7 @@ static int sl_unpack_CNID(DALLOC_CTX *query, const char *buf, int offset, int le count = query_data64 & 0xffff; cnids.ca_unkn1 = (query_data64 & 0xffff0000) >> 16; - cnids.ca_unkn2 = query_data64 >> 32; + cnids.ca_context = query_data64 >> 32; offset += 8; @@ -785,11 +864,37 @@ int main(int argc, char **argv) EC_NEG1_LOG( fd = open("spotlight-packet2.bin", O_RDONLY) ); EC_NEG1_LOG( len = read(fd, ibuf, 8192) ); + close(fd); EC_NEG1_LOG( dissect_spotlight(query, ibuf + 24) ); /* Now dump the whole thing */ dd_dump(query, 0); + int qlen; + char buf[MAX_SLQ_DAT]; + EC_NEG1_LOG( qlen = sl_pack(query, buf) ); + + EC_NEG1_LOG( fd = open("tmp", O_RDWR | O_CREAT, 0644) ); + write(fd, buf, qlen); + close(fd); + + SLVAL(buf, 0, INT64_C(0x0102030405060708U)); + +#if 0 + (((unsigned char *)((buf)))[(0)]) = (unsigned char)((((uint64_t)(0x0102030405060708UL))&0xFFFFFFFF&0xFFFF) &0xFF); + (((unsigned char *)((buf)))[(0)+1]) = (unsigned char)((((uint64_t)(0x0102030405060708UL))&0xFFFFFFFF&0xFFFF) >> 8); + (((unsigned char *)((buf)))[(0)+2]) = (unsigned char)((((uint64_t)(0x0102030405060708UL))&0xFFFFFFFF>>16) & 0xFF); + (((unsigned char *)((buf)))[(0)+2 +1]) = (unsigned char)((((uint64_t)(0x0102030405060708UL))&0xFFFFFFFF>>16)>>8); + (((unsigned char *)((buf)))[(0)+4]) = (unsigned char)((((uint64_t)(0x0102030405060708UL))>>32&0xFFFF)&0xFF); + (((unsigned char *)((buf)))[(0)+4 +1]) = (unsigned char)((((uint64_t)(0x0102030405060708UL))>>32&0xFFFF)>>8); + (((unsigned char *)((buf)))[(0)+4 +2]) = (unsigned char)((((uint64_t)(0x0102030405060708UL))>>32>>16)&0xFF); + (((unsigned char *)((buf)))[(0)+4 +2 +1]) = (unsigned char)((((uint64_t)(0x0102030405060708UL))>>32>>16)>>8); +#endif + + EC_NEG1_LOG( fd = open("tmp2", O_RDWR | O_CREAT, 0644) ); + write(fd, buf, 8); + close(fd); + EC_CLEANUP: if (mem_ctx) { talloc_free(mem_ctx); diff --git a/etc/afpd/spotlight.h b/etc/afpd/spotlight.h index 23c8b745..6168ba56 100644 --- a/etc/afpd/spotlight.h +++ b/etc/afpd/spotlight.h @@ -26,7 +26,7 @@ typedef DALLOC_CTX sl_array_t; /* an array of elements */ typedef DALLOC_CTX sl_dict_t; /* an array of key/value elements */ -typedef DALLOC_CTX sl_filemeta_t; /* an array of elements */ +typedef DALLOC_CTX sl_filemeta_t; /* contains one sl_array_t */ typedef int sl_nil_t; /* a nil element */ typedef bool sl_bool_t; /* a boolean, we avoid bool_t as it's a define for something else */ typedef struct timeval sl_time_t; /* a boolean, we avoid bool_t as it's a define for something else */ @@ -35,7 +35,7 @@ typedef struct { } sl_uuid_t; /* a UUID */ typedef struct { uint16_t ca_unkn1; - uint32_t ca_unkn2; + uint32_t ca_context; DALLOC_CTX *ca_cnids; } sl_cnids_t; /* an array of CNID */ diff --git a/include/atalk/byteorder.h b/include/atalk/byteorder.h index 97a02d66..1b8e25cf 100644 --- a/include/atalk/byteorder.h +++ b/include/atalk/byteorder.h @@ -125,15 +125,15 @@ it also defines lots of intermediate macros, just ignore those :-) #define LVALS(buf,pos) ((int64_t)LVAL(buf,pos)) #define SSVALX(buf,pos,val) (CVAL_NC(buf,pos+1)=(unsigned char)((val)&0xFF),CVAL_NC(buf,pos)=(unsigned char)((val)>>8)) -#define SIVALX(buf,pos,val) (SSVALX(buf,pos,val&0xFFFF),SSVALX(buf,pos+2,val>>16)) -#define SLVALX(buf,pos,val) (SLVALX(buf,pos,val&0xFFFFFFFF),SLVALX(buf,pos+4,val>>32)) +#define SIVALX(buf,pos,val) (SSVALX(buf,pos,((val)&0xFFFF)),SSVALX(buf,pos+2,(val)>>16)) +#define SLVALX(buf,pos,val) (SIVALX(buf,pos,((val)&0xFFFFFFFF)),SIVALX(buf,pos+4,(val)>>32)) #define SSVAL(buf,pos,val) SSVALX((buf),(pos),((uint16_t)(val))) #define SSVALS(buf,pos,val) SSVALX((buf),(pos),((int16)(val))) #define SIVAL(buf,pos,val) SIVALX((buf),(pos),((uint32_t)(val))) #define SIVALS(buf,pos,val) SIVALX((buf),(pos),((int32_t)(val))) #define SLVAL(buf,pos,val) SLVALX((buf),(pos),((uint64_t)(val))) -#define SLVAL(buf,pos,val) SLVALX((buf),(pos),((int64_t)(val))) +#define SLVALS(buf,pos,val) SLVALX((buf),(pos),((int64_t)(val))) #else @@ -145,8 +145,8 @@ it also defines lots of intermediate macros, just ignore those :-) #define LVALS(buf,pos) ((int64_t)LVAL(buf,pos)) #define SSVALX(buf,pos,val) (CVAL_NC(buf,pos)=(unsigned char)((val)&0xFF),CVAL_NC(buf,pos+1)=(unsigned char)((val)>>8)) -#define SIVALX(buf,pos,val) (SSVALX(buf,pos,val&0xFFFF),SSVALX(buf,pos+2,val>>16)) -#define SLVALX(buf,pos,val) (SIVALX(buf,pos,val&0xFFFFFFFF),SIVALX(buf,pos+4,val>>32)) +#define SIVALX(buf,pos,val) (SSVALX(buf,pos,((val)&0xFFFF)),SSVALX(buf,pos+2,(val)>>16)) +#define SLVALX(buf,pos,val) (SIVALX(buf,pos,((val)&0xFFFFFFFF)),SIVALX(buf,pos+4,(val)>>32)) #define SSVAL(buf,pos,val) SSVALX((buf),(pos),((uint16_t)(val))) #define SSVALS(buf,pos,val) SSVALX((buf),(pos),((int16)(val))) -- 2.39.2