1 /*
2 tools.c -- common tools for the all progs.
3 Copyright (C) 2001, 2002 Yury Umanets <torque@ukrpost.net>, see COPYING for
4 licensing and copyright details.
5 */
6
7 #ifdef HAVE_CONFIG_H
8 # include <config.h>
9 #endif
10
11 #include <stdio.h>
12 #include <stdlib.h>
13 #include <string.h>
14 #include <stdarg.h>
15 #include <errno.h>
16 #include <sys/stat.h>
17
18 #include <reiserfs/exception.h>
19 #include <reiserfs/debug.h>
20 #include <reiserfs/libprogs_tools.h>
21
22 #if ENABLE_NLS
23 # include <locale.h>
24 # include <libintl.h>
25 # define _(String) dgettext (PACKAGE, String)
26 #else
27 # define _(String) (String)
28 #endif
29
30 #define KB 1024
31 #define MB (1024 * KB)
32 #define GB (1024 * MB)
33
progs_strtol(const char * str,int * error)34 long progs_strtol(const char *str, int *error) {
35 char *err;
36 long result = 0;
37
38 if (error)
39 *error = 0;
40
41 if (!str) {
42 if (error) *error = 1;
43 return 0;
44 }
45
46 result = strtol(str, &err, 10);
47
48 if (errno == ERANGE || *err) {
49 if (error) *error = 1;
50 return 0;
51 }
52
53 return result;
54 }
55
56 /* Choose functions */
progs_choose_check(const char * chooses,int choose)57 int progs_choose_check(const char *chooses, int choose) {
58 unsigned i;
59
60 if (!chooses) return 0;
61
62 for (i = 0; i < strlen(chooses); i++)
63 if (chooses[i] == choose) return 1;
64
65 return 0;
66 }
67
progs_choose(const char * chooses,const char * error,const char * format,...)68 int progs_choose(const char *chooses, const char *error, const char *format, ...) {
69 va_list args;
70 int choose, prompts = 0;
71 char mess[4096], buf[255];
72
73 if (!chooses || !format || !error)
74 return 0;
75
76 memset(mess, 0, 4096);
77
78 va_start(args, format);
79 vsprintf(mess, format, args);
80 va_end(args);
81
82 fprintf(stderr, mess);
83 fflush(stderr);
84
85 do {
86 memset(buf, 0, 255);
87
88 fgets(buf, 255, stdin);
89 choose = buf[0];
90
91 if (progs_choose_check(chooses, choose))
92 break;
93
94 if (prompts < 2) {
95 fprintf(stderr, error);
96 fflush(stderr);
97 }
98 } while (prompts++ < 2);
99
100 if (!progs_choose_check(chooses, choose))
101 choose = 0;
102
103 return choose;
104 }
105
106 /* Device functions */
progs_dev_check(const char * dev)107 int progs_dev_check(const char *dev) {
108 struct stat st;
109
110 if (!dev)
111 return 0;
112
113 if (stat(dev, &st) == -1)
114 return 0;
115
116 if (!S_ISBLK(st.st_mode)) {
117 libreiserfs_exception_throw(EXCEPTION_WARNING, EXCEPTION_IGNORE,
118 _("Device %s isn't a block device."), dev);
119 }
120
121 return 1;
122 }
123
124 /* Parsing functions */
progs_digit_check(const char * str)125 int progs_digit_check(const char *str) {
126 int error = 0;
127
128 progs_digit_parse(str, 4096, &error);
129 return !error;
130 }
131
progs_digit_parse(const char * str,size_t blocksize,int * error)132 long progs_digit_parse(const char *str, size_t blocksize, int *error) {
133 long long size;
134 char number[255], label = 0;
135
136 if (error)
137 *error = 0;
138
139 if (!str || strlen(str) == 0 || !blocksize) {
140 if (error) *error = 1;
141 return 0;
142 }
143
144 memset(number, 0, 255);
145 strncpy(number, str, strlen(str));
146 label = number[strlen(number) - 1];
147
148 if (label == 'K' || label == 'M' || label == 'G')
149 number[strlen(number) - 1] = '\0';
150 else
151 label = 0;
152
153 if ((size = progs_strtol(number, error)) == 0 && *error)
154 return 0;
155
156 if (label == 0 || label == 'M')
157 size = size * MB;
158 else if (label == 'K')
159 size = size * KB;
160 else if (label == 'G')
161 size = size * GB;
162
163 return size / blocksize;
164 }
165
166