9 #symlinks_in_snapshot=[]
10 #unknown_in_snapshot=[]
11 #is_mount_in_snapshot=[]
12 def check_for_yaffs_errors(output):
16 error=yaffs_get_error()
17 debug_message("error######################################",0)
18 debug_message(("error code", error), 0)
20 def debug_message(message, debug_level):
21 """notew that debug level 0 will always be printed"""
22 """level 0 error messages"""
23 """level 1 basic tasks are shown(creating, deleating,ect)"""
24 """level 2 all process are shown"""
25 """level 3 shows minor tasks such as join_paths, ect"""
26 """level 4 is used for bug hunting and shows each step in detail"""
27 if current_debug_level>=debug_level:
28 # for i in range(0, len(message)):
32 def join_paths(path1, path2):
34 if path1[len(path1)-1]=="/"and path2[0]=="/":
36 elif path1[len(path1)-1]!="/"and path2[0]!="/":
42 debug_message(("adding path ", path1, " to ", path2, " resulting path: ", new_path), 3)
45 def subtract_paths(path1, path2):
46 if len(path1)>len(path2):
47 if path1[len(path1)-1]!="/":
49 if path2[len(path2)-1]!="/":
51 debug_message("the two path1 is longer than path2 and can therefore be subtracted.", 4)
52 ##if the two paths are diretly subtractable
53 if path1[0:len (path2)-1]==path2:
54 debug_message("the two paths are direcly subtractable", 4)
55 new_path=path1[len(path2):]
56 elif path1[1:len (path2)-1]==path2:
57 debug_message("the path1 has one more charecter at the begining. assuming that the first chareter is a slash", 4)##fix this assumption.
58 new_path=path1[len(path2)+1:]
59 elif path1[1:len (path2)]==path2[1:]:
60 debug_message("the path2 has one more charecter at the begining. assuming that the first chareter is a slash", 4)##fix this assumption.
62 new_path=path1[len(path2)-1:]
64 debug_message("error:could not subtract paths", 0)
65 debug_message( ("paths do not match:"+ path1+ " "+path2), 0)
68 debug_message( ("cannot subtract path2(:", path2, ") from path1(", path1, ")because path 2 is too long"), 0)
71 debug_message(("subtracting paths ", path2, " from ", path1, " resulting path: ", new_path), 3)
74 def create_file(file):
75 debug_message( "\n \n \n", 2)
76 file_path= join_paths(yaffs_root_dir_path, file["path"][len(path):])
77 debug_message( ("creating file:", file_path), 2)
78 debug_message (("mode", file["mode"]), 2)
79 debug_message("opening file",2)
80 # yaffs_ls(file["path"])
82 ##if there is already a file in yaffs then remove the file . this is to prevent yaffs from opening a nd writing to a read only file
83 if yaffs_access(file_path, 0)==0:##the 0 means does it exist.
84 debug_message ("file already exists in yaffs", 2)
85 output=yaffs_unlink(file_path)
86 debug_message(("unlinking", file_path, output), 2)
87 check_for_yaffs_errors(output)
89 current_handle=yaffs_open(file_path, yaffs_O_CREAT | yaffs_O_TRUNC| yaffs_O_RDWR, yaffs_S_IREAD | yaffs_S_IWRITE) ##opens a file with mode set to write
90 debug_message(("current_handle", current_handle), 2)
91 data_file=open(file["path"], "r")
92 output=yaffs_lseek(current_handle, 0, 0)
94 debug_message("error with yaffs lseeking", 2)
96 check_for_yaffs_errors(output)
97 data_to_be_written= data_file.read()
100 length_of_file=len(data_to_be_written)
101 debug_message (("length of data to be written",length_of_file), 2)
102 output=yaffs_write(current_handle,data_to_be_written , length_of_file)
104 debug_message(( "writing file:", output), 2)
106 debug_message(( "error writing file:", output), 0)
107 check_for_yaffs_errors(output)
108 output=yaffs_ftruncate(current_handle, length_of_file)
110 debug_message(( "truncating file:", output), 2)
112 debug_message(( "error truncating file:", output), 0)
113 check_for_yaffs_errors(output)
114 output=yaffs_close(current_handle)
116 debug_message(( "closing file:", output), 2)
118 debug_message(( "error closing file:", output), 0)
119 check_for_yaffs_errors(output)
120 ##changes the mode of the yaffs file to be the same as the scanned file
121 yaffs_chmod(file_path, file["mode"]);
123 debug_message(( "chmoding file:", output), 2)
125 debug_message(( "error chmoding file:", output), 0)
126 check_for_yaffs_errors(output)
130 def create_dir(dir, scanned_path, yaffs_path):
131 debug_message( "\n \n \n", 2)
132 absolute_dir_path=join_paths(yaffs_path, subtract_paths(dir["path"],scanned_path))
133 debug_message( ("creating dir:", absolute_dir_path), 2)
134 debug_message (("mode(in octal", oct(dir["mode"])), 2)
137 ##if there is already a dir in yaffs then remove the dir . this is to clean the yaffs folder if it already exists.
138 if yaffs_access(absolute_dir_path, 0)==0:##the 0 means does it exist.
139 debug_message ("folder already exists in yaffs", 2)
140 output=yaffs_unlink(absolute_dir_path)
141 debug_message(("unlinking", absolute_dir_path, output), 2)
142 check_for_yaffs_errors(output)
144 ##shis is a bug in yaffs which will not make a dir if there is a slash on the end
145 if absolute_dir_path[len(absolute_dir_path)-1]=="/":
146 absolute_dir_path=absolute_dir_path[0:len(absolute_dir_path)-1]
147 debug_message (("path has slash on the end. removing slash new path is:",absolute_dir_path) , 4)
149 output=yaffs_mkdir(absolute_dir_path, dir["mode"] )
151 debug_message(( "creating dir:", output), 2)
153 debug_message(( "error creating dir:", output), 0)
154 check_for_yaffs_errors(output)
159 def remove_file_from_path(path):
161 for i in range(0, len(path)):
164 new_path=path[:slash_id[len(slash_id)-1]]
165 debug_message( ("removed file from path", new_path), 2)
168 def is_dir_hidden(dir):
169 """this code tests if a directory is hidden (has a ./<name> format) and returns true if it is hidden"""
171 for i in range(0, len(dir)):
175 if dir[slash_id[len(slash_id)-1]+1]==".":
180 def scan_dir(path, search_hidden_directories=True, ):
181 """this function scans all of the files and directories in a directory. The function then calls its self on any of the directories that it found. this causes it to build up a tree of all the files and directories """
183 symlinks_in_snapshot=[]
185 dir_in_current_dir=[]
186 unknown_in_snapshot=[]
187 if os.path.exists(path)==False:
188 debug_message ("error#############################",0)
189 debug_message (("path:", path, " doesnot exist"), 0)
191 dir_snapshot=os.listdir(path)
192 for i in range(0, len(dir_snapshot)):
194 current_snapshot=os.path.join(path, dir_snapshot[i])
195 debug_message (("current snapshot:", current_snapshot), 2)
196 isDir=os.path.isdir(current_snapshot)
197 isFile=os.path.isfile(current_snapshot)
198 isLink=os.path.islink(current_snapshot)
199 isMount=os.path.ismount(current_snapshot)
201 stat=os.lstat(current_snapshot)
203 ##note the order of these if and elif statemens is importaint since a file can be symbloic link and a file
205 if search_hidden_directories==True or (is_dir_hidden(current_snapshot) ==False or search_hidden_directories==True ) :
206 # st_mode ##mode of the folder read/write ect
207 dir_in_snapshot.append({"path":current_snapshot, "mode":stat.st_mode})
208 dir_in_current_dir.append(current_snapshot)
210 debug_message( ("file is hidden so it is ingored", current_snapshot,), 1)
213 ##for some reason the os.readlink only gives the target link realative to the directory which the symbloic link is in. change this into a absolute path
215 x=remove_file_from_path(x)
216 target=join_paths(x,os.readlink(current_snapshot) )
217 symlinks_in_snapshot.append({"path":current_snapshot, "target":target})
220 # stat.st_ino ##inode number
221 # st_nlink ##number of hard links to this file
222 # st_size ##size of file
223 files_in_snapshot.append({"path":current_snapshot, "inode": stat.st_ino, "size":stat.st_size, "num_of_hardlinks":stat.st_nlink, "mode":stat.st_mode})
226 # is_mount_in_snapshot.append(current_snapshot)
228 unknown_in_snapshot.append(current_snapshot)
230 for i in range(0, len(dir_in_current_dir)):
231 scan_dir(dir_in_current_dir[i])
232 return (files_in_snapshot, dir_in_snapshot, symlinks_in_snapshot, unknown_in_snapshot)
234 ##def print_scanned_dir_list():
235 ## global files_in_snapshot
236 ## global symlinks_in_snapshot
237 ## print( "scanning dir", 2)
240 ## for i in range(0, len(files_in_snapshot)):
241 ## if files_in_snapshot[i]["num_of_hardlinks"]>1:
242 ## print "inode",files_in_snapshot[i]["inode"],"size",files_in_snapshot[i]["size"],"path:", files_in_snapshot[i]["path"], " num of hard links", files_in_snapshot[i]["num_of_hardlinks"]
245 ## print "inode",files_in_snapshot[i]["inode"],"size",files_in_snapshot[i]["size"],"path:", files_in_snapshot[i]["path"]
246 ### current_open_file=open(files_in_snapshot[i], "r")
247 ### #current_open_file.f.read(3)
248 ### lines_in_file=current_open_file.readlines()
249 ### #use for loop to write code into yaffs file
250 ### print "number of line of code:", len(lines_in_file)
251 ### print current_open_file
252 ## for i in range(0, len(symlinks_in_snapshot)):
253 ## print "symlinks in snapshot:", symlinks_in_snapshot[i]
254 ## for i in range(0, len(dir_in_snapshot)):
255 ## print "directories in snapshot:", dir_in_snapshot[i]
256 ## for i in range(0, len(unknown_in_snapshot)):
257 ## print "unknown objects in snapshot:", unknown_in_snapshot[i]
261 def copy_scanned_files_into_yaffs(files_in_snapshot, dir_in_snapshot, symlinks_in_snapshot, unknown_in_snapshot, path, yaffs_root_dir_path="/yaffs2/", yaffs_mount_point_path="/yaffs2/" ):
262 #files_in_snapshot, dir_in_snapshot, symlinks_in_snapshot, unknown_in_snapshot
263 #########################################copy directories into yaffs so the files can be created in these directories
264 debug_message("making directories in yaffs", 1)
265 if yaffs_root_dir_path!=yaffs_mount_point_path:
267 debug_message("making directories to the place in yaffs where the directories will copied to", 2)
268 root_branch_path=subtract_paths(yaffs_root_dir_path, yaffs_mount_point_path)
269 for i in range(0, len(root_branch_path)):
271 if root_branch_path[i]=="/" and i != 0:
273 debug_message(("slash_id", slash_id),4)
274 for i in range(0, len(slash_id)):
275 create_dir({"path":root_branch_path[:slash_id[i]], "mode": yaffs_S_IREAD | yaffs_S_IWRITE}, "/", yaffs_mount_point_path)
277 for i in range(0, len(dir_in_snapshot)):
278 create_dir(dir_in_snapshot[i], path, yaffs_root_dir_path)
282 #########################################copy file into yaffs
283 debug_message("copying scanned files into yaffs", 1)
287 debug_message("files to be copyied into yaffs", 2)
288 for a in range(0, len(files_in_snapshot)):
289 debug_message(files_in_snapshot[a], 2)
290 debug_message("\n\n\n", 2)
291 for i in range(0, len(files_in_snapshot)):
293 if files_in_snapshot[i]["num_of_hardlinks"]>1 and files_in_snapshot[i]["inode"] not in inode_blacklist :
294 debug_message("found a hard link", 2)
295 debug_message(("inode",files_in_snapshot[i]["inode"],"size",files_in_snapshot[i]["size"],"path:", files_in_snapshot[i]["path"], " num of hard links", files_in_snapshot[i]["num_of_hardlinks"] ), 2)
296 for a in range(0, len(files_in_snapshot) ) :
297 if files_in_snapshot[a]["inode"] ==files_in_snapshot[i]["inode"] :
298 ##and os.path.isfile(files_in_snapshot[i])
299 debug_message(("found this file which matches inode",files_in_snapshot[a]), 2)
300 list.append(files_in_snapshot[a])
301 debug_message(("length of list", len(list)), 2)
302 if len(list)==files_in_snapshot[i]["num_of_hardlinks"]:
304 for a in range(0, len(list)):
305 debug_message(list[a], 2)
306 ##add inode to blacklist. all of the indoes in the list should be the same.
307 inode_blacklist.append(list[0]["inode"])
308 ##create a file from the first hardlink.
310 target_path=yaffs_root_dir_path+list[0]["path"][len(path):]
311 for i in range(1, len(list)):
312 debug_message("creating_symlink", 2)
313 debug_message(("target path", target_path), 2)
314 hardlink_path=yaffs_root_dir_path+list[i]["path"][len(path):]
315 debug_message(("hardlink path", hardlink_path), 2)
316 output=yaffs_link(target_path,hardlink_path)
317 debug_message(("creating hardlink:", list[i]["path"], "output:", output), 1)
318 elif files_in_snapshot[i]["inode"] not in inode_blacklist :
319 create_file(files_in_snapshot[i])
322 ############################copy symlinks into yaffs
324 for i in range(0, len(symlinks_in_snapshot)):
325 debug_message(("symlinks in snapshot:", symlinks_in_snapshot[i]), 2)
326 target_path=join_paths(yaffs_root_dir_path, subtract_paths(symlinks_in_snapshot[i]["target"], path))
327 new_path=join_paths(yaffs_root_dir_path, subtract_paths(symlinks_in_snapshot[i]["path"], path))
328 output=yaffs_symlink(target_path, new_path)
329 debug_message(("created symlink",new_path , " > ", target_path, " output:", output), 1)
330 ##yaffs_symlink(const YCHAR *oldpath, const YCHAR *newpath);
333 for i in range(0, len(unknown_in_snapshot)):
334 debug_message( ("unknown object in snapshot:", unknown_in_snapshot[i]), 0)
337 def import_into_yaffs(file_path, yaffs_path="/yaffs2/", debug_level=1, copy_hidden_dir=True ,new_yaffs_trace_val=0 ):
338 # global current_debug_level
339 # global search_hidden_directories
340 # global yaffs_root_dir_path
343 # current_debug_level=debug_level
344 # search_hidden_directories=copy_hidden_dir
345 # yaffs_root_dir_path=yaffs_path
347 old_yaffs_trace_val=yaffs_get_trace()
348 yaffs_set_trace(new_yaffs_trace_val)
350 data=scan_dir(file_path, copy_hidden_dir)
351 copy_scanned_files_into_yaffs(data[0], data[1], data[2], data[3],file_path, yaffs_path)
353 yaffs_set_trace(old_yaffs_trace_val)
356 if __name__=="__main__":
358 yaffs_mount("/yaffs2/")
360 # absolute_path = os.path.abspath(os.path.curdir)
361 #print "absolute path:", absolute_path
362 current_debug_level=1
363 search_hidden_directories=True
364 yaffs_root_dir_path="/yaffs2/scanning/"
367 for i in range(2, len(sys.argv)):
368 if sys.argv[i]=="-d":
369 current_debug_level=int( sys.argv[i+1])
370 if sys.argv[i]=="-ignore_hidden_directories":
371 search_hidden_directories=False
374 # path="/home/timothy/work/yaffs/git/yaffs2"
375 # path="/home/timothy/my_stuff/old_laptop/timothy/programming_lejos/"
378 import_into_yaffs(path, yaffs_root_dir_path, current_debug_level, search_hidden_directories, 0 )
380 # copy_scanned_files_into_yaffs()
381 #print_scanned_dir_list()
383 print"unmounting yaffs:", yaffs_unmount("/yaffs2/")