~ubuntu-branches/ubuntu/jaunty/xarchiver/jaunty

« back to all changes in this revision

Viewing changes to src/lha.c

  • Committer: Bazaar Package Importer
  • Author(s): Daniel Baumann
  • Date: 2008-11-07 14:54:00 UTC
  • mfrom: (1.1.7 upstream) (2.1.5 sid)
  • Revision ID: james.westby@ubuntu.com-20081107145400-z0j3jmgads8coae2
Tags: 0.5.1-1
MergingĀ upstreamĀ versionĀ 0.5.1.

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
1
/*
2
 
 *  Copyright (C) 2006 Giuseppe Torelli - <colossus73@gmail.com>
 
2
 *  Copyright (C) 2008 Giuseppe Torelli - <colossus73@gmail.com>
3
3
 *  Copyright (C) 2006 Lukasz 'Sil2100' Zemczak - <sil2100@vexillium.org>
4
4
 *
5
5
 *  This program is free software; you can redistribute it and/or modify
19
19
 
20
20
#include "config.h"
21
21
#include "lha.h"
22
 
 
23
 
static gboolean LhaOpen (GIOChannel *ioc, GIOCondition cond, gpointer data);
24
 
void OpenLha ( XArchive *archive )
 
22
#include <unistd.h>
 
23
 
 
24
extern void xa_reload_archive_content(XArchive *archive);
 
25
extern void xa_create_liststore ( XArchive *archive, gchar *columns_names[]);
 
26
 
 
27
void xa_open_lha (XArchive *archive)
25
28
{
26
29
        gchar *command;
27
 
 
 
30
        jump_header = last_line = FALSE;
 
31
        unsigned short int i;
28
32
        command = g_strconcat ("lha l " , archive->escaped_path, NULL);
 
33
        archive->has_properties = archive->can_extract = archive->can_add = archive->has_test = TRUE;
 
34
        archive->has_sfx = FALSE;
29
35
        archive->dummy_size = 0;
30
36
        archive->nr_of_files = 0;
31
 
        archive->nr_of_dirs = 0;
32
37
        archive->format ="LHA";
33
 
        archive->parse_output = LhaOpen;
34
 
        SpawnAsyncProcess ( archive , command , 0, 0);
 
38
        archive->nc = 6;
 
39
        archive->parse_output = xa_get_lha_line_content;
 
40
        xa_spawn_async_process (archive,command);
35
41
        g_free (command);
36
42
 
37
43
        if (archive->child_pid == 0)
38
44
                return;
39
45
 
40
 
        char *names[]= {(_("Filename")),(_("Permissions")),(_("UID/GID")),(_("Size")),(_("Ratio")),(_("Timestamp"))};
41
 
        GType types[]= {G_TYPE_STRING,G_TYPE_STRING,G_TYPE_STRING,G_TYPE_UINT64,G_TYPE_STRING,G_TYPE_STRING};
42
 
        xa_create_liststore(6, names, (GType *)types, archive);
 
46
        GType types[]= {GDK_TYPE_PIXBUF,G_TYPE_STRING,G_TYPE_STRING,G_TYPE_STRING,G_TYPE_STRING,G_TYPE_UINT64,G_TYPE_STRING,G_TYPE_POINTER};
 
47
        archive->column_types = g_malloc0(sizeof(types));
 
48
        for (i = 0; i < 8; i++)
 
49
                archive->column_types[i] = types[i];
 
50
                
 
51
        char *names[]= {(_("Points to")),(_("Permissions")),(_("UID/GID")),(_("Size")),(_("Ratio")),(_("Timestamp"))};
 
52
        xa_create_liststore (archive,names);
43
53
}
44
54
 
45
 
static gboolean LhaOpen (GIOChannel *ioc, GIOCondition cond, gpointer data)
 
55
void xa_get_lha_line_content (gchar *line, gpointer data)
46
56
{
47
57
        XArchive *archive = data;
48
 
        GtkTreeIter iter;
49
 
        gchar *permissions = NULL;
50
 
        gchar *owner = NULL;
51
 
        gchar *ratio = NULL;
52
 
        gchar *timestamp = NULL;
53
 
        gchar *size = NULL;
54
 
        gchar *line = NULL;
55
 
        gchar *filename = NULL;
56
 
        GIOStatus status = G_IO_STATUS_NORMAL;
57
 
        unsigned short int a = 0, n = 0, num;
 
58
        XEntry *entry = NULL;
 
59
        gpointer item[6];
 
60
        unsigned int linesize,n,a;
 
61
        gboolean dir = FALSE;
 
62
        gchar *filename;
58
63
 
59
 
        if (cond & (G_IO_IN | G_IO_PRI) )
 
64
        if (last_line)
 
65
                return;
 
66
        if (jump_header == FALSE)
60
67
        {
61
 
                // We don't need the first two lines. No actual data there.
62
 
                g_io_channel_read_line(ioc, &line, NULL, NULL, NULL);
63
 
                if (line != NULL)
64
 
                        g_free (line);
65
 
 
66
 
                g_io_channel_read_line(ioc, &line, NULL, NULL, NULL);
67
 
                if (line != NULL)
68
 
                        g_free (line);
69
 
                do
 
68
                if (line[0] == '-')
70
69
                {
71
 
                        status = g_io_channel_read_line(ioc, &line, NULL, NULL, NULL);
72
 
                        if (line == NULL || (strncmp(line, "---------- -", 12) == 0))
73
 
                                break;
74
 
                        gtk_list_store_append (archive->liststore, &iter);
75
 
 
76
 
                        permissions = g_strndup(line, 10);
77
 
                        gtk_list_store_set (archive->liststore, &iter,1,permissions,-1);
78
 
                        if (strstr(permissions, "d") == NULL)
79
 
                                archive->nr_of_files++;
80
 
                        else
81
 
                                archive->nr_of_dirs++;
82
 
                        g_free (permissions);
83
 
 
84
 
                        owner = g_strndup(&line[11], 11);
85
 
                        gtk_list_store_set (archive->liststore, &iter,2,owner,-1);
86
 
                        g_free (owner);
87
 
 
88
 
                        num = strlen(line);
89
 
                        for(n = 23;n < num;n++)
90
 
                        if(line[n] != ' ')
91
 
                                break;
92
 
 
93
 
                        a = n;
94
 
                        for(;n < num;n++)
95
 
                        if(line[n] == ' ')
96
 
                                break;
97
 
 
98
 
                        size = g_strndup(&line[a], n - a);
99
 
                        gtk_list_store_set (archive->liststore, &iter,3,strtoll(size,NULL,0),-1);
100
 
                        archive->dummy_size += strtoll(size,NULL,0);
101
 
                        g_free(size);
102
 
 
103
 
                        ratio = g_strndup(&line[31], 7);
104
 
                        gtk_list_store_set (archive->liststore, &iter,4,ratio,-1);
105
 
                        g_free (ratio);
106
 
 
107
 
                        timestamp = g_strndup(&line[38], 13);
108
 
                        gtk_list_store_set (archive->liststore, &iter,5,timestamp,-1);
109
 
                        g_free (timestamp);
110
 
 
111
 
                        filename = g_strndup(&line[51], num - 51 - 1);
112
 
                        gtk_list_store_set (archive->liststore, &iter,0,filename,-1);
113
 
                        g_free (filename);
114
 
 
115
 
                        g_free(line);
 
70
                        jump_header = TRUE;
 
71
                        return;
116
72
                }
117
 
                while (status == G_IO_STATUS_NORMAL);
118
 
 
119
 
                if (status == G_IO_STATUS_ERROR || status == G_IO_STATUS_EOF)
120
 
                goto done;
121
 
        }
122
 
        else if (cond & (G_IO_ERR | G_IO_HUP | G_IO_NVAL) )
123
 
        {
124
 
done:
125
 
                g_io_channel_shutdown(ioc, TRUE, NULL);
126
 
                g_io_channel_unref(ioc);
127
 
                gtk_tree_view_set_model (GTK_TREE_VIEW(archive->treeview), archive->model);
128
 
                g_object_unref (archive->model);
129
 
                return FALSE;
130
 
        }
131
 
        return TRUE;
132
 
}
 
73
                return;
 
74
        }
 
75
        if (strncmp(line,"----",4) == 0)
 
76
        {
 
77
                last_line = TRUE;
 
78
                return;
 
79
        }
 
80
        linesize = strlen(line);
 
81
        archive->nr_of_files++;
 
82
 
 
83
        /* Permission */
 
