MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU 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
+ 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.,
+ 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include "module.h"
#include "misc.h"
-#include "pidwait.h"
-#include <errno.h>
#ifdef HAVE_REGEX_H
# include <regex.h>
#endif
function, data);
}
+/* easy way to bypass glib polling of io channel internal buffer */
+int g_input_add_poll(int fd, int priority, int condition,
+ GInputFunction function, void *data)
+{
+ GIOChannel *source = g_io_channel_unix_new(fd);
+ int ret = g_input_add_full(source, priority, condition, function, data);
+ g_io_channel_unref(source);
+ return ret;
+}
+
int g_timeval_cmp(const GTimeVal *tv1, const GTimeVal *tv2)
{
if (tv1->tv_sec < tv2->tv_sec)
return FALSE;
for (;;) {
- while (isspace((gint) *list)) list++;
+ while (i_isspace(*list)) list++;
if (*list == '\0') break;
ptr = strchr(list, ' ');
return -1;
}
-int execute(const char *cmd)
-{
- char **args;
-#ifndef WIN32
- int pid;
-#endif
-
- g_return_val_if_fail(cmd != NULL, -1);
-
-#ifndef WIN32
- pid = fork();
- if (pid == -1) return FALSE;
- if (pid != 0) {
- pidwait_add(pid);
- return pid;
- }
-
- args = g_strsplit(cmd, " ", -1);
- execvp(args[0], args);
- g_strfreev(args);
-
- _exit(99);
- return -1;
-#else
- args = g_strsplit(cmd, " ", -1);
- _spawnvp(_P_DETACH, args[0], args);
- g_strfreev(args);
- return 0;
-#endif
-}
-
GSList *gslist_find_string(GSList *list, const char *key)
{
for (list = list; list != NULL; list = list->next)
if (key[pos] == '\0')
return (char *) data;
- if (toupper(data[pos]) == toupper(key[pos]))
+ if (i_toupper(data[pos]) == i_toupper(key[pos]))
pos++;
else {
data++;
#define isbound(c) \
((unsigned char) (c) < 128 && \
- (isspace((int) (c)) || ispunct((int) (c))))
+ (i_isspace(c) || i_ispunct(c)))
-char *strstr_full_case(const char *data, const char *key, int icase)
+static char *strstr_full_case(const char *data, const char *key, int icase)
{
const char *start, *max;
int keylen, datalen, pos, match;
return (char *) data;
}
- match = icase ? (toupper(data[pos]) == toupper(key[pos])) :
+ match = icase ? (i_toupper(data[pos]) == i_toupper(key[pos])) :
data[pos] == key[pos];
if (match && (pos != 0 || data == start || isbound(data[-1])))
dir = g_strndup(path, (int) (p-path));
if (stat(dir, &statbuf) != 0) {
#ifndef WIN32
- if (mkdir(dir, mode) == -1) {
+ if (mkdir(dir, mode) == -1)
#else
- if (_mkdir(dir) == -1) {
+ if (_mkdir(dir) == -1)
#endif
+ {
g_free(dir);
return -1;
}
/* convert ~/ to $HOME */
char *convert_home(const char *path)
{
- return *path == '~' && (*(path+1) == '/' || *(path+1) == '\0') ?
- g_strconcat(g_get_home_dir(), path+1, NULL) :
- g_strdup(path);
+ const char *home;
+
+ if (*path == '~' && (*(path+1) == '/' || *(path+1) == '\0')) {
+ home = g_get_home_dir();
+ if (home == NULL)
+ home = ".";
+
+ return g_strconcat(home, path+1, NULL);
+ } else {
+ return g_strdup(path);
+ }
}
int g_istr_equal(gconstpointer v, gconstpointer v2)
unsigned int h = 0, g;
while (*s != '\0') {
- h = (h << 4) + toupper(*s);
+ h = (h << 4) + i_toupper(*s);
if ((g = h & 0xf0000000UL)) {
h = h ^ (g >> 24);
h = h ^ g;
newmask = mask = g_strdup(cmask);
for (; *mask != '\0' && *data != '\0'; mask++) {
if (*mask != '*') {
- if (*mask != '?' && toupper(*mask) != toupper(*data))
+ if (*mask != '?' && i_toupper(*mask) != i_toupper(*data))
break;
data++;
return FALSE;
while (*str != '\0' && *str != end_char) {
- if (!isdigit(*str)) return FALSE;
+ if (!i_isdigit(*str)) return FALSE;
str++;
}
return octal;
}
+/* string -> uoff_t */
+uoff_t str_to_uofft(const char *str)
+{
+ uoff_t ret;
+
+ ret = 0;
+ while (*str != '\0') {
+ ret = ret*10 + (*str - '0');
+ str++;
+ }
+
+ return ret;
+}
+
/* convert all low-ascii (<32) to ^<A..> combinations */
-char *show_lowascii(const char *channel)
+char *show_lowascii(const char *str)
{
- char *str, *p;
+ char *ret, *p;
- str = p = g_malloc(strlen(channel)*2+1);
- while (*channel != '\0') {
- if ((unsigned char) *channel >= 32)
- *p++ = *channel;
+ ret = p = g_malloc(strlen(str)*2+1);
+ while (*str != '\0') {
+ if ((unsigned char) *str >= 32)
+ *p++ = *str;
else {
*p++ = '^';
- *p++ = *channel + 'A'-1;
+ *p++ = *str + 'A'-1;
}
- channel++;
+ str++;
}
*p = '\0';
- return str;
+ return ret;
}
/* Get time in human readable form with localtime() + asctime() */
item_pos++;
}
- for (n = max_columns-1; n > 1; n--) {
+ for (n = max_columns-1; n >= 1; n--) {
if (columns_width[n] <= max_width &&
columns[n][n] > 0)
break;
g_slist_length(list), sorted);
return sorted;
}
+
+/* Expand escape string, the first character in data should be the
+ one after '\'. Returns the expanded character or -1 if error. */
+int expand_escape(const char **data)
+{
+ char digit[4];
+
+ switch (**data) {
+ case 't':
+ return '\t';
+ case 'r':
+ return '\r';
+ case 'n':
+ return '\n';
+ case 'e':
+ return 27; /* ESC */
+
+ case 'x':
+ /* hex digit */
+ if (!i_isxdigit((*data)[1]) || !i_isxdigit((*data)[2]))
+ return -1;
+
+ digit[0] = (*data)[1];
+ digit[1] = (*data)[2];
+ digit[2] = '\0';
+ *data += 2;
+ return strtol(digit, NULL, 16);
+ case 'c':
+ /* control character (\cA = ^A) */
+ (*data)++;
+ return i_toupper(**data) - 64;
+ case '0': case '1': case '2': case '3':
+ case '4': case '5': case '6': case '7':
+ /* octal */
+ digit[1] = digit[2] = digit[3] = '\0';
+ digit[0] = (*data)[0];
+ if ((*data)[1] >= '0' && (*data)[1] <= '7') {
+ ++*data;
+ digit[1] = **data;
+ if ((*data)[1] >= '0' && (*data)[1] <= '7') {
+ ++*data;
+ digit[2] = **data;
+ }
+ }
+ return strtol(digit, NULL, 8);
+ default:
+ return -1;
+ }
+}
+
+/* Escape all '"', "'" and '\' chars with '\' */
+char *escape_string(const char *str)
+{
+ char *ret, *p;
+
+ p = ret = g_malloc(strlen(str)*2+1);
+ while (*str != '\0') {
+ if (*str == '"' || *str == '\'' || *str == '\\')
+ *p++ = '\\';
+ *p++ = *str++;
+ }
+ *p = '\0';
+
+ return ret;
+}
+
+int strocpy(char *dest, const char *src, size_t dstsize)
+{
+ if (dstsize == 0)
+ return -1;
+
+ while (*src != '\0' && dstsize > 1) {
+ *dest++ = *src++;
+ dstsize--;
+ }
+
+ *dest++ = '\0';
+ return *src == '\0' ? 0 : -1;
+}
+
+int nearest_power(int num)
+{
+ int n = 1;
+
+ while (n < num) n <<= 1;
+ return n;
+}
+
+int parse_time_interval(const char *time, int *msecs)
+{
+ const char *desc;
+ int number, sign, len, ret, digits;
+
+ *msecs = 0;
+
+ /* max. return value is around 24 days */
+ number = 0; sign = 1; ret = TRUE; digits = FALSE;
+ while (i_isspace(*time))
+ time++;
+ if (*time == '-') {
+ sign = -sign;
+ time++;
+ while (i_isspace(*time))
+ time++;
+ }
+ for (;;) {
+ if (i_isdigit(*time)) {
+ number = number*10 + (*time - '0');
+ time++;
+ digits = TRUE;
+ continue;
+ }
+
+ if (!digits)
+ return FALSE;
+
+ /* skip punctuation */
+ while (*time != '\0' && i_ispunct(*time) && *time != '-')
+ time++;
+
+ /* get description */
+ for (len = 0, desc = time; i_isalpha(*time); time++)
+ len++;
+
+ while (i_isspace(*time))
+ time++;
+
+ if (len == 0) {
+ if (*time != '\0')
+ return FALSE;
+ *msecs += number * 1000; /* assume seconds */
+ *msecs *= sign;
+ return TRUE;
+ }
+
+ if (g_ascii_strncasecmp(desc, "days", len) == 0) {
+ if (number > 24) {
+ /* would overflow */
+ return FALSE;
+ }
+ *msecs += number * 1000*3600*24;
+ } else if (g_ascii_strncasecmp(desc, "hours", len) == 0)
+ *msecs += number * 1000*3600;
+ else if (g_ascii_strncasecmp(desc, "minutes", len) == 0 ||
+ g_ascii_strncasecmp(desc, "mins", len) == 0)
+ *msecs += number * 1000*60;
+ else if (g_ascii_strncasecmp(desc, "seconds", len) == 0 ||
+ g_ascii_strncasecmp(desc, "secs", len) == 0)
+ *msecs += number * 1000;
+ else if (g_ascii_strncasecmp(desc, "milliseconds", len) == 0 ||
+ g_ascii_strncasecmp(desc, "millisecs", len) == 0 ||
+ g_ascii_strncasecmp(desc, "mseconds", len) == 0 ||
+ g_ascii_strncasecmp(desc, "msecs", len) == 0)
+ *msecs += number;
+ else {
+ ret = FALSE;
+ }
+
+ /* skip punctuation */
+ while (*time != '\0' && i_ispunct(*time) && *time != '-')
+ time++;
+
+ if (*time == '\0')
+ break;
+
+ number = 0;
+ digits = FALSE;
+ }
+
+ *msecs *= sign;
+ return ret;
+}
+
+int parse_size(const char *size, int *bytes)
+{
+ const char *desc;
+ int number, len;
+
+ *bytes = 0;
+
+ /* max. return value is about 1.6 years */
+ number = 0;
+ while (*size != '\0') {
+ if (i_isdigit(*size)) {
+ number = number*10 + (*size - '0');
+ size++;
+ continue;
+ }
+
+ /* skip punctuation */
+ while (*size != '\0' && i_ispunct(*size))
+ size++;
+
+ /* get description */
+ for (len = 0, desc = size; i_isalpha(*size); size++)
+ len++;
+
+ if (len == 0) {
+ if (number == 0) {
+ /* "0" - allow it */
+ return TRUE;
+ }
+
+ *bytes += number*1024; /* assume kilobytes */
+ return FALSE;
+ }
+
+ if (g_ascii_strncasecmp(desc, "gbytes", len) == 0)
+ *bytes += number * 1024*1024*1024;
+ if (g_ascii_strncasecmp(desc, "mbytes", len) == 0)
+ *bytes += number * 1024*1024;
+ if (g_ascii_strncasecmp(desc, "kbytes", len) == 0)
+ *bytes += number * 1024;
+ if (g_ascii_strncasecmp(desc, "bytes", len) == 0)
+ *bytes += number;
+
+ /* skip punctuation */
+ while (*size != '\0' && i_ispunct(*size))
+ size++;
+ }
+
+ return TRUE;
+}
+
+char *ascii_strup(char *str)
+{
+ char *s;
+
+ for (s = str; *s; s++)
+ *s = g_ascii_toupper (*s);
+ return str;
+}
+
+char *ascii_strdown(char *str)
+{
+ char *s;
+
+ for (s = str; *s; s++)
+ *s = g_ascii_tolower (*s);
+ return str;
+}