00001
00002
00003
00004
00005
00006
00007
00008
00012 #include <iostream>
00013
00014 #include "zypp/base/Logger.h"
00015 #include "zypp/base/String.h"
00016 #include "zypp/source/Applydeltarpm.h"
00017 #include "zypp/ExternalProgram.h"
00018 #include "zypp/AutoDispose.h"
00019 #include "zypp/PathInfo.h"
00020 #include "zypp/TriBool.h"
00021
00022 using std::endl;
00023
00025 namespace zypp
00026 {
00027
00028 namespace applydeltarpm
00029 {
00030
00031 namespace
00032 {
00033
00034 const Pathname applydeltarpm_prog( "/usr/bin/applydeltarpm" );
00035 const str::regex applydeltarpm_tick ( "([0-9]+) percent finished" );
00036
00037
00038
00039
00040
00041
00042 bool applydeltarpm( const char *const argv_r[],
00043 const Progress & report_r = Progress() )
00044 {
00045 ExternalProgram prog( argv_r, ExternalProgram::Stderr_To_Stdout );
00046 str::smatch what;
00047 for ( std::string line = prog.receiveLine(); ! line.empty(); line = prog.receiveLine() )
00048 {
00049 if ( report_r && str::regex_search( line, what, applydeltarpm_tick ) )
00050 {
00051 report_r( str::strtonum<unsigned>( what[1] ) );
00052 }
00053 else
00054 DBG << "Applydeltarpm : " << line;
00055 }
00056 return( prog.close() == 0 );
00057 }
00058
00060 }
00062
00063
00064
00065
00066
00067
00068 bool haveApplydeltarpm()
00069 {
00070
00071 static TriBool _last = indeterminate;
00072 PathInfo prog( applydeltarpm_prog );
00073 bool have = prog.isX();
00074 if ( _last == have )
00075 ;
00076 else
00077 {
00078
00079 if ( (_last = have) )
00080 MIL << "Found executable " << prog << endl;
00081 else
00082 WAR << "No executable " << prog << endl;
00083 }
00084 return _last;
00085 }
00086
00087
00088
00089
00090
00091
00092 bool check( const std::string & sequenceinfo_r, bool quick_r )
00093 {
00094 if ( ! haveApplydeltarpm() )
00095 return false;
00096
00097 const char *const argv[] = {
00098 "/usr/bin/applydeltarpm",
00099 ( quick_r ? "-C" : "-c" ),
00100 "-s", sequenceinfo_r.c_str(),
00101 NULL
00102 };
00103
00104 return( applydeltarpm( argv ) );
00105 }
00106
00107
00108
00109
00110
00111
00112 bool check( const Pathname & delta_r, bool quick_r )
00113 {
00114 if ( ! haveApplydeltarpm() )
00115 return false;
00116
00117 const char *const argv[] = {
00118 "/usr/bin/applydeltarpm",
00119 ( quick_r ? "-C" : "-c" ),
00120 delta_r.asString().c_str(),
00121 NULL
00122 };
00123
00124 return( applydeltarpm( argv ) );
00125 }
00126
00127
00128
00129
00130
00131
00132 bool provide( const Pathname & delta_r, const Pathname & new_r,
00133 const Progress & report_r )
00134 {
00135
00136 AutoDispose<const Pathname> guard( new_r, filesystem::unlink );
00137
00138 if ( ! haveApplydeltarpm() )
00139 return false;
00140
00141 const char *const argv[] = {
00142 "/usr/bin/applydeltarpm",
00143 "-p", "-p",
00144 delta_r.asString().c_str(),
00145 new_r.asString().c_str(),
00146 NULL
00147 };
00148
00149 if ( ! applydeltarpm( argv, report_r ) )
00150 return false;
00151
00152 guard.resetDispose();
00153 return true;
00154 }
00155
00156
00157
00158
00159
00160
00161 bool provide( const Pathname & old_r, const Pathname & delta_r,
00162 const Pathname & new_r,
00163 const Progress & report_r )
00164 {
00165
00166 AutoDispose<const Pathname> guard( new_r, filesystem::unlink );
00167
00168 if ( ! haveApplydeltarpm() )
00169 return false;
00170
00171 const char *const argv[] = {
00172 "/usr/bin/applydeltarpm",
00173 "-p", "-p",
00174 "-r", old_r.asString().c_str(),
00175 delta_r.asString().c_str(),
00176 new_r.asString().c_str(),
00177 NULL
00178 };
00179
00180 if ( ! applydeltarpm( argv, report_r ) )
00181 return false;
00182
00183 guard.resetDispose();
00184 return true;
00185 }
00186
00188 }
00191 }