84
        line[10] = '\0';
 
85
        item[1] = line;
 
86
        if(line[0] == 'd')
 
87
                dir = TRUE;
 
88
 
 
89
        /* UID/GID */
 
90
        line[22] = '\0';
 
91
        item[2] = line + 11;
 
92
 
 
93
        //TODO verify the len of the size column with a big archive
 
94
        /* Size */
 
95
        for(n = 23;n < linesize;n++)
 
96
        if(line[n] != ' ')
 
97
                break;
 
98
 
 
99
        a = n;
 
100
        for(;n < linesize;n++)
 
101
        if(line[n] == ' ')
 
102
                break;
 
103
 
 
104
        line[a+(n-a)] = '\0';
 
105
        item[3] = line + a;
 
106
        archive->dummy_size += g_ascii_strtoull(item[3],NULL,0);
 
107
 
 
108
    /* Ratio */
 
109
    line[37] = '\0';
 
110
    item[4] = line + 31;
 
111
 
 
112
    /* Timestamp */
 
113
    line[50] = '\0';
 
114
    item[5] = line + 38;
 
115
 
 
116
        line[(linesize- 1)] = '\0';
 
117
        filename = line + 51;
 
118
 
 
119
        /* Symbolic link */
 
120
        gchar *temp = g_strrstr (filename,"->"); 
 
