debsystem.cc 6.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234
  1. // -*- mode: cpp; mode: fold -*-
  2. // Description /*{{{*/
  3. // $Id: debsystem.cc,v 1.4 2004/01/26 17:01:53 mdz Exp $
  4. /* ######################################################################
  5. System - Abstraction for running on different systems.
  6. Basic general structure..
  7. ##################################################################### */
  8. /*}}}*/
  9. // Include Files /*{{{*/
  10. #include <apt-pkg/debsystem.h>
  11. #include <apt-pkg/debversion.h>
  12. #include <apt-pkg/debindexfile.h>
  13. #include <apt-pkg/dpkgpm.h>
  14. #include <apt-pkg/configuration.h>
  15. #include <apt-pkg/error.h>
  16. #include <apt-pkg/fileutl.h>
  17. #include <apti18n.h>
  18. #include <sys/types.h>
  19. #include <unistd.h>
  20. #include <dirent.h>
  21. #include <errno.h>
  22. /*}}}*/
  23. debSystem debSys;
  24. // System::debSystem - Constructor /*{{{*/
  25. // ---------------------------------------------------------------------
  26. /* */
  27. debSystem::debSystem()
  28. {
  29. LockFD = -1;
  30. LockCount = 0;
  31. StatusFile = 0;
  32. Label = "Debian dpkg interface";
  33. VS = &debVS;
  34. }
  35. /*}}}*/
  36. // System::~debSystem - Destructor /*{{{*/
  37. // ---------------------------------------------------------------------
  38. /* */
  39. debSystem::~debSystem()
  40. {
  41. delete StatusFile;
  42. }
  43. /*}}}*/
  44. // System::Lock - Get the lock /*{{{*/
  45. // ---------------------------------------------------------------------
  46. /* This mirrors the operations dpkg does when it starts up. Note the
  47. checking of the updates directory. */
  48. bool debSystem::Lock()
  49. {
  50. // Disable file locking
  51. if (_config->FindB("Debug::NoLocking",false) == true || LockCount > 1)
  52. {
  53. LockCount++;
  54. return true;
  55. }
  56. // Create the lockfile
  57. string AdminDir = flNotFile(_config->Find("Dir::State::status"));
  58. LockFD = GetLock(AdminDir + "lock");
  59. if (LockFD == -1)
  60. {
  61. if (errno == EACCES || errno == EAGAIN)
  62. return _error->Error(_("Unable to lock the administration directory (%s), "
  63. "is another process using it?"),AdminDir.c_str());
  64. else
  65. return _error->Error(_("Unable to lock the administration directory (%s), "
  66. "are you root?"),AdminDir.c_str());
  67. }
  68. // See if we need to abort with a dirty journal
  69. if (CheckUpdates() == true)
  70. {
  71. close(LockFD);
  72. LockFD = -1;
  73. const char *cmd;
  74. if (getenv("SUDO_USER") != NULL)
  75. cmd = "sudo dpkg --configure -a";
  76. else
  77. cmd = "dpkg --configure -a";
  78. // TRANSLATORS: the %s contains the recovery command, usually
  79. // dpkg --configure -a
  80. return _error->Error(_("dpkg was interrupted, you must manually "
  81. "run '%s' to correct the problem. "), cmd);
  82. }
  83. LockCount++;
  84. return true;
  85. }
  86. /*}}}*/
  87. // System::UnLock - Drop a lock /*{{{*/
  88. // ---------------------------------------------------------------------
  89. /* */
  90. bool debSystem::UnLock(bool NoErrors)
  91. {
  92. if (LockCount == 0 && NoErrors == true)
  93. return false;
  94. if (LockCount < 1)
  95. return _error->Error(_("Not locked"));
  96. if (--LockCount == 0)
  97. {
  98. close(LockFD);
  99. LockCount = 0;
  100. }
  101. return true;
  102. }
  103. /*}}}*/
  104. // System::CheckUpdates - Check if the updates dir is dirty /*{{{*/
  105. // ---------------------------------------------------------------------
  106. /* This does a check of the updates directory (dpkg journal) to see if it has
  107. any entries in it. */
  108. bool debSystem::CheckUpdates()
  109. {
  110. // Check for updates.. (dirty)
  111. string File = flNotFile(_config->Find("Dir::State::status")) + "updates/";
  112. DIR *DirP = opendir(File.c_str());
  113. if (DirP == 0)
  114. return false;
  115. /* We ignore any files that are not all digits, this skips .,.. and
  116. some tmp files dpkg will leave behind.. */
  117. bool Damaged = false;
  118. for (struct dirent *Ent = readdir(DirP); Ent != 0; Ent = readdir(DirP))
  119. {
  120. Damaged = true;
  121. for (unsigned int I = 0; Ent->d_name[I] != 0; I++)
  122. {
  123. // Check if its not a digit..
  124. if (isdigit(Ent->d_name[I]) == 0)
  125. {
  126. Damaged = false;
  127. break;
  128. }
  129. }
  130. if (Damaged == true)
  131. break;
  132. }
  133. closedir(DirP);
  134. return Damaged;
  135. }
  136. /*}}}*/
  137. // System::CreatePM - Create the underlying package manager /*{{{*/
  138. // ---------------------------------------------------------------------
  139. /* */
  140. pkgPackageManager *debSystem::CreatePM(pkgDepCache *Cache) const
  141. {
  142. return new pkgDPkgPM(Cache);
  143. }
  144. /*}}}*/
  145. // System::Initialize - Setup the configuration space.. /*{{{*/
  146. // ---------------------------------------------------------------------
  147. /* These are the Debian specific configuration variables.. */
  148. bool debSystem::Initialize(Configuration &Cnf)
  149. {
  150. /* These really should be jammed into a generic 'Local Database' engine
  151. which is yet to be determined. The functions in pkgcachegen should
  152. be the only users of these */
  153. Cnf.CndSet("Dir::State::extended_states", Cnf.FindDir("Dir::State").append("extended_states"));
  154. Cnf.CndSet("Dir::State::status","/var/lib/dpkg/status");
  155. Cnf.CndSet("Dir::Bin::dpkg","/usr/bin/dpkg");
  156. if (StatusFile) {
  157. delete StatusFile;
  158. StatusFile = 0;
  159. }
  160. return true;
  161. }
  162. /*}}}*/
  163. // System::ArchiveSupported - Is a file format supported /*{{{*/
  164. // ---------------------------------------------------------------------
  165. /* The standard name for a deb is 'deb'.. There are no seperate versions
  166. of .deb to worry about.. */
  167. bool debSystem::ArchiveSupported(const char *Type)
  168. {
  169. if (strcmp(Type,"deb") == 0)
  170. return true;
  171. return false;
  172. }
  173. /*}}}*/
  174. // System::Score - Determine how 'Debiany' this sys is.. /*{{{*/
  175. // ---------------------------------------------------------------------
  176. /* We check some files that are sure tell signs of this being a Debian
  177. System.. */
  178. signed debSystem::Score(Configuration const &Cnf)
  179. {
  180. signed Score = 0;
  181. if (FileExists(Cnf.FindFile("Dir::State::status","/var/lib/dpkg/status")) == true)
  182. Score += 10;
  183. if (FileExists(Cnf.FindFile("Dir::Bin::dpkg","/usr/bin/dpkg")) == true)
  184. Score += 10;
  185. if (FileExists("/etc/debian_version") == true)
  186. Score += 10;
  187. return Score;
  188. }
  189. /*}}}*/
  190. // System::AddStatusFiles - Register the status files /*{{{*/
  191. // ---------------------------------------------------------------------
  192. /* */
  193. bool debSystem::AddStatusFiles(vector<pkgIndexFile *> &List)
  194. {
  195. if (StatusFile == 0)
  196. StatusFile = new debStatusIndex(_config->FindFile("Dir::State::status"));
  197. List.push_back(StatusFile);
  198. return true;
  199. }
  200. /*}}}*/
  201. // System::FindIndex - Get an index file for status files /*{{{*/
  202. // ---------------------------------------------------------------------
  203. /* */
  204. bool debSystem::FindIndex(pkgCache::PkgFileIterator File,
  205. pkgIndexFile *&Found) const
  206. {
  207. if (StatusFile == 0)
  208. return false;
  209. if (StatusFile->FindInCache(*File.Cache()) == File)
  210. {
  211. Found = StatusFile;
  212. return true;
  213. }
  214. return false;
  215. }
  216. /*}}}*/