xref: /aosp_15_r20/external/squashfs-tools/squashfs-tools/restore.c (revision 79398b2563bcbbbab54656397863972d8fa68df1)
1*79398b25SAndroid Build Coastguard Worker /*
2*79398b25SAndroid Build Coastguard Worker  * Create a squashfs filesystem.  This is a highly compressed read only
3*79398b25SAndroid Build Coastguard Worker  * filesystem.
4*79398b25SAndroid Build Coastguard Worker  *
5*79398b25SAndroid Build Coastguard Worker  * Copyright (c) 2013, 2014
6*79398b25SAndroid Build Coastguard Worker  * Phillip Lougher <[email protected]>
7*79398b25SAndroid Build Coastguard Worker  *
8*79398b25SAndroid Build Coastguard Worker  * This program is free software; you can redistribute it and/or
9*79398b25SAndroid Build Coastguard Worker  * modify it under the terms of the GNU General Public License
10*79398b25SAndroid Build Coastguard Worker  * as published by the Free Software Foundation; either version 2,
11*79398b25SAndroid Build Coastguard Worker  * or (at your option) any later version.
12*79398b25SAndroid Build Coastguard Worker  *
13*79398b25SAndroid Build Coastguard Worker  * This program is distributed in the hope that it will be useful,
14*79398b25SAndroid Build Coastguard Worker  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15*79398b25SAndroid Build Coastguard Worker  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16*79398b25SAndroid Build Coastguard Worker  * GNU General Public License for more details.
17*79398b25SAndroid Build Coastguard Worker  *
18*79398b25SAndroid Build Coastguard Worker  * You should have received a copy of the GNU General Public License
19*79398b25SAndroid Build Coastguard Worker  * along with this program; if not, write to the Free Software
20*79398b25SAndroid Build Coastguard Worker  * Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
21*79398b25SAndroid Build Coastguard Worker  *
22*79398b25SAndroid Build Coastguard Worker  * restore.c
23*79398b25SAndroid Build Coastguard Worker  */
24*79398b25SAndroid Build Coastguard Worker 
25*79398b25SAndroid Build Coastguard Worker #include <pthread.h>
26*79398b25SAndroid Build Coastguard Worker #include <sys/ioctl.h>
27*79398b25SAndroid Build Coastguard Worker #include <unistd.h>
28*79398b25SAndroid Build Coastguard Worker #include <signal.h>
29*79398b25SAndroid Build Coastguard Worker #include <sys/time.h>
30*79398b25SAndroid Build Coastguard Worker #include <stdio.h>
31*79398b25SAndroid Build Coastguard Worker #include <math.h>
32*79398b25SAndroid Build Coastguard Worker #include <stdarg.h>
33*79398b25SAndroid Build Coastguard Worker #include <errno.h>
34*79398b25SAndroid Build Coastguard Worker #include <stdlib.h>
35*79398b25SAndroid Build Coastguard Worker #include <dirent.h>
36*79398b25SAndroid Build Coastguard Worker #include <sys/types.h>
37*79398b25SAndroid Build Coastguard Worker #include <sys/stat.h>
38*79398b25SAndroid Build Coastguard Worker 
39*79398b25SAndroid Build Coastguard Worker #include "caches-queues-lists.h"
40*79398b25SAndroid Build Coastguard Worker #include "squashfs_fs.h"
41*79398b25SAndroid Build Coastguard Worker #include "mksquashfs.h"
42*79398b25SAndroid Build Coastguard Worker #include "error.h"
43*79398b25SAndroid Build Coastguard Worker #include "progressbar.h"
44*79398b25SAndroid Build Coastguard Worker #include "info.h"
45*79398b25SAndroid Build Coastguard Worker 
46*79398b25SAndroid Build Coastguard Worker #define FALSE 0
47*79398b25SAndroid Build Coastguard Worker #define TRUE 1
48*79398b25SAndroid Build Coastguard Worker 
49*79398b25SAndroid Build Coastguard Worker extern pthread_t reader_thread, writer_thread, main_thread;
50*79398b25SAndroid Build Coastguard Worker extern pthread_t *deflator_thread, *frag_deflator_thread, *frag_thread;
51*79398b25SAndroid Build Coastguard Worker extern struct queue *to_deflate, *to_writer, *to_frag, *to_process_frag;
52*79398b25SAndroid Build Coastguard Worker extern struct seq_queue *to_main;
53*79398b25SAndroid Build Coastguard Worker extern void restorefs();
54*79398b25SAndroid Build Coastguard Worker extern int processors;
55*79398b25SAndroid Build Coastguard Worker 
56*79398b25SAndroid Build Coastguard Worker static int interrupted = 0;
57*79398b25SAndroid Build Coastguard Worker static pthread_t restore_thread;
58*79398b25SAndroid Build Coastguard Worker 
restore_thrd(void * arg)59*79398b25SAndroid Build Coastguard Worker void *restore_thrd(void *arg)
60*79398b25SAndroid Build Coastguard Worker {
61*79398b25SAndroid Build Coastguard Worker 	sigset_t sigmask, old_mask;
62*79398b25SAndroid Build Coastguard Worker 	int i, sig;
63*79398b25SAndroid Build Coastguard Worker 
64*79398b25SAndroid Build Coastguard Worker 	sigemptyset(&sigmask);
65*79398b25SAndroid Build Coastguard Worker 	sigaddset(&sigmask, SIGINT);
66*79398b25SAndroid Build Coastguard Worker 	sigaddset(&sigmask, SIGTERM);
67*79398b25SAndroid Build Coastguard Worker 	sigaddset(&sigmask, SIGUSR1);
68*79398b25SAndroid Build Coastguard Worker 	pthread_sigmask(SIG_BLOCK, &sigmask, &old_mask);
69*79398b25SAndroid Build Coastguard Worker 
70*79398b25SAndroid Build Coastguard Worker 	while(1) {
71*79398b25SAndroid Build Coastguard Worker 		sigwait(&sigmask, &sig);
72*79398b25SAndroid Build Coastguard Worker 
73*79398b25SAndroid Build Coastguard Worker 		if((sig == SIGINT || sig == SIGTERM) && !interrupted) {
74*79398b25SAndroid Build Coastguard Worker 			ERROR("Interrupting will restore original "
75*79398b25SAndroid Build Coastguard Worker 				"filesystem!\n");
76*79398b25SAndroid Build Coastguard Worker                 	ERROR("Interrupt again to quit\n");
77*79398b25SAndroid Build Coastguard Worker 			interrupted = TRUE;
78*79398b25SAndroid Build Coastguard Worker 			continue;
79*79398b25SAndroid Build Coastguard Worker 		}
80*79398b25SAndroid Build Coastguard Worker 
81*79398b25SAndroid Build Coastguard Worker 		/* kill main thread/worker threads and restore */
82*79398b25SAndroid Build Coastguard Worker 		set_progressbar_state(FALSE);
83*79398b25SAndroid Build Coastguard Worker 		disable_info();
84*79398b25SAndroid Build Coastguard Worker 
85*79398b25SAndroid Build Coastguard Worker 		/* first kill the reader thread */
86*79398b25SAndroid Build Coastguard Worker 		pthread_cancel(reader_thread);
87*79398b25SAndroid Build Coastguard Worker 		pthread_join(reader_thread, NULL);
88*79398b25SAndroid Build Coastguard Worker 
89*79398b25SAndroid Build Coastguard Worker 		/*
90*79398b25SAndroid Build Coastguard Worker 		 * then flush the reader to deflator thread(s) output queue.
91*79398b25SAndroid Build Coastguard Worker 		 * The deflator thread(s) will idle
92*79398b25SAndroid Build Coastguard Worker 		 */
93*79398b25SAndroid Build Coastguard Worker 		queue_flush(to_deflate);
94*79398b25SAndroid Build Coastguard Worker 
95*79398b25SAndroid Build Coastguard Worker 		/* now kill the deflator thread(s) */
96*79398b25SAndroid Build Coastguard Worker 		for(i = 0; i < processors; i++)
97*79398b25SAndroid Build Coastguard Worker 			pthread_cancel(deflator_thread[i]);
98*79398b25SAndroid Build Coastguard Worker 		for(i = 0; i < processors; i++)
99*79398b25SAndroid Build Coastguard Worker 			pthread_join(deflator_thread[i], NULL);
100*79398b25SAndroid Build Coastguard Worker 
101*79398b25SAndroid Build Coastguard Worker 		/*
102*79398b25SAndroid Build Coastguard Worker 		 * then flush the reader to process fragment thread(s) output
103*79398b25SAndroid Build Coastguard Worker 		 * queue.  The process fragment thread(s) will idle
104*79398b25SAndroid Build Coastguard Worker 		 */
105*79398b25SAndroid Build Coastguard Worker 		queue_flush(to_process_frag);
106*79398b25SAndroid Build Coastguard Worker 
107*79398b25SAndroid Build Coastguard Worker 		/* now kill the process fragment thread(s) */
108*79398b25SAndroid Build Coastguard Worker 		for(i = 0; i < processors; i++)
109*79398b25SAndroid Build Coastguard Worker 			pthread_cancel(frag_thread[i]);
110*79398b25SAndroid Build Coastguard Worker 		for(i = 0; i < processors; i++)
111*79398b25SAndroid Build Coastguard Worker 			pthread_join(frag_thread[i], NULL);
112*79398b25SAndroid Build Coastguard Worker 
113*79398b25SAndroid Build Coastguard Worker 		/*
114*79398b25SAndroid Build Coastguard Worker 		 * then flush the reader/deflator/process fragment to main
115*79398b25SAndroid Build Coastguard Worker 		 * thread output queue.  The main thread will idle
116*79398b25SAndroid Build Coastguard Worker 		 */
117*79398b25SAndroid Build Coastguard Worker 		seq_queue_flush(to_main);
118*79398b25SAndroid Build Coastguard Worker 
119*79398b25SAndroid Build Coastguard Worker 		/* now kill the main thread */
120*79398b25SAndroid Build Coastguard Worker 		pthread_cancel(main_thread);
121*79398b25SAndroid Build Coastguard Worker 		pthread_join(main_thread, NULL);
122*79398b25SAndroid Build Coastguard Worker 
123*79398b25SAndroid Build Coastguard Worker 		/* then flush the main thread to fragment deflator thread(s)
124*79398b25SAndroid Build Coastguard Worker 		 * queue.  The fragment deflator thread(s) will idle
125*79398b25SAndroid Build Coastguard Worker 		 */
126*79398b25SAndroid Build Coastguard Worker 		queue_flush(to_frag);
127*79398b25SAndroid Build Coastguard Worker 
128*79398b25SAndroid Build Coastguard Worker 		/* now kill the fragment deflator thread(s) */
129*79398b25SAndroid Build Coastguard Worker 		for(i = 0; i < processors; i++)
130*79398b25SAndroid Build Coastguard Worker 			pthread_cancel(frag_deflator_thread[i]);
131*79398b25SAndroid Build Coastguard Worker 		for(i = 0; i < processors; i++)
132*79398b25SAndroid Build Coastguard Worker 			pthread_join(frag_deflator_thread[i], NULL);
133*79398b25SAndroid Build Coastguard Worker 
134*79398b25SAndroid Build Coastguard Worker 		/*
135*79398b25SAndroid Build Coastguard Worker 		 * then flush the main thread/fragment deflator thread(s)
136*79398b25SAndroid Build Coastguard Worker 		 * to writer thread queue.  The writer thread will idle
137*79398b25SAndroid Build Coastguard Worker 		 */
138*79398b25SAndroid Build Coastguard Worker 		queue_flush(to_writer);
139*79398b25SAndroid Build Coastguard Worker 
140*79398b25SAndroid Build Coastguard Worker 		/* now kill the writer thread */
141*79398b25SAndroid Build Coastguard Worker 		pthread_cancel(writer_thread);
142*79398b25SAndroid Build Coastguard Worker 		pthread_join(writer_thread, NULL);
143*79398b25SAndroid Build Coastguard Worker 
144*79398b25SAndroid Build Coastguard Worker 		TRACE("All threads cancelled\n");
145*79398b25SAndroid Build Coastguard Worker 
146*79398b25SAndroid Build Coastguard Worker 		restorefs();
147*79398b25SAndroid Build Coastguard Worker 	}
148*79398b25SAndroid Build Coastguard Worker }
149*79398b25SAndroid Build Coastguard Worker 
150*79398b25SAndroid Build Coastguard Worker 
init_restore_thread()151*79398b25SAndroid Build Coastguard Worker pthread_t *init_restore_thread()
152*79398b25SAndroid Build Coastguard Worker {
153*79398b25SAndroid Build Coastguard Worker 	pthread_create(&restore_thread, NULL, restore_thrd, NULL);
154*79398b25SAndroid Build Coastguard Worker 	return &restore_thread;
155*79398b25SAndroid Build Coastguard Worker }
156