DWORD DJFixLoginConfigFile( PCSTR pszPath ) { DWORD ceError = ERROR_SUCCESS; PCSTR pszFilePath = NULL; PSTR pszTmpPath = NULL; PSTR pszFinalPath = NULL; BOOLEAN bFileExists = FALSE; FILE* fp = NULL; FILE* fp_new = NULL; DynamicArray lines; PSTR currentSystem = NULL; memset(&lines, 0, sizeof(lines)); if (IsNullOrEmptyString(pszPath)) pszFilePath = LOGIN_CONFIG_PATH; else pszFilePath = pszPath; GCE(ceError = CTGetFileTempPath( pszFilePath, &pszFinalPath, &pszTmpPath)); GCE(ceError = CTCheckFileExists(pszFinalPath, &bFileExists)); if (!bFileExists) goto cleanup; GCE(ceError = CTOpenFile(pszFinalPath, "r", &fp)); GCE(ceError = CTReadLines(fp, &lines)); GCE(ceError = CTSafeCloseFile(&fp)); GCE(ceError = GetAuthType(&lines, ¤tSystem)); if(!strcmp(currentSystem, "PAM_AUTH")) goto cleanup; GCE(ceError = SetAuthType(&lines, "PAM_AUTH")); GCE(ceError = CTOpenFile(pszTmpPath, "w", &fp_new)); GCE(ceError = CTWriteLines(fp_new, &lines)); GCE(ceError = CTSafeCloseFile(&fp_new)); GCE(ceError = CTSafeReplaceFile(pszFilePath, pszTmpPath)); cleanup: CTSafeCloseFile(&fp); CTSafeCloseFile(&fp_new); CT_SAFE_FREE_STRING(currentSystem); CT_SAFE_FREE_STRING(pszTmpPath); CT_SAFE_FREE_STRING(pszFinalPath); CTFreeLines(&lines); return ceError; }
static QueryResult QueryPamMode(const JoinProcessOptions *options, LWException **exc) { BOOLEAN bFileExists = FALSE; DistroInfo distro; QueryResult result = NotApplicable; FILE* fp = NULL; DynamicArray lines; PCSTR pszFilePath = LOGIN_CONFIG_PATH; PSTR currentSystem = NULL; memset(&lines, 0, sizeof(lines)); memset(&distro, 0, sizeof(distro)); if(!options->joiningDomain || options->enableMultipleJoins) goto cleanup; LW_CLEANUP_CTERR(exc, DJGetDistroInfo(NULL, &distro)); if(distro.os != OS_AIX || strcmp(distro.version, "5.3")) goto cleanup; LW_CLEANUP_CTERR(exc, CTCheckFileExists(pszFilePath, &bFileExists)); if (!bFileExists) goto cleanup; result = SufficientlyConfigured; LW_CLEANUP_CTERR(exc, CTOpenFile(pszFilePath, "r", &fp)); LW_CLEANUP_CTERR(exc, CTReadLines(fp, &lines)); LW_CLEANUP_CTERR(exc, CTSafeCloseFile(&fp)); LW_CLEANUP_CTERR(exc, GetAuthType(&lines, ¤tSystem)); if(strcmp(currentSystem, "PAM_AUTH")) goto cleanup; result = FullyConfigured; cleanup: CT_SAFE_FREE_STRING(currentSystem); DJFreeDistroInfo(&distro); CTSafeCloseFile(&fp); CTFreeLines(&lines); return result; }
static DWORD WriteHostnameToSunFiles( PCSTR pOldShortHostname, PCSTR pNewShortHostname, PCSTR pDnsDomainName, PCSTR pOldFqdnHostname, PCSTR pNewFqdnHostname ) { DWORD ceError = ERROR_SUCCESS; FILE* fp = NULL; PSTR* ppszHostfilePaths = NULL; DWORD nPaths = 0; DWORD iPath = 0; PSTR pRealPath = NULL; PSTR pTempPath = NULL; PSTR pOldEscapedShortHostname = NULL; PSTR pOldEscapedFqdnHostname = NULL; PSTR pOldSedExpression = NULL; PSTR pSedExpression = NULL; BOOLEAN isSame = FALSE; DJ_LOG_INFO("Setting hostname to [%s]", pNewShortHostname); ceError = CTGetFileTempPath( "/etc/nodename", &pRealPath, &pTempPath); BAIL_ON_CENTERIS_ERROR(ceError); ceError = CTOpenFile( pTempPath, "w", &fp); BAIL_ON_CENTERIS_ERROR(ceError); if (fprintf(fp, "%s\n", pNewShortHostname) < 0) { ceError = LwMapErrnoToLwError(errno); BAIL_ON_CENTERIS_ERROR(ceError); } ceError = CTSafeCloseFile(&fp); BAIL_ON_CENTERIS_ERROR(ceError); ceError = CTFileContentsSame( pTempPath, pRealPath, &isSame); BAIL_ON_CENTERIS_ERROR(ceError); if (isSame) { BAIL_ON_CENTERIS_ERROR(ceError = CTRemoveFile(pTempPath)); } else { ceError = CTSafeReplaceFile(pRealPath, pTempPath); BAIL_ON_CENTERIS_ERROR(ceError); } CT_SAFE_FREE_STRING(pRealPath); CT_SAFE_FREE_STRING(pTempPath); ceError = CTGetFileTempPath( "/etc/defaultdomain", &pRealPath, &pTempPath); BAIL_ON_CENTERIS_ERROR(ceError); ceError = CTOpenFile( pTempPath, "w", &fp); BAIL_ON_CENTERIS_ERROR(ceError); fprintf(fp, "%s\n", pDnsDomainName); ceError = CTSafeCloseFile(&fp); BAIL_ON_CENTERIS_ERROR(ceError); ceError = CTFileContentsSame( pTempPath, pRealPath, &isSame); BAIL_ON_CENTERIS_ERROR(ceError); if (isSame) { BAIL_ON_CENTERIS_ERROR(ceError = CTRemoveFile(pTempPath)); } else { ceError = CTSafeReplaceFile(pRealPath, pTempPath); BAIL_ON_CENTERIS_ERROR(ceError); } /* The first column of the /etc/hostname.<interface> files is the IP * address of the interface. It may either be specified directly in the * file, or the file may refer to an entry in /etc/hosts. This program is * editing /etc/hosts, any old entries in the hostname files need to be * fixed. */ ceError = CTGetMatchingFilePathsInFolder("/etc", "hostname.*", &ppszHostfilePaths, &nPaths); BAIL_ON_CENTERIS_ERROR(ceError); ceError = SedEscapeLiteral( pOldShortHostname, &pOldEscapedShortHostname); BAIL_ON_CENTERIS_ERROR(ceError); ceError = LwAllocateStringPrintf( &pSedExpression, "s/^%s\\([ ].*\\)\\{0,1\\}$/%s\\1/", pOldEscapedShortHostname, pNewShortHostname); BAIL_ON_CENTERIS_ERROR(ceError); if (pOldFqdnHostname != NULL) { ceError = SedEscapeLiteral( pOldFqdnHostname, &pOldEscapedFqdnHostname); BAIL_ON_CENTERIS_ERROR(ceError); pOldSedExpression = pSedExpression; pSedExpression = NULL; ceError = LwAllocateStringPrintf( &pSedExpression, "%s;s/^%s\\([ ].*\\)\\{0,1\\}$/%s\\1/", pOldSedExpression, pOldEscapedFqdnHostname, pNewFqdnHostname); BAIL_ON_CENTERIS_ERROR(ceError); } for (iPath = 0; iPath < nPaths; iPath++) { if (!CTStrEndsWith(ppszHostfilePaths[iPath], ".lwidentity.bak") && !CTStrEndsWith(ppszHostfilePaths[iPath], ".lwidentity.orig")) { ceError = CTRunSedOnFile( ppszHostfilePaths[iPath], ppszHostfilePaths[iPath], FALSE, pSedExpression); BAIL_ON_CENTERIS_ERROR(ceError); } } error: if (ppszHostfilePaths) CTFreeStringArray(ppszHostfilePaths, nPaths); if (fp) { fclose(fp); } CT_SAFE_FREE_STRING(pRealPath); CT_SAFE_FREE_STRING(pTempPath); CT_SAFE_FREE_STRING(pOldEscapedShortHostname); CT_SAFE_FREE_STRING(pOldEscapedFqdnHostname); CT_SAFE_FREE_STRING(pOldSedExpression); CT_SAFE_FREE_STRING(pSedExpression); return ceError; }
static void ConfigureApparmor(BOOLEAN enable, LWException **exc) { DWORD ceError = ERROR_SUCCESS; BOOLEAN hasApparmor; BOOLEAN configured; BOOLEAN usingMr; FILE *file = NULL; PCSTR addString; PSTR restartPath = NULL; PSTR restartCommand = NULL; char *tempName = NULL; char *finalName = NULL; LW_CLEANUP_CTERR(exc, IsApparmorConfigured(&configured)); if(configured == enable) goto cleanup; LW_CLEANUP_CTERR(exc, CTCheckFileOrLinkExists(APPARMOR_NSSWITCH, &hasApparmor)); if(!hasApparmor) goto cleanup; GCE(ceError = CTGetFileTempPath( APPARMOR_NSSWITCH, &finalName, &tempName)); LW_CLEANUP_CTERR(exc, CTCheckFileHoldsPattern(finalName, "mr,", &usingMr)); if(usingMr) addString = PREFIXDIR "/lib/*.so* mr,\n" PREFIXDIR "/lib64/*.so* mr,\n" "/tmp/.lwidentity/pipe rw,\n" LOCALSTATEDIR "/lib/likewise/.lsassd rw,\n" LOCALSTATEDIR "/tmp/.lsaclient_* rw,\n"; else addString = PREFIXDIR "/lib/*.so* r,\n" PREFIXDIR "/lib64/*.so* r,\n" "/tmp/.lwidentity/pipe rw,\n" LOCALSTATEDIR "/lib/likewise/.lsassd rw,\n" LOCALSTATEDIR "/tmp/.lsaclient_* rw,\n"; if(enable) { LW_CLEANUP_CTERR(exc, CTCopyFileWithOriginalPerms(finalName, tempName)); LW_CLEANUP_CTERR(exc, CTOpenFile(tempName, "a", &file)); LW_CLEANUP_CTERR(exc, CTFilePrintf(file, "# likewise\n%s# end likewise\n", addString)); CTSafeCloseFile(&file); LW_CLEANUP_CTERR(exc, CTSafeReplaceFile(finalName, tempName)); } else { LW_CLEANUP_CTERR(exc, CTRunSedOnFile(finalName, finalName, FALSE, "/^[ \t]*#[ \t]*likewise[ \t]*$/,/^[ \t]*#[ \t]*end likewise[ \t]*$/d")); LW_CLEANUP_CTERR(exc, CTRunSedOnFile(finalName, finalName, FALSE, "/^[ \t]*#[ \t]*centeris[ \t]*$/,/^[ \t]*#[ \t]*end centeris[ \t]*$/d")); } ceError = CTFindFileInPath("rcapparmor", "/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin", &restartPath); if(ceError == ERROR_FILE_NOT_FOUND) { ceError = CTFindFileInPath("apparmor", "/etc/init.d/apparmor", &restartPath); } if(ceError == ERROR_FILE_NOT_FOUND) { ceError = ERROR_SUCCESS; } else if(!ceError) { LW_CLEANUP_CTERR(exc, CTAllocateStringPrintf(&restartCommand, "%s restart", restartPath)); LW_TRY(exc, CTCaptureOutputToExc(restartCommand, &LW_EXC)); } LW_CLEANUP_CTERR(exc, ceError); cleanup: if(file != NULL) { CTCloseFile(file); CTRemoveFile(tempName); } CT_SAFE_FREE_STRING(restartPath); CT_SAFE_FREE_STRING(restartCommand); CT_SAFE_FREE_STRING(tempName); CT_SAFE_FREE_STRING(finalName); }
void DJManageDaemons( BOOLEAN bStart, LWException **exc ) { BOOLEAN bFileExists = TRUE; FILE* fp = NULL; LWException *innerExc = NULL; int i; PLSA_LOG_INFO pLogInfo = NULL; BOOLEAN bLsassContacted = FALSE; DWORD dwError = 0; LW_HANDLE hLsa = NULL; LW_CLEANUP_CTERR(exc, CTCheckFileExists(PWGRD, &bFileExists)); if(bFileExists) { //Shutdown pwgr (a nscd-like daemon) on HP-UX because it only handles //usernames up to 8 characters in length. LW_TRY(exc, DJStartStopDaemon("pwgr", FALSE, &LW_EXC)); LW_CLEANUP_CTERR(exc, CTRunSedOnFile(PWGRD, PWGRD, FALSE, "s/=1/=0/")); } if(bStart) { // Set registry value for gpagentd to autostart. dwError = SetBooleanRegistryValue("Services\\gpagent", "Autostart", TRUE); // Trigger gpagentd start dwError = DJStartService("gpagent"); // Make sure lsass is responding bLsassContacted = FALSE; for (i = 0; !bLsassContacted && i < 30; i++) { DJ_LOG_INFO("Trying to contact lsassd"); if (hLsa) { LsaCloseServer(hLsa); hLsa = NULL; } dwError = LsaOpenServer(&hLsa); if (dwError == ERROR_FILE_NOT_FOUND || dwError == LW_ERROR_ERRNO_ECONNREFUSED) { DJ_LOG_INFO("Failed with %d", dwError); dwError = 0; sleep(1); continue; } LW_CLEANUP_CTERR(exc, dwError); LW_CLEANUP_CTERR(exc, LsaGetLogInfo(hLsa, &pLogInfo)); bLsassContacted = TRUE; } if (!bLsassContacted) { LW_RAISE_EX(exc, ERROR_SERVICE_NOT_ACTIVE, "Unable to reach lsassd", "The lsass daemon could not be reached for 30 seconds after trying to start it. Please verify it is running."); goto cleanup; } } else { dwError = SetBooleanRegistryValue("Services\\gpagent", "Autostart", FALSE); dwError = DJStopService("gpagent"); } cleanup: CTSafeCloseFile(&fp); if (pLogInfo) { LsaFreeLogInfo(pLogInfo); } if (hLsa) { LsaCloseServer(hLsa); } LW_HANDLE(&innerExc); }
//Solaris and AIX should have this DWORD CTGetPidOfCmdLine( PCSTR programName, PCSTR programFilename, PCSTR cmdLine, uid_t owner, pid_t *pid, size_t *count ) { DWORD ceError = ERROR_NOT_SUPPORTED; size_t fillCount = 0; size_t foundCount = 0; struct stat findStat; DIR *dir = NULL; struct dirent *dirEntry = NULL; PSTR filePath = NULL; struct psinfo infoStruct; FILE *infoFile = NULL; struct stat compareStat; BOOLEAN bFileExists; #if defined(__LWI_SOLARIS__) int (*getzoneid)() = NULL; int zoneid = -1; #endif if(count) { fillCount = *count; *count = 0; } else if(pid != NULL) fillCount = 1; if(programFilename != NULL) { while(stat(programFilename, &findStat) < 0) { if(errno == EINTR) continue; GCE(ceError = LwMapErrnoToLwError(errno)); } } if ((dir = opendir("/proc")) == NULL) { GCE(ceError = LwMapErrnoToLwError(errno)); } #if defined(__LWI_SOLARIS__) getzoneid = dlsym(RTLD_DEFAULT, "getzoneid"); if (getzoneid) { zoneid = getzoneid(); } #endif while(1) { errno = 0; dirEntry = readdir(dir); if(dirEntry == NULL) { if(errno != 0) GCE(ceError = LwMapErrnoToLwError(errno)); else { //No error here. We simply read the last entry break; } } if(dirEntry->d_name[0] == '.') continue; // On AIX, there is a /proc/sys which does not contain a psinfo if(!isdigit((int)dirEntry->d_name[0])) continue; CT_SAFE_FREE_STRING(filePath); GCE(ceError = CTAllocateStringPrintf(&filePath, "/proc/%s/psinfo", dirEntry->d_name)); GCE(ceError = CTCheckFileOrLinkExists(filePath, &bFileExists)); if(!bFileExists) { // On AIX 6.1, a defunct process can lack a psinfo file. continue; } GCE(ceError = CTSafeCloseFile(&infoFile)); GCE(ceError = CTOpenFile(filePath, "r", &infoFile)); if(fread(&infoStruct, sizeof(infoStruct), 1, infoFile) != 1) { GCE(ceError = LwMapErrnoToLwError(errno)); } #if defined(__LWI_SOLARIS__) if (zoneid != -1) { int processzoneid = -1; #ifdef HAVE_STRUCT_PSINFO_PR_ZONEID processzoneid = (int) infoStruct.pr_zoneid; #else processzoneid = (int) *(infoStruct.pr_filler + sizeof(infoStruct.pr_filler)/sizeof(infoStruct.pr_filler[0]) - 3); #endif if (zoneid != processzoneid) { continue; } } #endif if (owner != (uid_t)-1 && owner != infoStruct.pr_euid) { continue; } if (programName != NULL && strcmp(infoStruct.pr_fname, programName)) { continue; } if (cmdLine != NULL && strcmp(infoStruct.pr_psargs, cmdLine)) { continue; } if(programFilename != NULL) { CT_SAFE_FREE_STRING(filePath); GCE(ceError = CTAllocateStringPrintf(&filePath, "/proc/%s/object/a.out", dirEntry->d_name)); while(stat(filePath, &compareStat) < 0) { if(errno == EINTR) continue; if(errno == ENOENT || errno == ENOTDIR) { //This process wasn't executed from a file? goto not_match; } GCE(ceError = LwMapErrnoToLwError(errno)); } if(findStat.st_ino != compareStat.st_ino) continue; if(findStat.st_dev != compareStat.st_dev) continue; if(findStat.st_rdev != compareStat.st_rdev) continue; } //This is a match if(foundCount < fillCount) pid[foundCount] = infoStruct.pr_pid; foundCount++; not_match: ; } if(count) *count = foundCount; else if(!ceError && foundCount == 0) ceError = ERROR_PROC_NOT_FOUND; cleanup: if(dir != NULL) closedir(dir); CT_SAFE_FREE_STRING(filePath); CTSafeCloseFile(&infoFile); return ceError; }
DWORD CTGetLikewiseVersion( PSTR *product, PSTR *version, PSTR *build, PSTR *revision ) { FILE *versionFile = NULL; PSTR line = NULL; BOOLEAN isEndOfFile = FALSE; DWORD ceError = ERROR_SUCCESS; BOOLEAN bIsEnterprise = FALSE; PSTR _product = NULL; PSTR _version = NULL; PSTR _build = NULL; PSTR _revision = NULL; *version = NULL; *build = NULL; *revision = NULL; #ifdef MINIMAL_JOIN GCE(ceError = CTOpenFile(LOCALSTATEDIR "/VERSION", "r", &versionFile)); #else ceError = CTOpenFile(PREFIXDIR "/data/ENTERPRISE_VERSION", "r", &versionFile); if (ceError == 0) { bIsEnterprise = TRUE; } else { GCE(ceError = CTOpenFile(PREFIXDIR "/data/VERSION", "r", &versionFile)); } #endif while (TRUE) { CT_SAFE_FREE_STRING(line); GCE(ceError = CTReadNextLine(versionFile, &line, &isEndOfFile)); if (isEndOfFile) break; CTStripWhitespace(line); if (!strncmp(line, "VERSION=", sizeof("VERSION=") - 1)) { GCE(ceError = CTStrdup(line + sizeof("VERSION=") - 1, &_version)); } else if (!strncmp(line, "BUILD=", sizeof("BUILD=") - 1)) { GCE(ceError = CTStrdup(line + sizeof("BUILD=") - 1, &_build)); } else if (!strncmp(line, "REVISION=", sizeof("REVISION=") - 1)) { GCE(ceError = CTStrdup(line + sizeof("REVISION=") - 1, &_revision)); } } if (bIsEnterprise) { GCE(ceError = CTStrdup("Enterprise", &_product)); } else { GCE(ceError = CTStrdup("Open", &_product)); } if (_version == NULL) { GCE(ceError = CTStrdup("unknown", &_version)); } if (_build == NULL) { GCE(ceError = CTStrdup("unknown", &_build)); } if (_revision == NULL) { GCE(ceError = CTStrdup("unknown", &_revision)); } GCE(ceError = CTSafeCloseFile(&versionFile)); *product = _product; *version = _version; *build = _build; *revision = _revision; _product = NULL; _version = NULL; _build = NULL; _revision = NULL; cleanup: CTSafeCloseFile(&versionFile); CT_SAFE_FREE_STRING(line); CT_SAFE_FREE_STRING(_version); CT_SAFE_FREE_STRING(_build); CT_SAFE_FREE_STRING(_revision); return ceError; }
DWORD CTGetPidOfCmdLine( PCSTR programName, PCSTR programFilename, PCSTR cmdLine, uid_t owner, pid_t *pid, size_t *count ) { DWORD ceError = ERROR_NOT_SUPPORTED; size_t fillCount = 0; size_t foundCount = 0; struct stat findStat; #if HAVE_DECL_PSTAT_GETPROC //HPUX should have this struct pst_status mystatus; struct pst_status status[10]; int inBuffer; int i; #endif #ifdef HAVE_STRUCT_PSINFO //Solaris and AIX should have this DIR *dir = NULL; struct dirent *dirEntry = NULL; PSTR filePath = NULL; struct psinfo infoStruct; FILE *infoFile = NULL; struct stat compareStat; BOOLEAN bFileExists; #endif #if defined(HAVE_KVM_GETPROCS) && HAVE_DECL_KERN_PROC_PATHNAME //FreeBSD has this char pathBuffer[MAXPATHLEN]; size_t len; int unfilteredCount; kvm_t *kd = NULL; struct kinfo_proc *procs; int i; struct kinfo_proc *pos; int sysctlName[4] = { CTL_KERN, KERN_PROC, KERN_PROC_PATHNAME, 0 }; #endif if(count) { fillCount = *count; *count = 0; } else if(pid != NULL) fillCount = 1; if(programFilename != NULL) { while(stat(programFilename, &findStat) < 0) { if(errno == EINTR) continue; GCE(ceError = LwMapErrnoToLwError(errno)); } } #if HAVE_DECL_PSTAT_GETPROC //First get the process info for this process inBuffer = pstat_getproc(&mystatus, sizeof(mystatus), 0, getpid()); if(inBuffer != 1) GCE(ceError = LwMapErrnoToLwError(errno)); //Now look at all processes inBuffer = pstat_getproc(status, sizeof(status[0]), sizeof(status)/sizeof(status[0]), 0); if(inBuffer < 0) GCE(ceError = LwMapErrnoToLwError(errno)); while(inBuffer > 0) { for(i = 0; i < inBuffer; i++) { if(memcmp(&mystatus.pst_rdir, &status[i].pst_rdir, sizeof(mystatus.pst_rdir))) { /* This process has a different root directory (it is being run via a chroot). Let's not count this process as a match. */ continue; } if (owner != (uid_t)-1 && owner != status[i].pst_euid) { continue; } if (programName != NULL && strcmp(status[i].pst_ucomm, programName)) { continue; } if (cmdLine != NULL && strcmp(status[i].pst_cmd, cmdLine)) { continue; } if(programFilename != NULL && ( status[i].pst_text.psf_fileid != findStat.st_ino || status[i].pst_text.psf_fsid.psfs_id != findStat.st_dev || status[i].pst_text.psf_fsid.psfs_type != findStat.st_fstype )) { continue; } //This is a match if(foundCount < fillCount) pid[foundCount] = status[i].pst_pid; foundCount++; } //Continue looking at the process list where we left off inBuffer = pstat_getproc(status, sizeof(status[0]), sizeof(status)/sizeof(status[0]), status[inBuffer - 1].pst_idx + 1); if(inBuffer < 0) GCE(ceError = LwMapErrnoToLwError(errno)); } ceError = ERROR_SUCCESS; #endif #ifdef HAVE_STRUCT_PSINFO if ((dir = opendir("/proc")) == NULL) { GCE(ceError = LwMapErrnoToLwError(errno)); } while(1) { errno = 0; dirEntry = readdir(dir); if(dirEntry == NULL) { if(errno != 0) GCE(ceError = LwMapErrnoToLwError(errno)); else { //No error here. We simply read the last entry break; } } if(dirEntry->d_name[0] == '.') continue; // On AIX, there is a /proc/sys which does not contain a psinfo if(!isdigit((int)dirEntry->d_name[0])) continue; CT_SAFE_FREE_STRING(filePath); GCE(ceError = CTAllocateStringPrintf(&filePath, "/proc/%s/psinfo", dirEntry->d_name)); GCE(ceError = CTCheckFileOrLinkExists(filePath, &bFileExists)); if(!bFileExists) { // On AIX 6.1, a defunct process can lack a psinfo file. continue; } GCE(ceError = CTSafeCloseFile(&infoFile)); GCE(ceError = CTOpenFile(filePath, "r", &infoFile)); if(fread(&infoStruct, sizeof(infoStruct), 1, infoFile) != 1) { GCE(ceError = LwMapErrnoToLwError(errno)); } if (owner != (uid_t)-1 && owner != infoStruct.pr_euid) { continue; } if (programName != NULL && strcmp(infoStruct.pr_fname, programName)) { continue; } if (cmdLine != NULL && strcmp(infoStruct.pr_psargs, cmdLine)) { continue; } if(programFilename != NULL) { CT_SAFE_FREE_STRING(filePath); GCE(ceError = CTAllocateStringPrintf(&filePath, "/proc/%s/object/a.out", dirEntry->d_name)); while(stat(filePath, &compareStat) < 0) { if(errno == EINTR) continue; if(errno == ENOENT || errno == ENOTDIR) { //This process wasn't executed from a file? goto not_match; } GCE(ceError = LwMapErrnoToLwError(errno)); } if(findStat.st_ino != compareStat.st_ino) continue; if(findStat.st_dev != compareStat.st_dev) continue; if(findStat.st_rdev != compareStat.st_rdev) continue; } //This is a match if(foundCount < fillCount) pid[foundCount] = infoStruct.pr_pid; foundCount++; not_match: ; } #endif #if defined(HAVE_KVM_GETPROCS) && HAVE_DECL_KERN_PROC_PATHNAME kd = kvm_open(NULL, "/dev/null", NULL, O_RDONLY, NULL); if (kd == NULL) GCE(ceError = DWORD_ACCESS_DENIED); procs = kvm_getprocs(kd, KERN_PROC_PROC, 0, &unfilteredCount); if (procs == NULL) GCE(ceError = DWORD_ACCESS_DENIED); pos = procs; for(i = 0; i < unfilteredCount; i++, pos = (struct kinfo_proc *)((char *)pos + pos->ki_structsize)) { if (owner != (uid_t)-1 && owner != pos->ki_uid) { continue; } if (programName != NULL && strcmp(pos->ki_comm, programName)) { continue; } if (cmdLine != NULL) { char **args = kvm_getargv(kd, pos, 0); char **argPos = args; PCSTR cmdLinePos = cmdLine; while (*cmdLinePos != '\0') { if (argPos == NULL || *argPos == NULL) break; if (strncmp(cmdLinePos, *argPos, strlen(*argPos))) break; cmdLinePos += strlen(*argPos); argPos++; if(cmdLinePos[0] == ' ') cmdLinePos++; } if(*cmdLinePos != '\0' || (argPos != NULL && *argPos != NULL)) { //not a match continue; } } if (programFilename != NULL) { pathBuffer[0] = '\0'; if (pos->ki_textvp != NULL) { sysctlName[3] = pos->ki_pid; len = sizeof(pathBuffer); if( sysctl(sysctlName, 4, pathBuffer, &len, NULL, 0) < 0) { /* If the executable path does not exist (e.g. because the file was deleted after the program started), move on */ if (errno == ENOENT) continue; GCE(ceError = LwMapErrnoToLwError(errno)); } } if(strcmp(programFilename, pathBuffer)) continue; } //This is a match if(foundCount < fillCount) pid[foundCount] = pos->ki_pid; foundCount++; } ceError = ERROR_SUCCESS; #endif if(count) *count = foundCount; else if(!ceError && foundCount == 0) ceError = ERROR_PROC_NOT_FOUND; cleanup: #ifdef HAVE_STRUCT_PSINFO if(dir != NULL) closedir(dir); CT_SAFE_FREE_STRING(filePath); CTSafeCloseFile(&infoFile); #endif #if defined(HAVE_KVM_GETPROCS) && HAVE_DECL_KERN_PROC_PATHNAME if(kd != NULL) { kvm_close(kd); } #endif return ceError; }