Changeset 32490deb for libcfa/src
- Timestamp:
- Jan 31, 2024, 6:40:25 PM (22 months ago)
- Branches:
- master
- Children:
- 496ffc17
- Parents:
- c75b30a (diff), e71b09a (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the(diff)links above to see all the changes relative to each parent. - Location:
- libcfa/src
- Files:
-
- 4 edited
-
collections/string_res.cfa (modified) (2 diffs)
-
fstream.cfa (modified) (2 diffs)
-
iostream.cfa (modified) (8 diffs)
-
iostream.hfa (modified) (10 diffs)
Legend:
- Unmodified
- Added
- Removed
-
libcfa/src/collections/string_res.cfa
rc75b30a r32490deb 10 10 // Created On : Fri Sep 03 11:00:00 2021 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Tue Jan 16 22:19:27202413 // Update Count : 3512 // Last Modified On : Mon Jan 22 23:12:42 2024 13 // Update Count : 43 14 14 // 15 15 … … 263 263 bool cont = false; 264 264 265 _Istream_C strcf = { cstr, (_Istream_str_base)f };265 _Istream_Cwidth cf = { cstr, (_Istream_str_base)f }; 266 266 if ( ! cf.flags.rwd ) cf.wd = wd; 267 267 -
libcfa/src/fstream.cfa
rc75b30a r32490deb 10 10 // Created On : Wed May 27 17:56:53 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Wed Nov 15 10:51:14 202313 // Update Count : 55 212 // Last Modified On : Sun Jan 28 09:56:08 2024 13 // Update Count : 554 14 14 // 15 15 … … 209 209 void ?{}( ifstream & is, void * file ) with( is ) { 210 210 file$ = file; 211 nlOnOff$ = false; 211 nlOnOff$ = false; // => skip newlines when reading single characters 212 212 } // ?{} 213 213 -
libcfa/src/iostream.cfa
rc75b30a r32490deb 10 10 // Created On : Wed May 27 17:56:53 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Wed Jan 3 10:53:13202413 // Update Count : 1 89812 // Last Modified On : Sun Jan 28 11:58:54 2024 13 // Update Count : 1917 14 14 // 15 15 … … 944 944 istype & nl( istype & is ) { 945 945 fmt( is, "%*[^\n]" ); // ignore characters to newline 946 if ( ! eof( is ) && getANL$( is ) ) fmt( is, "%*c" );// read newline946 if ( ! eof( is ) ) fmt( is, "%*c" ); // read newline 947 947 return is; 948 948 } // nl … … 984 984 } 985 985 986 istype & ?|?( istype & is, _Istream_Cquoted f ) with( f ) { 987 char fmtstr[32]; // storage scanset and format codes 986 istype & ?|?( istype & is, _Istream_Cquoted f ) with( f.cstr ) { 987 int args; 988 fini: { 989 args = fmt( is, "%*[ \f\n\r\t\v]" ); // remove leading whitespace 990 if ( eof( is ) ) break fini; 991 char rfmt[4] = { delimiters[0], '%', 'n', '\0' }; 992 int len = 0; // may not be set in fmt 993 args = fmt( is, rfmt, &len ); // remove leading quote 994 if ( len == 0 || eof( is ) ) break fini; 995 996 // Change the remainder of the read into a getline by reseting the closing delimiter. 997 if ( delimiters[1] != '\0' ) { 998 delimiters[0] = delimiters[1]; 999 delimiters[1] = '\0'; 1000 } // if 1001 flags.delimiter = true; 1002 return is | *(_Istream_Cstr *)&f; 1003 } // fini 1004 // read failed => no pattern match => set string to null 1005 if ( ! flags.ignore && s != 0p && args == 0 ) s[0] = '\0'; 1006 if ( args == 1 && eof( is ) ) { // data but scan ended at EOF 1007 clear( is ); // => reset EOF => detect again on next read 1008 } // if 1009 return is; 1010 } 1011 1012 istype & ?|?( istype & is, _Istream_Cstr f ) with( f.cstr ) { 1013 const char * scanset; 1014 size_t nscanset = 0; 1015 if ( flags.delimiter ) scanset = delimiters; // getline ? 1016 else scanset = f.cstr.scanset; 1017 if ( scanset ) nscanset = strlen( scanset ); 1018 1019 char fmtstr[nscanset + 32]; // storage for scanset and format codes 988 1020 fmtstr[0] = '%'; 989 990 1021 int pos = 1; 991 1022 int args; 992 1023 bool check = true; 993 1024 994 if ( cstr.flags.ignore ) { check = false; fmtstr[1] = '*'; pos += 1; }995 int rwd = cstr.wd;996 if ( cstr.wd != -1 ) {// => just ignore versus ignore with width1025 if ( flags.ignore ) { check = false; fmtstr[1] = '*'; pos += 1; } 1026 int rwd = wd; 1027 if ( wd != -1 ) { // => just ignore versus ignore with width 997 1028 // wd is buffer bytes available (for input chars + null terminator) 998 1029 // rwd is count of input chars 999 1030 // no maximum width necessary because text ignored => width is read width 1000 if ( cstr.flags.rwd ) check = false; 1001 else rwd = cstr.wd - 1; 1031 if ( flags.rwd ) check = false; 1032 else rwd = wd - 1; 1033 assert( rwd > 0 ); 1002 1034 pos += sprintf( &fmtstr[pos], "%d", rwd ); 1003 1035 } // if 1004 1036 1005 int len = 0; // may not be set in fmt1006 char enddelim;1007 if ( ! cstr.flags.inex ) { // => quoted getline1008 args = fmt( is, "%*[ \f\n\r\t\v]" ); // remove leading whitespace1009 if ( eof( is ) ) goto Eof;1010 char rfmt[4] = { cstr.delimiters[0], '%', 'n', '\0' };1011 args = fmt( is, rfmt, &len ); // remove leading quote1012 if ( len == 0 || eof( is ) ) goto Eof;1013 } // if1014 enddelim = cstr.delimiters[1] == '\0' ? cstr.delimiters[0] : cstr.delimiters[1];1015 sprintf( &fmtstr[pos], "[^%c]%%n", enddelim );1016 if ( cstr.flags.ignore ) args = fmt( is, fmtstr, &len ); // no string argument for '*'1017 else args = fmt( is, fmtstr, cstr.s, &len );1018 if ( check && len == rwd && ! eof( is ) ) { // might not fit1019 char peek;1020 fmt( is, "%c", &peek ); // check for delimiter1021 if ( ! eof( is ) ) {1022 if ( peek != enddelim ) {1023 ungetc( is, peek );1024 throwResume ExceptionInst( cstring_length );1025 } // if1026 } // if1027 } else fmt( is, "%*c" ); // remove delimiter1028 Eof: ;1029 if ( rwd > 0 && args == 0 ) cstr.s[0] = '\0'; // read failed => no pattern match => set string to null1030 if ( args == 1 && eof( is ) ) { // data but scan ended at EOF1031 clear( is ); // => reset EOF => detect again on next read1032 } // if1033 return is;1034 }1035 1036 istype & ?|?( istype & is, _Istream_Cstr f ) with( f ) {1037 const char * scanset;1038 size_t nscanset = 0;1039 if ( flags.delimiter ) scanset = delimiters; // getline ?1040 else scanset = f.scanset;1041 if ( scanset ) nscanset = strlen( scanset );1042 1043 char fmtstr[nscanset + 32]; // storage for scanset and format codes1044 fmtstr[0] = '%';1045 1046 int pos = 1;1047 int args;1048 bool check = true;1049 1050 if ( f.flags.ignore ) { check = false; fmtstr[1] = '*'; pos += 1; }1051 int rwd = f.wd;1052 if ( f.wd != -1 ) { // => just ignore versus ignore with width1053 // wd is buffer bytes available (for input chars + null terminator)1054 // rwd is count of input chars1055 // no maximum width necessary because text ignored => width is read width1056 if ( f.flags.rwd ) check = false;1057 else rwd = f.wd - 1;1058 pos += sprintf( &fmtstr[pos], "%d", rwd );1059 } // if1060 1061 1037 if ( ! scanset ) { // %s, %*s, %ws, %*ws 1062 // fprintf( stderr, "cstr %s\n", f.s );1038 // fprintf( stderr, "cstr %s\n", s ); 1063 1039 strcpy( &fmtstr[pos], "s%n" ); 1064 1040 int len = 0; // may not be set in fmt 1065 if ( f .flags.ignore ) args = fmt( is, fmtstr, &len ); // no string argument for '*'1066 else args = fmt( is, fmtstr, f.s, &len );1067 // fprintf( stderr, "cstr %s %d %d %d %s\n", fmtstr, args, len, f.wd, f.s );1041 if ( flags.ignore ) args = fmt( is, fmtstr, &len ); // no string argument for '*' 1042 else args = fmt( is, fmtstr, s, &len ); 1043 // fprintf( stderr, "cstr %s %d %d %d %s\n", fmtstr, args, len, wd, s ); 1068 1044 if ( check && len >= rwd && ! eof( is ) ) { // might not fit 1069 1045 char peek; … … 1076 1052 } // if 1077 1053 // FIX ME: CFA strings need to be modified to NOT change the argument for this case, then this can be removed. 1078 if ( rwd > 0 && args == 0 ) f.s[0]= '\0';// read failed => no pattern match => set string to null1054 if ( ! flags.ignore && args == 0 ) s[0]= '\0'; // read failed => no pattern match => set string to null 1079 1055 } else { 1080 if ( f .flags.delimiter ) { // getline1056 if ( flags.delimiter ) { // getline 1081 1057 int len = 0; // may not be set in fmt 1082 sprintf( &fmtstr[pos], "[^%c]%%n", f.delimiters[0] ); 1083 if ( f.flags.ignore ) args = fmt( is, fmtstr, &len ); // no string argument for '*' 1084 else args = fmt( is, fmtstr, f.s, &len ); 1058 if ( delimiters[2] != '\0' ) { // read single character ? 1059 sprintf( &fmtstr[pos], "c%%n" ); 1060 } else { 1061 sprintf( &fmtstr[pos], "[^%c]%%n", delimiters[0] ); 1062 } // if 1063 if ( flags.ignore ) args = fmt( is, fmtstr, &len ); // no string argument for '*' 1064 else args = fmt( is, fmtstr, s, &len ); 1085 1065 if ( check && len == rwd && ! eof( is ) ) { // might not fit 1086 fmtstr[0] = f.delimiters[0]; fmtstr[1] = '%'; fmtstr[2] = 'n'; fmtstr[3] = '\0';1087 fmt( is, fmtstr, &len ); // removedelimiter1066 char peek; 1067 fmt( is, "%c", &peek ); // check for delimiter 1088 1068 if ( ! eof( is ) ) { 1089 // if ( peek != f.delimiter[0] ) { 1090 if ( len != 1 ) { 1091 // ungetc( is, peek ); 1069 if ( peek != delimiters[0] ) { 1070 ungetc( is, peek ); 1092 1071 throwResume ExceptionInst( cstring_length ); 1093 1072 } // if … … 1097 1076 // incl %[xxx], %*[xxx], %w[xxx], %*w[xxx] 1098 1077 // excl %[^xxx], %*[^xxx], %w[^xxx], %*w[^xxx] 1099 sprintf( &fmtstr[pos], "[%s%s]%%n", f .flags.inex ? "^" : "", scanset );1100 // fprintf( stderr, "incl/excl %s %d\n", fmtstr, f.wd );1078 sprintf( &fmtstr[pos], "[%s%s]%%n", flags.inex ? "^" : "", scanset ); 1079 // fprintf( stderr, "incl/excl %s %d\n", fmtstr, wd ); 1101 1080 int len = 0; // may not be set in fmt 1102 if ( f .flags.ignore ) args = fmt( is, fmtstr, &len ); // no string argument for '*'1103 else args = fmt( is, fmtstr, f.s, &len );1104 // fprintf( stderr, "incl/excl %s \"%s\" %d %d %d %d %d %c\n", fmtstr, f.s, args, f.wd, len, eof( is ), check, f.s[f.wd] );1081 if ( flags.ignore ) args = fmt( is, fmtstr, &len ); // no string argument for '*' 1082 else args = fmt( is, fmtstr, s, &len ); 1083 // fprintf( stderr, "incl/excl %s \"%s\" %d %d %d %d %d %c\n", fmtstr, s, args, wd, len, eof( is ), check, s[wd] ); 1105 1084 if ( check && len == rwd && ! eof( is ) ) { // might not fit 1106 1085 // fprintf( stderr, "overflow\n" ); … … 1110 1089 if ( ! eof( is ) ) { 1111 1090 ungetc( is, peek ); 1112 if ( f .flags.inex ^ strchr( f.scanset, peek ) != 0p ) throwResume ExceptionInst( cstring_length );1091 if ( flags.inex ^ strchr( scanset, peek ) != 0p ) throwResume ExceptionInst( cstring_length ); 1113 1092 } // if 1114 1093 } // if 1115 1094 } // if 1116 if ( rwd > 0 && args == 0 ) f.s[0]= '\0';// read failed => no pattern match => set string to null1095 if ( ! flags.ignore && args == 0 ) s[0]= '\0'; // read failed => no pattern match => set string to null 1117 1096 } // if 1118 1097 if ( args == 1 && eof( is ) ) { // data but scan ended at EOF … … 1120 1099 clear( is ); // => reset EOF => detect again on next read 1121 1100 } // if 1122 return is;1123 } // ?|?1124 1125 istype & ?|?( istype & is, _Istream_Char f ) {1126 fmt( is, "%*c" ); // argument variable unused1127 1101 return is; 1128 1102 } // ?|? … … 1145 1119 } // distribution 1146 1120 1121 INPUT_FMT_IMPL( char, "c" ) 1147 1122 INPUT_FMT_IMPL( signed char, "hhi" ) 1148 1123 INPUT_FMT_IMPL( unsigned char, "hhi" ) -
libcfa/src/iostream.hfa
rc75b30a r32490deb 10 10 // Created On : Wed May 27 17:56:53 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Wed Jan 3 10:53:18202413 // Update Count : 61012 // Last Modified On : Sun Jan 28 11:56:29 2024 13 // Update Count : 733 14 14 // 15 15 … … 196 196 // *********************************** integral *********************************** 197 197 198 // See 6.7.9. 19) The initialization shall occur in initializer list order, each initializer provided for a particular199 // subobject overriding any previously listed initializer for the same subobject; ***all subobjects that are not200 // initialized explicitly shall be initialized implicitly the same as objects that have static storage duration.***201 202 198 #define INTEGRAL_FMT_DECL( T, CODE ) \ 203 199 static inline { \ 204 _Ostream_Manip(T) bin( T val ) { return (_Ostream_Manip(T))@{ val, 1, 0,'b', { .all : 0 } }; } \205 _Ostream_Manip(T) oct( T val ) { return (_Ostream_Manip(T))@{ val, 1, 0,'o', { .all : 0 } }; } \206 _Ostream_Manip(T) hex( T val ) { return (_Ostream_Manip(T))@{ val, 1, 0,'x', { .all : 0 } }; } \207 _Ostream_Manip(T) wd( unsigned int w , T val ) { return (_Ostream_Manip(T))@{ val, w, 0,CODE, { .all : 0 } }; } \208 _Ostream_Manip(T) wd( unsigned int w , unsigned int pc, T val ) { return (_Ostream_Manip(T))@{ val, w, pc,CODE, { .flags.pc : true } }; } \209 _Ostream_Manip(T) & wd( unsigned int w , _Ostream_Manip(T) & fmt ) { fmt.wd = w; return fmt; } \210 _Ostream_Manip(T) & wd( unsigned int w , unsigned int pc, _Ostream_Manip(T) & fmt ) { fmt.wd = w; fmt.pc = pc; fmt.flags.pc = true; return fmt; } \200 _Ostream_Manip(T) bin( T val ) { return (_Ostream_Manip(T))@{ .val : val, .wd : 1, .pc : 0, .base : 'b', { .all : 0 } }; } \ 201 _Ostream_Manip(T) oct( T val ) { return (_Ostream_Manip(T))@{ .val : val, .wd : 1, .pc : 0, .base : 'o', { .all : 0 } }; } \ 202 _Ostream_Manip(T) hex( T val ) { return (_Ostream_Manip(T))@{ .val : val, .wd : 1, .pc : 0, .base : 'x', { .all : 0 } }; } \ 203 _Ostream_Manip(T) wd( unsigned int wd, T val ) { return (_Ostream_Manip(T))@{ .val : val, .wd : wd, .pc : 0, .base : CODE, { .all : 0 } }; } \ 204 _Ostream_Manip(T) wd( unsigned int wd, unsigned int pc, T val ) { return (_Ostream_Manip(T))@{ .val : val, .wd : wd, .pc : pc, .base : CODE, { .flags.pc : true } }; } \ 205 _Ostream_Manip(T) & wd( unsigned int wd, _Ostream_Manip(T) & fmt ) { fmt.wd = wd; return fmt; } \ 206 _Ostream_Manip(T) & wd( unsigned int wd, unsigned int pc, _Ostream_Manip(T) & fmt ) { fmt.wd = wd; fmt.pc = pc; fmt.flags.pc = true; return fmt; } \ 211 207 _Ostream_Manip(T) & left( _Ostream_Manip(T) & fmt ) { fmt.flags.left = true; return fmt; } \ 212 208 _Ostream_Manip(T) & upcase( _Ostream_Manip(T) & fmt ) { if ( fmt.base == 'x' || fmt.base == 'b' ) fmt.base -= 32; /* upper case */ return fmt; } \ 213 209 _Ostream_Manip(T) & nobase( _Ostream_Manip(T) & fmt ) { fmt.flags.nobsdp = true; return fmt; } \ 214 210 _Ostream_Manip(T) & pad0( _Ostream_Manip(T) & fmt ) { fmt.flags.pad0 = true; return fmt; } \ 215 _Ostream_Manip(T) sign( T val ) { return (_Ostream_Manip(T))@{ val, 1, 0,CODE, { .flags.sign : true } }; } \211 _Ostream_Manip(T) sign( T val ) { return (_Ostream_Manip(T))@{ .val : val, .wd : 1, .pc : 0, .base : CODE, { .flags.sign : true } }; } \ 216 212 _Ostream_Manip(T) & sign( _Ostream_Manip(T) & fmt ) { fmt.flags.sign = true; return fmt; } \ 217 213 } /* distribution */ \ … … 241 237 #define FLOATING_POINT_FMT_DECL( T ) \ 242 238 static inline { \ 243 _Ostream_Manip(T) hex( T val ) { return (_Ostream_Manip(T))@{ val, 1, 0, 'a', { .all : 0 } }; } \ 244 _Ostream_Manip(T) sci( T val ) { return (_Ostream_Manip(T))@{ val, 1, 0, 'e', { .all : 0 } }; } \ 245 _Ostream_Manip(T) eng( T val ) { return (_Ostream_Manip(T))@{ val, 1, -1, 'g', { .flags.eng : true } }; } \ 246 _Ostream_Manip(T) wd( unsigned int w, T val ) { return (_Ostream_Manip(T))@{ val, w, 0, 'g', { .all : 0 } }; } \ 247 _Ostream_Manip(T) wd( unsigned int w, unsigned int pc, T val ) { return (_Ostream_Manip(T))@{ val, w, pc, 'f', { .flags.pc : true } }; } \ 248 _Ostream_Manip(T) ws( unsigned int w, unsigned int pc, T val ) { return (_Ostream_Manip(T))@{ val, w, pc, 'g', { .flags.pc : true } }; } \ 249 _Ostream_Manip(T) & wd( unsigned int w, _Ostream_Manip(T) & fmt ) { if ( fmt.flags.eng ) fmt.base = 'f'; fmt.wd = w; return fmt; } \ 250 _Ostream_Manip(T) & wd( unsigned int w, unsigned int pc, _Ostream_Manip(T) & fmt ) { if ( fmt.flags.eng ) fmt.base = 'f'; fmt.wd = w; fmt.pc = pc; fmt.flags.pc = true; return fmt; } \ 251 _Ostream_Manip(T) & ws( unsigned int w, unsigned int pc, _Ostream_Manip(T) & fmt ) { fmt.wd = w; fmt.pc = pc; fmt.flags.pc = true; return fmt; } \ 239 _Ostream_Manip(T) hex( T val ) { return (_Ostream_Manip(T))@{ .val : val, .wd : 1, .pc : 0, .base : 'a', { .all : 0 } }; } \ 240 _Ostream_Manip(T) sci( T val ) { return (_Ostream_Manip(T))@{ .val : val, .wd : 1, .pc : 0, .base : 'e', { .all : 0 } }; } \ 241 _Ostream_Manip(T) eng( T val ) { return (_Ostream_Manip(T))@{ .val : val, 1, -1, .base : 'g', { .flags.eng : true } }; } \ 242 _Ostream_Manip(T) wd( unsigned int wd, T val ) { return (_Ostream_Manip(T))@{ .val : val, .wd : wd, .pc : 0, .base : 'g', { .all : 0 } }; } \ 243 _Ostream_Manip(T) wd( unsigned int wd, unsigned int pc, T val ) { return (_Ostream_Manip(T))@{ .val : val, .wd : wd, .pc : pc, .base : 'f', { .flags.pc : true } }; } \ 244 _Ostream_Manip(T) ws( unsigned int wd, unsigned int pc, T val ) { return (_Ostream_Manip(T))@{ .val : val, .wd : wd, .pc : pc, .base : 'g', { .flags.pc : true } }; } \ 245 _Ostream_Manip(T) & wd( unsigned int wd, _Ostream_Manip(T) & fmt ) { if ( fmt.flags.eng ) fmt.base = 'f'; fmt.wd = wd; return fmt; } \ 246 _Ostream_Manip(T) & wd( unsigned int wd, unsigned int pc, _Ostream_Manip(T) & fmt ) { \ 247 if ( fmt.flags.eng ) fmt.base = 'f'; fmt.wd = wd; fmt.pc = pc; fmt.flags.pc = true; return fmt; } \ 248 _Ostream_Manip(T) & ws( unsigned int wd, unsigned int pc, _Ostream_Manip(T) & fmt ) { fmt.wd = wd; fmt.pc = pc; fmt.flags.pc = true; return fmt; } \ 252 249 _Ostream_Manip(T) & left( _Ostream_Manip(T) & fmt ) { fmt.flags.left = true; return fmt; } \ 253 _Ostream_Manip(T) upcase( T val ) { return (_Ostream_Manip(T))@{ val, 1, 0,'G', { .all : 0 } }; } \250 _Ostream_Manip(T) upcase( T val ) { return (_Ostream_Manip(T))@{ .val : val, .wd : 1, .pc : 0, .base : 'G', { .all : 0 } }; } \ 254 251 _Ostream_Manip(T) & upcase( _Ostream_Manip(T) & fmt ) { fmt.base -= 32; /* upper case */ return fmt; } \ 255 252 _Ostream_Manip(T) & pad0( _Ostream_Manip(T) & fmt ) { fmt.flags.pad0 = true; return fmt; } \ 256 _Ostream_Manip(T) sign( T val ) { return (_Ostream_Manip(T))@{ val, 1, 0,'g', { .flags.sign : true } }; } \253 _Ostream_Manip(T) sign( T val ) { return (_Ostream_Manip(T))@{ .val : val, .wd : 1, .pc : 0, .base : 'g', { .flags.sign : true } }; } \ 257 254 _Ostream_Manip(T) & sign( _Ostream_Manip(T) & fmt ) { fmt.flags.sign = true; return fmt; } \ 258 _Ostream_Manip(T) nodp( T val ) { return (_Ostream_Manip(T))@{ val, 1, 0,'g', { .flags.nobsdp : true } }; } \255 _Ostream_Manip(T) nodp( T val ) { return (_Ostream_Manip(T))@{ .val : val, .wd : 1, .pc : 0, .base : 'g', { .flags.nobsdp : true } }; } \ 259 256 _Ostream_Manip(T) & nodp( _Ostream_Manip(T) & fmt ) { fmt.flags.nobsdp = true; return fmt; } \ 260 _Ostream_Manip(T) unit( T val ) { return (_Ostream_Manip(T))@{ val, 1, 0,'g', { .flags.nobsdp : true } }; } \257 _Ostream_Manip(T) unit( T val ) { return (_Ostream_Manip(T))@{ .val : val, .wd : 1, .pc : 0, .base : 'g', { .flags.nobsdp : true } }; } \ 261 258 _Ostream_Manip(T) & unit( _Ostream_Manip(T) & fmt ) { fmt.flags.nobsdp = true; return fmt; } \ 262 259 } /* distribution */ \ … … 272 269 273 270 static inline { 274 _Ostream_Manip(char) bin( char c ) { return (_Ostream_Manip(char))@{ c, 1, 0,'b', { .all : 0 } }; }275 _Ostream_Manip(char) oct( char c ) { return (_Ostream_Manip(char))@{ c, 1, 0,'o', { .all : 0 } }; }276 _Ostream_Manip(char) hex( char c ) { return (_Ostream_Manip(char))@{ c, 1, 0,'x', { .all : 0 } }; }277 _Ostream_Manip(char) wd( unsigned int w , char c ) { return (_Ostream_Manip(char))@{ c, w, 0,'c', { .all : 0 } }; }278 _Ostream_Manip(char) & wd( unsigned int w , _Ostream_Manip(char) & fmt ) { fmt.wd = w; return fmt; }271 _Ostream_Manip(char) bin( char c ) { return (_Ostream_Manip(char))@{ .val : c, .wd : 1, .pc : 0, .base : 'b', { .all : 0 } }; } 272 _Ostream_Manip(char) oct( char c ) { return (_Ostream_Manip(char))@{ .val : c, .wd : 1, .pc : 0, .base : 'o', { .all : 0 } }; } 273 _Ostream_Manip(char) hex( char c ) { return (_Ostream_Manip(char))@{ .val : c, .wd : 1, .pc : 0, .base : 'x', { .all : 0 } }; } 274 _Ostream_Manip(char) wd( unsigned int wd, char c ) { return (_Ostream_Manip(char))@{ c, wd, 0, .base : 'c', { .all : 0 } }; } 275 _Ostream_Manip(char) & wd( unsigned int wd, _Ostream_Manip(char) & fmt ) { fmt.wd = wd; return fmt; } 279 276 _Ostream_Manip(char) & left( _Ostream_Manip(char) & fmt ) { fmt.flags.left = true; return fmt; } 280 277 _Ostream_Manip(char) & upcase( _Ostream_Manip(char) & fmt ) { if ( fmt.base == 'x' || fmt.base == 'b' ) fmt.base -= 32; /* upper case */ return fmt; } … … 289 286 290 287 static inline { 291 _Ostream_Manip(const char *) bin( const char s[] ) { return (_Ostream_Manip(const char *))@{ s, 1, 0,'b', { .all : 0 } }; }292 _Ostream_Manip(const char *) oct( const char s[] ) { return (_Ostream_Manip(const char *))@{ s, 1, 0,'o', { .all : 0 } }; }293 _Ostream_Manip(const char *) hex( const char s[] ) { return (_Ostream_Manip(const char *))@{ s, 1, 0,'x', { .all : 0 } }; }294 _Ostream_Manip(const char *) wd( unsigned int w , const char s[] ) { return (_Ostream_Manip(const char *))@{ s, w, 0,'s', { .all : 0 } }; }295 _Ostream_Manip(const char *) wd( unsigned int w , unsigned int pc, const char s[] ) { return (_Ostream_Manip(const char *))@{ s, w, pc,'s', { .flags.pc : true } }; }296 _Ostream_Manip(const char *) & wd( unsigned int w , _Ostream_Manip(const char *) & fmt ) { fmt.wd = w; return fmt; }297 _Ostream_Manip(const char *) & wd( unsigned int w , unsigned int pc, _Ostream_Manip(const char *) & fmt ) { fmt.wd = w; fmt.pc = pc; fmt.flags.pc = true; return fmt; }288 _Ostream_Manip(const char *) bin( const char s[] ) { return (_Ostream_Manip(const char *))@{ .val : s, .wd : 1, .pc : 0, .base : 'b', { .all : 0 } }; } 289 _Ostream_Manip(const char *) oct( const char s[] ) { return (_Ostream_Manip(const char *))@{ .val : s, .wd : 1, .pc : 0, .base : 'o', { .all : 0 } }; } 290 _Ostream_Manip(const char *) hex( const char s[] ) { return (_Ostream_Manip(const char *))@{ .val : s, .wd : 1, .pc : 0, .base : 'x', { .all : 0 } }; } 291 _Ostream_Manip(const char *) wd( unsigned int wd, const char s[] ) { return (_Ostream_Manip(const char *))@{ s, wd, 0, .base : 's', { .all : 0 } }; } 292 _Ostream_Manip(const char *) wd( unsigned int wd, unsigned int pc, const char s[] ) { return (_Ostream_Manip(const char *))@{ s, .wd : wd, .pc : pc, .base : 's', { .flags.pc : true } }; } 293 _Ostream_Manip(const char *) & wd( unsigned int wd, _Ostream_Manip(const char *) & fmt ) { fmt.wd = wd; return fmt; } 294 _Ostream_Manip(const char *) & wd( unsigned int wd, unsigned int pc, _Ostream_Manip(const char *) & fmt ) { fmt.wd = wd; fmt.pc = pc; fmt.flags.pc = true; return fmt; } 298 295 _Ostream_Manip(const char *) & left( _Ostream_Manip(const char *) & fmt ) { fmt.flags.left = true; return fmt; } 299 296 _Ostream_Manip(const char *) & nobase( _Ostream_Manip(const char *) & fmt ) { fmt.flags.nobsdp = true; return fmt; } … … 385 382 386 383 static inline { 387 _Istream_Cskip skip( const char scanset[] ) { return (_Istream_Cskip)@{ scanset,0 }; }388 _Istream_Cskip skip( unsigned int wd ) { return (_Istream_Cskip)@{ 0p,wd }; }384 _Istream_Cskip skip( const char scanset[] ) { return (_Istream_Cskip)@{ .scanset : scanset, .wd : 0 }; } 385 _Istream_Cskip skip( unsigned int wd ) { return (_Istream_Cskip)@{ .scanset : 0p, .wd : wd }; } 389 386 } // distribution 390 387 … … 400 397 unsigned char ignore:1; // do not change input argument 401 398 unsigned char inex:1; // include/exclude characters in scanset 402 unsigned char delimiter:1; // delimit character 399 unsigned char delimiter:1; // delimit character(s) 403 400 unsigned char rwd:1; // read width 404 401 } flags; … … 406 403 }; // _Istream_str_base 407 404 408 struct _Istream_C str{405 struct _Istream_Cwidth { 409 406 char * s; 410 407 inline _Istream_str_base; 411 408 }; // _Istream_Cstr 412 409 410 // Restrict nesting of input manipulators to those combinations that make sense. 411 412 struct _Istream_Cstr { 413 _Istream_Cwidth cstr; 414 }; // _Istream_Cstr 415 413 416 struct _Istream_Cquoted { 414 _Istream_C strcstr;417 _Istream_Cwidth cstr; 415 418 }; // _Istream_Cquoted 416 419 417 420 static inline { 418 // width must include room for null terminator 419 _Istream_Cstr wdi( unsigned int wd, char s[] ) { return (_Istream_Cstr)@{ s, { {0p}, wd, {.all : 0} } }; } 420 _Istream_Cstr wdi( unsigned int wd, unsigned int rwd, char s[] ) { 421 if ( wd <= rwd ) throw (cstring_length){ &cstring_length_vt }; 422 return (_Istream_Cstr)@{ s, { {0p}, rwd, {.flags.rwd : true} } }; 421 // width must include room for null terminator, (gcc) scanf does not allow a 0 width => wd > 1 (1 char and null) and rd > 0 (1 char); 422 _Istream_Cwidth wdi( unsigned int wd, char s[] ) { 423 if ( wd <= 1 ) throw (cstring_length){ &cstring_length_vt }; // minimum 1 character and null terminator 424 return (_Istream_Cwidth)@{ .s : s, { {.scanset : 0p}, .wd : wd, {.all : 0} } }; 423 425 } 424 _Istream_C quoted & quoted( _Istream_Cstr & fmt, const char Ldelimiter = '"', const char Rdelimiter = '\0') {425 fmt.delimiters[0] = Ldelimiter; fmt.delimiters[1] = Rdelimiter; fmt.delimiters[2] = '\0';426 return (_Istream_C quoted &)fmt;426 _Istream_Cwidth wdi( unsigned int wd, unsigned int rwd, char s[] ) { 427 if ( wd <= 1 || wd <= rwd ) throw (cstring_length){ &cstring_length_vt }; // minimum 1 character, null terminator, plus subset 428 return (_Istream_Cwidth)@{ .s : s, { {.scanset : 0p}, .wd : rwd, {.flags.rwd : true} } }; 427 429 } 428 _Istream_C str & getline( _Istream_Cstr & fmt, const char delimiter = '\n' ) {429 fmt.delimiters[0] = delimiter; fmt.delimiters[1] = '\0'; fmt.flags.delimiter = true; fmt.flags.inex = true; return fmt;430 _Istream_Cquoted quoted( char & ch, const char Ldelimiter = '\'', const char Rdelimiter = '\0' ) { 431 return (_Istream_Cquoted)@{ { .s : &ch, { {.delimiters : { Ldelimiter, Rdelimiter, '\1' }}, .wd : 1, {.flags.rwd : true} } } }; 430 432 } 431 _Istream_Cstr & incl( const char scanset[], _Istream_Cstr & fmt ) { fmt.scanset = scanset; fmt.flags.inex = false; return fmt; } 432 _Istream_Cstr & excl( const char scanset[], _Istream_Cstr & fmt ) { fmt.scanset = scanset; fmt.flags.inex = true; return fmt; } 433 _Istream_Cstr ignore( char s[] ) { return (_Istream_Cstr)@{ s, { {0p}, -1, {.flags.ignore : true} } }; } 434 _Istream_Cstr & ignore( _Istream_Cstr & fmt ) { fmt.flags.ignore = true; return fmt; } 433 _Istream_Cquoted & quoted( _Istream_Cwidth & f, const char Ldelimiter = '"', const char Rdelimiter = '\0' ) { 434 f.delimiters[0] = Ldelimiter; f.delimiters[1] = Rdelimiter; f.delimiters[2] = '\0'; 435 return (_Istream_Cquoted &)f; 436 } 437 _Istream_Cstr & getline( _Istream_Cwidth & f, const char delimiter = '\n' ) { 438 f.delimiters[0] = delimiter; f.delimiters[1] = '\0'; f.flags.delimiter = true; return (_Istream_Cstr &)f; 439 } 440 _Istream_Cstr & incl( const char scanset[], _Istream_Cwidth & f ) { f.scanset = scanset; f.flags.inex = false; return (_Istream_Cstr &)f; } 441 _Istream_Cstr & excl( const char scanset[], _Istream_Cwidth & f ) { f.scanset = scanset; f.flags.inex = true; return (_Istream_Cstr &)f; } 442 _Istream_Cstr ignore( const char s[] ) { return (_Istream_Cwidth)@{ .s : (char *)s, { {.scanset : 0p}, .wd : -1, {.flags.ignore : true} } }; } 443 _Istream_Cstr & ignore( _Istream_Cwidth & f ) { f.flags.ignore = true; return (_Istream_Cstr &)f; } 444 _Istream_Cquoted & ignore( _Istream_Cquoted & f ) { f.cstr.flags.ignore = true; return (_Istream_Cquoted &)f; } 445 _Istream_Cstr & ignore( _Istream_Cstr & f ) { f.cstr.flags.ignore = true; return (_Istream_Cstr &)f; } 435 446 } // distribution 436 447 437 448 forall( istype & | basic_istream( istype ) ) { 438 istype & ?|?( istype & is, _Istream_Cstr f );439 449 istype & ?|?( istype & is, _Istream_Cskip f ); 440 450 istype & ?|?( istype & is, _Istream_Cquoted f ); 441 } // distribution 442 443 struct _Istream_Char { 444 bool ignore; // do not change input argument 445 }; // _Istream_Char 446 447 static inline { 448 _Istream_Char ignore( const char ) { return (_Istream_Char)@{ true }; } 449 _Istream_Char & ignore( _Istream_Char & fmt ) { fmt.ignore = true; return fmt; } 450 } // distribution 451 forall( istype & | basic_istream( istype ) ) { 452 istype & ?|?( istype & is, _Istream_Char f ); 453 } 451 istype & ?|?( istype & is, _Istream_Cstr f ); 452 static inline { 453 istype & ?|?( istype & is, _Istream_Cwidth f ) { return is | *(_Istream_Cstr *)&f; } 454 } // distribution 455 } // distribution 454 456 455 457 forall( T & | sized( T ) ) … … 462 464 #define INPUT_FMT_DECL( T ) \ 463 465 static inline { \ 464 _Istream_Manip(T) ignore( const T & val ) { return (_Istream_Manip(T))@{ (T &)val, -1, true }; } \ 466 _Istream_Manip(T) wdi( unsigned int wd, T & val ) { return (_Istream_Manip(T))@{ .val : val, .wd : wd, .ignore : false }; } \ 467 _Istream_Manip(T) ignore( const T & val ) { return (_Istream_Manip(T))@{ .val : (T &)val, .wd : -1, .ignore : true }; } \ 465 468 _Istream_Manip(T) & ignore( _Istream_Manip(T) & fmt ) { fmt.ignore = true; return fmt; } \ 466 _Istream_Manip(T) wdi( unsigned int wd, T & val ) { return (_Istream_Manip(T))@{ val, wd, false }; } \467 _Istream_Manip(T) & wdi( unsigned int wd, _Istream_Manip(T) & fmt ) { fmt.wd = wd; return fmt; } \468 469 } /* distribution */ \ 469 470 forall( istype & | basic_istream( istype ) ) { \ … … 471 472 } // ?|? 472 473 474 INPUT_FMT_DECL( char ) 473 475 INPUT_FMT_DECL( signed char ) 474 476 INPUT_FMT_DECL( unsigned char )
Note:
See TracChangeset
for help on using the changeset viewer.