/* * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU Library General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ #include "util.h" #ifndef TRUE #define TRUE 0 #endif #ifndef FALSE #define FALSE 1 #endif #ifndef PASSWD_FILE #define PASSWD_FILE "/etc/mypasswd" #endif int str2int(const char * string) { /* ----------------------------------------------------------------------------- * Convert a string to int * * @param const char *, the given string * @return int -1 if the given string do not represent an integer * -------------------------------------------------------------------------- */ int result = 0; int int_tmp; const char * pts = string; while (*pts != '\0') { int_tmp = *pts - 48; if((int_tmp >= 0) && (int_tmp <= 9)) { result = 10*result + int_tmp; } else if (*pts != ' ') { return -1; } pts++; } return result; } char * substring(const char * src, int start, int length) { /* ----------------------------------------------------------------------------- * get a substring in a string * * @param const char *, source string * @param int, the offset * @param int, the length * @return char *, result in a dynamically allocated memory * so the result must be free() * -------------------------------------------------------------------------- */ char *result = (char *)malloc(sizeof(char) * length + 1); if (result == NULL) { logmsg(LOG_ERR, "substring() : %s", strerror(errno)); return NULL; } memcpy(result, &src[start], length); result[length] = '\0'; return result; } char * str_replace(const char * strfrom, const char * strby, const char * strin) { /* ----------------------------------------------------------------------------- * Replace a string by another string in a string * * @param const char *, string to replace * @param const char *, string replacement * @param const char *, source string * @return char *, result in a dynamically allocated memory * so the result must be free() * -------------------------------------------------------------------------- */ char *result = NULL, *tmp, *pos; char *p = (char *)strin; size_t len_from, len_by, len, total_len = 0; len_from = strlen(strfrom); len_by = strlen(strby); while ((pos = strstr(p, strfrom)) != NULL) { /* Compute the new length */ len = (pos - p) + len_by; tmp = realloc(result, (total_len + len) * sizeof(char) + 1); if (tmp == NULL) { logmsg(LOG_ERR, "str_replace() : %s", strerror(errno)); return NULL; } result = tmp; memcpy(&result[total_len], p, sizeof(char) * (pos - p)); memcpy(&result[total_len + (pos - p)], strby, sizeof(char) * len_by); total_len += len; p = pos + len_from; } if (*p) { len = strlen(p); tmp = realloc(result, (total_len + len) * sizeof(char) + 1); if (tmp == NULL) { logmsg(LOG_ERR, "str_replace() : %s", strerror(errno)); return NULL; } result = tmp; memcpy(&result[total_len], p, sizeof(char) * len); total_len += len; } result[total_len] = '\0'; if (total_len > 0) return result; return strdup(strin); } char * trim(const char * strin) { /* ----------------------------------------------------------------------------- * Trim in the given string * * @param const char * * @return char *, result in a dynamically allocated memory * so the result must be free() * -------------------------------------------------------------------------- */ char * result = NULL; char *pts_start, *pts_end; unsigned int left = 0; unsigned int right = 0; size_t size = strlen(strin); const char delimiters[] = " \t\n\r"; if (size <= 0) return NULL; pts_start = (char *)strin; pts_end = (char *)&strin[size - 1]; /* Left trim */ while((*pts_start != '\0') && ((strchr(delimiters, (int)*pts_start)) != NULL)) { left++; pts_start++; } /* Right trim */ while((pts_end != strin) && ((strchr(delimiters, (int)*pts_end)) != NULL)) { right++; pts_end--; } result = (char *)malloc((size - left - right) * sizeof(char) + 1); if (result == NULL) { logmsg(LOG_ERR, "trim() : %s", strerror(errno)); return NULL; } memcpy(result, (void *)&strin[left], (size - left - right) * sizeof(char)); result[size - left - right] = '\0'; return result; } char * stripcrlf(char * str) { /* ----------------------------------------------------------------------------- * Strip CRLR in the given string * * @param char * * @return char * * -------------------------------------------------------------------------- */ char *pts = str + strlen(str); while(pts - str >= 0) { if ((*pts == 10) || (*pts == 13)) *pts = '\0'; pts--; } return pts; } char * str2upper(const char * strin) { /* ----------------------------------------------------------------------------- * Upper case all character in the given string * * @param const char * * @return char *, result in a dynamically allocated memory * so the result must be free() * -------------------------------------------------------------------------- */ char * result = NULL, * pts; result = strdup(strin); if (result == NULL) { logmsg(LOG_ERR, "str2upper() : strdup error"); return NULL; } for (pts = result; *pts; pts++) { if ((*pts >= 97) && (*pts <= 122)) *pts -= 32; } return result; } char * str2lower(const char * strin) { /* ----------------------------------------------------------------------------- * Lower case all character in the given string * * @param const char * * @return char *, result in a dynamically allocated memory * so the result must be free() * -------------------------------------------------------------------------- */ char * result = NULL, * pts; result = strdup(strin); if (result == NULL) { logmsg(LOG_ERR, "str2upper() : strdup error"); return NULL; } for (pts = result; *pts; pts++) { if ((*pts >= 65) && (*pts <= 90)) *pts += 32; } return result; } char * getlocaltime() { /* ----------------------------------------------------------------------------- * Get local datetime in YYY-MM-DD hh:mm:ss format * * @return char *, result in a statically allocated memory * -------------------------------------------------------------------------- */ static char strtime[20]; time_t timer = time(NULL); struct tm now = *localtime(&timer); snprintf(strtime, sizeof(strtime), "%4d-%02d-%02d %02d:%02d:%02d", now.tm_year + 1900, now.tm_mon, now.tm_mday, now.tm_hour, now.tm_min, now.tm_sec); return strtime; } char * getdate() { /* ----------------------------------------------------------------------------- * Get date in YYYY-MM-DD format * * @param int * @return char *, result in a statically allocated memory * -------------------------------------------------------------------------- */ static char strtime[11]; time_t timer = time(NULL); struct tm now = *localtime(&timer); snprintf(strtime, sizeof(strtime), "%4d-%02d-%02d", now.tm_year+1900, now.tm_mon+1, now.tm_mday); return strtime; } char * gettime() { /* ----------------------------------------------------------------------------- * Get time * * @return char *, result in a statically allocated memory * -------------------------------------------------------------------------- */ static char strtime[11]; time_t timer = time(NULL); struct tm now = *localtime(&timer); snprintf(strtime, sizeof(strtime), "%02d:%02d:%02d", now.tm_hour, now.tm_min, now.tm_sec); return strtime; } char * formatdate(int secondes) { /* ----------------------------------------------------------------------------- * Format second to date * * @param int * @return char *, result in a statically allocated memory * -------------------------------------------------------------------------- */ int jour, heure, minute, seconde; static char strtime[20]; jour = secondes / 86400; heure = (secondes - (jour * 86400)) / 3600; minute = (secondes - (jour * 86400) - (heure * 3600)) / 60; seconde = secondes - (jour * 86400) - (heure * 3600) - (minute * 60); snprintf(strtime, sizeof(strtime), "%dj %02dh%02dm%02ds", jour, heure, minute, seconde); return strtime; } char * addslashes(char * str_in) { /* ----------------------------------------------------------------------------- * Addslashes before characters such as ', `, " * * @param const char * * @return char *, result in a dynamically allocated memory * so the result must be free() * -------------------------------------------------------------------------- */ char *result, *result_realloc, *result_tmp; char * pts = str_in; int len = strlen(str_in)+1; result = (char *)malloc(len); if (result == NULL) { logmsg(LOG_ERR, "addslashes : malloc error"); return NULL; } memset(result, 0, len); result_tmp = result; /* printf("%s %d %d\n", pts, len, sizeof(char)); */ while(*pts != '\0') { switch((int)*pts) { case 39: /* ' */ case 34: /* " */ case 96: /* ` */ len++; result_realloc = (char *)realloc(result, len); if (result_realloc == NULL) { logmsg(LOG_ERR, "addslashes : realloc error"); free(result); return NULL; } result = result_realloc; *(result+len-1) = '\0'; *result_tmp = (char)92; result_tmp++; break; } *result_tmp = *pts; pts++; result_tmp++; } *result_tmp = '\0'; /* printf("%s\n", result); printf("%s\n", result_tmp); printf("len %d, %d, %d, %d\n", len, result_tmp-result, strlen(result), strlen(result_tmp)); */ return result; } #ifdef USE_CRYPT char * md5(const char * pwd) { /* ----------------------------------------------------------------------------- * Crypt a string in a md5 crypt manner * * @param const char *, the string to crypt * @return char *, the crypt result in a static memory * -------------------------------------------------------------------------- */ char salt[3]; char des_salt[12]; char *tmp = NULL; memset(&salt, 0, 3); memset(&des_salt, 0, 12); if (strlen(pwd) < 2) { return NULL; } snprintf(salt, sizeof(salt), "%c%c", *pwd, *(pwd+1)); tmp = crypt(pwd, salt); if (tmp != NULL && strlen(tmp) > 2) { snprintf(des_salt, sizeof(des_salt), "$1$%s", tmp + 2); des_salt[12] = '\0'; return (char *)crypt(pwd, des_salt); } return NULL; } #endif void vsysdaemonlog(const char *pgm, const char * filename, const char * line, va_list ap) { /* ----------------------------------------------------------------------------- * Custom log system to a file * * @param const char *, program name * @param const char *, file name * @param const char *, printf format * @param va_list, arguments list * -------------------------------------------------------------------------- */ int pid; char *msg = NULL, *logline = NULL, *date = NULL, *time = NULL; FILE *fd = NULL; vasprintf(&msg, line, ap); date = getdate(); time = gettime(); pid = getpid(); logline = xstrdup("%s %s %s[%d]: %s", date, time, pgm, pid, msg); free(msg); msg = NULL; if (logline == NULL) logmsg(LOG_ERR, "%s at vsysdaemonlog() : Error on xstrdup", pgm); fd = fopen(filename, "a"); if (fd != NULL) { if (!fwrite((void *)logline, 1, strlen(logline), fd)) { logmsg(LOG_ERR, "%s at vsysdaemonlog() : Log failed on %s", pgm, filename); } } else { logmsg(LOG_ERR, "%s at vsysdaemonlog() : Open Log file failed on %s", pgm, filename); } free(logline); fclose(fd); } void sysdaemonlog(const char *pgm, const char * filename, const char * line, ...) { /* ----------------------------------------------------------------------------- * Custom log system to a file * * @param const char *, program name * @param const char *, file name * @param const char *, printf format * -------------------------------------------------------------------------- */ va_list args; va_start(args, line); vsysdaemonlog(pgm, filename, line, args); va_end(args); } char * xstrdup(const char * str, ...) { /* ----------------------------------------------------------------------------- * Concat strings in a newly allocated memory * * @param const char *, printf format * @return char *, result in a dynamically allocated memory * so the result must be free() * -------------------------------------------------------------------------- */ va_list ap; char *result = NULL; va_start(ap, str); vasprintf(&result, str, ap); va_end(ap); return result; } int getuidbyname(const char *login) { /* ----------------------------------------------------------------------------- * Get the uid number by name * * @param const char *, login name * @return int or -1 if login is not found * -------------------------------------------------------------------------- */ struct passwd * usrinfo; usrinfo = getpwnam(login); if (usrinfo == NULL) { logmsg(LOG_ERR, "getuidbyname() : no such user %s", login); return -1; } return usrinfo->pw_uid; } int getgidbyname(const char *group) { /* ----------------------------------------------------------------------------- * Get the gid number by name * * @param const char *, group name * @return int or -1 if group is not found * -------------------------------------------------------------------------- */ struct group * grpinfo; grpinfo = getgrnam(group); if (grpinfo == NULL) { logmsg(LOG_ERR, "getgidbyname() : no such group %s", group); return -1; } return grpinfo->gr_gid; } char *get_homedir() { /* ----------------------------------------------------------------------------- * Get home path * * @return char *, path in a dynamically allocated memory * so the result must be free() * -------------------------------------------------------------------------- */ char *path = NULL; struct passwd * usrinfo; usrinfo = getpwuid(getuid()); if ((path = strdup((const char *)usrinfo->pw_dir)) == NULL) { logmsg(LOG_ERR, "get_homedir() : strdup error"); } return path; } char *get_currentdir() { /* ----------------------------------------------------------------------------- * Get current path * * @return char *, path in a dynamically allocated memory * so the result must be free() * -------------------------------------------------------------------------- */ char * path = NULL; char * path_tmp = NULL; int size = 16; for(;;) { if ((path_tmp = (char *)realloc(path, size)) == NULL) { logmsg(LOG_ERR, "get_currentdir() : realloc error"); break; } path = path_tmp; if (getcwd(path, size) != NULL) { break; } if (errno != ERANGE) { break; } size *= 2; } return path; } char * get_dir_cdup(const char *path) { /* ----------------------------------------------------------------------------- * Get parent path * * @param const char *, directory * @return char *, path in a dynamically allocated memory * so the result must be free() * -------------------------------------------------------------------------- */ unsigned int i = 0; char *result = NULL; unsigned int last_i = strlen(path) - 1; result = strdup(path); if (result == NULL) return NULL; for (i = last_i; (i >= 0) && (*(result+i) != '/'); i--) { *(result+i) = '\0'; } if ((*(result+i) == '/') && (i > 0)) *(result+i) = '\0'; return result; } unsigned int fexist(const char *path, char type) { /* ----------------------------------------------------------------------------- * Check if file exists * * @param const char *, port number or name service * @param char, 'd' for a directory, 'f' for a file * @return int * -------------------------------------------------------------------------- */ struct stat s; int status; status = stat (path, &s); switch(type) { case 'd': if (status == 0 && S_ISDIR (s.st_mode)) return s.st_size; break; case 'f': if (status == 0 && S_ISREG (s.st_mode)) return s.st_size; break; } return 0; } char * file_exists (const char *directory, const char *filename) { /* ----------------------------------------------------------------------------- * Check if file exists in a directory * * @param const char *, directory * @param const char *, file name * @return char *, the full path in a dynamically allocated memory * so the result must be free() * -------------------------------------------------------------------------- */ char *full_filename = NULL; struct stat s; int status; size_t len = strlen(directory) + 1 + strlen(filename) + 1; full_filename = (char *) malloc(sizeof(char) * len); if (full_filename == NULL) { logmsg(LOG_ERR, "file_exists() : malloc error"); return NULL; } strlcpy(full_filename, directory, sizeof(char) * len); strlcat(full_filename, "/", sizeof(char) * len); strlcat(full_filename, filename, sizeof(char) * len); status = stat (full_filename, &s); if (status == 0 && S_ISREG (s.st_mode)) return full_filename; free (full_filename); return NULL; } int init_perl_script(const char *path, int pipes[2]) { /* ----------------------------------------------------------------------------- * Init a perl script with the associated pipe descriptor to write and read * * @param const char *, perl script path * @param int[2], that will contains 2 descriptors * @return int, 1 for parent process * -------------------------------------------------------------------------- */ int tube1[2]; int tube2[2]; char *argv[3]; int i; if ((pipe(tube1) != 0) || (pipe(tube2) != 0)) return 0; switch(fork()) { case -1: /* Erreur fork */ close(tube1[0]); close(tube1[1]); close(tube2[0]); close(tube2[1]); exit(-1); break; case 0 : /* Processus enfant */ signal(SIGHUP, SIG_IGN); close(tube1[1]); /* Fermeture tube1 entrée ECRITURE */ close(tube2[0]); /* Fermeture tube2 sortie LECTURE */ dup2(tube1[0], STDIN_FILENO); close(tube1[0]); dup2(tube2[1], STDOUT_FILENO); close(tube2[1]); /* On ferme tous les descripteurs sauf STDOUT et STDIN */ for(i = 2; i < OPEN_MAX; i++) close(i); argv[0] = "/usr/bin/perl"; argv[1] = (char *)path; argv[2] = NULL; execv("/usr/bin/perl", argv); return 0; break; default : /* Processus père lisant dans la socket */ close(tube1[0]); /* Fermeture tube1 sortie LECTURE */ close(tube2[1]); /* Fermeture tube2 entrée ECRITURE */ /*tubes[0] = tube2[0];*/ /* Tube de lecture */ /*tubes[1] = tube1[1];*/ /* Tube d'écriture */ pipes[1] = tube1[1]; pipes[0] = tube2[0]; signal(SIGCHLD, SIG_IGN); break; } return 1; } int process_daemon() { /* ----------------------------------------------------------------------------- * Daemonize a process * @return int, 1 for parent process, 0 for child process * -------------------------------------------------------------------------- */ int i = 0; /* Processus Démon */ switch (fork ()) { case -1: /* Erreur fork */ logmsg(LOG_ERR, "process_daemon() : %s (%d) : Fork Error", strerror(errno), errno); return errno; break; case 0: /* Processus enfant = démon: */ chdir("/"); setsid(); /* Fermeture de tous les descripteurs */ for (i = 0; i < _POSIX_OPEN_MAX; i++) close(i); break; default: /* Processus Parent */ return 1; } return 0; }