1 // This file is part of Deark.
2 // Copyright (C) 2016 Jason Summers
3 // See the file COPYING for terms of use.
7 #include <deark-config.h>
8 #include <deark-private.h>
9 DE_DECLARE_MODULE(de_module_psionapp
);
11 typedef struct localctx_struct
{
12 int convert_images
; // 0=extract PIC, 1=convert PIC
15 static void handle_embedded_file(deark
*c
, lctx
*d
, i64 offset
, i64 len
)
19 int extract_this_file
;
22 de_dbg(c
, "embedded file at %d, len=%d", (int)offset
, (int)len
);
25 extract_this_file
= 0;
27 if(len
>0 && c
->extract_level
>=2)
28 extract_this_file
= 1;
30 // As far as I can tell, there's no way to tell the type of an
31 // embedded file, except by sniffing it.
32 de_read(buf
, offset
, 16);
34 if(!de_memcmp(buf
, "PIC\xdc\x30\x30", 6)) {
35 // Looks like a PIC file
38 extract_this_file
= 1;
42 if(extract_this_file
) {
43 if(is_pic
&& d
->convert_images
) {
44 // Convert PIC to PNG.
45 // For consistency, this option shouldn't exist. But I'm not sure that
46 // PIC files embedded in APP files are really the same as PIC files on
47 // their own. They might need special handling. Until I'm sure they don't,
48 // I'll leave this option here.
49 de_run_module_by_id_on_slice(c
, "psionpic", NULL
, c
->infile
, offset
, len
);
52 // Just extract the file
53 dbuf_create_file_from_slice(c
->infile
, offset
, len
, ext
, NULL
, is_pic
?0:DE_CREATEFLAG_IS_AUX
);
57 de_dbg(c
, "(not extracting this file)");
61 static void do_opo_opa(deark
*c
, lctx
*d
)
68 de_declare_fmt(c
, "Psion OPO/OPA");
70 // The second header marks the end of the embedded files section, I guess.
71 offset_2ndheader
= de_getu16le(18);
72 de_dbg(c
, "offset of second header: %d", (int)offset_2ndheader
);
75 // Read length of source filename
76 n
= (i64
)de_getbyte(pos
);
79 while(pos
<offset_2ndheader
) {
80 // Read length of this embedded file
81 len
= de_getu16le(pos
);
83 handle_embedded_file(c
, d
, pos
, len
);
88 static void do_img_app(deark
*c
, lctx
*d
)
94 de_declare_fmt(c
, "Psion IMG/APP");
97 offset
= de_getu16le(40 + 4*i
);
98 len
= de_getu16le(40 + 4*i
+ 2);
100 handle_embedded_file(c
, d
, offset
, len
);
104 static void de_run_psionapp(deark
*c
, de_module_params
*mparams
)
110 d
= de_malloc(c
, sizeof(lctx
));
112 s
= de_get_ext_option(c
, "psionapp:convertpic");
114 d
->convert_images
= 1;
128 static int de_identify_psionapp(deark
*c
)
132 if(!de_memcmp(b
, "ImageFileType**\0", 16))
134 if(!de_memcmp(b
, "OPLObjectFile**\0", 16))
139 void de_module_psionapp(deark
*c
, struct deark_module_info
*mi
)
142 mi
->desc
= "Psion .APP/.IMG and .OPA/.OPO";
143 mi
->desc2
= "extract images";
144 mi
->run_fn
= de_run_psionapp
;
145 mi
->identify_fn
= de_identify_psionapp
;