1 /*
2 * Copyright (C) 2008 Giuseppe Torelli - <colossus73@gmail.com>
3 *
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; either version 2 of the License, or
7 * (at your option) any later version.
8 *
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
13 *
14 * You should have received a copy of the GNU General Public License
15 * along with this program; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
17 * MA 02110-1301 USA.
18 */
19
20 #include <string.h>
21 #include "zip.h"
22 #include "date_utils.h"
23 #include "main.h"
24 #include "string_utils.h"
25 #include "support.h"
26 #include "window.h"
27
xa_zip_ask(XArchive * archive)28 void xa_zip_ask (XArchive *archive)
29 {
30 gchar *sfx;
31
32 sfx = g_find_program_in_path("unzipsfx");
33
34 archive->can_test = TRUE;
35 archive->can_extract = TRUE;
36 archive->can_add = archiver[archive->type].is_compressor;
37 archive->can_delete = archiver[archive->type].is_compressor;
38 archive->can_sfx = (sfx && archiver[archive->type].is_compressor);
39 archive->can_password = TRUE;
40 archive->can_full_path[0] = TRUE;
41 archive->can_full_path[1] = archiver[archive->type].is_compressor;
42 archive->can_touch = TRUE;
43 archive->can_overwrite = TRUE;
44 archive->can_update[0] = TRUE;
45 archive->can_update[1] = archiver[archive->type].is_compressor;
46 archive->can_freshen[0] = TRUE;
47 archive->can_freshen[1] = archiver[archive->type].is_compressor;
48 archive->can_move = archiver[archive->type].is_compressor;
49
50 g_free(sfx);
51 }
52
xa_zip_password_str(XArchive * archive)53 static gchar *xa_zip_password_str (XArchive *archive)
54 {
55 if (archive->password)
56 return g_strconcat(" -P", archive->password, NULL);
57 else
58 return g_strdup("");
59 }
60
xa_zip_parse_output(gchar * line,XArchive * archive)61 static void xa_zip_parse_output (gchar *line, XArchive *archive)
62 {
63 XEntry *entry = NULL;
64
65 gchar *filename;
66 gpointer item[9];
67 unsigned int linesize,n,a;
68 gboolean encrypted,dir;
69 guint64 size;
70
71 encrypted = dir = FALSE;
72 if ((line[0] != '-') && (line[0] != 'd') && (line[0] != 'l') && (line[0] != '?'))
73 return;
74
75 linesize = strlen(line);
76
77 /* permissions */
78 for(n=0; n < linesize && line[n] == ' '; n++);
79 a = n;
80 for(; n < linesize && line[n] != ' '; n++);
81
82 line[n]='\0';
83 item[5] = line + a;
84 if ( (line+a)[0] == 'd')
85 dir = TRUE;
86 n++;
87
88 /* version */
89 for(; n < linesize && line[n] == ' '; n++);
90 a = n;
91 for(; n < linesize && line[n] != ' '; n++);
92
93 line[n] = '\0';
94 item[8] = line + a;
95 n++;
96
97 /* OS */
98 for(; n < linesize && line[n] == ' '; n++);
99 a = n;
100 for(; n < linesize && line[n] != ' '; n++);
101
102 line[n]='\0';
103 item[7] = line + a;
104 n++;
105
106 /* size */
107 for(; n < linesize && line[n] == ' '; n++);
108 a = n;
109 for(; n < linesize && line[n] != ' '; n++);
110
111 line[n]='\0';
112 item[0] = line + a;
113 size = g_ascii_strtoull(item[0], NULL, 0);
114 n++;
115
116 /* text/binary */
117 for(; n < linesize && line[n] == ' '; n++);
118 a = n;
119 for(; n < linesize && line[n] != ' '; n++);
120
121 line[n]='\0';
122 if ((line+a)[0] == 'B' || (line+a)[0] == 'T')
123 {
124 archive->has_password = TRUE;
125 encrypted = TRUE;
126 }
127 n++;
128
129 /* compressed size */
130 for(; n < linesize && line[n] == ' '; n++);
131 a = n;
132 for(; n < linesize && line[n] != ' '; n++);
133
134 line[n]='\0';
135 item[1] = line + a;
136 n++;
137
138 /* method */
139 for(; n < linesize && line[n] == ' '; n++);
140 a = n;
141 for(; n < linesize && line[n] != ' '; n++);
142
143 line[n]='\0';
144 item[6] = line + a;
145 n++;
146
147 /* date */
148 for(; n < linesize && line[n] == ' '; n++);
149 a = n;
150 for(; n < linesize && line[n] != ' '; n++);
151
152 line[n]='\0';
153 item[3] = date_YY_MMM_DD(line + a);
154 n++;
155
156 /* time */
157 for(; n < linesize && line[n] == ' '; n++);
158 a = n;
159 for(; n < linesize && line[n] != ' '; n++);
160
161 line[n]='\0';
162 item[4] = line + a;
163 n++;
164
165 /* filename */
166 line[linesize-1] = '\0';
167 filename = line + n;
168
169 /* saving */
170 if (size)
171 item[2] = g_strdup_printf("%.1f%%", 100.0 - 100.0 * g_ascii_strtoull(item[1], NULL, 0) / size);
172 else
173 item[2] = g_strdup("-");
174
175 entry = xa_set_archive_entries_for_each_row(archive, filename, item);
176
177 if (entry)
178 {
179 if (dir)
180 entry->is_dir = TRUE;
181
182 entry->is_encrypted = encrypted;
183
184 if (!entry->is_dir)
185 archive->files++;
186
187 archive->files_size += size;
188 }
189
190 g_free(item[2]);
191 }
192
xa_zip_list(XArchive * archive)193 void xa_zip_list (XArchive *archive)
194 {
195 const GType types[] = {GDK_TYPE_PIXBUF, G_TYPE_STRING, G_TYPE_UINT64, G_TYPE_UINT64, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_POINTER};
196 const gchar *titles[] = {_("Original Size"), _("Compressed"), _("Saving"), _("Date"), _("Time"), _("Permissions"), _("Method"), _("OS"), _("Version")};
197 guint i;
198
199 gchar *command = g_strconcat(archiver[archive->type].program[0], " -Z -l ", archive->path[1], NULL);
200 archive->files_size = 0;
201 archive->files = 0;
202 archive->parse_output = xa_zip_parse_output;
203 xa_spawn_async_process (archive,command);
204 g_free ( command );
205
206 archive->columns = 12;
207 archive->size_column = 2;
208 archive->column_types = g_malloc0(sizeof(types));
209
210 for (i = 0; i < archive->columns; i++)
211 archive->column_types[i] = types[i];
212
213 xa_create_liststore(archive, titles);
214 }
215
xa_zip_test(XArchive * archive)216 void xa_zip_test (XArchive *archive)
217 {
218 gchar *password_str, *command;
219
220 password_str = xa_zip_password_str(archive);
221 command = g_strconcat(archiver[archive->type].program[0], " -t", password_str, " ", archive->path[1], NULL);
222 g_free(password_str);
223
224 xa_run_command(archive, command);
225 g_free(command);
226 }
227
xa_zip_extract(XArchive * archive,GSList * file_list)228 gboolean xa_zip_extract (XArchive *archive, GSList *file_list)
229 {
230 GString *files;
231 gchar *password_str, *command;
232 gboolean result;
233
234 files = xa_quote_filenames(file_list, "*?[]", TRUE);
235 password_str = xa_zip_password_str(archive);
236 command = g_strconcat(archiver[archive->type].program[0],
237 archive->do_full_path ? "" : " -j",
238 archive->do_touch ? " -DD" : "",
239 archive->do_overwrite ? " -o" : (archive->do_update ? " -ou" : (archive->do_freshen ? " -of" : " -n")),
240 password_str, " ",
241 archive->path[1], files->str,
242 " -d ", archive->extraction_dir, NULL);
243 g_free(password_str);
244 g_string_free(files,TRUE);
245
246 result = xa_run_command(archive, command);
247 g_free(command);
248
249 return result;
250 }
251
xa_zip_add(XArchive * archive,GSList * file_list,gchar * compression)252 void xa_zip_add (XArchive *archive, GSList *file_list, gchar *compression)
253 {
254 GString *files;
255 gchar *password_str, *command;
256
257 if (archive->location_path != NULL)
258 archive->child_dir = g_strdup(archive->working_dir);
259
260 if (!compression)
261 compression = "6";
262
263 files = xa_quote_filenames(file_list, NULL, TRUE); // no escaping for adding!
264 password_str = xa_zip_password_str(archive);
265 command = g_strconcat(archiver[archive->type].program[1],
266 archive->do_update ? " -ou" : "",
267 archive->do_freshen ? " -of" : "",
268 archive->do_move ? " -m" : "",
269 " -", compression,
270 password_str, " ",
271 archive->path[1], files->str, NULL);
272 g_free(password_str);
273 g_string_free(files,TRUE);
274
275 xa_run_command(archive, command);
276 g_free(command);
277 }
278
xa_zip_delete(XArchive * archive,GSList * file_list)279 void xa_zip_delete (XArchive *archive, GSList *file_list)
280 {
281 GString *files;
282 gchar *command;
283
284 files = xa_quote_filenames(file_list, "*?[]", TRUE);
285 command = g_strconcat(archiver[archive->type].program[1], " -d ", archive->path[1], files->str, NULL);
286 g_string_free(files,TRUE);
287
288 xa_run_command(archive, command);
289 g_free(command);
290 }
291