]> Gitweb @ Texas Instruments - Open Source Git Repositories - git.TI.com/gitweb - android-sdk/arm-ds5-gator.git/blob - daemon/LocalCapture.cpp
Merge branch 'master' into android
[android-sdk/arm-ds5-gator.git] / daemon / LocalCapture.cpp
1 /**
2  * Copyright (C) ARM Limited 2010-2012. All rights reserved.
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 version 2 as
6  * published by the Free Software Foundation.
7  */
9 #include <sys/stat.h>
10 #include <sys/types.h>
11 #include <dirent.h>
12 #include <string.h>
13 #include <stdlib.h>
14 #include <unistd.h>
15 #include "LocalCapture.h"
16 #include "SessionData.h"
17 #include "Logging.h"
18 #include "OlyUtility.h"
20 extern void handleException();
22 LocalCapture::LocalCapture() {}
24 LocalCapture::~LocalCapture() {}
26 void LocalCapture::createAPCDirectory(char* target_path, char* name) {
27         gSessionData->apcDir = createUniqueDirectory(target_path, ".apc", name);
28         if ((removeDirAndAllContents(gSessionData->apcDir) != 0 || mkdir(gSessionData->apcDir, S_IRWXU | S_IRWXG | S_IROTH | S_IXOTH) != 0)) {
29                 logg->logError(__FILE__, __LINE__, "Unable to create directory %s", gSessionData->apcDir);
30                 handleException();
31         }
32 }
34 void LocalCapture::write(char* string) {
35         char* file = (char*)malloc(PATH_MAX);
37         // Set full path
38         snprintf(file, PATH_MAX, "%s/session.xml", gSessionData->apcDir);
40         // Write the file
41         if (util->writeToDisk(file, string) < 0) {
42                 logg->logError(__FILE__, __LINE__, "Error writing %s\nPlease verify the path.", file);
43                 handleException();
44         }
46         free(file);
47 }
49 char* LocalCapture::createUniqueDirectory(const char* initialPath, const char* ending, char* title) {
50         int i;
51         char* output;
52         char* path = (char*)malloc(PATH_MAX);
54         // Ensure the path is an absolute path, i.e. starts with a slash
55         if (initialPath == 0 || strlen(initialPath) == 0) {
56                 if (getcwd(path, PATH_MAX) == 0)
57                         logg->logMessage("Unable to retrive the current working directory");
58                 strncat(path, "/@F_@N", PATH_MAX - strlen(path) - 1);
59         } else if (initialPath[0] != '/') {
60                 if (getcwd(path, PATH_MAX) == 0)
61                         logg->logMessage("Unable to retrive the current working directory");
62                 strncat(path, "/", PATH_MAX - strlen(path) - 1);
63                 strncat(path, initialPath, PATH_MAX - strlen(path) - 1);
64         } else {
65                 strncpy(path, initialPath, PATH_MAX);
66                 path[PATH_MAX - 1] = 0; // strncpy does not guarantee a null-terminated string
67         }
69         // Convert to uppercase
70         replaceAll(path, "@f", "@F", PATH_MAX);
71         replaceAll(path, "@n", "@N", PATH_MAX);
73         // Replace @F with the session xml title
74         replaceAll(path, "@F", title, PATH_MAX);
76         // Add ending if it is not already there
77         if (strcmp(&path[strlen(path) - strlen(ending)], ending) != 0) {
78                 strncat(path, ending, PATH_MAX - strlen(path) - 1);
79         }
81         // Replace @N with a unique integer
82         if (strstr(path, "@N")) {
83                 char* tempPath = (char*)malloc(PATH_MAX);
84                 for (i = 1; i < 1000; i++) {
85                         char number[4];
86                         snprintf(number, sizeof(number), "%03d", i);
87                         strcpy(tempPath, path);
88                         replaceAll(tempPath, "@N", number, PATH_MAX);
89                         struct stat mFileInfo;
90                         if (stat(tempPath, &mFileInfo) != 0) {
91                                 // if the direcotry does not exist, break
92                                 break;
93                         }
94                 }
96                 if (i == 1000) {
97                         logg->logError(__FILE__, __LINE__, "Unable to create .apc directory, please delete older directories.");
98                         handleException();
99                 }
101                 output = strdup(tempPath);
102                 free(tempPath);
103         } else {
104                 output = strdup(path);
105         }
107         free(path);
108         return output;
111 //Replaces all occurrences of <find> in <target> with <replace> provided enough <size> is available
112 void LocalCapture::replaceAll(char* target, const char* find, const char* replace, unsigned int size) {
113         char* nextOccurrence;
114         unsigned int count = 0;
116         // Duplicate the original string
117         char* original = strdup(target);
118         char* ptr = original;
120         // Determine number of <find>s
121         ptr = strstr(ptr, find);
122         while (ptr) {
123                 count++;
124                 ptr += strlen(find);
125                 ptr = strstr(ptr, find);
126         }
128         // Is there enough space available
129         if (strlen(target) + (strlen(replace) - strlen(find)) * count > size - 1) {
130                 free(original);
131                 return;
132         }
134         // Reset
135         ptr = original;
137         nextOccurrence = strstr(ptr, find);
138         while (nextOccurrence) {
139                 // Move pointers to location of replace
140                 int length = nextOccurrence - ptr;
141                 target += length;
142                 ptr += length;
144                 // Replace <find> with <replace>
145                 memcpy(target, replace, strlen(replace));
147                 // Increment over <replace>/<find>
148                 target += strlen(replace);
149                 ptr += strlen(find);
151                 // Copy remainder of ptr
152                 strcpy(target, ptr);
154                 // Get next occurrence
155                 nextOccurrence = strstr(ptr, find);
156         }
158         free(original);
161 int LocalCapture::removeDirAndAllContents(char *path) {
162         int error = 0;
163         struct stat mFileInfo;
164         // Does the path exist?
165         if (stat(path, &mFileInfo) == 0) {
166                 // Is it a directory?
167                 if (mFileInfo.st_mode & S_IFDIR) {
168                         DIR * dir = opendir(path);
169                         dirent* entry = readdir(dir);
170                         while (entry) {
171                                 if (strcmp(entry->d_name, ".") != 0 && strcmp(entry->d_name, "..") != 0) {
172                                         char* newpath = (char*)malloc(strlen(path) + strlen(entry->d_name) + 2);
173                                         sprintf(newpath, "%s/%s", path, entry->d_name);
174                                         error = removeDirAndAllContents(newpath);
175                                         free(newpath);
176                                         if (error) break;
177                                 }
178                                 entry = readdir(dir);
179                         }
180                         closedir(dir);
181                         if (error == 0) {
182                                 error = rmdir(path);
183                         }
184                 } else {
185                         error = remove(path);
186                 }
187         }
188         return error;
191 void LocalCapture::copyImages(ImageLinkList* ptr) {
192         char* dstfilename = (char*)malloc(PATH_MAX);
194         while (ptr) {
195                 strncpy(dstfilename, gSessionData->apcDir, PATH_MAX);
196                 dstfilename[PATH_MAX - 1] = 0; // strncpy does not guarantee a null-terminated string
197                 if (gSessionData->apcDir[strlen(gSessionData->apcDir) - 1] != '/')
198                         strncat(dstfilename, "/", PATH_MAX - strlen(dstfilename) - 1);
199                 strncat(dstfilename, util->getFilePart(ptr->path), PATH_MAX - strlen(dstfilename) - 1);
200                 if (util->copyFile(ptr->path, dstfilename))
201                         logg->logMessage("copied file %s to %s", ptr->path, dstfilename);
202                 else
203                         logg->logMessage("copy of file %s to %s failed", ptr->path, dstfilename);
205                 ptr = ptr->next;
206         }
207         free(dstfilename);