/* * Returns a static array of length FILENAME_MAX + 1, which contains * $XDG_CONFIG_HOME/NotificaThor or, if the variable is not set, * ~/.config/NotificaThor. * * Returns: Pointer to static array. */ char * get_home_config() { char *env = getenv( "XDG_CONFIG_HOME"); static char ret[FILENAME_MAX + 1]; if( !env || !*env ) cpycat( cpycat( ret, getenv( "HOME")), "/.config/NotificaThor"); else cpycat( cpycat( ret, env), "/NotificaThor"); return ret; };
/* * Returns a static array of length FILENAME_MAX + 1, which contains * $XDG_CACHE_HOME or, if the variable is not set, * ~/.cache. * * Returns: Pointer to static array. */ char * get_xdg_cache() { char *env = getenv( "XDG_CACHE_HOME"); static char ret[FILENAME_MAX + 1]; if( !env || !*env ) cpycat( cpycat( ret, getenv( "HOME")), "/.cache"); else cpycat( ret, env); return ret; };
int get_next_line(int const fd, char **line) { static char *str; int res; char *buf; char *tmp; if (fd < 0 || !line || BUFF_SIZE < 1 || BUFF_SIZE > 10000000) return (-1); buf = (char*)malloc(sizeof(char) * (BUFF_SIZE + 1)); if (str == NULL) str = ft_strnew(BUFF_SIZE); tmp = ft_strncpy(ft_memalloc(BUFF_SIZE), str, BUFF_SIZE); while (!(ft_strchr(tmp, '\n'))) { if ((res = read(fd, buf, BUFF_SIZE)) < 1) return (line_verif(line, &tmp, res, &str)); buf[res] = '\0'; tmp = cpycat(tmp, buf); } *line = read_line(tmp); if (ft_strchr(tmp, '\n')) str = ft_strncpy(str, ft_strchr(tmp, '\n') + 1, BUFF_SIZE); free(tmp); free(buf); return (1); }
int main(int argc, char *argv[]) { int result; int i, count; FILE *inFile, *outFile; char *tmpname, *bakname; bool usageOnly; count = 1; gOptions.filename = NULL; gOptions.boilerplate = NULL; gOptions.onlyPrototypes = false; /* Run through the arguments, pulling out just the options. While we're doing this, shuffle down any non-option args (i.e. the filenames) so that they're contiguous */ usageOnly = (argc > 1); for (i = 1; i < argc; ++i) { if (argv[i][0] == '-') { switch (argv[i][1]) { case 'V': case 'v': printVersion(argv[0]); break; case '?': case 'h': printUsage(argv[0]); break; case 'b': if (++i < argc) { gOptions.boilerplate = argv[i]; usageOnly = false; } break; case 'p': gOptions.onlyPrototypes = true; usageOnly = false; break; case '-': /* the 'wordy' varients */ if (strcmp(argv[i],"--version") == 0) { printVersion(argv[0]); break; } else if (strcmp(argv[i],"--help") == 0) { printUsage(argv[0]); break; } /* fall through if there's no match */ default: fprintf(stderr, "### error: unknown option \'%s\' given to %s\n", argv[i],argv[0]); break; } } else { /* copy the pointer, if it's not at the same index */ if (count != i) argv[count] = argv[i]; ++count; usageOnly = false; } } /* argv[1] through argv[count] now contains only filenames */ result = 0; if (!usageOnly) { if (count <= 1) /* one is really zero, since it started at 1 */ { /* assume stdin to stdout */ gOptions.filename = NULL; result = processFile(stdout, stdin); } else for (i = 1; i < count; ++i) { gOptions.filename = filenameFromPath(argv[i]); tmpname = NULL; inFile = fopen(argv[i],"r"); if (inFile == NULL) { fprintf(stderr, "### error: unable to open '%s' for reading (in %s)\n", argv[i], argv[0]); result = -1; } else { tmpname = cpycat(argv[i],".tmp"); if (tmpname != NULL) { outFile = fopen(tmpname,"w"); if (outFile == NULL) { fprintf(stderr, "### error: unable to open '%s' for writing (in %s)\n", tmpname, argv[0]); result = -2; } else { /* this performs the actual processing */ result = processFile(outFile, inFile); fclose(outFile); } /* don't free tmpname yet; need it below */ } fclose(inFile); } /* only rename the files if everything went smoothly */ if (tmpname != NULL) { if (result == 0) { bakname = cpycat(argv[i],".bak"); if (bakname != NULL) { result = rename(argv[i], bakname); if (result != 0) { fprintf(stderr, "### error: unable to rename '%s' to '%s' (in %s)\n", argv[i], bakname, argv[0]); result = -3; } else { result = rename(tmpname, argv[i]); if (result != 0) { fprintf(stderr, "### error: unable to rename '%s' to '%s' (in %s)\n", tmpname, argv[i], argv[0]); result = -4; } } free(bakname); } } free(tmpname); } } } return result; }
/* * Parses the config file. * * Returns: 0 on success, -1 on error. */ int parse_conf() { FILE *fconf; char buffer[MAX_LINE_LEN + 1]; int c; #ifndef TESTING char *config_file = get_home_config(); #else /* Not TESTING */ char config_file[FILENAME_MAX]; #endif /* Not TESTING */ #ifndef TESTING strcat( config_file, "/rc.conf"); if( (fconf = fopen( config_file, "r")) == NULL ) { #endif /* TESTING */ cpycat( config_file, DEFAULT_CONFIG); if( (fconf = fopen( config_file, "r")) == NULL ) { thor_errlog( LOG_ERR, "Opening config file"); #ifdef VERBOSE thor_log( LOG_DEBUG, "DEFAULT CONFIGURATION:"); print_config(); #endif /* VERBOSE */ return -1; } #ifndef TESTING } #endif /* TESTING */ thor_log( LOG_DEBUG, "Config file: '%s'", config_file); if( inofd != -1 ) { if( inotify_add_watch( inofd, config_file, IN_MODIFY|IN_DELETE_SELF|IN_MOVE_SELF|IN_CLOSE_WRITE) == -1 ) thor_ferrlog( LOG_ERR, "Installing Inotify watch on '%s'", config_file); } /** default values **/ *config_default_theme = '\0'; strcpy( config_default_font, CONFIG_DEFAULT_FONT); line = 0; while( (c = fgetline( fconf, buffer)) != -1 ) { char *key, *value; line++; if( c != '\n') { if( !feof( fconf) ) { thor_log( LOG_ERR, "%s%d - line too long ( MAX = %d ).", log_msg, line, MAX_LINE_LEN); while( (c = fgetc( fconf)) != '\n' && c != EOF ); continue; } } if( *buffer == '\0' ) continue; /** get the key **/ key = strtok_r( buffer, "=", &value); if( *key == '#' ) // comment continue; if( *value == '\0' ) { thor_log( LOG_ERR, "%s%d - missing value.", log_msg, line); continue; } if( strcmp( key, "use_argb") == 0 ) parse_bool( value, &config_use_argb); else if( strcmp( key, "use_xshape") == 0 ) { if( strcmp( value, "whole") == 0 ) config_use_xshape = 2; else parse_bool( value, &config_use_xshape); } else if( strcmp( key, "default_theme") == 0 ) strncpy( config_default_theme, value, MAX_THEME_LEN); else if( strcmp( key, "default_font") == 0 ) strncpy( config_default_font, value, MAX_FONT_LEN); else if( strcmp( key, "osd_default_timeout") == 0 ) { char *endptr; double to = strtod( value, &endptr); if( *endptr == 0 ) config_osd_default_timeout = to; else thor_log( LOG_ERR, "%s%d - '%s' is not a valid number.", log_msg, line, value); } else if( strcmp( key, "osd_default_x") == 0 ) parse_coord( value, &config_osd_default_x); else if( strcmp( key, "osd_default_y") == 0 ) parse_coord( value, &config_osd_default_y); else { thor_log( LOG_ERR, "%s%d - unknown key '%s'.", log_msg, line, key); } } fclose( fconf); #ifdef VERBOSE thor_log( LOG_DEBUG, "CONFIGURATION:"); print_config(); #endif /* VERBOSE */ return 0; };