diff options
author | Vincent Sanders <vince@kyllikki.org> | 2018-02-03 23:04:49 +0000 |
---|---|---|
committer | Vincent Sanders <vince@kyllikki.org> | 2018-02-03 23:04:49 +0000 |
commit | eeb93199c64db0c47dc73bb1b5a3c7d16d8172e2 (patch) | |
tree | 34aca0598b291654dd1823965cb813d927d34e11 | |
parent | e6af9e997df381f053f3f8c85a678ad07677c791 (diff) | |
download | libnspdf-eeb93199c64db0c47dc73bb1b5a3c7d16d8172e2.tar.gz libnspdf-eeb93199c64db0c47dc73bb1b5a3c7d16d8172e2.tar.bz2 |
make value extraction the same interface as getting
-rw-r--r-- | src/cos_object.c | 47 | ||||
-rw-r--r-- | src/cos_object.h | 7 | ||||
-rw-r--r-- | src/document.c | 22 | ||||
-rw-r--r-- | src/page.c | 2 |
4 files changed, 52 insertions, 26 deletions
diff --git a/src/cos_object.c b/src/cos_object.c index 12adcc9..ad7a17f 100644 --- a/src/cos_object.c +++ b/src/cos_object.c @@ -178,31 +178,42 @@ nspdferror cos_free_object(struct cos_object *cos_obj) * this finds and returns a value for a given key removing it from a dictionary */ nspdferror -cos_extract_dictionary_value(struct cos_object *dict, +cos_extract_dictionary_value(struct nspdf_doc *doc, + struct cos_object *dict, const char *key, struct cos_object **value_out) { - struct cos_dictionary_entry *entry; - struct cos_dictionary_entry **prev; + nspdferror res; - if (dict->type != COS_TYPE_DICTIONARY) { - return NSPDFERROR_TYPE; - } + res = nspdf__xref_get_referenced(doc, &dict); + if (res == NSPDFERROR_OK) { + if (dict->type != COS_TYPE_DICTIONARY) { + res = NSPDFERROR_TYPE; - prev = &dict->u.dictionary; - entry = *prev; - while (entry != NULL) { - if (strcmp(entry->key->u.name, key) == 0) { - *value_out = entry->value; - *prev = entry->next; - cos_free_object(entry->key); - free(entry); - return NSPDFERROR_OK; + } else { + struct cos_dictionary_entry **prev; + struct cos_dictionary_entry *entry; + + res = NSPDFERROR_NOTFOUND; + + prev = &dict->u.dictionary; + entry = *prev; + while (entry != NULL) { + if (strcmp(entry->key->u.name, key) == 0) { + *value_out = entry->value; + *prev = entry->next; + cos_free_object(entry->key); + free(entry); + res = NSPDFERROR_OK; + break; + } + prev = &entry->next; + entry = *prev; + } } - prev = &entry->next; - entry = *prev; } - return NSPDFERROR_NOTFOUND; + return res; + } diff --git a/src/cos_object.h b/src/cos_object.h index a1a70ee..1214a65 100644 --- a/src/cos_object.h +++ b/src/cos_object.h @@ -149,6 +149,11 @@ nspdferror cos_free_object(struct cos_object *cos_obj); * the entry from the dictionary. Once extracted the caller owns the returned * object and must free it. * + * Get the value for a key from a dictionary, If the dictionary is an object + * reference it will be dereferenced first which will parse any previously + * unreferenced indirect objects. + * + * \param doc The document the cos object belongs to or NULL to supress dereferencing. * \param dict The dictionary * \param key The key to lookup * \param value_out The value object associated with the key @@ -156,7 +161,7 @@ nspdferror cos_free_object(struct cos_object *cos_obj); * NSPDFERROR_TYPE if the object passed in \p dict is not a dictionary. * NSPDFERROR_NOTFOUND if the key is not present in the dictionary. */ -nspdferror cos_extract_dictionary_value(struct cos_object *dict, const char *key, struct cos_object **value_out); +nspdferror cos_extract_dictionary_value(struct nspdf_doc *doc, struct cos_object *dict, const char *key, struct cos_object **value_out); /** diff --git a/src/document.c b/src/document.c index dcf8395..bd3d314 100644 --- a/src/document.c +++ b/src/document.c @@ -240,7 +240,7 @@ decode_xref_trailer(struct nspdf_doc *doc, unsigned int xref_offset) goto decode_xref_trailer_failed; } - res = cos_extract_dictionary_value(trailer, "Root", &doc->root); + res = cos_extract_dictionary_value(NULL, trailer, "Root", &doc->root); if (res != NSPDFERROR_OK) { printf("no Root!\n"); goto decode_xref_trailer_failed; @@ -251,17 +251,17 @@ decode_xref_trailer(struct nspdf_doc *doc, unsigned int xref_offset) goto decode_xref_trailer_failed; } - res = cos_extract_dictionary_value(trailer, "Encrypt", &doc->encrypt); + res = cos_extract_dictionary_value(NULL, trailer, "Encrypt", &doc->encrypt); if ((res != NSPDFERROR_OK) && (res != NSPDFERROR_NOTFOUND)) { goto decode_xref_trailer_failed; } - res = cos_extract_dictionary_value(trailer, "Info", &doc->info); + res = cos_extract_dictionary_value(NULL, trailer, "Info", &doc->info); if ((res != NSPDFERROR_OK) && (res != NSPDFERROR_NOTFOUND)) { goto decode_xref_trailer_failed; } - res = cos_extract_dictionary_value(trailer, "ID", &doc->id); + res = cos_extract_dictionary_value(NULL, trailer, "ID", &doc->id); if ((res != NSPDFERROR_OK) && (res != NSPDFERROR_NOTFOUND)) { goto decode_xref_trailer_failed; } @@ -353,7 +353,7 @@ static nspdferror decode_catalog(struct nspdf_doc *doc) return res; } - // Type = Catalog + /* Type = Catalog */ res = cos_get_dictionary_name(doc, catalog, "Type", &type); if (res != NSPDFERROR_OK) { return res; @@ -362,7 +362,13 @@ static nspdferror decode_catalog(struct nspdf_doc *doc) return NSPDFERROR_FORMAT; } - // Pages + /* Pages */ + + /** todo this should get the dictionary Pages object and check it is an + * indirect reference (spec says it *must* be) then below has the reference + * to free in xref table + */ + res = cos_get_dictionary_dictionary(doc, catalog, "Pages", &pages); if (res != NSPDFERROR_OK) { return res; @@ -373,6 +379,10 @@ static nspdferror decode_catalog(struct nspdf_doc *doc) return res; } + /** \todo need to free referenced object when page resources tree is copied + * instead of being owned by the reference. Right now we leak like a seive + */ + return res; } @@ -175,7 +175,7 @@ nspdf__decode_page_tree(struct nspdf_doc *doc, } /* optional page contents */ - res = cos_get_dictionary_value(doc, + res = cos_extract_dictionary_value(doc, page_tree_node, "Contents", &(page->contents)); |