1 /* 2 * Copyright (C) 2007, 2008 Nokia Corporation 3 * 4 * This program is free software; you can redistribute it and/or modify 5 * it under the terms of the GNU General Public License as published by 6 * the Free Software Foundation; either version 2 of the License, or 7 * (at your option) any later version. 8 * 9 * This program is distributed in the hope that it will be useful, 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See 12 * the GNU General Public License for more details. 13 * 14 * You should have received a copy of the GNU General Public License 15 * along with this program; if not, write to the Free Software 16 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 17 */ 18 19 /* 20 * This file contains various common stuff used by UBI utilities. 21 * 22 * Authors: Artem Bityutskiy 23 * Adrian Hunter 24 */ 25 26 #define PROGRAM_NAME "ubiutils" 27 28 #include <sys/time.h> 29 #include <sys/types.h> 30 #include <stdio.h> 31 #include <string.h> 32 #include <ctype.h> 33 #include <stdlib.h> 34 #include <unistd.h> 35 #include "libubi.h" 36 37 /** 38 * get_multiplier - convert size specifier to an integer multiplier. 39 * @str: the size specifier string 40 * 41 * This function parses the @str size specifier, which may be one of 42 * 'KiB', 'MiB', or 'GiB' into an integer multiplier. Returns positive 43 * size multiplier in case of success and %-1 in case of failure. 44 */ 45 static int get_multiplier(const char *str) 46 { 47 if (!str) 48 return 1; 49 50 /* Remove spaces before the specifier */ 51 while (*str == ' ' || *str == '\t') 52 str += 1; 53 54 if (!strcmp(str, "KiB")) 55 return 1024; 56 if (!strcmp(str, "MiB")) 57 return 1024 * 1024; 58 if (!strcmp(str, "GiB")) 59 return 1024 * 1024 * 1024; 60 61 return -1; 62 } 63 64 /** 65 * ubiutils_get_bytes - convert a string containing amount of bytes into an 66 * integer 67 * @str: string to convert 68 * 69 * This function parses @str which may have one of 'KiB', 'MiB', or 'GiB' 70 * size specifiers. Returns positive amount of bytes in case of success and %-1 71 * in case of failure. 72 */ 73 long long ubiutils_get_bytes(const char *str) 74 { 75 char *endp; 76 long long bytes = strtoull(str, &endp, 0); 77 78 if (endp == str || bytes < 0) { 79 fprintf(stderr, "incorrect amount of bytes: \"%s\"\n", str); 80 return -1; 81 } 82 83 if (*endp != '\0') { 84 int mult = get_multiplier(endp); 85 86 if (mult == -1) { 87 fprintf(stderr, "bad size specifier: \"%s\" - " 88 "should be 'KiB', 'MiB' or 'GiB'\n", endp); 89 return -1; 90 } 91 bytes *= mult; 92 } 93 94 return bytes; 95 } 96 97 /** 98 * ubiutils_print_bytes - print bytes. 99 * @bytes: variable to print 100 * @bracket: whether brackets have to be put or not 101 * 102 * This is a helper function which prints amount of bytes in a human-readable 103 * form, i.e., it prints the exact amount of bytes following by the approximate 104 * amount of Kilobytes, Megabytes, or Gigabytes, depending on how big @bytes 105 * is. 106 */ 107 void ubiutils_print_bytes(long long bytes, int bracket) 108 { 109 const char *p; 110 111 if (bracket) 112 p = " ("; 113 else 114 p = ", "; 115 116 printf("%lld bytes", bytes); 117 118 if (bytes > 1024 * 1024 * 1024) 119 printf("%s%.1f GiB", p, (double)bytes / (1024 * 1024 * 1024)); 120 else if (bytes > 1024 * 1024) 121 printf("%s%.1f MiB", p, (double)bytes / (1024 * 1024)); 122 else if (bytes > 1024 && bytes != 0) 123 printf("%s%.1f KiB", p, (double)bytes / 1024); 124 else 125 return; 126 127 if (bracket) 128 printf(")"); 129 } 130 131 /** 132 * ubiutils_print_text - print text and fold it. 133 * @stream: file stream to print to 134 * @text: text to print 135 * @width: maximum allowed text width 136 * 137 * Print text and fold it so that each line would not have more then @width 138 * characters. 139 */ 140 void ubiutils_print_text(FILE *stream, const char *text, int width) 141 { 142 int pos, bpos = 0; 143 const char *p; 144 char line[1024]; 145 146 if (width > 1023) { 147 fprintf(stream, "%s\n", text); 148 return; 149 } 150 p = text; 151 pos = 0; 152 while (p[pos]) { 153 while (!isspace(p[pos])) { 154 line[pos] = p[pos]; 155 if (!p[pos]) 156 break; 157 ++pos; 158 if (pos == width) { 159 line[pos] = '\0'; 160 fprintf(stream, "%s\n", line); 161 p += pos; 162 pos = 0; 163 } 164 } 165 while (pos < width) { 166 line[pos] = p[pos]; 167 if (!p[pos]) { 168 bpos = pos; 169 break; 170 } 171 if (isspace(p[pos])) 172 bpos = pos; 173 ++pos; 174 } 175 line[bpos] = '\0'; 176 fprintf(stream, "%s\n", line); 177 p += bpos; 178 pos = 0; 179 while (p[pos] && isspace(p[pos])) 180 ++p; 181 } 182 } 183 184 /** 185 * ubiutils_srand - randomly seed the standard pseudo-random generator. 186 * 187 * This helper function seeds the standard libc pseudo-random generator with a 188 * more or less random value to make sure the 'rand()' call does not return the 189 * same sequence every time UBI utilities run. Returns zero in case of success 190 * and a %-1 in case of error. 191 */ 192 int ubiutils_srand(void) 193 { 194 struct timeval tv; 195 struct timezone tz; 196 unsigned int seed; 197 198 /* 199 * Just assume that a combination of the PID + current time is a 200 * reasonably random number. 201 */ 202 if (gettimeofday(&tv, &tz)) 203 return -1; 204 205 seed = (unsigned int)tv.tv_sec; 206 seed += (unsigned int)tv.tv_usec; 207 seed *= getpid(); 208 seed %= RAND_MAX; 209 srand(seed); 210 return 0; 211 } 212
This page was automatically generated by LXR 0.3.1. • OpenWrt