diff options
| author | 2009-02-09 20:39:14 +0100 | |
|---|---|---|
| committer | 2009-02-09 21:02:56 +0100 | |
| commit | fa4a22dde897c0e2a8cc89b7479f0513c9455d37 (patch) | |
| tree | 877b0140a133fb34c821ff70bde1a4a8c6ef5ab1 /src | |
| parent | ff1fa73f33e9223e69cbb71e70b084e3482dce3f (diff) | |
| download | libplist-fa4a22dde897c0e2a8cc89b7479f0513c9455d37.tar.gz libplist-fa4a22dde897c0e2a8cc89b7479f0513c9455d37.tar.bz2 | |
Make it compile on MSVC 2005.
Diffstat (limited to 'src')
| -rw-r--r-- | src/bplist.c | 127 | ||||
| -rw-r--r-- | src/plist.c | 24 | ||||
| -rw-r--r-- | src/plist.h | 2 | ||||
| -rw-r--r-- | src/xplist.c | 63 |
4 files changed, 139 insertions, 77 deletions
diff --git a/src/bplist.c b/src/bplist.c index 6e00f39..fb24a1e 100644 --- a/src/bplist.c +++ b/src/bplist.c | |||
| @@ -75,6 +75,7 @@ static void byte_convert(uint8_t * address, size_t size) | |||
| 75 | #endif | 75 | #endif |
| 76 | } | 76 | } |
| 77 | 77 | ||
| 78 | |||
| 78 | #define UINT_TO_HOST(x, n) \ | 79 | #define UINT_TO_HOST(x, n) \ |
| 79 | (n == 8 ? GUINT64_FROM_BE( *(uint64_t *)(x) ) : \ | 80 | (n == 8 ? GUINT64_FROM_BE( *(uint64_t *)(x) ) : \ |
| 80 | (n == 4 ? GUINT32_FROM_BE( *(uint32_t *)(x) ) : \ | 81 | (n == 4 ? GUINT32_FROM_BE( *(uint32_t *)(x) ) : \ |
| @@ -220,11 +221,14 @@ static plist_t parse_array_node(char *bnode, uint64_t size, uint32_t ref_size) | |||
| 220 | 221 | ||
| 221 | static plist_t parse_bin_node(char *object, uint8_t dict_size, char **next_object) | 222 | static plist_t parse_bin_node(char *object, uint8_t dict_size, char **next_object) |
| 222 | { | 223 | { |
| 224 | uint16_t type = 0; | ||
| 225 | uint64_t size = 0; | ||
| 226 | |||
| 223 | if (!object) | 227 | if (!object) |
| 224 | return NULL; | 228 | return NULL; |
| 225 | 229 | ||
| 226 | uint16_t type = *object & 0xF0; | 230 | type = (*object) & 0xF0; |
| 227 | uint64_t size = *object & 0x0F; | 231 | size = (*object) & 0x0F; |
| 228 | object++; | 232 | object++; |
| 229 | 233 | ||
| 230 | switch (type) { | 234 | switch (type) { |
| @@ -364,6 +368,22 @@ static gpointer copy_plist_data(gconstpointer src, gpointer data) | |||
| 364 | 368 | ||
| 365 | void plist_from_bin(const char *plist_bin, uint32_t length, plist_t * plist) | 369 | void plist_from_bin(const char *plist_bin, uint32_t length, plist_t * plist) |
| 366 | { | 370 | { |
| 371 | char *trailer = NULL; | ||
| 372 | |||
| 373 | uint8_t offset_size = 0; | ||
| 374 | uint8_t dict_param_size = 0; | ||
| 375 | uint64_t num_objects = 0; | ||
| 376 | uint64_t root_object = 0; | ||
| 377 | uint64_t offset_table_index = 0; | ||
| 378 | |||
| 379 | plist_t *nodeslist = NULL; | ||
| 380 | uint64_t i = 0; | ||
| 381 | uint64_t current_offset = 0; | ||
| 382 | char *offset_table = NULL; | ||
| 383 | uint32_t j = 0, str_i = 0, str_j = 0; | ||
| 384 | uint32_t index1 = 0, index2 = 0; | ||
| 385 | |||
| 386 | |||
| 367 | //first check we have enough data | 387 | //first check we have enough data |
| 368 | if (!(length >= BPLIST_MAGIC_SIZE + BPLIST_VERSION_SIZE + BPLIST_TRL_SIZE)) | 388 | if (!(length >= BPLIST_MAGIC_SIZE + BPLIST_VERSION_SIZE + BPLIST_TRL_SIZE)) |
| 369 | return; | 389 | return; |
| @@ -375,39 +395,34 @@ void plist_from_bin(const char *plist_bin, uint32_t length, plist_t * plist) | |||
| 375 | return; | 395 | return; |
| 376 | 396 | ||
| 377 | //now parse trailer | 397 | //now parse trailer |
| 378 | const char *trailer = plist_bin + (length - BPLIST_TRL_SIZE); | 398 | trailer = plist_bin + (length - BPLIST_TRL_SIZE); |
| 379 | 399 | ||
| 380 | uint8_t offset_size = trailer[BPLIST_TRL_OFFSIZE_IDX]; | 400 | offset_size = trailer[BPLIST_TRL_OFFSIZE_IDX]; |
| 381 | uint8_t dict_param_size = trailer[BPLIST_TRL_PARMSIZE_IDX]; | 401 | dict_param_size = trailer[BPLIST_TRL_PARMSIZE_IDX]; |
| 382 | uint64_t num_objects = be64dec(trailer + BPLIST_TRL_NUMOBJ_IDX); | 402 | num_objects = be64dec(trailer + BPLIST_TRL_NUMOBJ_IDX); |
| 383 | uint64_t root_object = be64dec(trailer + BPLIST_TRL_ROOTOBJ_IDX); | 403 | root_object = be64dec(trailer + BPLIST_TRL_ROOTOBJ_IDX); |
| 384 | uint64_t offset_table_index = be64dec(trailer + BPLIST_TRL_OFFTAB_IDX); | 404 | offset_table_index = be64dec(trailer + BPLIST_TRL_OFFTAB_IDX); |
| 385 | 405 | ||
| 386 | if (num_objects == 0) | 406 | if (num_objects == 0) |
| 387 | return; | 407 | return; |
| 388 | 408 | ||
| 389 | //allocate serialized array of nodes | 409 | //allocate serialized array of nodes |
| 390 | plist_t *nodeslist = NULL; | ||
| 391 | nodeslist = (plist_t *) malloc(sizeof(plist_t) * num_objects); | 410 | nodeslist = (plist_t *) malloc(sizeof(plist_t) * num_objects); |
| 392 | 411 | ||
| 393 | if (!nodeslist) | 412 | if (!nodeslist) |
| 394 | return; | 413 | return; |
| 395 | 414 | ||
| 396 | //parse serialized nodes | 415 | //parse serialized nodes |
| 397 | uint64_t i = 0; | 416 | offset_table = plist_bin + offset_table_index; |
| 398 | uint64_t current_offset = 0; | ||
| 399 | const char *offset_table = plist_bin + offset_table_index; | ||
| 400 | for (i = 0; i < num_objects; i++) { | 417 | for (i = 0; i < num_objects; i++) { |
| 418 | char *obj = NULL; | ||
| 401 | current_offset = UINT_TO_HOST(offset_table + i * offset_size, offset_size); | 419 | current_offset = UINT_TO_HOST(offset_table + i * offset_size, offset_size); |
| 402 | 420 | ||
| 403 | char *obj = plist_bin + current_offset; | 421 | obj = plist_bin + current_offset; |
| 404 | nodeslist[i] = parse_bin_node(obj, dict_param_size, &obj); | 422 | nodeslist[i] = parse_bin_node(obj, dict_param_size, &obj); |
| 405 | } | 423 | } |
| 406 | 424 | ||
| 407 | //setup children for structured types | 425 | //setup children for structured types |
| 408 | uint32_t j = 0, str_i = 0, str_j = 0; | ||
| 409 | uint32_t index1 = 0, index2 = 0; | ||
| 410 | |||
| 411 | for (i = 0; i < num_objects; i++) { | 426 | for (i = 0; i < num_objects; i++) { |
| 412 | 427 | ||
| 413 | plist_data_t data = plist_get_data(nodeslist[i]); | 428 | plist_data_t data = plist_get_data(nodeslist[i]); |
| @@ -514,14 +529,17 @@ static guint plist_data_hash(gconstpointer key) | |||
| 514 | 529 | ||
| 515 | static gboolean plist_data_compare(gconstpointer a, gconstpointer b) | 530 | static gboolean plist_data_compare(gconstpointer a, gconstpointer b) |
| 516 | { | 531 | { |
| 532 | plist_data_t val_a = NULL; | ||
| 533 | plist_data_t val_b = NULL; | ||
| 534 | |||
| 517 | if (!a || !b) | 535 | if (!a || !b) |
| 518 | return FALSE; | 536 | return FALSE; |
| 519 | 537 | ||
| 520 | if (!((GNode *) a)->data || !((GNode *) b)->data) | 538 | if (!((GNode *) a)->data || !((GNode *) b)->data) |
| 521 | return FALSE; | 539 | return FALSE; |
| 522 | 540 | ||
| 523 | plist_data_t val_a = plist_get_data((plist_t) a); | 541 | val_a = plist_get_data((plist_t) a); |
| 524 | plist_data_t val_b = plist_get_data((plist_t) b); | 542 | val_b = plist_get_data((plist_t) b); |
| 525 | 543 | ||
| 526 | if (val_a->type != val_b->type) | 544 | if (val_a->type != val_b->type) |
| 527 | return FALSE; | 545 | return FALSE; |
| @@ -574,6 +592,7 @@ struct serialize_s { | |||
| 574 | 592 | ||
| 575 | static void serialize_plist(GNode * node, gpointer data) | 593 | static void serialize_plist(GNode * node, gpointer data) |
| 576 | { | 594 | { |
| 595 | uint64_t *index_val = NULL; | ||
| 577 | struct serialize_s *ser = (struct serialize_s *) data; | 596 | struct serialize_s *ser = (struct serialize_s *) data; |
| 578 | uint64_t current_index = ser->objects->len; | 597 | uint64_t current_index = ser->objects->len; |
| 579 | 598 | ||
| @@ -584,7 +603,7 @@ static void serialize_plist(GNode * node, gpointer data) | |||
| 584 | return; | 603 | return; |
| 585 | } | 604 | } |
| 586 | //insert new ref | 605 | //insert new ref |
| 587 | uint64_t *index_val = (uint64_t *) malloc(sizeof(uint64_t)); | 606 | index_val = (uint64_t *) malloc(sizeof(uint64_t)); |
| 588 | *index_val = current_index; | 607 | *index_val = current_index; |
| 589 | g_hash_table_insert(ser->ref_table, node, index_val); | 608 | g_hash_table_insert(ser->ref_table, node, index_val); |
| 590 | 609 | ||
| @@ -639,6 +658,7 @@ static void write_date(GByteArray * bplist, double val) | |||
| 639 | 658 | ||
| 640 | static void write_raw_data(GByteArray * bplist, uint8_t mark, uint8_t * val, uint64_t size) | 659 | static void write_raw_data(GByteArray * bplist, uint8_t mark, uint8_t * val, uint64_t size) |
| 641 | { | 660 | { |
| 661 | uint8_t *buff = NULL; | ||
| 642 | uint8_t marker = mark | (size < 15 ? size : 0xf); | 662 | uint8_t marker = mark | (size < 15 ? size : 0xf); |
| 643 | g_byte_array_append(bplist, &marker, sizeof(uint8_t)); | 663 | g_byte_array_append(bplist, &marker, sizeof(uint8_t)); |
| 644 | if (size >= 15) { | 664 | if (size >= 15) { |
| @@ -647,7 +667,7 @@ static void write_raw_data(GByteArray * bplist, uint8_t mark, uint8_t * val, uin | |||
| 647 | g_byte_array_append(bplist, int_buff->data, int_buff->len); | 667 | g_byte_array_append(bplist, int_buff->data, int_buff->len); |
| 648 | g_byte_array_free(int_buff, TRUE); | 668 | g_byte_array_free(int_buff, TRUE); |
| 649 | } | 669 | } |
| 650 | uint8_t *buff = (uint8_t *) malloc(size); | 670 | buff = (uint8_t *) malloc(size); |
| 651 | memcpy(buff, val, size); | 671 | memcpy(buff, val, size); |
| 652 | g_byte_array_append(bplist, buff, size); | 672 | g_byte_array_append(bplist, buff, size); |
| 653 | free(buff); | 673 | free(buff); |
| @@ -677,6 +697,12 @@ static void write_unicode(GByteArray * bplist, gunichar2 * val, uint64_t size) | |||
| 677 | 697 | ||
| 678 | static void write_array(GByteArray * bplist, GNode * node, GHashTable * ref_table, uint8_t dict_param_size) | 698 | static void write_array(GByteArray * bplist, GNode * node, GHashTable * ref_table, uint8_t dict_param_size) |
| 679 | { | 699 | { |
| 700 | uint64_t idx = 0; | ||
| 701 | uint8_t *buff = NULL; | ||
| 702 | |||
| 703 | GNode *cur = NULL; | ||
| 704 | uint64_t i = 0; | ||
| 705 | |||
| 680 | uint64_t size = g_node_n_children(node); | 706 | uint64_t size = g_node_n_children(node); |
| 681 | uint8_t marker = BPLIST_ARRAY | (size < 15 ? size : 0xf); | 707 | uint8_t marker = BPLIST_ARRAY | (size < 15 ? size : 0xf); |
| 682 | g_byte_array_append(bplist, &marker, sizeof(uint8_t)); | 708 | g_byte_array_append(bplist, &marker, sizeof(uint8_t)); |
| @@ -687,11 +713,8 @@ static void write_array(GByteArray * bplist, GNode * node, GHashTable * ref_tabl | |||
| 687 | g_byte_array_free(int_buff, TRUE); | 713 | g_byte_array_free(int_buff, TRUE); |
| 688 | } | 714 | } |
| 689 | 715 | ||
| 690 | uint64_t idx = 0; | 716 | buff = (uint8_t *) malloc(size * dict_param_size); |
| 691 | uint8_t *buff = (uint8_t *) malloc(size * dict_param_size); | ||
| 692 | 717 | ||
| 693 | GNode *cur = NULL; | ||
| 694 | uint64_t i = 0; | ||
| 695 | for (i = 0, cur = node->children; cur && i < size; cur = cur->next, i++) { | 718 | for (i = 0, cur = node->children; cur && i < size; cur = cur->next, i++) { |
| 696 | idx = *(uint64_t *) (g_hash_table_lookup(ref_table, cur)); | 719 | idx = *(uint64_t *) (g_hash_table_lookup(ref_table, cur)); |
| 697 | memcpy(buff + i * dict_param_size, &idx, dict_param_size); | 720 | memcpy(buff + i * dict_param_size, &idx, dict_param_size); |
| @@ -706,6 +729,13 @@ static void write_array(GByteArray * bplist, GNode * node, GHashTable * ref_tabl | |||
| 706 | 729 | ||
| 707 | static void write_dict(GByteArray * bplist, GNode * node, GHashTable * ref_table, uint8_t dict_param_size) | 730 | static void write_dict(GByteArray * bplist, GNode * node, GHashTable * ref_table, uint8_t dict_param_size) |
| 708 | { | 731 | { |
| 732 | uint64_t idx1 = 0; | ||
| 733 | uint64_t idx2 = 0; | ||
| 734 | uint8_t *buff = NULL; | ||
| 735 | |||
| 736 | GNode *cur = NULL; | ||
| 737 | uint64_t i = 0; | ||
| 738 | |||
| 709 | uint64_t size = g_node_n_children(node) / 2; | 739 | uint64_t size = g_node_n_children(node) / 2; |
| 710 | uint8_t marker = BPLIST_DICT | (size < 15 ? size : 0xf); | 740 | uint8_t marker = BPLIST_DICT | (size < 15 ? size : 0xf); |
| 711 | g_byte_array_append(bplist, &marker, sizeof(uint8_t)); | 741 | g_byte_array_append(bplist, &marker, sizeof(uint8_t)); |
| @@ -716,12 +746,8 @@ static void write_dict(GByteArray * bplist, GNode * node, GHashTable * ref_table | |||
| 716 | g_byte_array_free(int_buff, TRUE); | 746 | g_byte_array_free(int_buff, TRUE); |
| 717 | } | 747 | } |
| 718 | 748 | ||
| 719 | uint64_t idx1 = 0; | 749 | buff = (uint8_t *) malloc(size * 2 * dict_param_size); |
| 720 | uint64_t idx2 = 0; | ||
| 721 | uint8_t *buff = (uint8_t *) malloc(size * 2 * dict_param_size); | ||
| 722 | 750 | ||
| 723 | GNode *cur = NULL; | ||
| 724 | uint64_t i = 0; | ||
| 725 | for (i = 0, cur = node->children; cur && i < size; cur = cur->next->next, i++) { | 751 | for (i = 0, cur = node->children; cur && i < size; cur = cur->next->next, i++) { |
| 726 | idx1 = GPOINTER_TO_UINT(g_hash_table_lookup(ref_table, cur)); | 752 | idx1 = GPOINTER_TO_UINT(g_hash_table_lookup(ref_table, cur)); |
| 727 | memcpy(buff + i * dict_param_size, &idx1, dict_param_size); | 753 | memcpy(buff + i * dict_param_size, &idx1, dict_param_size); |
| @@ -740,41 +766,55 @@ static void write_dict(GByteArray * bplist, GNode * node, GHashTable * ref_table | |||
| 740 | 766 | ||
| 741 | void plist_to_bin(plist_t plist, char **plist_bin, uint32_t * length) | 767 | void plist_to_bin(plist_t plist, char **plist_bin, uint32_t * length) |
| 742 | { | 768 | { |
| 769 | GPtrArray *objects = NULL; | ||
| 770 | GHashTable *ref_table = NULL; | ||
| 771 | struct serialize_s ser_s; | ||
| 772 | uint8_t offset_size = 0; | ||
| 773 | uint8_t dict_param_size = 0; | ||
| 774 | uint64_t num_objects = 0; | ||
| 775 | uint64_t root_object = 0; | ||
| 776 | uint64_t offset_table_index = 0; | ||
| 777 | GByteArray *bplist_buff = NULL; | ||
| 778 | uint64_t i = 0; | ||
| 779 | uint8_t *buff = NULL; | ||
| 780 | uint64_t *offsets = NULL; | ||
| 781 | uint8_t pad[6] = { 0, 0, 0, 0, 0, 0 }; | ||
| 782 | uint8_t trailer[BPLIST_TRL_SIZE]; | ||
| 783 | |||
| 743 | //check for valid input | 784 | //check for valid input |
| 744 | if (!plist || !plist_bin || *plist_bin || !length) | 785 | if (!plist || !plist_bin || *plist_bin || !length) |
| 745 | return; | 786 | return; |
| 746 | 787 | ||
| 747 | //list of objects | 788 | //list of objects |
| 748 | GPtrArray *objects = g_ptr_array_new(); | 789 | objects = g_ptr_array_new(); |
| 749 | //hashtable to write only once same nodes | 790 | //hashtable to write only once same nodes |
| 750 | GHashTable *ref_table = g_hash_table_new(plist_data_hash, plist_data_compare); | 791 | ref_table = g_hash_table_new(plist_data_hash, plist_data_compare); |
| 751 | 792 | ||
| 752 | //serialize plist | 793 | //serialize plist |
| 753 | struct serialize_s ser_s = { objects, ref_table }; | 794 | ser_s.objects = objects; |
| 795 | ser_s.ref_table = ref_table; | ||
| 754 | serialize_plist(plist, &ser_s); | 796 | serialize_plist(plist, &ser_s); |
| 755 | 797 | ||
| 756 | //now stream to output buffer | 798 | //now stream to output buffer |
| 757 | uint8_t offset_size = 0; //unknown yet | 799 | offset_size = 0; //unknown yet |
| 758 | uint8_t dict_param_size = get_needed_bytes(objects->len); | 800 | dict_param_size = get_needed_bytes(objects->len); |
| 759 | uint64_t num_objects = objects->len; | 801 | num_objects = objects->len; |
| 760 | uint64_t root_object = 0; //root is first in list | 802 | root_object = 0; //root is first in list |
| 761 | uint64_t offset_table_index = 0; //unknown yet | 803 | offset_table_index = 0; //unknown yet |
| 762 | 804 | ||
| 763 | //setup a dynamic bytes array to store bplist in | 805 | //setup a dynamic bytes array to store bplist in |
| 764 | GByteArray *bplist_buff = g_byte_array_new(); | 806 | bplist_buff = g_byte_array_new(); |
| 765 | 807 | ||
| 766 | //set magic number and version | 808 | //set magic number and version |
| 767 | g_byte_array_append(bplist_buff, BPLIST_MAGIC, BPLIST_MAGIC_SIZE); | 809 | g_byte_array_append(bplist_buff, BPLIST_MAGIC, BPLIST_MAGIC_SIZE); |
| 768 | g_byte_array_append(bplist_buff, BPLIST_VERSION, BPLIST_VERSION_SIZE); | 810 | g_byte_array_append(bplist_buff, BPLIST_VERSION, BPLIST_VERSION_SIZE); |
| 769 | 811 | ||
| 770 | //write objects and table | 812 | //write objects and table |
| 771 | uint64_t i = 0; | 813 | offsets = (uint64_t *) malloc(num_objects * sizeof(uint64_t)); |
| 772 | uint8_t *buff = NULL; | ||
| 773 | uint64_t offsets[num_objects]; | ||
| 774 | for (i = 0; i < num_objects; i++) { | 814 | for (i = 0; i < num_objects; i++) { |
| 775 | 815 | ||
| 776 | offsets[i] = bplist_buff->len; | ||
| 777 | plist_data_t data = plist_get_data(g_ptr_array_index(objects, i)); | 816 | plist_data_t data = plist_get_data(g_ptr_array_index(objects, i)); |
| 817 | offsets[i] = bplist_buff->len; | ||
| 778 | 818 | ||
| 779 | switch (data->type) { | 819 | switch (data->type) { |
| 780 | case PLIST_BOOLEAN: | 820 | case PLIST_BOOLEAN: |
| @@ -830,7 +870,6 @@ void plist_to_bin(plist_t plist, char **plist_bin, uint32_t * length) | |||
| 830 | } | 870 | } |
| 831 | 871 | ||
| 832 | //experimental pad to reflect apple's files | 872 | //experimental pad to reflect apple's files |
| 833 | uint8_t pad[6] = { 0, 0, 0, 0, 0, 0 }; | ||
| 834 | g_byte_array_append(bplist_buff, pad, 6); | 873 | g_byte_array_append(bplist_buff, pad, 6); |
| 835 | 874 | ||
| 836 | //setup trailer | 875 | //setup trailer |
| @@ -838,7 +877,6 @@ void plist_to_bin(plist_t plist, char **plist_bin, uint32_t * length) | |||
| 838 | root_object = GUINT64_FROM_BE(root_object); | 877 | root_object = GUINT64_FROM_BE(root_object); |
| 839 | offset_table_index = GUINT64_FROM_BE(offset_table_index); | 878 | offset_table_index = GUINT64_FROM_BE(offset_table_index); |
| 840 | 879 | ||
| 841 | uint8_t trailer[BPLIST_TRL_SIZE]; | ||
| 842 | memcpy(trailer + BPLIST_TRL_OFFSIZE_IDX, &offset_size, sizeof(uint8_t)); | 880 | memcpy(trailer + BPLIST_TRL_OFFSIZE_IDX, &offset_size, sizeof(uint8_t)); |
| 843 | memcpy(trailer + BPLIST_TRL_PARMSIZE_IDX, &dict_param_size, sizeof(uint8_t)); | 881 | memcpy(trailer + BPLIST_TRL_PARMSIZE_IDX, &dict_param_size, sizeof(uint8_t)); |
| 844 | memcpy(trailer + BPLIST_TRL_NUMOBJ_IDX, &num_objects, sizeof(uint64_t)); | 882 | memcpy(trailer + BPLIST_TRL_NUMOBJ_IDX, &num_objects, sizeof(uint64_t)); |
| @@ -853,4 +891,5 @@ void plist_to_bin(plist_t plist, char **plist_bin, uint32_t * length) | |||
| 853 | *length = bplist_buff->len; | 891 | *length = bplist_buff->len; |
| 854 | 892 | ||
| 855 | g_byte_array_free(bplist_buff, TRUE); | 893 | g_byte_array_free(bplist_buff, TRUE); |
| 894 | free(offsets); | ||
| 856 | } | 895 | } |
diff --git a/src/plist.c b/src/plist.c index 758fe53..87a1de5 100644 --- a/src/plist.c +++ b/src/plist.c | |||
| @@ -77,15 +77,17 @@ static plist_t plist_add_sub_element(plist_t node, plist_type type, const void * | |||
| 77 | if (node_type == PLIST_DICT || node_type == PLIST_ARRAY) { | 77 | if (node_type == PLIST_DICT || node_type == PLIST_ARRAY) { |
| 78 | //only structured types are allowed to have nulll value | 78 | //only structured types are allowed to have nulll value |
| 79 | if (value || (!value && (type == PLIST_DICT || type == PLIST_ARRAY))) { | 79 | if (value || (!value && (type == PLIST_DICT || type == PLIST_ARRAY))) { |
| 80 | //now handle value | ||
| 81 | plist_data_t data = plist_new_plist_data(); | ||
| 82 | data->type = type; | ||
| 83 | data->length = length; | ||
| 84 | 80 | ||
| 85 | glong len = 0; | 81 | glong len = 0; |
| 86 | glong items_read = 0; | 82 | glong items_read = 0; |
| 87 | glong items_written = 0; | 83 | glong items_written = 0; |
| 88 | GError *error = NULL; | 84 | GError *error = NULL; |
| 85 | plist_t subnode = NULL; | ||
| 86 | |||
| 87 | //now handle value | ||
| 88 | plist_data_t data = plist_new_plist_data(); | ||
| 89 | data->type = type; | ||
| 90 | data->length = length; | ||
| 89 | 91 | ||
| 90 | switch (type) { | 92 | switch (type) { |
| 91 | case PLIST_BOOLEAN: | 93 | case PLIST_BOOLEAN: |
| @@ -119,7 +121,7 @@ static plist_t plist_add_sub_element(plist_t node, plist_type type, const void * | |||
| 119 | break; | 121 | break; |
| 120 | } | 122 | } |
| 121 | 123 | ||
| 122 | plist_t subnode = plist_new_node(data); | 124 | subnode = plist_new_node(data); |
| 123 | if (node) | 125 | if (node) |
| 124 | g_node_append(node, subnode); | 126 | g_node_append(node, subnode); |
| 125 | return subnode; | 127 | return subnode; |
| @@ -185,10 +187,11 @@ static char compare_node_value(plist_type type, plist_data_t data, const void *v | |||
| 185 | 187 | ||
| 186 | static plist_t plist_find_node(plist_t plist, plist_type type, const void *value, uint64_t length) | 188 | static plist_t plist_find_node(plist_t plist, plist_type type, const void *value, uint64_t length) |
| 187 | { | 189 | { |
| 190 | plist_t current = NULL; | ||
| 191 | |||
| 188 | if (!plist) | 192 | if (!plist) |
| 189 | return NULL; | 193 | return NULL; |
| 190 | 194 | ||
| 191 | plist_t current = NULL; | ||
| 192 | for (current = plist_get_first_child(plist); current; current = plist_get_next_sibling(current)) { | 195 | for (current = plist_get_first_child(plist); current; current = plist_get_next_sibling(current)) { |
| 193 | 196 | ||
| 194 | plist_data_t data = plist_get_data(current); | 197 | plist_data_t data = plist_get_data(current); |
| @@ -217,16 +220,17 @@ plist_t plist_find_node_by_string(plist_t plist, const char *value) | |||
| 217 | 220 | ||
| 218 | static void plist_get_type_and_value(plist_t node, plist_type * type, void *value, uint64_t * length) | 221 | static void plist_get_type_and_value(plist_t node, plist_type * type, void *value, uint64_t * length) |
| 219 | { | 222 | { |
| 220 | if (!node) | ||
| 221 | return; | ||
| 222 | |||
| 223 | //for unicode | 223 | //for unicode |
| 224 | glong len = 0; | 224 | glong len = 0; |
| 225 | glong items_read = 0; | 225 | glong items_read = 0; |
| 226 | glong items_written = 0; | 226 | glong items_written = 0; |
| 227 | GError *error = NULL; | 227 | GError *error = NULL; |
| 228 | plist_data_t data = NULL; | ||
| 229 | |||
| 230 | if (!node) | ||
| 231 | return; | ||
| 228 | 232 | ||
| 229 | plist_data_t data = plist_get_data(node); | 233 | data = plist_get_data(node); |
| 230 | 234 | ||
| 231 | *type = data->type; | 235 | *type = data->type; |
| 232 | *length = data->length; | 236 | *length = data->length; |
diff --git a/src/plist.h b/src/plist.h index 830da75..48b66f1 100644 --- a/src/plist.h +++ b/src/plist.h | |||
| @@ -24,11 +24,9 @@ | |||
| 24 | 24 | ||
| 25 | #include "plist/plist.h" | 25 | #include "plist/plist.h" |
| 26 | 26 | ||
| 27 | #include <stdint.h> | ||
| 28 | 27 | ||
| 29 | #include <sys/types.h> | 28 | #include <sys/types.h> |
| 30 | #include <sys/stat.h> | 29 | #include <sys/stat.h> |
| 31 | #include <unistd.h> | ||
| 32 | #include <glib.h> | 30 | #include <glib.h> |
| 33 | 31 | ||
| 34 | 32 | ||
diff --git a/src/xplist.c b/src/xplist.c index 20b2795..b404e79 100644 --- a/src/xplist.c +++ b/src/xplist.c | |||
| @@ -102,7 +102,7 @@ struct xml_node { | |||
| 102 | static xmlDocPtr new_xml_plist() | 102 | static xmlDocPtr new_xml_plist() |
| 103 | { | 103 | { |
| 104 | char *plist = strdup(plist_base); | 104 | char *plist = strdup(plist_base); |
| 105 | xmlDocPtr plist_xml = xmlReadMemory(plist, strlen(plist), NULL, NULL, 0); | 105 | xmlDocPtr plist_xml = xmlParseMemory(plist, strlen(plist)); |
| 106 | 106 | ||
| 107 | if (!plist_xml) | 107 | if (!plist_xml) |
| 108 | return NULL; | 108 | return NULL; |
| @@ -126,11 +126,8 @@ static void free_plist(xmlDocPtr plist) | |||
| 126 | 126 | ||
| 127 | static void node_to_xml(GNode * node, gpointer xml_struct) | 127 | static void node_to_xml(GNode * node, gpointer xml_struct) |
| 128 | { | 128 | { |
| 129 | if (!node) | 129 | struct xml_node *xstruct = NULL; |
| 130 | return; | 130 | plist_data_t node_data = NULL; |
| 131 | |||
| 132 | struct xml_node *xstruct = (struct xml_node *) xml_struct; | ||
| 133 | plist_data_t node_data = plist_get_data(node); | ||
| 134 | 131 | ||
| 135 | xmlNodePtr child_node = NULL; | 132 | xmlNodePtr child_node = NULL; |
| 136 | char isStruct = FALSE; | 133 | char isStruct = FALSE; |
| @@ -138,12 +135,23 @@ static void node_to_xml(GNode * node, gpointer xml_struct) | |||
| 138 | const xmlChar *tag = NULL; | 135 | const xmlChar *tag = NULL; |
| 139 | gchar *val = NULL; | 136 | gchar *val = NULL; |
| 140 | 137 | ||
| 138 | //for base64 | ||
| 139 | gchar *valtmp = NULL; | ||
| 140 | |||
| 141 | //for unicode | 141 | //for unicode |
| 142 | glong len = 0; | 142 | glong len = 0; |
| 143 | glong items_read = 0; | 143 | glong items_read = 0; |
| 144 | glong items_written = 0; | 144 | glong items_written = 0; |
| 145 | GError *error = NULL; | 145 | GError *error = NULL; |
| 146 | 146 | ||
| 147 | uint32_t i = 0; | ||
| 148 | |||
| 149 | if (!node) | ||
| 150 | return; | ||
| 151 | |||
| 152 | xstruct = (struct xml_node *) xml_struct; | ||
| 153 | node_data = plist_get_data(node); | ||
| 154 | |||
| 147 | switch (node_data->type) { | 155 | switch (node_data->type) { |
| 148 | case PLIST_BOOLEAN: | 156 | case PLIST_BOOLEAN: |
| 149 | { | 157 | { |
| @@ -182,7 +190,7 @@ static void node_to_xml(GNode * node, gpointer xml_struct) | |||
| 182 | 190 | ||
| 183 | case PLIST_DATA: | 191 | case PLIST_DATA: |
| 184 | tag = XPLIST_DATA; | 192 | tag = XPLIST_DATA; |
| 185 | gchar *valtmp = g_base64_encode(node_data->buff, node_data->length); | 193 | valtmp = g_base64_encode(node_data->buff, node_data->length); |
| 186 | val = format_string(valtmp, 60, xstruct->depth); | 194 | val = format_string(valtmp, 60, xstruct->depth); |
| 187 | g_free(valtmp); | 195 | g_free(valtmp); |
| 188 | break; | 196 | break; |
| @@ -202,7 +210,6 @@ static void node_to_xml(GNode * node, gpointer xml_struct) | |||
| 202 | break; | 210 | break; |
| 203 | } | 211 | } |
| 204 | 212 | ||
| 205 | uint32_t i = 0; | ||
| 206 | for (i = 0; i < xstruct->depth; i++) { | 213 | for (i = 0; i < xstruct->depth; i++) { |
| 207 | xmlNodeAddContent(xstruct->xml, BAD_CAST("\t")); | 214 | xmlNodeAddContent(xstruct->xml, BAD_CAST("\t")); |
| 208 | } | 215 | } |
| @@ -232,6 +239,16 @@ static void node_to_xml(GNode * node, gpointer xml_struct) | |||
| 232 | static void xml_to_node(xmlNodePtr xml_node, plist_t * plist_node) | 239 | static void xml_to_node(xmlNodePtr xml_node, plist_t * plist_node) |
| 233 | { | 240 | { |
| 234 | xmlNodePtr node = NULL; | 241 | xmlNodePtr node = NULL; |
| 242 | plist_data_t data = NULL; | ||
| 243 | plist_t subnode = NULL; | ||
| 244 | |||
| 245 | //for string | ||
| 246 | unsigned char *tmp = NULL; | ||
| 247 | glong len = 0; | ||
| 248 | glong items_read = 0; | ||
| 249 | glong items_written = 0; | ||
| 250 | GError *error = NULL; | ||
| 251 | int type = 0; | ||
| 235 | 252 | ||
| 236 | if (!xml_node) | 253 | if (!xml_node) |
| 237 | return; | 254 | return; |
| @@ -243,8 +260,8 @@ static void xml_to_node(xmlNodePtr xml_node, plist_t * plist_node) | |||
| 243 | if (!node) | 260 | if (!node) |
| 244 | break; | 261 | break; |
| 245 | 262 | ||
| 246 | plist_data_t data = plist_new_plist_data(); | 263 | data = plist_new_plist_data(); |
| 247 | plist_t subnode = plist_new_node(data); | 264 | subnode = plist_new_node(data); |
| 248 | if (*plist_node) | 265 | if (*plist_node) |
| 249 | g_node_append(*plist_node, subnode); | 266 | g_node_append(*plist_node, subnode); |
| 250 | else | 267 | else |
| @@ -289,12 +306,12 @@ static void xml_to_node(xmlNodePtr xml_node, plist_t * plist_node) | |||
| 289 | 306 | ||
| 290 | if (!xmlStrcmp(node->name, XPLIST_STRING)) { | 307 | if (!xmlStrcmp(node->name, XPLIST_STRING)) { |
| 291 | 308 | ||
| 292 | unsigned char *tmp = xmlNodeGetContent(node); | 309 | tmp = xmlNodeGetContent(node); |
| 293 | glong len = strlen((char *) tmp); | 310 | len = strlen((char *) tmp); |
| 294 | glong items_read = 0; | 311 | items_read = 0; |
| 295 | glong items_written = 0; | 312 | items_written = 0; |
| 296 | GError *error = NULL; | 313 | error = NULL; |
| 297 | int type = xmlDetectCharEncoding(tmp, len); | 314 | type = xmlDetectCharEncoding(tmp, len); |
| 298 | 315 | ||
| 299 | if (XML_CHAR_ENCODING_UTF8 == type) { | 316 | if (XML_CHAR_ENCODING_UTF8 == type) { |
| 300 | data->unicodeval = g_utf8_to_utf16((char *) tmp, len, &items_read, &items_written, &error); | 317 | data->unicodeval = g_utf8_to_utf16((char *) tmp, len, &items_read, &items_written, &error); |
| @@ -339,15 +356,19 @@ static void xml_to_node(xmlNodePtr xml_node, plist_t * plist_node) | |||
| 339 | 356 | ||
| 340 | void plist_to_xml(plist_t plist, char **plist_xml, uint32_t * length) | 357 | void plist_to_xml(plist_t plist, char **plist_xml, uint32_t * length) |
| 341 | { | 358 | { |
| 359 | xmlDocPtr plist_doc = NULL; | ||
| 360 | xmlNodePtr root_node = NULL; | ||
| 361 | struct xml_node root = { NULL, 0 }; | ||
| 362 | int size = 0; | ||
| 363 | |||
| 342 | if (!plist || !plist_xml || *plist_xml) | 364 | if (!plist || !plist_xml || *plist_xml) |
| 343 | return; | 365 | return; |
| 344 | xmlDocPtr plist_doc = new_xml_plist(); | 366 | plist_doc = new_xml_plist(); |
| 345 | xmlNodePtr root_node = xmlDocGetRootElement(plist_doc); | 367 | root_node = xmlDocGetRootElement(plist_doc); |
| 346 | struct xml_node root = { root_node, 0 }; | 368 | root.xml = root_node; |
| 347 | 369 | ||
| 348 | node_to_xml(plist, &root); | 370 | node_to_xml(plist, &root); |
| 349 | 371 | ||
| 350 | int size = 0; | ||
| 351 | xmlDocDumpMemory(plist_doc, (xmlChar **) plist_xml, &size); | 372 | xmlDocDumpMemory(plist_doc, (xmlChar **) plist_xml, &size); |
| 352 | if (size >= 0) | 373 | if (size >= 0) |
| 353 | *length = size; | 374 | *length = size; |
| @@ -356,7 +377,7 @@ void plist_to_xml(plist_t plist, char **plist_xml, uint32_t * length) | |||
| 356 | 377 | ||
| 357 | void plist_from_xml(const char *plist_xml, uint32_t length, plist_t * plist) | 378 | void plist_from_xml(const char *plist_xml, uint32_t length, plist_t * plist) |
| 358 | { | 379 | { |
| 359 | xmlDocPtr plist_doc = xmlReadMemory(plist_xml, length, NULL, NULL, 0); | 380 | xmlDocPtr plist_doc = xmlParseMemory(plist_xml, length); |
| 360 | xmlNodePtr root_node = xmlDocGetRootElement(plist_doc); | 381 | xmlNodePtr root_node = xmlDocGetRootElement(plist_doc); |
| 361 | 382 | ||
| 362 | xml_to_node(root_node, plist); | 383 | xml_to_node(root_node, plist); |
