-rw-r--r-- | core/symlinker/main.cpp | 220 |
1 files changed, 113 insertions, 107 deletions
diff --git a/core/symlinker/main.cpp b/core/symlinker/main.cpp index 6a04980..96e7f3c 100644 --- a/core/symlinker/main.cpp +++ b/core/symlinker/main.cpp | |||
@@ -1,179 +1,185 @@ | |||
1 | |||
2 | /* OPIE */ | ||
3 | #include <opie2/odebug.h> | ||
4 | |||
5 | /* QT */ | ||
1 | #include <qapplication.h> | 6 | #include <qapplication.h> |
2 | #include <qfile.h> | 7 | #include <qfile.h> |
3 | #include <qfileinfo.h> | 8 | #include <qfileinfo.h> |
4 | #include <qdir.h> | 9 | #include <qdir.h> |
5 | #include <qtextstream.h> | 10 | #include <qtextstream.h> |
6 | #include <qstringlist.h> | 11 | #include <qstringlist.h> |
7 | 12 | ||
13 | /* STD */ | ||
8 | #include <stdlib.h> | 14 | #include <stdlib.h> |
9 | #include <unistd.h> //symlink() | 15 | #include <unistd.h> //symlink() |
10 | #include <sys/stat.h> // mkdir() | 16 | #include <sys/stat.h> // mkdir() |
11 | 17 | ||
12 | #include <sys/vfs.h> | 18 | #include <sys/vfs.h> |
13 | #include <mntent.h> | 19 | #include <mntent.h> |
14 | #include <errno.h> | 20 | #include <errno.h> |
15 | 21 | ||
16 | static const char *listDir = "/usr/lib/ipkg/externinfo/"; | 22 | static const char *listDir = "/usr/lib/ipkg/externinfo/"; |
17 | 23 | ||
18 | static void createSymlinks( const QString &location, const QString &package ) | 24 | static void createSymlinks( const QString &location, const QString &package ) |
19 | { | 25 | { |
20 | 26 | ||
21 | QFile inFile( location + "/usr/lib/ipkg/info/" + package + ".list" ); | 27 | QFile inFile( location + "/usr/lib/ipkg/info/" + package + ".list" ); |
22 | mkdir( "/usr/lib/ipkg", 0777 ); | 28 | mkdir( "/usr/lib/ipkg", 0777 ); |
23 | mkdir( listDir, 0777 ); | 29 | mkdir( listDir, 0777 ); |
24 | 30 | ||
25 | QFile outFile( listDir + package + ".list"); | 31 | QFile outFile( listDir + package + ".list"); |
26 | 32 | ||
27 | // qDebug( "createSymlinks %s -> %s", inFile.name().ascii(), outFile.name().ascii() ); | 33 | // odebug << "createSymlinks " << inFile.name().ascii() << " -> " << outFile.name().ascii() << "" << oendl; |
28 | 34 | ||
29 | 35 | ||
30 | 36 | ||
31 | if ( inFile.open(IO_ReadOnly) && outFile.open(IO_WriteOnly)) { | 37 | if ( inFile.open(IO_ReadOnly) && outFile.open(IO_WriteOnly)) { |
32 | QTextStream in(&inFile); | 38 | QTextStream in(&inFile); |
33 | QTextStream out(&outFile); | 39 | QTextStream out(&outFile); |
34 | 40 | ||
35 | QString s; | 41 | QString s; |
36 | while ( !in.eof() ) { // until end of file... | 42 | while ( !in.eof() ) { // until end of file... |
37 | s = in.readLine(); // line of text excluding '\n' | 43 | s = in.readLine(); // line of text excluding '\n' |
38 | // qDebug( "Read: %s", s.ascii() ); | 44 | // odebug << "Read: " << s.ascii() << "" << oendl; |
39 | if (s.find(location,0,true) >= 0){ | 45 | if (s.find(location,0,true) >= 0){ |
40 | // qDebug( "Found!" ); | 46 | // odebug << "Found!" << oendl; |
41 | s = s.replace(location,""); | 47 | s = s.replace(location,""); |
42 | } | 48 | } |
43 | // qDebug( "Read after: %s", s.ascii() ); | 49 | // odebug << "Read after: " << s.ascii() << "" << oendl; |
44 | 50 | ||
45 | // for s, do link/mkdir. | 51 | // for s, do link/mkdir. |
46 | if ( s.right(1) == "/" ) { | 52 | if ( s.right(1) == "/" ) { |
47 | // qDebug("do mkdir for %s", s.ascii()); | 53 | // odebug << "do mkdir for " << s.ascii() << "" << oendl; |
48 | mkdir( s.ascii(), 0777 ); | 54 | mkdir( s.ascii(), 0777 ); |
49 | //possible optimization: symlink directories | 55 | //possible optimization: symlink directories |
50 | //that don't exist already. -- Risky. | 56 | //that don't exist already. -- Risky. |
51 | } else { | 57 | } else { |
52 | // qDebug("do symlink for %s", s.ascii()); | 58 | // odebug << "do symlink for " << s.ascii() << "" << oendl; |
53 | QFileInfo ffi( s ); | 59 | QFileInfo ffi( s ); |
54 | //Don't try to symlink if a regular file exists already | 60 | //Don't try to symlink if a regular file exists already |
55 | if ( !ffi.exists() || ffi.isSymLink() ) { | 61 | if ( !ffi.exists() || ffi.isSymLink() ) { |
56 | if (symlink( (location+s).ascii(), s.ascii() ) != 0){ | 62 | if (symlink( (location+s).ascii(), s.ascii() ) != 0){ |
57 | if (errno == ENOENT){ | 63 | if (errno == ENOENT){ |
58 | // perror("Symlink Failed! "); | 64 | // perror("Symlink Failed! "); |
59 | QString e=s.ascii(); | 65 | QString e=s.ascii(); |
60 | e = e.replace(ffi.fileName(),""); | 66 | e = e.replace(ffi.fileName(),""); |
61 | // qDebug("DirName : %s",e.ascii() ); | 67 | // odebug << "DirName : " << e.ascii() << "" << oendl; |
62 | system ( QString("mkdir -p ")+e.ascii() ); | 68 | system ( QString("mkdir -p ")+e.ascii() ); |
63 | if (symlink( (location+s).ascii(), s.ascii() ) != 0) | 69 | if (symlink( (location+s).ascii(), s.ascii() ) != 0) |
64 | qDebug ("Big problem creating symlink and directory"); | 70 | odebug << "Big problem creating symlink and directory" << oendl; |
65 | } | 71 | } |
66 | } | 72 | } |
67 | // qDebug ( "Created %s" ,s.ascii() ); | 73 | // qDebug ( "Created %s" ,s.ascii() ); |
68 | out << s << "\n"; | 74 | out << s << "\n"; |
69 | } else { | 75 | } else { |
70 | qDebug( "%s exists already, not symlinked", s.ascii() ); | 76 | odebug << "" << s.ascii() << " exists already, not symlinked" << oendl; |
71 | } | 77 | } |
72 | } | 78 | } |
73 | } | 79 | } |
74 | inFile.close(); | 80 | inFile.close(); |
75 | outFile.close(); | 81 | outFile.close(); |
76 | } | 82 | } |
77 | } | 83 | } |
78 | 84 | ||
79 | 85 | ||
80 | 86 | ||
81 | static void removeSymlinks( const QString &package ) | 87 | static void removeSymlinks( const QString &package ) |
82 | { | 88 | { |
83 | QFile inFile( listDir + package + ".list" ); | 89 | QFile inFile( listDir + package + ".list" ); |
84 | 90 | ||
85 | if ( inFile.open(IO_ReadOnly) ) { | 91 | if ( inFile.open(IO_ReadOnly) ) { |
86 | QTextStream in(&inFile); | 92 | QTextStream in(&inFile); |
87 | 93 | ||
88 | QString s; | 94 | QString s; |
89 | while ( !in.eof() ) { // until end of file... | 95 | while ( !in.eof() ) { // until end of file... |
90 | s = in.readLine(); // line of text excluding '\n' | 96 | s = in.readLine(); // line of text excluding '\n' |
91 | // qDebug("remove symlink %s", s.ascii()); | 97 | // odebug << "remove symlink " << s.ascii() << "" << oendl; |
92 | QFileInfo ffi( s ); | 98 | QFileInfo ffi( s ); |
93 | //Confirm that it's still a symlink. | 99 | //Confirm that it's still a symlink. |
94 | if ( ffi.isSymLink() ){ | 100 | if ( ffi.isSymLink() ){ |
95 | unlink( s.ascii() ); | 101 | unlink( s.ascii() ); |
96 | // qDebug ( "Removed %s", s.ascii() );} | 102 | // qDebug ( "Removed %s", s.ascii() );} |
97 | // else | 103 | // else |
98 | // qDebug( "Not removed %s", s.ascii() ); | 104 | // odebug << "Not removed " << s.ascii() << "" << oendl; |
99 | } | 105 | } |
100 | } | 106 | } |
101 | inFile.close(); | 107 | inFile.close(); |
102 | inFile.remove(); | 108 | inFile.remove(); |
103 | } | 109 | } |
104 | } | 110 | } |
105 | 111 | ||
106 | 112 | ||
107 | 113 | ||
108 | /* | 114 | /* |
109 | Slightly hacky: we can't use StorageInfo, since we don't have a | 115 | Slightly hacky: we can't use StorageInfo, since we don't have a |
110 | QApplication. We look for filesystems that have the directory | 116 | QApplication. We look for filesystems that have the directory |
111 | /usr/lib/ipkg/info, and assume that they are removable media | 117 | /usr/lib/ipkg/info, and assume that they are removable media |
112 | with packages installed. This is safe even if eg. /usr is on a | 118 | with packages installed. This is safe even if eg. /usr is on a |
113 | separate filesystem, since then we would be testing for | 119 | separate filesystem, since then we would be testing for |
114 | /usr/usr/lib/ipkg/info, which should not exist. (And if it | 120 | /usr/usr/lib/ipkg/info, which should not exist. (And if it |
115 | does they deserve to have it treated as removable.) | 121 | does they deserve to have it treated as removable.) |
116 | */ | 122 | */ |
117 | 123 | ||
118 | static void updateSymlinks() | 124 | static void updateSymlinks() |
119 | { | 125 | { |
120 | QDir lists( listDir ); | 126 | QDir lists( listDir ); |
121 | QStringList knownPackages = lists.entryList( "*.list" ); // No tr | 127 | QStringList knownPackages = lists.entryList( "*.list" ); // No tr |
122 | 128 | ||
123 | struct mntent *me; | 129 | struct mntent *me; |
124 | FILE *mntfp = setmntent( "/etc/mtab", "r" ); | 130 | FILE *mntfp = setmntent( "/etc/mtab", "r" ); |
125 | 131 | ||
126 | if ( mntfp ) { | 132 | if ( mntfp ) { |
127 | while ( (me = getmntent( mntfp )) != 0 ) { | 133 | while ( (me = getmntent( mntfp )) != 0 ) { |
128 | QString root = me->mnt_dir; | 134 | QString root = me->mnt_dir; |
129 | if ( root == "/" ) | 135 | if ( root == "/" ) |
130 | continue; | 136 | continue; |
131 | 137 | ||
132 | QString info = root + "/usr/lib/ipkg/info"; | 138 | QString info = root + "/usr/lib/ipkg/info"; |
133 | QDir infoDir( info ); | 139 | QDir infoDir( info ); |
134 | // qDebug( "looking at %s", info.ascii() ); | 140 | // odebug << "looking at " << info.ascii() << "" << oendl; |
135 | if ( infoDir.isReadable() ) { | 141 | if ( infoDir.isReadable() ) { |
136 | const QFileInfoList *packages = infoDir.entryInfoList( "*.list" ); // No tr | 142 | const QFileInfoList *packages = infoDir.entryInfoList( "*.list" ); // No tr |
137 | QFileInfoListIterator it( *packages ); | 143 | QFileInfoListIterator it( *packages ); |
138 | QFileInfo *fi; | 144 | QFileInfo *fi; |
139 | while (( fi = *it )) { | 145 | while (( fi = *it )) { |
140 | ++it; | 146 | ++it; |
141 | if ( knownPackages.contains( fi->fileName() ) ) { | 147 | if ( knownPackages.contains( fi->fileName() ) ) { |
142 | // qDebug( "found %s and we've seen it before", fi->fileName().latin1() ); | 148 | // odebug << "found " << fi->fileName() << " and we've seen it before" << oendl; |
143 | knownPackages.remove( fi->fileName() ); | 149 | knownPackages.remove( fi->fileName() ); |
144 | } else { | 150 | } else { |
145 | //it's a new one | 151 | //it's a new one |
146 | createSymlinks( root, fi->baseName() ); | 152 | createSymlinks( root, fi->baseName() ); |
147 | } | 153 | } |
148 | 154 | ||
149 | } | 155 | } |
150 | 156 | ||
151 | } | 157 | } |
152 | } | 158 | } |
153 | endmntent( mntfp ); | 159 | endmntent( mntfp ); |
154 | } | 160 | } |
155 | 161 | ||
156 | for ( QStringList::Iterator it = knownPackages.begin(); | 162 | for ( QStringList::Iterator it = knownPackages.begin(); |
157 | it != knownPackages.end(); ++it ) { | 163 | it != knownPackages.end(); ++it ) { |
158 | // strip ".info" off the end. | 164 | // strip ".info" off the end. |
159 | removeSymlinks( (*it).left((*it).length()-5) ); | 165 | removeSymlinks( (*it).left((*it).length()-5) ); |
160 | } | 166 | } |
161 | } | 167 | } |
162 | 168 | ||
163 | 169 | ||
164 | 170 | ||
165 | int main( int argc, char *argv[] ) | 171 | int main( int argc, char *argv[] ) |
166 | { | 172 | { |
167 | QApplication a( argc, argv, QApplication::Tty ); | 173 | QApplication a( argc, argv, QApplication::Tty ); |
168 | 174 | ||
169 | QString command = argc > 1 ? argv[1] : "update"; // No tr | 175 | QString command = argc > 1 ? argv[1] : "update"; // No tr |
170 | 176 | ||
171 | if ( command == "update" ) // No tr | 177 | if ( command == "update" ) // No tr |
172 | updateSymlinks(); | 178 | updateSymlinks(); |
173 | else if ( command == "create" && argc > 3 ) // No tr | 179 | else if ( command == "create" && argc > 3 ) // No tr |
174 | createSymlinks( argv[2], argv[3] ); | 180 | createSymlinks( argv[2], argv[3] ); |
175 | else if ( command == "remove" && argc > 2 ) // No tr | 181 | else if ( command == "remove" && argc > 2 ) // No tr |
176 | removeSymlinks( argv[2] ); | 182 | removeSymlinks( argv[2] ); |
177 | else | 183 | else |
178 | qWarning( "Argument error" ); | 184 | owarn << "Argument error" << oendl; |
179 | } | 185 | } |