/* * Copyright 2019 Rockchip Electronics Co., Ltd * Dayao Ji * * SPDX-License-Identifier: GPL-2.0+ */ #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include "cutils/android_reboot.h" //#include "common.h" #include "rkutility/sdboot.h" //#include "otautil/roots.h" //#include "otautil/sysutil.h" //#include "install.h" //#include "recovery_ui/ui.h" //#include "recovery_ui/screen_ui.h" //#include "rkupdate/Upgrade.h" //#include enum InstallResult { INSTALL_SUCCESS, INSTALL_ERROR, INSTALL_CORRUPT, INSTALL_NONE, INSTALL_SKIPPED, INSTALL_RETRY, INSTALL_KEY_INTERRUPTED, INSTALL_REBOOT, }; using namespace std; //extern RecoveryUI* ui; SDBoot::SDBoot(){ status = INSTALL_ERROR; bootwhere(); bUpdateModel = false; } bool SDBoot::isSDboot(){ return bSDBoot; } bool SDBoot::isUSBboot(){ return bUsbBoot; } bool SDBoot::parse_config(char *pConfig,VEC_SD_CONFIG &vecItem) { printf("in parse_config\n"); std::stringstream configStream(pConfig); std::string strLine,strItemName,strItemValue; std::string::size_type line_size,pos; vecItem.clear(); STRUCT_SD_CONFIG_ITEM item; while (!configStream.eof()) { getline(configStream,strLine); line_size = strLine.size(); if (line_size==0) continue; if (strLine[line_size-1]=='\r') { strLine = strLine.substr(0,line_size-1); } printf("%s\n",strLine.c_str()); pos = strLine.find("="); if (pos==std::string::npos) { continue; } if (strLine[0]=='#') { continue; } strItemName = strLine.substr(0,pos); strItemValue = strLine.substr(pos+1); strItemName.erase(0,strItemName.find_first_not_of(" ")); strItemName.erase(strItemName.find_last_not_of(" ")+1); strItemValue.erase(0,strItemValue.find_first_not_of(" ")); strItemValue.erase(strItemValue.find_last_not_of(" ")+1); if ((strItemName.size()>0)&&(strItemValue.size()>0)) { item.strKey = strItemName; item.strValue = strItemValue; vecItem.push_back(item); } } printf("out parse_config\n"); return true; } bool SDBoot::parse_config_file(const char *pConfigFile,VEC_SD_CONFIG &vecItem) { FILE *file=NULL; file = fopen(pConfigFile,"rb"); if( !file ){ return false; } int iFileSize; fseek(file,0,SEEK_END); iFileSize = ftell(file); fseek(file,0,SEEK_SET); char *pConfigBuf=NULL; pConfigBuf = new char[iFileSize+1]; if (!pConfigBuf) { fclose(file); return false; } memset(pConfigBuf,0,iFileSize+1); int iRead; iRead = fread(pConfigBuf,1,iFileSize,file); if (iRead!=iFileSize) { fclose(file); delete []pConfigBuf; return false; } fclose(file); bool bRet; bRet = parse_config(pConfigBuf,vecItem); delete []pConfigBuf; printf("out parse_config_file\n"); return bRet; } std::vector SDBoot::get_sd_config(char *configFile, int argc, char **argv){ std::vector args(argv, argv + argc); char arg[64]; VEC_SD_CONFIG vecItem; unsigned long i; if (!parse_config_file(configFile,vecItem)) { printf("out get_args_from_sd:parse_config_file\n"); return args; } for (i=0;i SDBoot::get_args_from_usb(int argc, char **argv){ printf("in get_args_from_usb\n"); std::vector args; ensure_usb_mounted(); if (!bUsbMounted) { printf("out get_args_from_usb:bUsbMounted=false\n"); return args; } char configFile[64]; strcpy(configFile, USB_ROOT); strcat(configFile, "/sd_boot_config.config"); args = get_sd_config(configFile, argc, argv); return args; } void SDBoot::bootwhere(){ bSDBoot = false; char param[1024]; int fd, ret; char *s=NULL; printf("read cmdline\n"); memset(param,0,1024); fd= open("/proc/cmdline", O_RDONLY); ret = read(fd, (char*)param, 1024); s = strstr(param,"sdfwupdate"); if(s != NULL){ bSDBoot = true; }else{ bSDBoot = false; } s = strstr(param, "usbfwupdate"); if(s != NULL){ bUsbBoot = true; }else{ bUsbBoot = false; } close(fd); } void SDBoot::ensure_usb_mounted(){ int i; for(i = 0; i < 10; i++) { if(0 == mount_usb_device()){ bUsbMounted = true; break; }else { printf("delay 1sec\n"); sleep(1); } } } int SDBoot::mount_usb_device() { char configFile[64]; char usbDevice[64]; int result; DIR* d=NULL; struct dirent* de; d = opendir(USB_ROOT); if (d) {//check whether usb_root has mounted strcpy(configFile, USB_ROOT); strcat(configFile, "/sd_boot_config.config"); if (access(configFile,F_OK)==0) { closedir(d); return 0; } closedir(d); } else { if (errno==ENOENT) { if (mkdir(USB_ROOT,0755)!=0) { printf("failed to create %s dir,err=%s!\n",USB_ROOT,strerror(errno)); return -1; } } else { printf("failed to open %s dir,err=%s\n!",USB_ROOT,strerror(errno)); return -1; } } d = opendir("/dev/block"); if(d != NULL) { while((de = readdir(d))) { printf("/dev/block/%s\n", de->d_name); if((strncmp(de->d_name, "sd", 2) == 0) &&(isxdigit(de->d_name[strlen(de->d_name)-1])!=0)){ memset(usbDevice, 0, sizeof(usbDevice)); sprintf(usbDevice, "/dev/block/%s", de->d_name); printf("try to mount usb device %s by vfat", usbDevice); result = mount(usbDevice, USB_ROOT, "vfat", MS_NOATIME | MS_NODEV | MS_NODIRATIME, "shortname=mixed,utf8"); if(result != 0) { printf("try to mount usb device %s by ntfs\n", usbDevice); result = mount(usbDevice, USB_ROOT, "ntfs", MS_NOATIME | MS_NODEV | MS_NODIRATIME, ""); } if(result == 0) { //strcpy(USB_DEVICE_PATH,usbDevice); USB_DEVICE_PATH = usbDevice; closedir(d); return 0; } } } closedir(d); } return -2; } bool SDBoot::do_direct_parse_config_file(const char * pConfigFile,VEC_SD_CONFIG & vecItem){ printf("enter do_direct_parse_config_file!\n"); return parse_config_file(pConfigFile, vecItem); } int SDBoot::do_rk_factory_mode(){ //pcba_test printf("enter pcba test!\n"); status = INSTALL_SUCCESS; const char *args[2]; args[0] = "/sbin/pcba_core"; args[1] = NULL; pid_t child = fork(); if (child == 0) { execv(args[0], (char* const*)args); fprintf(stderr, "run_program: execv failed: %s\n", strerror(errno)); status = INSTALL_ERROR; //pcbaTestPass = false; } int child_status; waitpid(child, &child_status, 0); if (WIFEXITED(child_status)) { if (WEXITSTATUS(child_status) != 0) { printf("pcba test error coder is %d \n", WEXITSTATUS(child_status)); status = INSTALL_ERROR; //pcbaTestPass = false; } } else if (WIFSIGNALED(child_status)) { printf("run_program: child terminated by signal %d\n", WTERMSIG(child_status)); status = INSTALL_ERROR; //pcbaTestPass = false; } return status; } void SDBoot::sdboot_set_status(int stat){ printf("enter sdboot_set_status !\n"); status = stat; } int SDBoot::sdboot_get_status(void){ printf("enter sdboot_get_status !\n"); return status; } bool SDBoot::sdboot_get_bSDBoot(void){ printf("enter sdboot_get_bSDBoot !\n"); return bSDBoot; } void SDBoot::sdboot_set_bSDBoot(bool is_sdboot){ printf("enter sdboot_set_bSDBoot !\n"); bSDBoot = is_sdboot; } bool SDBoot::sdboot_get_bUsbBoot(void){ printf("enter sdboot_get_bUsbBoot !\n"); return bUsbBoot; } void SDBoot::sdboot_set_bUsbBoot(bool is_usbboot){ printf("enter sdboot_set_bUsbBoot !\n"); bUsbBoot = is_usbboot; } void SDBoot::sdboot_set_bUpdateModel(bool bUpdate){ printf("enter sdboot_set_bUpdateModel !\n"); bUpdateModel = bUpdate; } bool SDBoot::sdboot_get_bUpdateModel(void){ printf("enter sdboot_get_bUpdateModel !\n"); return bUpdateModel; } std::string SDBoot::sdboot_get_usb_device_path(void){ printf("enter sdboot_get_usb_device_path !\n"); return USB_DEVICE_PATH; } void SDBoot::sdboot_set_bSDMounted(bool bMounted){ printf("enter sdboot_set_bUpdateModel !\n"); bSDMounted = bMounted; } bool SDBoot::sdboot_get_bSDMounted(void){ printf("enter sdboot_get_bUpdateModel !\n"); return bSDMounted; } bool SDBoot::sdboot_get_bUsbMounted(void){ printf("enter sdboot_get_bUpdateModel !\n"); return bUsbMounted; }