121
        if (temp) 
 
122
        {
 
123
                gint len = strlen(filename) - strlen(temp);
 
124
                item[0] = (filename +=3) + len;
 
125
                filename -= 3;
 
126
                filename[strlen(filename) - strlen(temp)-1] = '\0';
 
127
        }
 
128
        else
 
129
                item[0] = NULL;
 
130
 
 
131
        entry = xa_set_archive_entries_for_each_row (archive,filename,item);
 
132
}
 
133
 
 
134
gboolean isLha ( FILE *ptr )
 
135
{
 
136
        unsigned char magic[2];
 
137
        fseek(ptr, 0, SEEK_SET);
 
138
        if(fseek(ptr, 19, SEEK_CUR) < 0)
 
139
                return FALSE;
 
140
        if(fread(magic, 1, 2, ptr) == 0)
 
141
                return FALSE;
 
142
 
 
143
        if(magic[0] == 0x20 && magic[1] <= 0x03)
 
144
                return TRUE;
 
145
        else
 
146
                return FALSE;
 
147
}
 
148
 
 
149
void xa_lha_delete (XArchive *archive,GSList *names)
 
150
{
 
151
        gchar *command,*e_filename = NULL;
 
152
        GSList *list = NULL,*_names;
 
153
        GString *files = g_string_new("");
 
154
 
 
155
        _names = names;
 
156
        while (_names)
 
157
        {
 
158
                e_filename  = xa_escape_filename((gchar*)_names->data,"$'`\"\\!?* ()[]&|:;<>#");
 
159
                g_string_prepend (files,e_filename);
 
160
                g_string_prepend_c (files,' ');
 
161
                _names = _names->next;
 
162
        }
 
163
        g_slist_foreach(names,(GFunc)g_free,NULL);
 
164
        g_slist_free(names);
 
165
 
 
166
        command = g_strconcat ("lha d " , archive->escaped_path," ",files->str,NULL);
 
167
        g_string_free(files,TRUE);
 
168
        list = g_slist_append(list,command);
 
169
 
 
170
        xa_run_command (archive,list);
 
171
        if (archive->status == XA_ARCHIVESTATUS_DELETE)
 
172
                xa_reload_archive_content(archive);
 
173
}
 
174
 
 
175
void xa_lha_add (XArchive *archive,GString *files,gchar *compression_string)
 
176
{
 
177
        GSList *list = NULL;
 
178
        gchar *command = NULL;
 
179
 
 
180
        if (archive->location_entry_path != NULL)
 
181
                archive->working_dir = g_strdup(archive->tmp);
 
182
 
 
183
        if (compression_string == NULL)
 
184
                compression_string = "5";
 
185
        command = g_strconcat( "lha ",
 
186
                                                        archive->remove_files ? "m" : "a",
 
187
                                                        archive->update ? "u" : "",
 
188
                                                        "o",compression_string,
 
189
                                                        " ",
 
190
                                                        archive->escaped_path,
 
191
                                                        files->str,NULL);
 
192
        g_string_free(files,TRUE);
 
193
        list = g_slist_append(list,command);
 
194
 
 
195
        xa_run_command (archive,list);
 
196
        xa_reload_archive_content(archive);
 
197
}
 
198
 
 
199
gboolean xa_lha_extract(XArchive *archive,GSList *files)
 
200
{
 
201
        gchar *command,*e_filename = NULL;
 
202
        GSList *list = NULL,*_files = NULL;
 
203
        GString *names = g_string_new("");
 
204
        gboolean result = FALSE;
 
205
 
 
206
        _files = files;
 
207
        while (_files)
 
208
        {
 
209
                e_filename  = xa_escape_filename((gchar*)_files->data,"$'`\"\\!?* ()[]&|:;<>#");
 
210
                g_string_prepend (names,e_filename);
 
211
                g_string_prepend_c (names,' ');
 
212
                _files = _files->next;
 
213
        }
 
214
        g_slist_foreach(_files,(GFunc)g_free,NULL);
 
215
        g_slist_free(_files);
 
216
 
 
217
        command = g_strconcat ("lha ",  archive->full_path ? "x" : "xi",
 
218
                                                                        archive->overwrite ? "f" : "", "w=",
 
219
                                                                        archive->extraction_path," ",archive->escaped_path,names->str,NULL);
 
220
        g_string_free(names,TRUE);
 
221
        list = g_slist_append(list,command);
 
222
 
 
223
        result = xa_run_command (archive,list);
 
224
        return result;
 
225
}
 
226
 
 
227
void xa_lha_test (XArchive *archive)
 
228
{
 
229
        gchar *command = NULL;
 
230
        GSList *list = NULL;
 
231
 
 
232
        archive->status = XA_ARCHIVESTATUS_TEST;
 
233
        command = g_strconcat ("lha t ",archive->escaped_path,NULL);
 
234
 
 
235
        list = g_slist_append(list,command);
 
236
        xa_run_command (archive,list);
 
237
 }