mod_ResourceWatcher.cpp 54 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458
  1. // mod_ResourceWatcher.cpp : 定义 DLL 应用程序的导出函数。
  2. //
  3. #include "stdafx.h"
  4. #include "mod_ResourceWatcher.h"
  5. #include "CommEntityUtil.hpp"
  6. #include "array.h"
  7. #include "fileutil.h"
  8. #include "iniutil.h"
  9. #include "toolkit.h"
  10. #include "osutil.h"
  11. #if defined(RVC_OS_LINUX)
  12. #include "SogouVersion.h"
  13. #include <winpr/sysinfo.h>
  14. #endif //RVC_OS_LINUX
  15. #include "publicFunExport.h"
  16. #include <map>
  17. #include <regex.h>
  18. struct SogouRunVersionInfo
  19. {
  20. CSimpleStringA strInstallDir;
  21. CSimpleStringA strVersion;
  22. SogouRunVersionInfo():strInstallDir(true),strVersion(true){}
  23. CSimpleStringA ToString() const {
  24. CSimpleStringA result(true);
  25. if(!strInstallDir.IsNullOrEmpty()) {
  26. result += strInstallDir;
  27. result += "#";
  28. }
  29. if(!strVersion.IsNullOrEmpty()) {
  30. result += strVersion;
  31. }
  32. return result;
  33. }
  34. };
  35. struct SogouInstallStateInfo
  36. {
  37. DWORD dwInstalledStatus;
  38. CSimpleStringA strInstallDate;
  39. SogouInstallStateInfo():dwInstalledStatus(-1),strInstallDate(true){}
  40. CSimpleStringA ToString() const {
  41. CSimpleStringA result(true);
  42. if(!strInstallDate.IsNullOrEmpty()) {
  43. //result += strInstallDate;
  44. result += GetInstallTime().ToTimeString();
  45. result += "#";
  46. }
  47. result += CSimpleStringA::Format("%u", dwInstalledStatus);
  48. return result;
  49. }
  50. CSmallDateTime GetInstallTime() const {
  51. if(!strInstallDate.IsNullOrEmpty()) {
  52. DWORD dwSecsSince1970(0);
  53. sscanf_s(strInstallDate.GetData(), "%u", &dwSecsSince1970);
  54. dwSecsSince1970 -= 946656000; // 2000-1970
  55. return CSmallDateTime(dwSecsSince1970);
  56. }
  57. return CSmallDateTime::BeginTime;
  58. }
  59. };
  60. struct SogouInstallInfo
  61. {
  62. SogouInstallStateInfo state;
  63. SogouRunVersionInfo program;
  64. CSimpleStringA Stringfy() const
  65. {
  66. return (state.ToString() + "||" + program.ToString());
  67. }
  68. bool IsInstalledSuccess() const {
  69. return (state.dwInstalledStatus == 0);
  70. }
  71. };
  72. void ResourceWatcherServiceSession::Handle_Fetch(
  73. SpReqAnsContext<ResourceWatcherService_Fetch_Req, ResourceWatcherService_Fetch_Ans>::Pointer ctx)
  74. {
  75. m_pEntity->Fetch(ctx);
  76. }
  77. void ResourceWatcherServiceSession::Handle_GetDevInfo(
  78. SpReqAnsContext<ResourceWatcherService_GetDevInfo_Req, ResourceWatcherService_GetDevInfo_Ans>::Pointer ctx)
  79. {
  80. LOG_FUNCTION();
  81. m_pEntity->GetDevInfo(ctx);
  82. }
  83. void ResourceWatcherServiceSession::Handle_GetCardSwiper(SpReqAnsContext<ResourceWatcherService_GetCardSwiper_Req, ResourceWatcherService_GetCardSwiper_Ans>::Pointer ctx)
  84. {
  85. LOG_FUNCTION();
  86. m_pEntity->GetCSwiperStatus(ctx);
  87. }
  88. void ResourceWatcherServiceSession::Handle_GetCpuType(SpReqAnsContext<ResourceWatcherService_GetCpuType_Req, ResourceWatcherService_GetCpuType_Ans>::Pointer ctx)
  89. {
  90. LOG_FUNCTION();
  91. m_pEntity->GetCPUType(ctx);
  92. }
  93. void ResourceWatcherServiceSession::Handle_OperateFile
  94. (SpReqAnsContext<ResourceWatcherService_OperateFile_Req,
  95. ResourceWatcherService_OperateFile_Ans>::Pointer ctx)
  96. {
  97. LOG_FUNCTION();
  98. m_pEntity->OperateFile(ctx);
  99. }
  100. void ResourceWatcherServiceSession::Handle_ExtractEventLog(
  101. SpReqAnsContext<ResourceWatcherService_ExtractEventLog_Req, ResourceWatcherService_ExtractEventLog_Ans>::Pointer ctx)
  102. {
  103. LOG_FUNCTION();
  104. m_pEntity->RetrieveEventLog(ctx);
  105. }
  106. void ResourceWatcherServiceSession::Handle_UpdateDNS(SpReqAnsContext<ResourceWatcherService_UpdateDNS_Req, ResourceWatcherService_UpdateDNS_Ans>::Pointer ctx)
  107. {
  108. LOG_FUNCTION();
  109. m_pEntity->UpdateDNS(ctx);
  110. }
  111. void ResourceWatcherServiceSession::Handle_GetNetworkInfo(SpReqAnsContext<ResourceWatcherService_GetNetworkInfo_Req, ResourceWatcherService_GetNetworkInfo_Ans>::Pointer ctx)
  112. {
  113. LOG_FUNCTION();
  114. m_pEntity->GetNetworkInfo(ctx);
  115. }
  116. void ResourceWatcherServiceSession::Handle_GetThirdPartyInstallState(SpReqAnsContext<ResourceWatcherService_GetThirdPartyInstallState_Req, ResourceWatcherService_GetThirdPartyInstallState_Ans>::Pointer ctx)
  117. {
  118. LOG_FUNCTION();
  119. m_pEntity->GetThirdPartyInstallState(ctx);
  120. }
  121. void ResourceWatcherServiceSession::Handle_InstallThirdPartyProgram(SpReqAnsContext<ResourceWatcherService_InstallThirdPartyProgram_Req, ResourceWatcherService_InstallThirdPartyProgram_Ans>::Pointer ctx)
  122. {
  123. LOG_FUNCTION();
  124. m_pEntity->InstallThirdPartyProgram(ctx);
  125. }
  126. void ResourceWatcherServiceSession::Handle_BizLinkDetect(SpReqAnsContext<ResourceWatcherService_BizLinkDetect_Req, ResourceWatcherService_BizLinkDetect_Ans>::Pointer ctx)
  127. {
  128. LOG_FUNCTION();
  129. m_pEntity->BizLinkDetect(ctx);
  130. }
  131. void ResourceWatcherServiceSession::Handle_CheckNetType(SpReqAnsContext<ResourceWatcherService_CheckNetType_Req, ResourceWatcherService_CheckNetType_Ans>::Pointer ctx)
  132. {
  133. LOG_FUNCTION();
  134. m_pEntity->CheckNetType(ctx);
  135. }
  136. void ResourceWatcherServiceSession::Handle_GetBizLinks(SpReqAnsContext<ResourceWatcherService_GetBizLinks_Req, ResourceWatcherService_GetBizLinks_Ans>::Pointer ctx)
  137. {
  138. LOG_FUNCTION();
  139. m_pEntity->GetBizLinks(ctx);
  140. }
  141. void ResourceWatcherServiceSession::Handle_GetTerminalVersionList(SpReqAnsContext<ResourceWatcherService_GetTerminalVersionList_Req, ResourceWatcherService_GetTerminalVersionList_Ans>::Pointer ctx)
  142. {
  143. LOG_FUNCTION();
  144. m_pEntity->GetTerminalVersionList(ctx);
  145. }
  146. void ResourceWatcherServiceSession::Handle_ManipulateVersion(SpReqAnsContext<ResourceWatcherService_ManipulateVersion_Req, ResourceWatcherService_ManipulateVersion_Ans>::Pointer ctx)
  147. {
  148. LOG_FUNCTION();
  149. m_pEntity->ManipulateVersion(ctx);
  150. }
  151. void ResourceWatcherServiceSession::Handle_UninstallThirdPartyProgram(SpReqAnsContext<ResourceWatcherService_UninstallThirdPartyProgram_Req, ResourceWatcherService_UninstallThirdPartyProgram_Ans>::Pointer ctx)
  152. {
  153. LOG_FUNCTION();
  154. m_pEntity->UninstallThirdPartyProgram(ctx);
  155. }
  156. void ResourceWatcherServiceSession::Handle_RestartThirdPartyProgram(SpReqAnsContext<ResourceWatcherService_RestartThirdPartyProgram_Req, ResourceWatcherService_RestartThirdPartyProgram_Ans>::Pointer ctx)
  157. {
  158. LOG_FUNCTION();
  159. m_pEntity->RestartThirdPartyProgram(ctx);
  160. }
  161. void ResourceWatcherServiceSession::Handle_ProcessDetectThirdPartyProgram(SpReqAnsContext<ResourceWatcherService_ProcessDetectThirdPartyProgram_Req, ResourceWatcherService_ProcessDetectThirdPartyProgram_Ans>::Pointer ctx)
  162. {
  163. LOG_FUNCTION();
  164. m_pEntity->ProcessDetectThirdPartyProgram(ctx);
  165. }
  166. void ResourceWatcherEntity::UpdateDNS(SpReqAnsContext<ResourceWatcherService_UpdateDNS_Req, ResourceWatcherService_UpdateDNS_Ans>::Pointer ctx)
  167. {
  168. ctx->Answer(Error_NotImpl);
  169. }
  170. void ResourceWatcherEntity::GetNetworkInfo(SpReqAnsContext<ResourceWatcherService_GetNetworkInfo_Req, ResourceWatcherService_GetNetworkInfo_Ans>::Pointer ctx)
  171. {
  172. char buf[512];
  173. toolkit_interface_address_t* info;
  174. int count, i;
  175. toolkit_interface_addresses(&info, &count);
  176. i = count;
  177. Dbg("Number of interfaces: %d", count);
  178. if (count <= 0) {
  179. ctx->Answer(Error_NotExist);
  180. return;
  181. }
  182. int realCount = 0;
  183. while (i--) {
  184. toolkit_interface_address_t& interface = info[i];
  185. if (interface.address.address4.sin_family == AF_INET/* && !interface.is_internal*/) {
  186. realCount++;
  187. }
  188. }
  189. if (realCount <= 0) {
  190. ctx->Answer(Error_NotExist);
  191. return;
  192. }
  193. ctx->Ans.status = 0;
  194. ctx->Ans.current = "";
  195. ctx->Ans.ips.Init(realCount);
  196. ctx->Ans.names.Init(realCount);
  197. ctx->Ans.macs.Init(realCount);
  198. ctx->Ans.masks.Init(realCount);
  199. ctx->Ans.gateways.Init(realCount);
  200. ctx->Ans.dns.Init(realCount);
  201. int cnt = 0, active = -1;
  202. for (i = 0; i < count; ++i) {
  203. toolkit_interface_address_t& interface = info[i];
  204. if (interface.address.address4.sin_family == AF_INET) {
  205. ctx->Ans.names[cnt] = interface.name;
  206. toolkit_ip4_name(&interface.address.address4, buf, sizeof(buf));
  207. if (strcmp(buf, "127.0.0.1") != 0) active = cnt;
  208. ctx->Ans.ips[cnt] = buf;
  209. ctx->Ans.macs[cnt] = "";
  210. ctx->Ans.masks[cnt] = "";
  211. ctx->Ans.gateways[cnt] = "";
  212. ctx->Ans.dns[cnt] = "";
  213. cnt++;
  214. }
  215. }
  216. toolkit_free_interface_addresses(info, count);
  217. const char* parent = "/etc/NetworkManager/system-connections";
  218. array_header_t* subs;
  219. subs = fileutil_get_sub_files_a(parent);
  220. if (subs) {
  221. for (i = 0; i < subs->nelts; ++i) {
  222. char path[256] = { 0 };
  223. char* dir = ARRAY_IDX(subs, i, char*);
  224. char value[128];
  225. inifile_read_str_s("connection", "interface-name", "", value, 127, dir);
  226. if (strlen(value) == 0) continue;
  227. for (int j = 0; j < realCount; ++j) {
  228. if (ctx->Ans.names[j].Compare(value) == 0) {
  229. memset(value, 0, sizeof(value));
  230. inifile_read_str_s("connection", "id", "", value, 127, dir);
  231. if (strlen(value) > 0) {
  232. ctx->Ans.names[j] = CSimpleStringA::Format("%s#%s", value, ctx->Ans.names[j].GetData());
  233. }
  234. if (active == j) {
  235. ctx->Ans.current = ctx->Ans.names[j];
  236. }
  237. memset(value, 0, sizeof(value));
  238. inifile_read_str_s("ethernet", "mac-address", "", value, 127, dir);
  239. ctx->Ans.macs[j] = value;
  240. memset(value, 0, sizeof(value));
  241. inifile_read_str_s("ipv4", "dns", "", value, 127, dir);
  242. ctx->Ans.dns[j] = value;
  243. break;
  244. }
  245. }
  246. }
  247. toolkit_array_free2(subs);
  248. }
  249. ctx->Answer(Error_Succeed);
  250. }
  251. void ResourceWatcherEntity::GetThirdPartyInstallState(SpReqAnsContext<ResourceWatcherService_GetThirdPartyInstallState_Req, ResourceWatcherService_GetThirdPartyInstallState_Ans>::Pointer ctx)
  252. {
  253. ErrorCodeEnum result(Error_Succeed);
  254. if (ctx->Req.mode == 1) {//查看搜狗输入法安装状态
  255. SogouInstallInfo info;
  256. info.state.dwInstalledStatus = Sogou_GetInstallStatus();
  257. info.state.strInstallDate = Sogou_GetInstallTime();
  258. info.program.strInstallDir = Sogou_GetInstallPath();
  259. info.program.strVersion = Sogou_GetVersion();
  260. const int maxTimes = 5;
  261. int curTimes = 0;
  262. while (info.state.dwInstalledStatus == 0 && info.program.strVersion.IsNullOrEmpty() && curTimes < maxTimes) {
  263. Sleep(1200);
  264. info.program.strVersion = Sogou_GetVersion();
  265. curTimes++;
  266. }
  267. Dbg("%d, %s, %s, %s"
  268. , info.state.dwInstalledStatus, info.state.strInstallDate.GetData()
  269. , info.program.strInstallDir.GetData(), info.program.strVersion.GetData());
  270. Dbg("InstallTime: %s", info.state.GetInstallTime().ToTimeString().GetData());
  271. ctx->Ans.status = info.IsInstalledSuccess() ? 1 : 0;
  272. ctx->Ans.reserverd1 = info.state.GetInstallTime().ToTimeString();
  273. ctx->Ans.path = info.program.strInstallDir;
  274. ctx->Ans.version = info.program.strVersion;
  275. } else if (ctx->Req.mode == 2) { //检测字体的安装状态
  276. CSimpleStringA strFontDir("/usr/share/fonts/truetype");
  277. CSimpleStringA strRVCTTFsDir(strFontDir + SPLIT_SLASH_STR + "RVCTTFs");
  278. if (!ExistsDirA(strRVCTTFsDir)) {
  279. ctx->Ans.status = 0;
  280. ctx->Ans.reserverd1 = CSimpleStringA::Format("%s 文件夹不存在", (LPCTSTR)strRVCTTFsDir);
  281. } else {
  282. CSimpleStringA ttf1 = strRVCTTFsDir + SPLIT_SLASH_STR + "HYQiHei-55S.ttf";
  283. CSimpleStringA ttf2 = strRVCTTFsDir + SPLIT_SLASH_STR + "HYQiHei-65S.ttf";
  284. CSimpleStringA ttfdir = strRVCTTFsDir + SPLIT_SLASH_STR + "fonts.dir";
  285. CSimpleStringA ttfscale = strRVCTTFsDir + SPLIT_SLASH_STR + "fonts.scale";
  286. CSimpleStringA ttfuuid = strRVCTTFsDir + SPLIT_SLASH_STR + ".uuid";
  287. int existCheck = 0;
  288. if (!ExistsFileA(ttf1)) {
  289. existCheck |= 1;
  290. }
  291. if (!ExistsFileA(ttf2)) {
  292. existCheck |= 2;
  293. }
  294. if (!ExistsFileA(ttfdir)) {
  295. existCheck |= 4;
  296. }
  297. if (!ExistsFileA(ttfscale)) {
  298. existCheck |= 8;
  299. }
  300. if (!ExistsFileA(ttfuuid)) {
  301. existCheck |= 16;
  302. }
  303. if (existCheck != 0) {
  304. ctx->Ans.status = 0;
  305. ctx->Ans.reserverd1 = CSimpleStringA::Format("安装文件不存在:0x%X", existCheck);
  306. } else {
  307. ctx->Ans.status = 1;
  308. ctx->Ans.reserverd1 = "";
  309. ctx->Ans.path = strRVCTTFsDir;
  310. ctx->Ans.version = "";
  311. }
  312. }
  313. } else {
  314. result = Error_NotSupport;
  315. }
  316. ctx->Answer(result);
  317. return;
  318. }
  319. ErrorCodeEnum SetFileExecutePriviledge(LPCTSTR lpcszDirOrFilePath)
  320. {
  321. ErrorCodeEnum result(Error_Succeed);
  322. if (ExistsDirA(lpcszDirOrFilePath)) {
  323. do
  324. {
  325. array_header_t* subs;
  326. subs = fileutil_get_sub_dirs_a(lpcszDirOrFilePath);
  327. if (subs) {
  328. for (int i = 0; i < subs->nelts; ++i) {
  329. char* dir = ARRAY_IDX(subs, i, char*);
  330. const char* dirname = &dir[strlen(lpcszDirOrFilePath) + 1];
  331. ErrorCodeEnum tmpResult = SetFileExecutePriviledge(dir);
  332. if (tmpResult != Error_Succeed) {
  333. toolkit_array_free2(subs);
  334. return tmpResult;
  335. }
  336. }
  337. }
  338. } while (false);
  339. do {
  340. array_header_t* subs;
  341. subs = fileutil_get_sub_files_a(lpcszDirOrFilePath);
  342. if (subs) {
  343. for (int i = 0; i < subs->nelts; ++i) {
  344. char* path = ARRAY_IDX(subs, i, char*);
  345. mode_t f_attrib = S_IRUSR | S_IWUSR | S_IXUSR | S_IRGRP | S_IWGRP | S_IXGRP | S_IROTH | S_IXOTH;
  346. if (chmod(path, f_attrib) != 0) {
  347. Dbg("chmod file priviledge failed, %s, %d", path, errno);
  348. toolkit_array_free2(subs);
  349. return Error_Unexpect;
  350. }
  351. }
  352. toolkit_array_free2(subs);
  353. }
  354. } while (false);
  355. } else if(ExistsFileA(lpcszDirOrFilePath)) {
  356. mode_t f_attrib = S_IRUSR | S_IWUSR | S_IXUSR | S_IRGRP | S_IWGRP | S_IXGRP | S_IROTH | S_IXOTH;
  357. if (chmod(lpcszDirOrFilePath, f_attrib) != 0) {
  358. Dbg("chmod file priviledge failed, %s, %d", lpcszDirOrFilePath, errno);
  359. return Error_Unexpect;
  360. }
  361. } else {
  362. result = Error_InvalidState;
  363. }
  364. return result;
  365. }
  366. void ResourceWatcherEntity::InstallThirdPartyProgram(SpReqAnsContext<ResourceWatcherService_InstallThirdPartyProgram_Req, ResourceWatcherService_InstallThirdPartyProgram_Ans>::Pointer ctx)
  367. {
  368. ErrorCodeEnum result(Error_Succeed);
  369. ErrorCodeEnum tmpResult(Error_Succeed);
  370. CSimpleStringA tmpMsg(true);
  371. if (ctx->Req.type == 1) {//安装搜狗输入法
  372. Dbg("to install sogou input...");
  373. const bool doNotStartup(true); //安装后是否启动搜狗输入法服务,据搜狗反馈,不能通过root权限启动Sogou输入法
  374. CSimpleStringA strInstallPkgPath;
  375. tmpResult = GetSogouPkgDirPath(strInstallPkgPath);
  376. if (tmpResult != 0) {
  377. tmpMsg = CSimpleStringA::Format("指定位置找不到输入法安装包");
  378. } else {
  379. tmpResult = SetFileExecutePriviledge(strInstallPkgPath);
  380. if (tmpResult != Error_Succeed) {
  381. tmpMsg = CSimpleStringA::Format("%s 修改文件夹权限失败", strInstallPkgPath.GetData());
  382. tmpResult = Error_NotExist;
  383. } else {
  384. CSimpleStringA strRunIniFilePath = strInstallPkgPath + SPLIT_SLASH_STR + "Run.ini";
  385. if (ExistsFileA(strRunIniFilePath)) {
  386. char* p = inifile_read_str(strRunIniFilePath, "Action", "ToRun", "");
  387. CSimpleStringA strInstallScriptFile(strInstallPkgPath + SPLIT_SLASH_STR + p);
  388. toolkit_free(p);
  389. Dbg("install script file: %s", strInstallScriptFile.GetData());
  390. if (ExistsFileA(strInstallScriptFile)) {
  391. char app[MAX_PATH] = { '\0' };
  392. sprintf(app, "bash %s", strInstallScriptFile.GetData());
  393. tmpResult = RunShellScript(app);
  394. if (tmpResult != 0) {
  395. tmpMsg = CSimpleStringA::Format("执行 '%s' 失败", app);
  396. } else if(!doNotStartup) {
  397. CSimpleStringA strStartupScriptFile(strInstallPkgPath + SPLIT_SLASH_STR + "startup_service.sh");
  398. Dbg("startup script file: %s", strStartupScriptFile.GetData());
  399. if (!ExistsFileA(strStartupScriptFile)) {
  400. tmpMsg = CSimpleStringA::Format("%s 启动脚本文件不存在,请重启设备再次验证", strStartupScriptFile.GetData());
  401. tmpResult = Error_NotExist;
  402. } else {
  403. Sleep(1000);
  404. do {
  405. char app[MAX_PATH] = { '\0' };
  406. tk_process_t* process = NULL;
  407. tk_process_option_t option;
  408. option.exit_cb = NULL;
  409. option.file = NULL;
  410. option.flags = 0;
  411. #if 0
  412. auto users = GetUserNameList(true);
  413. if (users.size() == 1) {
  414. sprintf(app, "su -m -p -c \"bash %s\" %s", strStartupScriptFile.GetData(), users[0].c_str());
  415. } else {
  416. for (auto it = users.cbegin(); it != users.cend(); ++it) {
  417. Dbg("user:%s", it->c_str());
  418. }
  419. sprintf(app, "bash %s", strStartupScriptFile.GetData());
  420. }
  421. #else
  422. sprintf(app, "bash %s", strStartupScriptFile.GetData());
  423. #endif
  424. option.params = app;
  425. const int res = process_spawn(&option, &process);
  426. if (0 == res) {
  427. FREE(process);
  428. Dbg("execute {%s} suc", app);
  429. } else {
  430. tmpMsg = CSimpleStringA::Format("执行 '%s' 失败:%s", app, toolkit_strerror(res));
  431. tmpResult = Error_Process;
  432. }
  433. } while (false);
  434. }
  435. }
  436. } else {
  437. tmpMsg = CSimpleStringA::Format("%s 执行文件不存在", strInstallScriptFile.GetData());
  438. tmpResult = Error_NotExist;
  439. }
  440. } else {
  441. tmpMsg = CSimpleStringA::Format("%s 文件不存在,请检查安装包完整性", strRunIniFilePath.GetData());
  442. tmpResult = Error_NotExist;
  443. }
  444. }
  445. }
  446. if (tmpResult == Error_Succeed) {
  447. Sleep(1500);
  448. const CSimpleStringA strResultLogFilePath = strInstallPkgPath + SPLIT_SLASH_STR + "result.log";
  449. do
  450. {
  451. const int maxTimes = 5;
  452. int curTimes = 0;
  453. while (!ExistsFileA(strResultLogFilePath) && curTimes < maxTimes) {
  454. Sleep(1500);
  455. curTimes++;
  456. }
  457. } while (false);
  458. if (!ExistsFileA(strResultLogFilePath)) {
  459. tmpResult = Error_NotExist;
  460. tmpMsg = CSimpleStringA::Format("安装成功标志文件不存在!");
  461. } else {
  462. FILE* pResultLog = fopen(strResultLogFilePath, "r");
  463. if (pResultLog == NULL) {
  464. tmpResult = Error_IO;
  465. tmpMsg = CSimpleStringA::Format("打开安装成功标志文件失败!%s", strerror(errno));
  466. } else {
  467. char szTmp[1024] = {'\0'};
  468. int nRead = fread(szTmp, 1, sizeof(szTmp), pResultLog);
  469. int installResult(-1);
  470. char installMsg[256] = { '\0' };
  471. sscanf(szTmp, "result=%d&msg=%s", &installResult, installMsg);
  472. fclose(pResultLog);
  473. if (installResult != 0) {
  474. tmpResult = Error_Unexpect;
  475. tmpMsg = CSimpleStringA::Format("%s", szTmp);
  476. } else {
  477. SogouInstallInfo info;
  478. info.state.dwInstalledStatus = Sogou_GetInstallStatus();
  479. info.state.strInstallDate = Sogou_GetInstallTime();
  480. info.program.strInstallDir = Sogou_GetInstallPath();
  481. info.program.strVersion = Sogou_GetVersion();
  482. const int maxTimes = 5;
  483. int curTimes = 0;
  484. while (!doNotStartup && info.state.dwInstalledStatus == 0 && info.program.strVersion.IsNullOrEmpty() && curTimes < maxTimes) {
  485. Sleep(1200);
  486. info.program.strVersion = Sogou_GetVersion();
  487. curTimes++;
  488. }
  489. Dbg("InstallTime: %s", info.state.GetInstallTime().ToTimeString().GetData());
  490. Dbg("%d, %s, %s, %s"
  491. , info.state.dwInstalledStatus, info.state.strInstallDate.GetData()
  492. , info.program.strInstallDir.GetData(), info.program.strVersion.GetData());
  493. if (!info.IsInstalledSuccess()) {
  494. tmpResult = Error_FailVerify;
  495. tmpMsg = CSimpleStringA::Format("检测安装状态失败!");
  496. } else {
  497. ctx->Ans.path = info.program.strInstallDir;
  498. ctx->Ans.reserverd1 = info.program.strVersion;
  499. ctx->Ans.reserverd2 = info.state.GetInstallTime().ToTimeString();
  500. }
  501. }
  502. }
  503. }
  504. }
  505. } else if (ctx->Req.type == 2) {//安装花了钱的字体
  506. Dbg("to install cmb font input...%d", m_bInitMode);
  507. CSimpleStringA strAdDataDirPath(true);
  508. tmpResult = GetFunction()->GetPath("Ad", strAdDataDirPath);
  509. if (strAdDataDirPath.IsNullOrEmpty() && m_bInitMode) {
  510. strAdDataDirPath = "/opt/rvc/adData";
  511. }
  512. if (strAdDataDirPath.IsNullOrEmpty()) {
  513. tmpResult = Error_Unexpect;
  514. tmpMsg = "获取安装包路径Ad失败";
  515. } else {
  516. CSimpleStringA strInstallPkgPath = strAdDataDirPath + SPLIT_SLASH_STR "HYQiHei";
  517. if (!ExistsDirA(strInstallPkgPath)) {
  518. tmpMsg = CSimpleStringA::Format("%s 文件夹不存在", strInstallPkgPath.GetData());
  519. tmpResult = Error_NotExist;
  520. } else {
  521. CSimpleStringA strRunIniFilePath = strInstallPkgPath + SPLIT_SLASH_STR + "Run.ini";
  522. if (ExistsFileA(strRunIniFilePath)) {
  523. char* p = inifile_read_str(strRunIniFilePath, "Action", "ToRun", "");
  524. CSimpleStringA strInstallScriptFile(strInstallPkgPath + SPLIT_SLASH_STR + p);
  525. toolkit_free(p);
  526. Dbg("RunScript file: %s", strInstallScriptFile.GetData());
  527. if (ExistsFileA(strInstallScriptFile)) {
  528. do {
  529. char app[MAX_PATH] = { '\0' };
  530. tk_process_t* process = NULL;
  531. tk_process_option_t option;
  532. option.exit_cb = NULL;
  533. option.file = NULL;
  534. option.flags = 0;
  535. sprintf(app, "bash %s", strInstallScriptFile.GetData());
  536. option.params = app;
  537. const int res = process_spawn(&option, &process);
  538. if (0 == res) {
  539. FREE(process);
  540. Dbg("execute {%s} suc", strInstallScriptFile.GetData());
  541. } else {
  542. tmpMsg = CSimpleStringA::Format("执行 %s 失败:%s", strInstallScriptFile.GetData(), toolkit_strerror(res));
  543. tmpResult = Error_Process;
  544. }
  545. } while (false);
  546. } else {
  547. tmpMsg = CSimpleStringA::Format("%s 执行文件不存在", strInstallScriptFile.GetData());
  548. tmpResult = Error_NotExist;
  549. }
  550. } else {
  551. tmpMsg = CSimpleStringA::Format("%s 文件不存在", strRunIniFilePath.GetData());
  552. tmpResult = Error_NotExist;
  553. }
  554. }
  555. }
  556. if (tmpResult == Error_Succeed) {
  557. ///**TODO(Gifur@10/21/2021): 二次校验 */
  558. }
  559. } else {
  560. result = Error_NotSupport;
  561. }
  562. ctx->Ans.result = tmpResult;
  563. ctx->Ans.msg = tmpMsg;
  564. ctx->Answer(result);
  565. return;
  566. }
  567. void ResourceWatcherEntity::GetTerminalVersionList(SpReqAnsContext<ResourceWatcherService_GetTerminalVersionList_Req, ResourceWatcherService_GetTerminalVersionList_Ans>::Pointer ctx)
  568. {
  569. CSimpleStringA strVersionBaseDir(true);
  570. GetFunction()->GetPath("RootVer", strVersionBaseDir);
  571. const CSimpleStringA strActiveFile = strVersionBaseDir + SPLIT_SLASH_STR + "active.txt";
  572. CSystemStaticInfo staticInfo;
  573. GetFunction()->GetSystemStaticInfo(staticInfo);
  574. CSimpleStringA strCurrVer = staticInfo.InstallVersion.ToString();
  575. Dbg("get current version [%s]", (LPCTSTR)strCurrVer);
  576. std::vector<std::string> verlist;
  577. array_header_t* arr;
  578. arr = fileutil_get_sub_dirs_a(strVersionBaseDir);
  579. if (arr) {
  580. do {
  581. regex_t reg;
  582. CSimpleStringA strPattern("^[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+[\(\)A-Za-z_-]*$");
  583. int ret = regcomp(&reg, strPattern, REG_EXTENDED | REG_NOSUB);
  584. if (ret) {
  585. char ebuff[256];
  586. regerror(ret, &reg, ebuff, 256);
  587. Dbg("regex failed: %s", ebuff);
  588. ctx->Ans.msg = CSimpleStringA::Format("内部错误:REGEX %s", ebuff);
  589. ctx->Ans.current = -1;
  590. break;
  591. } else {
  592. for (int i = 0; i < arr->nelts; ++i) {
  593. char* versionDir = ARRAY_IDX(arr, i, char*);
  594. char* versionDirName = &versionDir[strVersionBaseDir.GetLength() + 1];
  595. ret = regexec(&reg, versionDirName, 0, NULL, 0);
  596. if (0 == ret) {
  597. Dbg("filename %s matched!", versionDirName);
  598. verlist.push_back(std::string(versionDirName));
  599. }
  600. }
  601. }
  602. } while (false);
  603. toolkit_array_free2(arr);
  604. }
  605. if (!verlist.empty()) {
  606. const int count = verlist.size();
  607. ctx->Ans.index.Init(count);
  608. ctx->Ans.version.Init(count);
  609. ctx->Ans.remark.Init(count);
  610. ctx->Ans.type.Init(count);
  611. ctx->Ans.status.Init(count);
  612. for (int i = 0; i < count; ++i) {
  613. ctx->Ans.index[i] = i;
  614. ctx->Ans.version[i] = verlist[i].c_str();
  615. if (verlist[i].compare(strCurrVer.GetData()) == 0) {
  616. ctx->Ans.current = i;
  617. }
  618. ctx->Ans.remark[i] = "";
  619. ctx->Ans.type[i] = ctx->Ans.status[i] = 0;
  620. }
  621. }
  622. ctx->Answer(Error_Succeed);
  623. }
  624. namespace
  625. {
  626. bool UpdateCurrentVersionName(LPCTSTR filePath, LPCTSTR versionStr, LPCTSTR backupPath)
  627. {
  628. if (fileutil_copy_file(backupPath, filePath) != 0) {
  629. return false;
  630. }
  631. FILE* fp = fopen(filePath, "wb+");
  632. if (fp == NULL) {
  633. return false;
  634. }
  635. bool result(false);
  636. do
  637. {
  638. int ret = fwrite(versionStr, strlen(versionStr), 1, fp);
  639. if (ret != 1) {
  640. Dbg("fwrite failed: %d", ret);
  641. break;
  642. }
  643. fflush(fp);
  644. fclose(fp);
  645. fp = fopen(filePath, "rb");
  646. if (fp != NULL) {
  647. char value[32] = { 0 };
  648. int ret2 = fread(value, strlen(versionStr), 1, fp);
  649. if (ret2 == 1) {
  650. if (strcmp(value, versionStr) == 0)
  651. Dbg("read agagin the value is the same!");
  652. else {
  653. break;
  654. }
  655. }
  656. }
  657. result = true;
  658. } while (false);
  659. fclose(fp);
  660. if (!result && backupPath) {
  661. fileutil_copy_file(filePath, backupPath);
  662. fileutil_delete_file(backupPath);
  663. }
  664. if (result && backupPath) {
  665. fileutil_delete_file(backupPath);
  666. }
  667. return result;
  668. }
  669. }
  670. void ResourceWatcherEntity::ManipulateVersion(SpReqAnsContext<ResourceWatcherService_ManipulateVersion_Req, ResourceWatcherService_ManipulateVersion_Ans>::Pointer ctx)
  671. {
  672. ErrorCodeEnum result(Error_Succeed);
  673. int tmpResult(0);
  674. CSimpleStringA tmpMsg(true);
  675. switch (ctx->Req.operation) {
  676. case 1: //设置为此版本为当前版本
  677. {
  678. CSimpleStringA strVersionBaseDir(true);
  679. GetFunction()->GetPath("RootVer", strVersionBaseDir);
  680. const CSimpleStringA strActiveFile = strVersionBaseDir + SPLIT_SLASH_STR + "active.txt";
  681. const CSimpleStringA strActiveFileBackup = strActiveFile + "activebak.txt";
  682. CSystemStaticInfo staticInfo;
  683. GetFunction()->GetSystemStaticInfo(staticInfo);
  684. CSimpleStringA strCurrVer = staticInfo.InstallVersion.ToString();
  685. Dbg("get current version [%s]", (LPCTSTR)strCurrVer);
  686. if (!UpdateCurrentVersionName(strActiveFile, ctx->Req.value, strActiveFileBackup)) {
  687. tmpResult = Error_Unexpect;
  688. tmpMsg = "切换版本失败";
  689. }
  690. }
  691. break;
  692. case 2: //删除此版本
  693. {
  694. CSimpleStringA strVersionBaseDir(true);
  695. GetFunction()->GetPath("RootVer", strVersionBaseDir);
  696. const CSimpleStringA strVersionDirPath = strVersionBaseDir + SPLIT_SLASH_STR + ctx->Req.value;
  697. if (ExistsDirA(strVersionDirPath)) {
  698. if (!RemoveDirRecursiveA(strVersionDirPath)) {
  699. tmpResult = Error_Unexpect;
  700. tmpMsg = "删除版本失败";
  701. }
  702. }
  703. }
  704. break;
  705. default:
  706. result = Error_NotSupport;
  707. break;
  708. }
  709. ctx->Ans.result = tmpResult;
  710. ctx->Ans.msg = tmpMsg;
  711. ctx->Answer(result);
  712. }
  713. void ResourceWatcherEntity::UninstallThirdPartyProgram(SpReqAnsContext<ResourceWatcherService_UninstallThirdPartyProgram_Req, ResourceWatcherService_UninstallThirdPartyProgram_Ans>::Pointer ctx)
  714. {
  715. ErrorCodeEnum result(Error_Succeed);
  716. ErrorCodeEnum tmpResult(Error_Succeed);
  717. CSimpleStringA tmpMsg(true);
  718. if (ctx->Req.type == 1) {
  719. Dbg("to uninstall sogou input...");
  720. CSimpleStringA strInstallPkgPath;
  721. tmpResult = GetSogouPkgDirPath(strInstallPkgPath);
  722. if (tmpResult == Error_Succeed) {
  723. do
  724. {
  725. tmpResult = SetFileExecutePriviledge(strInstallPkgPath);
  726. if (tmpResult != Error_Succeed) {
  727. tmpMsg = CSimpleStringA::Format("%s 修改文件夹权限失败", strInstallPkgPath.GetData());
  728. tmpResult = Error_NoPrivilege;
  729. break;
  730. }
  731. const CSimpleStringA strShutdownScriptFile = strInstallPkgPath + SPLIT_SLASH_STR + "shutdown_service.sh";
  732. const CSimpleStringA strUninstallScriptFile = strInstallPkgPath + SPLIT_SLASH_STR + "uninstall_sogouime.sh";
  733. if (!ExistsFileA(strShutdownScriptFile)) {
  734. tmpMsg = CSimpleStringA::Format("%s 文件不存在!", strShutdownScriptFile.GetData());
  735. tmpResult = Error_InvalidState;
  736. break;
  737. }
  738. if (!ExistsFileA(strUninstallScriptFile)) {
  739. tmpMsg = CSimpleStringA::Format("%s 文件不存在!", strUninstallScriptFile.GetData());
  740. tmpResult = Error_InvalidState;
  741. break;
  742. }
  743. char app[MAX_PATH] = { '\0' };
  744. sprintf(app, "bash %s", strShutdownScriptFile.GetData());
  745. tmpResult = RunShellScript(app);
  746. if (tmpResult != 0) {
  747. tmpMsg = CSimpleStringA::Format("执行 '%s' 失败", app);
  748. } else {
  749. Sleep(300);
  750. sprintf(app, "bash %s", strUninstallScriptFile.GetData());
  751. tmpResult = RunShellScript(app);
  752. if (tmpResult != 0) {
  753. tmpMsg = CSimpleStringA::Format("执行 '%s' 失败", app);
  754. } else {
  755. Sleep(100);
  756. }
  757. }
  758. } while (false);
  759. }
  760. } else {
  761. result = Error_NotSupport;
  762. }
  763. ctx->Ans.result = tmpResult;
  764. ctx->Ans.msg = tmpMsg;
  765. ctx->Answer(result);
  766. return;
  767. }
  768. void ResourceWatcherEntity::RestartThirdPartyProgram(SpReqAnsContext<ResourceWatcherService_RestartThirdPartyProgram_Req, ResourceWatcherService_RestartThirdPartyProgram_Ans>::Pointer ctx)
  769. {
  770. ErrorCodeEnum result(Error_Succeed);
  771. ErrorCodeEnum tmpResult(Error_Succeed);
  772. int restartRe = false;
  773. CSimpleStringA tmpMsg(true);
  774. std::string res("");
  775. if (ctx->Req.type == 1) {//重启搜狗输入法
  776. //CSimpleStringA csBinPath;
  777. //ErrorCodeEnum eErrPath = GetFunction()->GetPath("Bin", csBinPath);
  778. //if (eErrPath != Error_Succeed)
  779. //{
  780. // //Dbg("GetBasePath failed (%d).", eErrPath));
  781. // tmpMsg = "GetBasePath failed.";
  782. //}
  783. //else
  784. //{
  785. // CSimpleStringA startPath = CSimpleStringA::Format("%s\\spScript\\SogouServStarter.bat", csBinPath.GetData());
  786. // int startFlag = WinExec(startPath.GetData(), SW_SHOWNORMAL);
  787. // if (startFlag > 31)
  788. // {
  789. // tmpMsg = CSimpleStringA::Format("已执行搜狗启动脚本!路径:%s。", startPath.GetData());
  790. // restartRe = 1;
  791. // }
  792. // else
  793. // {
  794. // tmpMsg = CSimpleStringA::Format("执行启动脚本异常!路径:%s。", startPath.GetData());
  795. // restartRe = 0;
  796. // }
  797. //}
  798. }
  799. ctx->Ans.result = restartRe;
  800. ctx->Ans.msg = tmpMsg;
  801. ctx->Answer(result);
  802. return;
  803. }
  804. void ResourceWatcherEntity::ProcessDetectThirdPartyProgram(SpReqAnsContext<ResourceWatcherService_ProcessDetectThirdPartyProgram_Req, ResourceWatcherService_ProcessDetectThirdPartyProgram_Ans>::Pointer ctx)
  805. {
  806. ErrorCodeEnum result(Error_Succeed);
  807. ErrorCodeEnum tmpResult(Error_Succeed);
  808. int procDetectRe = false;
  809. CSimpleStringA tmpMsg(true);
  810. std::string res("");
  811. if (ctx->Req.type == 1) {//检测搜狗输入法进程
  812. CAutoArray<CSimpleStringA> pName(2);
  813. pName[0] = "SogouImeMon.exe";
  814. pName[1] = "SogouImeWebSrv.exe";
  815. res = DoCheckCertainProcessStatus(pName);
  816. if (res.length() == 0)
  817. {
  818. procDetectRe = false;
  819. tmpMsg = "Can't find Sogou Process.";
  820. }
  821. else
  822. {
  823. procDetectRe = true;
  824. tmpMsg = CSimpleStringA::Format("%s", res.c_str());
  825. }
  826. }
  827. ctx->Ans.result = procDetectRe;
  828. ctx->Ans.msg = tmpMsg;
  829. result = tmpResult;
  830. ctx->Answer(result);
  831. return;
  832. }
  833. #if defined(RVC_OS_WIN)
  834. //1: 32bit process running at 64bit platform
  835. //0:
  836. static int Is32R64Platform()
  837. {
  838. static int isWow64 = -1;
  839. typedef BOOL(WINAPI* LPFN_ISWOW64PROCESS)(HANDLE, PBOOL);
  840. if (isWow64 == -1) {
  841. BOOL bIsWow64 = FALSE;
  842. LPFN_ISWOW64PROCESS fnIsWow64Process =
  843. (LPFN_ISWOW64PROCESS)GetProcAddress(GetModuleHandle("kernel32"), "IsWow64Process");
  844. if (NULL != fnIsWow64Process) {
  845. if (!fnIsWow64Process(GetCurrentProcess(), &bIsWow64)) {
  846. Dbg("detect is running with 64bit or not failed: %u", GetLastError());
  847. return -1;
  848. } else {
  849. isWow64 = bIsWow64 ? 1 : 0;
  850. }
  851. }
  852. }
  853. return isWow64;
  854. }
  855. static bool GetRegistValue(HKEY hKey, LPCTSTR lpcszParam,
  856. DWORD* pDwValue, CHAR* pSzValue, const DWORD* pDwSizeOfSz)
  857. {
  858. if (pDwValue != NULL) {
  859. DWORD dwType = REG_DWORD;
  860. DWORD dwValue = 0;
  861. DWORD dwSize = sizeof(DWORD);
  862. LONG lResult = RegQueryValueExA(hKey, lpcszParam, NULL, &dwType, (LPBYTE)&dwValue, &dwSize);
  863. if (lResult == ERROR_SUCCESS) {
  864. Dbg("Value of \"%s\": %d", lpcszParam, dwValue);
  865. *pDwValue = dwValue;
  866. return true;
  867. } else {
  868. Dbg("RegQueryValueEx for \"%s\" error, result=%ld.", lpcszParam, lResult);
  869. return false;
  870. }
  871. } else if (pSzValue != NULL) {
  872. DWORD dwType = REG_SZ;
  873. DWORD dwSize = MAX_PATH * sizeof(CHAR);
  874. TCHAR szValue[MAX_PATH + 1] = { 0 };
  875. LONG lResult = RegQueryValueEx(hKey, lpcszParam, NULL, &dwType, (LPBYTE)szValue, &dwSize);
  876. if (lResult == ERROR_SUCCESS) {
  877. Dbg("Value of \"%s\": %s", lpcszParam, szValue);
  878. strcpy_s(pSzValue, *pDwSizeOfSz, szValue);
  879. return true;
  880. } else {
  881. Dbg("RegQueryValueEx for \"InstallTime\" error, result=%ld.", lResult);
  882. return false;
  883. }
  884. }
  885. Dbg("invalid param for \"%s\"", lpcszParam);
  886. return false;
  887. }
  888. static LONG GetSogouInstallState(SogouInstallStateInfo& info)
  889. {
  890. HKEY hKey;
  891. LONG lResult = -1;
  892. DWORD dwFlag = KEY_READ | KEY_QUERY_VALUE | KEY_ENUMERATE_SUB_KEYS;
  893. lResult = RegOpenKeyEx(HKEY_CURRENT_USER, "SOFTWARE\\SogouPCIme", 0, dwFlag, &hKey);
  894. if (lResult == ERROR_SUCCESS) {
  895. DWORD dwValue = (DWORD)-1;
  896. const bool res1 = GetRegistValue(hKey, "InstallFlag", &dwValue, NULL, NULL);
  897. if (res1) {
  898. info.dwInstalledStatus = dwValue;
  899. }
  900. TCHAR szValue[MAX_PATH + 1] = { 0 };
  901. DWORD dwLength = MAX_PATH;
  902. //1970 0x83AA7E80
  903. const bool res2 = GetRegistValue(hKey, "InstallTime", NULL, szValue, &dwLength);
  904. if (res2) {
  905. info.strInstallDate = szValue;
  906. Dbg("InstallTime: %s", info.GetInstallTime().ToTimeString().GetData());
  907. }
  908. if (res1 && res2) {
  909. lResult = 0;
  910. } else {
  911. lResult = -1;
  912. }
  913. } else {
  914. Dbg("%s::RegOpenKeyEx error, Result=%ld.", __FUNCTION__, lResult);
  915. }
  916. RegCloseKey(hKey);
  917. return lResult;
  918. }
  919. static LONG GetSogouExecuteInfo(SogouRunVersionInfo& info, BOOL f32bit = TRUE)
  920. {
  921. HKEY hKey;
  922. LONG lResult = -1;
  923. PVOID oldValue = NULL;
  924. Wow64DisableWow64FsRedirection(&oldValue);
  925. DWORD dwFlag = KEY_READ | KEY_QUERY_VALUE | KEY_ENUMERATE_SUB_KEYS;
  926. lResult = RegOpenKeyEx(HKEY_LOCAL_MACHINE,
  927. f32bit ? "SOFTWARE\\SogouPCIme" : "SOFTWARE\\WOW6432Node\\SogouPCIme", 0, dwFlag, &hKey);
  928. if (lResult == ERROR_SUCCESS) {
  929. TCHAR szVersion[MAX_PATH + 1] = { 0 }, szDefault[MAX_PATH + 1] = { 0 };
  930. DWORD dwLength = MAX_PATH;
  931. const bool res1 = GetRegistValue(hKey, "Version", NULL, szVersion, &dwLength);
  932. if (res1) info.strVersion = szVersion;
  933. const bool res2 = GetRegistValue(hKey, "", NULL, szDefault, &dwLength);
  934. if (res2) info.strInstallDir = szDefault;
  935. if (res1 && res2) {
  936. lResult = 0;
  937. } else {
  938. lResult = -1;
  939. }
  940. } else {
  941. Dbg("%s::RegOpenKeyEx(32bit=%d) error, Result=%ld.", __FUNCTION__, f32bit, lResult);
  942. }
  943. RegCloseKey(hKey);
  944. Wow64RevertWow64FsRedirection(oldValue);
  945. return lResult;
  946. }
  947. #endif //RVC_OS_WIN
  948. ErrorCodeEnum ResourceWatcherEntity::DoCheckInstallStateJob()
  949. {
  950. LOG_FUNCTION();
  951. CSmartPointer<IEntityFunction> spFunction = GetFunction();
  952. CSmartPointer<IConfigInfo> spConfig;
  953. ErrorCodeEnum err = spFunction->OpenConfig(Config_Run, spConfig);
  954. BOOL fNeedAlarm = TRUE;
  955. SogouInstallInfo info;
  956. #if defined(RVC_OS_WIN)
  957. GetSogouInstallState(info.state);
  958. BOOL is32Bit = Is64BitPlatform() ? FALSE : TRUE;
  959. if (ERROR_FILE_NOT_FOUND == GetSogouExecuteInfo(info.program, is32Bit))
  960. GetSogouExecuteInfo(info.program, !is32Bit);
  961. #else
  962. info.state.dwInstalledStatus = Sogou_GetInstallStatus();
  963. info.state.strInstallDate = Sogou_GetInstallTime();
  964. info.program.strInstallDir = Sogou_GetInstallPath();
  965. info.program.strVersion = Sogou_GetVersion();
  966. /** 重试获取版本号 [Gifur@2022224]*/
  967. const int maxTimes = 3;
  968. int curTimes = 0;
  969. while (info.state.dwInstalledStatus == 0 && info.program.strVersion.IsNullOrEmpty() && curTimes < maxTimes) {
  970. Sleep(1500);
  971. info.program.strVersion = Sogou_GetVersion();
  972. curTimes++;
  973. }
  974. Dbg("%d, %s, %s, %s"
  975. , info.state.dwInstalledStatus, info.state.strInstallDate.GetData()
  976. , info.program.strInstallDir.GetData(), info.program.strVersion.GetData());
  977. Dbg("InstallTime: %s", info.state.GetInstallTime().ToTimeString().GetData());
  978. #endif //RVC_OS_WIN
  979. CSimpleStringA strLastRecord(true);
  980. err = spConfig->ReadConfigValue("SogouInput", "LastInstalledRecord", strLastRecord);
  981. if (strLastRecord.IsNullOrEmpty() || info.Stringfy().Compare(strLastRecord) != 0) {
  982. spConfig->WriteConfigValue("SogouInput", "LastInstalledRecord", info.Stringfy());
  983. fNeedAlarm = TRUE;
  984. } else {
  985. //Report info per day.
  986. int nLastRecordTime = 0;
  987. err = spConfig->ReadConfigValueInt("SogouInput", "LastReportTime", nLastRecordTime);
  988. SYSTEMTIME stTaskTime = CSmallDateTime(nLastRecordTime).ToSystemTime();
  989. Dbg("Last Sogou install check time: %04d-%02d-%02d %02d:%02d:%02d",
  990. stTaskTime.wYear, stTaskTime.wMonth, stTaskTime.wDay,
  991. stTaskTime.wHour, stTaskTime.wMinute, stTaskTime.wSecond);
  992. SYSTEMTIME stNow = {};
  993. GetLocalTime(&stNow);
  994. if (nLastRecordTime > 0 && stTaskTime.wYear == stNow.wYear
  995. && stTaskTime.wMonth == stNow.wMonth && stTaskTime.wDay == stNow.wDay) {
  996. //The Same Day
  997. fNeedAlarm = FALSE;
  998. } else {
  999. fNeedAlarm = TRUE;
  1000. }
  1001. }
  1002. if (fNeedAlarm) {
  1003. const DWORD dwUserCode = info.IsInstalledSuccess() ? LOG_ERR_SOGOU_INPUT_INSTALLED : LOG_ERR_SOGOU_INPUT_NOTINSTALLED;
  1004. LogWarn(Severity_Middle, Error_DataCheck, dwUserCode, info.Stringfy());
  1005. spConfig->WriteConfigValue("SogouInput", "LastReportTime",
  1006. CSimpleStringA::Format("0x%08X", (DWORD)CSmallDateTime::GetNow()));
  1007. } else {
  1008. Dbg("Do not Report.");
  1009. }
  1010. return Error_Succeed;
  1011. }
  1012. void ResourceWatcherEntity::DoCheckSogouProcessStatus()
  1013. {
  1014. static int old_process_id[2] = { -1, -1 };
  1015. char* relate_processes[2] = {"sogouImeWebSrv", "sogouImeService"};
  1016. int count = 3;
  1017. alive_process_info processes[3];
  1018. memset(processes, 0, sizeof(processes));
  1019. osutil_detect_unique_app(relate_processes, array_size(relate_processes), &count, processes);
  1020. CAutoArray<CSimpleStringA> msgs(array_size(relate_processes));
  1021. int cnt(0);
  1022. for (int i = 0; i < array_size(relate_processes); ++i) {
  1023. int k = -1;
  1024. for (int j = 0; j < count; ++j) {
  1025. if (strcmp(processes[j].name, relate_processes[i]) == 0) {
  1026. k = j;
  1027. break;
  1028. }
  1029. }
  1030. if (k != -1 && old_process_id[i] == -1) {
  1031. old_process_id[i] = processes[k].pid;
  1032. } else if (k != -1 && (processes[k].pid != old_process_id[i])) {
  1033. msgs[cnt++] = CSimpleStringA::Format("{\"name\":\"%s\", \"prev\":%d, \"pid\":%d}"
  1034. , relate_processes[i], old_process_id[i], processes[k].pid);
  1035. old_process_id[i] = processes[k].pid;
  1036. } else if(k == -1 && old_process_id[i] != 0) {
  1037. msgs[cnt++] = CSimpleStringA::Format("{\"name\":\"%s\", \"prev\":%d, \"pid\":%d}"
  1038. , relate_processes[i], old_process_id[i], 0);
  1039. old_process_id[i] = 0;
  1040. }
  1041. }
  1042. if (cnt > 0) {
  1043. std::string uploadInfo("");
  1044. if (cnt > 1) {
  1045. uploadInfo = "{";
  1046. }
  1047. for (int i = 0; i < cnt; ++i) {
  1048. if (i != 0) {
  1049. uploadInfo += ",";
  1050. }
  1051. uploadInfo += msgs[i].GetData();
  1052. }
  1053. if (cnt > 1) {
  1054. uploadInfo += "}";
  1055. }
  1056. LogWarn(Severity_Middle, Error_Debug, LOG_RESOURCEWATCHER_SOGOU_PROCESS_STATUS_CHANGE, uploadInfo.c_str());
  1057. }
  1058. }
  1059. //# all available outputs
  1060. //OUTPUTS = $(xrandr | awk '$2 ~ /connected/ {print $1}')
  1061. //echo outputs : $OUTPUTS
  1062. //# get info from xrandr
  1063. //XRANDR = `xrandr`
  1064. //
  1065. //connectedOutputs = $(echo "$XRANDR" | grep " connected" | sed - e "s/\([A-Z0-9]\+\) connected.*/\1/")
  1066. //activeOutput = $(echo "$XRANDR" | grep - e " connected [^(]" | sed - e "s/\([A-Z0-9]\+\) connected.*/\1/")
  1067. //connected = $(echo $connectedOutputs | wc - w)
  1068. //echo connectedOutputs : ${ connectedOutputs }
  1069. //echo activeOutput : ${ activeOutput }
  1070. //echo connected : ${ connected }
  1071. ErrorCodeEnum ResourceWatcherEntity::ConfigMonitorSetting(const UOS::MonitorInfo& config)
  1072. {
  1073. ErrorCodeEnum result(Error_Succeed);
  1074. CSimpleStringA strExecute("xrandr");
  1075. //Get monitor info
  1076. do {
  1077. std::string sucContent, failedContent;
  1078. CSimpleStringA strCmd("xrandr | grep \" connected\" | sed -e \"s/\([A-Z0-9]\+\) connected.*/\1/\"");
  1079. bool ret = SP::Module::Util::ShellExecute(strCmd.GetData(), sucContent, failedContent);
  1080. Dbg("{%s}:{%s}{%s}", strCmd.GetData(), sucContent.c_str(), failedContent.c_str());
  1081. } while (false);
  1082. do {
  1083. std::string sucContent, failedContent;
  1084. CSimpleStringA strCmd("xrandr |awk '$2 ~ /connected/ {print $1}'");
  1085. bool ret = SP::Module::Util::ShellExecute(strCmd.GetData(), sucContent, failedContent);
  1086. Dbg("{%s}:{%s}{%s}", strCmd.GetData(), sucContent.c_str(), failedContent.c_str());
  1087. } while (false);
  1088. CSimpleStringA strCmd(strExecute);
  1089. if (!config.name.empty()) {
  1090. strCmd += CSimpleStringA::Format(" --output %s", config.name.c_str());
  1091. //Set resolution
  1092. if (config.nResolutionX != 0 && config.nResolutionY != 0) {
  1093. CSimpleStringA tmp = CSimpleStringA::Format(" --mode %dx%d", config.nResolutionX, config.nResolutionY);
  1094. strCmd += tmp;
  1095. }
  1096. if (config.refreshRate != 0) {
  1097. CSimpleStringA tmp = CSimpleStringA::Format(" --rate %d", config.refreshRate);
  1098. strCmd += tmp;
  1099. }
  1100. //set primary
  1101. if (config.isPrimary) {
  1102. strCmd += " --primary";
  1103. } else if (config.posDirecttion != -1 && !config.other.empty()) {
  1104. CSimpleStringA posDir(true);
  1105. switch (config.posDirecttion) {
  1106. case 0:
  1107. posDir = "--same-as";
  1108. case 1:
  1109. posDir = "--above";
  1110. break;
  1111. case 2:
  1112. posDir = "--right-of";
  1113. break;
  1114. case 3:
  1115. posDir = "--above";
  1116. break;
  1117. case 4:
  1118. posDir = "--left-of";
  1119. break;
  1120. default:
  1121. result = Error_Param;
  1122. break;
  1123. }
  1124. if (result == Error_Succeed) {
  1125. CSimpleStringA tmp = CSimpleStringA::Format(" %s %s", posDir.GetData(), config.other.c_str());
  1126. strCmd += tmp;
  1127. }
  1128. }
  1129. }
  1130. do
  1131. {
  1132. std::string sucContent, failedContent;
  1133. bool ret = SP::Module::Util::ShellExecute(strCmd.GetData(), sucContent, failedContent);
  1134. Dbg("{%s}:{%s}{%s}", strCmd.GetData(), sucContent.c_str(), failedContent.c_str());
  1135. } while (false);
  1136. do {
  1137. std::string sucContent, failedContent;
  1138. strCmd = strExecute;
  1139. bool ret = SP::Module::Util::ShellExecute(strCmd.GetData(), sucContent, failedContent);
  1140. Dbg("{%s}:{%s}{%s}", strCmd.GetData(), sucContent.c_str(), failedContent.c_str());
  1141. } while (false);
  1142. return result;
  1143. }
  1144. std::vector<std::string> ResourceWatcherEntity::GetUserNameList(bool bExcludeRoot)
  1145. {
  1146. std::vector<std::string> results;
  1147. array_header_t* arr;
  1148. arr = fileutil_get_sub_dirs_a("/home");
  1149. if (arr) {
  1150. int i;
  1151. for (i = 0; i < arr->nelts; ++i) {
  1152. char szDestSubDir[256] = { 0 };
  1153. char* dir = ARRAY_IDX(arr, i, char*);
  1154. Dbg("sub dir: %s", dir);
  1155. strcpy(szDestSubDir, dir);
  1156. strcat(szDestSubDir, SPLIT_SLASH_STR);
  1157. strcat(szDestSubDir, ".config/kwinrc");
  1158. if (ExistsFileA(szDestSubDir)) {
  1159. std::string strUserName((const char*)&dir[strlen("/home/")]);
  1160. Dbg("username:%s", strUserName.c_str());
  1161. if (strUserName.compare("root") != 0 || !bExcludeRoot) {
  1162. results.push_back(strUserName);
  1163. }
  1164. }
  1165. }
  1166. toolkit_array_free2(arr);
  1167. }
  1168. return results;
  1169. }
  1170. ErrorCodeEnum ResourceWatcherEntity::GetSogouPkgDirPath(CSimpleStringA& strPkgPath)
  1171. {
  1172. CSimpleStringA strAdDataDirPath(true);
  1173. CSimpleStringA strInstallPkgPath(true);
  1174. ErrorCodeEnum result = GetFunction()->GetPath("Ad", strAdDataDirPath);
  1175. if (strAdDataDirPath.IsNullOrEmpty() && m_bInitMode) {
  1176. strAdDataDirPath = "/opt/rvc/adData";
  1177. }
  1178. if (strAdDataDirPath.IsNullOrEmpty()) {
  1179. return Error_Unexpect;
  1180. }
  1181. array_header_t* subs;
  1182. subs = fileutil_get_sub_dirs_a(strAdDataDirPath);
  1183. if (subs) {
  1184. for (int i = 0; i < subs->nelts; ++i) {
  1185. char* dir = ARRAY_IDX(subs, i, char*);
  1186. const char* dirname = &dir[strAdDataDirPath.GetLength() + 1];
  1187. if (CSimpleStringA(dirname).IsStartWith("sogou", true)) {
  1188. if (strInstallPkgPath.IsNullOrEmpty()) {
  1189. Dbg("found it: %s", dir);
  1190. strInstallPkgPath = dir;
  1191. } else if (strInstallPkgPath.Compare(dir) < 0) {
  1192. Dbg("replace %s with %s", (LPCTSTR)strInstallPkgPath, dir);
  1193. strInstallPkgPath = dir;
  1194. }
  1195. }
  1196. }
  1197. toolkit_array_free2(subs);
  1198. }
  1199. if (strInstallPkgPath.IsNullOrEmpty()) {
  1200. return Error_NotExist;
  1201. }
  1202. strPkgPath = strInstallPkgPath;
  1203. return Error_Succeed;
  1204. }
  1205. ErrorCodeEnum ResourceWatcherEntity::RunShellScript(LPCTSTR cmdline)
  1206. {
  1207. char app[MAX_PATH] = { '\0' };
  1208. tk_process_t* process = NULL;
  1209. tk_process_option_t option;
  1210. option.exit_cb = NULL;
  1211. option.file = NULL;
  1212. option.flags = 0;
  1213. option.params = (char*)cmdline;
  1214. const int res = process_spawn(&option, &process);
  1215. if (0 == res) {
  1216. Dbg("execute {%s}, pid: %d", cmdline, process->pid);
  1217. FREE(process);
  1218. return Error_Succeed;
  1219. } else {
  1220. Dbg("execute {%s} failed: %d", cmdline, res);
  1221. return Error_Unexpect;
  1222. }
  1223. }
  1224. void ResourceWatcherEntity::OnSysVarEvent(const char* pszKey, const char* pszValue, const char* pszOldValue, const char* pszEntityName)
  1225. {
  1226. Dbg("OnSysVarEvent pszKey = %s, pszValue = %s", pszKey, pszValue);
  1227. if ((_strnicmp(pszKey, "UIState", strlen("UIState")) == 0)) {
  1228. if (_strnicmp(pszValue, "M", strlen("M")) == 0) {
  1229. ClearVersionTask* task = new ClearVersionTask(&m_fsm);
  1230. GetFunction()->PostThreadPoolTask(task);
  1231. }
  1232. }
  1233. }
  1234. std::string ResourceWatcherEntity::DoCheckCertainProcessStatus(const CAutoArray<CSimpleStringA>& pName)
  1235. {
  1236. int pSize = pName.GetCount();
  1237. /*static int old_process_id[pSize];
  1238. memset(old_process_id, -1, sizeof(old_process_id));*/
  1239. vector<int> old_process_id;
  1240. CAutoArray<CSimpleStringA> msgs;
  1241. alive_process_info* processes = new alive_process_info[pSize];
  1242. char** relate_processes = new char* [pSize];
  1243. int count = pSize;
  1244. for (int i = 0; i < pSize; ++i)
  1245. {
  1246. old_process_id.push_back(-1);
  1247. CSimpleStringA temp("");
  1248. msgs.Append(&temp, 0, 1);
  1249. relate_processes[i] = const_cast<char*>(pName[i].GetData());
  1250. Dbg("relate_process name: %s.", relate_processes[i]);
  1251. }
  1252. Dbg("COUNT = %d!", count);
  1253. osutil_detect_unique_app(relate_processes, pSize, &count, processes);
  1254. int cnt(0);
  1255. for (int i = 0; i < pSize; ++i) {
  1256. int k = -1;
  1257. for (int j = 0; j < count; ++j) {
  1258. if (strcmp(processes[j].name, relate_processes[i]) == 0) {
  1259. k = j;
  1260. break;
  1261. }
  1262. }
  1263. if (k != -1 && old_process_id[i] == -1) {
  1264. msgs[cnt++] = CSimpleStringA::Format("{\"name\":\"%s\", \"pid\":%d}"
  1265. , relate_processes[i], processes[k].pid);
  1266. old_process_id[i] = processes[k].pid;
  1267. }
  1268. else if (k != -1 && (processes[k].pid != old_process_id[i])) {
  1269. msgs[cnt++] = CSimpleStringA::Format("{\"name\":\"%s\", \"prev\":%d, \"pid\":%d}"
  1270. , relate_processes[i], old_process_id[i], processes[k].pid);
  1271. old_process_id[i] = processes[k].pid;
  1272. }
  1273. else if (k == -1 && old_process_id[i] != 0) {
  1274. msgs[cnt++] = CSimpleStringA::Format("{\"name\":\"%s\", \"prev\":%d, \"pid\":%d}"
  1275. , relate_processes[i], old_process_id[i], 0);
  1276. old_process_id[i] = 0;
  1277. }
  1278. }
  1279. std::string uploadInfo("");
  1280. if (cnt > 0) {
  1281. if (cnt > 1) {
  1282. uploadInfo = "{";
  1283. }
  1284. for (int i = 0; i < cnt; ++i) {
  1285. if (i != 0) {
  1286. uploadInfo += ",";
  1287. }
  1288. uploadInfo += msgs[i].GetData();
  1289. }
  1290. if (cnt > 1) {
  1291. uploadInfo += "}";
  1292. }
  1293. }
  1294. return uploadInfo;
  1295. }
  1296. SP_BEGIN_ENTITY_MAP()
  1297. SP_ENTITY(ResourceWatcherEntity)
  1298. SP_END_ENTITY_MAP()