1 1.9 andvar # $NetBSD: printf.sh,v 1.9 2022/05/24 20:50:20 andvar Exp $ 2 1.1 kre # 3 1.1 kre # Copyright (c) 2018 The NetBSD Foundation, Inc. 4 1.1 kre # All rights reserved. 5 1.1 kre # 6 1.1 kre # Redistribution and use in source and binary forms, with or without 7 1.1 kre # modification, are permitted provided that the following conditions 8 1.1 kre # are met: 9 1.1 kre # 1. Redistributions of source code must retain the above copyright 10 1.1 kre # notice, this list of conditions and the following disclaimer. 11 1.1 kre # 2. Redistributions in binary form must reproduce the above copyright 12 1.1 kre # notice, this list of conditions and the following disclaimer in the 13 1.1 kre # documentation and/or other materials provided with the distribution. 14 1.1 kre # 15 1.1 kre # THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 16 1.1 kre # ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 17 1.1 kre # TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 18 1.1 kre # PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 19 1.1 kre # BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 20 1.1 kre # CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 21 1.1 kre # SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 22 1.1 kre # INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 23 1.1 kre # CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 24 1.1 kre # ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 25 1.1 kre # POSSIBILITY OF SUCH DAMAGE. 26 1.1 kre # 27 1.1 kre 28 1.1 kre Running_under_ATF=false 29 1.1 kre test -n "${Atf_Shell}" && test -n "${Atf_Check}" && Running_under_ATF=true 30 1.1 kre 31 1.1 kre Tests= 32 1.1 kre 33 1.1 kre # create a test case: 34 1.1 kre # "$1" is basic test name, "$2" is description 35 1.1 kre define() 36 1.1 kre { 37 1.1 kre NAME=$1; shift 38 1.1 kre 39 1.1 kre if $Running_under_ATF 40 1.1 kre then 41 1.1 kre eval "${NAME}_head() { set descr 'Tests printf: $*'; }" 42 1.1 kre eval "${NAME}_body() { ${NAME} ; }" 43 1.1 kre else 44 1.1 kre eval "TEST_${NAME}_MSG="'"$*"' 45 1.1 kre fi 46 1.1 kre 47 1.1 kre Tests="${Tests} ${NAME}" 48 1.1 kre } 49 1.1 kre 50 1.1 kre 51 1.1 kre # 1st arg is printf format conversion specifier 52 1.1 kre # other args (if any) are args to that format 53 1.1 kre # returns success if that conversion specifier is supported, false otherwise 54 1.1 kre supported() 55 1.1 kre { 56 1.1 kre FMT="$1"; shift 57 1.1 kre 58 1.1 kre case "$#" in 59 1.1 kre 0) set -- 123;; # provide an arg for format to use 60 1.1 kre esac 61 1.1 kre 62 1.1 kre (do_printf >/dev/null 2>&1 "%${FMT}" "$@") 63 1.1 kre } 64 1.1 kre 65 1.1 kre LastErrorTest= 66 1.1 kre 67 1.1 kre $Running_under_ATF || { 68 1.1 kre 69 1.1 kre # Provide functions to emulate (roughly) what ATF gives us 70 1.1 kre # (that we actually use) 71 1.1 kre 72 1.1 kre atf_skip() { 73 1.1 kre echo >&2 "${CurrentTest} skipped: ${MSG} $*" 74 1.1 kre } 75 1.1 kre atf_fail() { 76 1.1 kre if [ "${CurrentTest}" != "${LastErrorTest}" ] 77 1.1 kre then 78 1.1 kre echo >&2 "======== In Test ${CurrentTest}:" 79 1.1 kre LastErrorTest="${CurrentTest}" 80 1.1 kre fi 81 1.1 kre echo >&2 "${CurrentTest} FAIL: ${MSG} $*" 82 1.1 kre RVAL=1 83 1.1 kre } 84 1.1 kre atf_require_prog() { 85 1.1 kre # Just allow progs we want to run to be, or not be, found 86 1.1 kre return 0 87 1.1 kre } 88 1.1 kre } 89 1.1 kre 90 1.1 kre # 1st arg is the result expected, remaining args are handed to do_printf 91 1.1 kre # to execute, fail if result does not match the expected result (treated 92 1.1 kre # as a sh pattern), or if do_printf fails 93 1.1 kre expect() 94 1.1 kre { 95 1.1 kre WANT="$1"; shift 96 1.1 kre negated=false 97 1.1 kre 98 1.1 kre case "${WANT}" in 99 1.1 kre ('!') WANT="$1"; negated=true; shift;; 100 1.1 kre esac 101 1.1 kre 102 1.1 kre RES="$( do_printf "$@" 2>&3 && echo X )" || atf_fail "$* ... Exit $?" 103 1.1 kre 104 1.1 kre RES=${RES%X} # hack to defeat \n removal from $() output 105 1.1 kre 106 1.1 kre if $negated 107 1.1 kre then 108 1.1 kre case "${RES}" in 109 1.1 kre (${WANT}) 110 1.1 kre atf_fail \ 111 1.1 kre "$* ... Expected anything but <<${WANT}>>, Received <<${RES}>>" 112 1.1 kre ;; 113 1.1 kre (*) 114 1.1 kre ;; 115 1.1 kre esac 116 1.1 kre else 117 1.1 kre case "${RES}" in 118 1.1 kre (${WANT}) 119 1.1 kre ;; 120 1.1 kre (*) 121 1.5 kre atf_fail "$* ... Expected <<${WANT}>> Received <<${RES}>>" 122 1.1 kre ;; 123 1.1 kre esac 124 1.1 kre fi 125 1.1 kre return 0 126 1.1 kre } 127 1.1 kre 128 1.1 kre # a variant which allows for two possible results 129 1.1 kre # It would be nice to have just one function, and allow the pattern 130 1.1 kre # to contain alternatives ... but that would require use of eval 131 1.1 kre # to parse, and that then gets tricky with quoting the pattern. 132 1.1 kre # and we only ever need two (so far anyway), so this is easier... 133 1.1 kre expect2() 134 1.1 kre { 135 1.1 kre WANT1="$1"; shift 136 1.1 kre WANT2="$1"; shift 137 1.1 kre 138 1.1 kre RES="$( do_printf "$@" 2>&3 && echo X )" || atf_fail "$* ... Exit $?" 139 1.1 kre 140 1.1 kre RES=${RES%X} # hack to defeat \n removal from $() output 141 1.1 kre 142 1.1 kre case "${RES}" in 143 1.1 kre (${WANT1} | ${WANT2}) 144 1.1 kre ;; 145 1.1 kre (*) 146 1.1 kre atf_fail \ 147 1.1 kre "$* ... Expected <<${WANT1}|${WANT2}>> Received <<${RES}>>" 148 1.1 kre ;; 149 1.1 kre esac 150 1.1 kre return 0 151 1.1 kre } 152 1.1 kre 153 1.1 kre expect_fail() 154 1.1 kre { 155 1.1 kre WANT="$1"; shift # we do not really expect this, but ... 156 1.1 kre 157 1.1 kre RES=$( do_printf "$@" 2>/dev/null && echo X ) && { 158 1.1 kre RES=${RES%X} 159 1.1 kre case "${RES}" in 160 1.1 kre (${WANT}) 161 1.1 kre atf_fail \ 162 1.1 kre "$* ... success${WANT:+ with expected <<${WANT}>>}" 163 1.1 kre ;; 164 1.1 kre ('') 165 1.1 kre atf_fail "$* ... success (without output)" 166 1.1 kre ;; 167 1.1 kre (*) 168 1.1 kre atf_fail "$* ... success with <<${RES}>> (not <<${WANT}>>)" 169 1.1 kre ;; 170 1.1 kre esac 171 1.1 kre 172 1.1 kre RVAL=1 173 1.1 kre return 0 174 1.1 kre } 175 1.1 kre 176 1.1 kre RES=$( do_printf "$@" 2>&1 >/dev/null ) 177 1.1 kre STAT=$? 178 1.1 kre test -z "${RES}" && 179 1.1 kre atf_fail "$* ... failed (${STAT}) without error message" 180 1.1 kre 181 1.6 kre RES="$( do_printf "$@" 2>/dev/null || : ; echo X )" 182 1.1 kre RES=${RES%X} # hack to defeat \n removal from $() output 183 1.1 kre 184 1.1 kre case "${RES}" in 185 1.1 kre (${WANT}) 186 1.1 kre # All is good, printf failed, sent a message to stderr 187 1.1 kre # and printed what it should to stdout 188 1.1 kre ;; 189 1.1 kre (*) 190 1.1 kre atf_fail \ 191 1.1 kre "$* ... should fail with <<${WANT}>> did exit(${STAT}) with <<${RES}>>" 192 1.1 kre ;; 193 1.1 kre esac 194 1.1 kre return 0 195 1.1 kre } 196 1.1 kre 197 1.1 kre ########################################################################## 198 1.1 kre ########################################################################## 199 1.1 kre # 200 1.1 kre # Actual tests follow 201 1.1 kre # 202 1.1 kre ########################################################################## 203 1.1 kre ########################################################################## 204 1.1 kre 205 1.1 kre basic() 206 1.1 kre { 207 1.1 kre setmsg basic 208 1.1 kre 209 1.4 kre if (do_printf >/dev/null 2>&1) 210 1.4 kre then 211 1.4 kre atf_fail "with no args successful" 212 1.4 kre fi 213 1.4 kre if test -n "$( do_printf 2>/dev/null )" 214 1.4 kre then 215 1.4 kre atf_fail "with no args produces text on stdout" 216 1.4 kre fi 217 1.4 kre if test -z "$( do_printf 2>&1 )" 218 1.4 kre then 219 1.4 kre atf_fail "with no args no err/usage message" 220 1.4 kre fi 221 1.4 kre 222 1.4 kre for A in - -- X 1 223 1.1 kre do 224 1.1 kre if (do_printf "%${A}%" >/dev/null 2>&1) 225 1.1 kre then 226 1.1 kre atf_fail "%${A}% successful" 227 1.1 kre fi 228 1.1 kre done 229 1.1 kre 230 1.1 kre expect abcd abcd 231 1.1 kre expect % %% 232 1.1 kre expect xxx%yyy xxx%%yyy 233 1.4 kre expect -123 -123 234 1.1 kre 235 1.1 kre # technically these are all unspecified, but the only rational thing 236 1.1 kre expect_fail '' %3% 237 1.1 kre expect_fail a a%.% 238 1.1 kre expect_fail '' '%*%b' # cannot continue after bad format 239 1.1 kre expect_fail a a%-%b # hence 'b' is not part of output 240 1.1 kre 241 1.1 kre return $RVAL 242 1.1 kre } 243 1.1 kre define basic 'basic functionality' 244 1.1 kre 245 1.1 kre format_escapes() 246 1.1 kre { 247 1.1 kre setmsg format_escapes 248 1.1 kre 249 1.1 kre expect "${BSL}" '\\' 250 1.1 kre expect '?' '\\' # must be just 1 char 251 1.1 kre 252 1.1 kre expect "${NL}" '\n' 253 1.1 kre expect " " '\t' # a literal <tab> in " " 254 1.1 kre 255 1.1 kre expect "0" '\60' 256 1.1 kre expect "1" '\061' 257 1.1 kre expect "21" '\0621' 258 1.1 kre expect "${NL}" '\12' 259 1.1 kre expect "" '\1' 260 1.1 kre 261 1.1 kre expect "" '\b' 262 1.1 kre expect "" '\f' 264 1.1 kre expect " " '\r' 266 1.1 kre expect "" '\a' 267 1.1 kre expect "" '\v' 269 1.1 kre 270 1.1 kre expect "hello${NL}world${NL}!!${NL}" 'hello\nworld\n\a\a!!\n' 271 1.1 kre 272 1.1 kre atf_require_prog wc 273 1.1 kre atf_require_prog od 274 1.1 kre atf_require_prog tr 275 1.1 kre 276 1.1 kre for fmt in '\0' '\00' '\000' 277 1.1 kre do 278 1.1 kre RES=$(( $( do_printf "${fmt}" | wc -c ) )) 279 1.1 kre if [ "${RES}" -ne 1 ] 280 1.1 kre then 281 1.1 kre atf_fail "'${fmt}' output $RES bytes, expected 1" 282 1.1 kre elif [ $(( $( do_printf "${fmt}" | od -A n -to1 ) )) -ne 0 ] 283 1.1 kre then 284 1.1 kre RES="$( do_printf "${fmt}" | od -A n -to1 | tr -d ' ')" 285 1.1 kre atf_fail \ 286 1.1 kre "'${fmt}' output was '\\${RES}' should be '\\000'" 287 1.1 kre fi 288 1.1 kre done 289 1.1 kre 290 1.1 kre # There are no expected failures here, as all other \Z 291 1.1 kre # sequences produce unspecified results -- anything is OK. 292 1.1 kre 293 1.1 kre return $RVAL 294 1.1 kre } 295 1.1 kre define format_escapes "backslash escapes in format string" 296 1.1 kre 297 1.1 kre s_strings() 298 1.1 kre { 299 1.1 kre setmsg s_strings 300 1.1 kre 301 1.1 kre # The # and 0 flags produce undefined results (so don't test) 302 1.1 kre # The + and ' ' flags are ignored (only apply to signed conversions) 303 1.1 kre 304 1.1 kre expect abcd %s abcd 305 1.1 kre expect ' a' %3s a 306 1.1 kre expect 'a ' %-3s a 307 1.1 kre expect abcd %3s abcd 308 1.1 kre expect abcd %-3s abcd 309 1.1 kre 310 1.1 kre expect a %.1s abcd 311 1.1 kre expect ab %.2s abcd 312 1.1 kre expect abc %.3s abcd 313 1.1 kre expect abcd %.4s abcd 314 1.1 kre expect abcd %.5s abcd 315 1.1 kre expect abcd %.6s abcd 316 1.1 kre 317 1.1 kre expect ' a' %4.1s abcd 318 1.1 kre expect ' ab' %4.2s abcd 319 1.1 kre expect ' abc' %4.3s abcd 320 1.1 kre expect abcd %4.4s abcd 321 1.1 kre expect abcd %4.5s abcd 322 1.1 kre expect abcd %4.6s abcd 323 1.1 kre 324 1.1 kre expect ' a' %7.1s abcd 325 1.1 kre expect 'ab ' %-7.2s abcd 326 1.1 kre expect ' abc' %7.3s abcd 327 1.1 kre expect ' abcd' %7.4s abcd 328 1.1 kre expect 'abcd ' %-7.5s abcd 329 1.1 kre expect ' abcd' %7.6s abcd 330 1.1 kre 331 1.1 kre expect 'aba a' %.2s%.1s%2.1s abcd abcd abcd 332 1.1 kre 333 1.1 kre expect 123 %s 123 334 1.1 kre expect 1 %.1s 123 335 1.1 kre expect 12 %+.2s 123 336 1.1 kre expect -1 %+.2s -123 337 1.1 kre expect 12 '% .2s' 123 338 1.1 kre expect -1 '%+.2s' -123 339 1.1 kre 340 1.1 kre expect '' %s '' 341 1.1 kre expect ' ' %1s '' 342 1.1 kre expect ' ' %6s '' 343 1.1 kre expect ' ' %2.1s '' 344 1.1 kre expect '' %.0s abcd 345 1.1 kre expect ' ' %2.0s abcd 346 1.1 kre expect ' ' %-3.0s abcd 347 1.1 kre 348 1.1 kre # %s is just so boring! There are no possible failures to test. 349 1.1 kre 350 1.1 kre return $RVAL 351 1.1 kre } 352 1.1 kre define s_strings "%s string output" 353 1.1 kre 354 1.1 kre c_chars() 355 1.1 kre { 356 1.1 kre setmsg c_chars 357 1.1 kre 358 1.1 kre expect a '%c' a 359 1.1 kre expect a '%c' abc 360 1.1 kre expect 'ad' '%c%c' abc def 361 1.1 kre expect '@ a@a @' "@%3c@%-3c@" a a 362 1.1 kre expect '@ a@a @' "@%2c@%-4c@" a a 363 1.1 kre 364 1.1 kre # do not test with '' (null string) as operand to %c 365 1.1 kre # as whether that produces \0 or nothing is unspecified. 366 1.1 kre # (test NetBSD specific behaviour in NetBSD specific test) 367 1.1 kre 368 1.1 kre return $RVAL 369 1.1 kre } 370 1.1 kre define c_chars '%c (character) format conversions' 371 1.1 kre 372 1.1 kre d_decimal() 373 1.1 kre { 374 1.1 kre setmsg d_decimal 375 1.1 kre 376 1.1 kre expect 0 '%d' 0 377 1.1 kre expect 1 '%d' 1 378 1.1 kre expect 999 '%d' 999 379 1.1 kre expect -77 '%d' -77 380 1.1 kre expect 51 '%d' 0x33 381 1.1 kre expect 51 '%d' 063 382 1.1 kre 383 1.1 kre expect ' 2' '%4d' 2 384 1.1 kre expect '0002' '%04d' 2 385 1.1 kre expect '-002' '%04d' -2 386 1.1 kre expect '2 ' '%-4d' 2 387 1.1 kre expect ' 02' '%4.2d' 2 388 1.1 kre expect ' 22' '%4.2d' 22 389 1.1 kre expect ' 222' '%4.2d' 222 390 1.1 kre expect '2222' '%4.2d' 2222 391 1.1 kre expect '22222' '%4.2d' 22222 392 1.1 kre expect ' -02' '%4.2d' -2 393 1.1 kre expect '02 ' '%-4.2d' 2 394 1.1 kre expect '-02 ' '%-4.2d' -2 395 1.1 kre expect '22 ' '%-4.2d' 22 396 1.1 kre expect '222 ' '%-4.2d' 222 397 1.1 kre expect '2222' '%-4.2d' 2222 398 1.1 kre expect '22222' '%-4.2d' 22222 399 1.1 kre expect 1 '%.0d' 1 400 1.1 kre expect '' '%.0d' 0 401 1.1 kre expect '' '%.d' 0 402 1.1 kre expect ' ' '%3.d' 0 403 1.1 kre expect ' ' '%-4.d' 0 404 1.1 kre expect ' ' '%05.d' 0 405 1.1 kre 406 1.8 kre expect 65 '%d' "'A" 407 1.8 kre expect 065 '%03d' "'A" 408 1.3 kre expect 49 '%d' "'1" 409 1.1 kre expect_fail 45 '%d' "'-1" 410 1.1 kre expect_fail 43 '%d' "'+1" 411 1.1 kre expect 00 '%.2d' "'" 412 1.1 kre 413 1.8 kre expect 68 '%d' '"D' 414 1.8 kre expect 069 '%03d' '"E' 415 1.1 kre expect 51 '%d' '"3' 416 1.1 kre expect_fail 45 '%d' '"-3' 417 1.1 kre expect_fail 43 '%d' '"+3' 418 1.1 kre 419 1.1 kre expect -1 '% d' -1 420 1.1 kre expect ' 1' '% d' 1 421 1.1 kre expect -1 '% 1d' -1 422 1.1 kre expect ' 1' '% 1d' 1 423 1.1 kre expect -1 '% 0d' -1 424 1.1 kre expect ' 1' '% 0d' 1 425 1.1 kre expect ' -1' '% 5d' -1 426 1.1 kre expect ' 1' '% 5d' 1 427 1.1 kre expect ' 01' '%0 3d' 1 428 1.1 kre expect '-01' '%0 3d' -1 429 1.1 kre expect ' 03' '% 4.2d' 3 430 1.1 kre expect ' -03' '% 4.2d' -3 431 1.1 kre 432 1.1 kre expect -1 '%+d' -1 433 1.1 kre expect +1 '%+d' 1 434 1.1 kre expect ' -7' '%+3d' -7 435 1.1 kre expect ' +7' '%+3d' 7 436 1.1 kre expect ' -02' '%+4.2d' -2 437 1.1 kre expect ' +02' '%+4.2d' 2 438 1.1 kre expect '-09 ' '%-+4.2d' -9 439 1.1 kre expect '+09 ' '%+-4.2d' 9 440 1.1 kre 441 1.1 kre # space flag is ignored if + is given, so same results as just above 442 1.1 kre expect -1 '%+ d' -1 443 1.1 kre expect +1 '%+ d' 1 444 1.1 kre expect ' -7' '%+ 3d' -7 445 1.1 kre expect ' +7' '%+ 3d' 7 446 1.1 kre expect ' -02' '%+ 4.2d' -2 447 1.1 kre expect ' +02' '%+ 4.2d' 2 448 1.1 kre expect '-09 ' '%- +4.2d' -9 449 1.1 kre expect '+09 ' '% +-4.2d' 9 450 1.1 kre 451 1.1 kre expect_fail '0' %d junk 452 1.1 kre expect_fail '123' %d 123kb 453 1.1 kre expect_fail '15' %d 0xfooD 454 1.1 kre 455 1.1 kre expect_fail '0 1 2' %d%2d%2d junk 1 2 456 1.1 kre expect_fail '3 1 2' %d%2d%2d 3 1+1 2 457 1.1 kre 458 1.1 kre return $RVAL 459 1.1 kre } 460 1.1 kre define d_decimal '%d (decimal integer) conversions' 461 1.1 kre 462 1.1 kre i_decimal() 463 1.1 kre { 464 1.1 kre setmsg i_decimal 465 1.1 kre 466 1.1 kre supported i || { 467 1.1 kre atf_skip "%i conversion not supported" 468 1.1 kre return $RVAL 469 1.1 kre } 470 1.1 kre 471 1.1 kre expect 0 '%i' 0 472 1.1 kre expect 1 '%i' 1 473 1.1 kre expect 999 '%i' 999 474 1.1 kre expect -77 '%i' -77 475 1.1 kre expect 51 '%i' 0x33 476 1.1 kre expect 51 '%i' 063 477 1.3 kre expect '02 ' '%-4.2i' 2 478 1.3 kre expect ' +02' '%+ 4.2i' 2 479 1.1 kre 480 1.1 kre expect 0 '%i' '"' 481 1.1 kre 482 1.1 kre expect_fail '0' %i x22 483 1.1 kre expect_fail '123' %i 123Mb 484 1.1 kre expect_fail '15' %i 0xfooD 485 1.1 kre 486 1.1 kre return $RVAL 487 1.1 kre } 488 1.1 kre define i_decimal '%i (decimal integer) conversions' 489 1.1 kre 490 1.1 kre u_unsigned() 491 1.1 kre { 492 1.1 kre setmsg u_unsigned 493 1.1 kre 494 1.1 kre # Only tests of negative numbers are that we do not 495 1.1 kre # fail, and do not get a '-' in the result 496 1.1 kre 497 1.1 kre # This is because the number of bits available is not defined 498 1.1 kre # so we cannot anticipate what value a negative number will 499 1.1 kre # produce when interpreted as unsigned (unlike hex and octal 500 1.1 kre # where we can at least examine the least significant bits) 501 1.1 kre 502 1.1 kre expect 0 '%u' 0 503 1.1 kre expect 1 '%u' 1 504 1.1 kre expect 999 '%u' 999 505 1.1 kre expect 51 '%u' 0x33 506 1.1 kre expect 51 '%u' 063 507 1.1 kre 508 1.1 kre expect ! '-*' '%u' -77 509 1.1 kre 510 1.1 kre expect ' 2' '%4u' 2 511 1.1 kre expect '0002' '%04u' 2 512 1.1 kre expect '2 ' '%-4u' 2 513 1.1 kre expect ' 02' '%4.2u' 2 514 1.1 kre expect ' 22' '%4.2u' 22 515 1.1 kre expect ' 222' '%4.2u' 222 516 1.1 kre expect '2222' '%4.2u' 2222 517 1.1 kre expect '22222' '%4.2u' 22222 518 1.1 kre expect '02 ' '%-4.2u' 2 519 1.1 kre expect '22 ' '%-4.2u' 22 520 1.1 kre expect '222 ' '%-4.2u' 222 521 1.1 kre expect '2222' '%-4.2u' 2222 522 1.1 kre expect '22222' '%-4.2u' 22222 523 1.1 kre expect 1 '%.0u' 1 524 1.1 kre expect '' '%.0u' 0 525 1.1 kre expect '' '%.u' 0 526 1.1 kre expect ' ' '%3.u' 0 527 1.1 kre expect ' ' '%-4.u' 0 528 1.1 kre expect ' ' '%05.u' 0 529 1.1 kre 530 1.8 kre expect 65 '%u' "'A" 531 1.8 kre expect 065 '%03u' "'A" 532 1.1 kre expect 49 '%u' "'1" 533 1.1 kre expect_fail 45 '%u' "'-1" 534 1.1 kre expect_fail 43 '%u' "'+1" 535 1.1 kre 536 1.8 kre expect 68 '%u' '"D' 537 1.8 kre expect 069 '%03u' '"E' 538 1.1 kre expect 51 '%u' '"3' 539 1.1 kre expect_fail 45 '%u' '"-3' 540 1.1 kre expect_fail 43 '%u' '"+3' 541 1.1 kre 542 1.1 kre # Note that the ' ' and '+' flags only apply to signed conversions 543 1.1 kre # so they should be simply ignored for '%u' 544 1.1 kre expect 1 '% u' 1 545 1.1 kre expect 1 '% 1u' 1 546 1.1 kre expect 1 '% 0u' 1 547 1.1 kre expect ' 1' '% 5u' 1 548 1.1 kre expect 001 '%0 3u' 1 549 1.1 kre expect ' 03' '% 4.2u' 3 550 1.1 kre 551 1.1 kre expect ! '-*' '% u' -1 552 1.1 kre 553 1.1 kre expect 1 '%+u' 1 554 1.1 kre expect ' 7' '%+3u' 7 555 1.1 kre expect ' 02' '%+4.2u' 2 556 1.1 kre expect '09 ' '%+-4.2u' 9 557 1.1 kre 558 1.1 kre expect ! '-*' '%+u' -7 559 1.1 kre 560 1.1 kre expect_fail '0' %u junk 561 1.1 kre expect_fail '123' %u 123kb 562 1.1 kre expect_fail '15' %u 0xfooD 563 1.1 kre 564 1.1 kre expect_fail '0 1 2' %u%2u%2u junk 1 2 565 1.1 kre expect_fail '3 1 2' %u%2u%2u 3 1+1 2 566 1.1 kre 567 1.1 kre return $RVAL 568 1.1 kre } 569 1.1 kre define u_unsigned '%u (unsigned decimal integer) conversions' 570 1.1 kre 571 1.1 kre o_octal() 572 1.1 kre { 573 1.1 kre setmsg o_octal 574 1.1 kre 575 1.1 kre expect 0 '%o' 0 576 1.1 kre expect 1 '%o' 1 577 1.1 kre expect 1747 '%o' 999 578 1.1 kre expect 63 '%o' 0x33 579 1.1 kre expect 63 '%o' 063 580 1.1 kre 581 1.1 kre expect ' 2' '%4o' 2 582 1.1 kre expect '0002' '%04o' 2 583 1.1 kre expect '2 ' '%-4o' 2 584 1.1 kre expect ' 02' '%4.2o' 2 585 1.1 kre expect '02 ' '%-4.2o' 2 586 1.1 kre expect 1 '%.0o' 1 587 1.1 kre expect '' '%.0o' 0 588 1.1 kre 589 1.1 kre expect ' 3' %3o 03 590 1.1 kre expect ' 33' %3o 033 591 1.1 kre expect '333' %3o 0333 592 1.1 kre expect '3333' %3o 03333 593 1.1 kre expect '33333' %3o 033333 594 1.1 kre 595 1.1 kre expect '4 ' %-3o 04 596 1.1 kre expect '45 ' %-3o 045 597 1.1 kre expect '456' %-3o 0456 598 1.1 kre expect '4567' %-3o 04567 599 1.1 kre expect '45670' %-3o 045670 600 1.1 kre 601 1.1 kre expect '04 ' %#-3o 04 602 1.1 kre expect '045' %-#3o 045 603 1.1 kre expect '0456' %#-3o 0456 604 1.1 kre expect '04567' %-#3o 04567 605 1.1 kre expect '045670' %#-3o 045670 606 1.1 kre 607 1.8 kre expect 101 '%o' "'A" 608 1.8 kre expect 0101 '%04o' "'A" 609 1.1 kre expect 61 '%o' "'1" 610 1.1 kre expect_fail 55 '%o' "'-1" 611 1.1 kre expect_fail 53 '%o' "'+1" 612 1.1 kre 613 1.1 kre expect 01747 '%#o' 999 614 1.1 kre expect ' 02' '%#4o' 2 615 1.1 kre expect '02 ' '%#-4.2o' 2 616 1.8 kre expect 0101 '%#o' "'A" 617 1.8 kre expect 0101 '%#04o' "'A" 618 1.1 kre expect 061 '%#o' "'1" 619 1.1 kre expect_fail 055 '%#o' "'-1" 620 1.1 kre expect_fail 053 '%#o' "'+1" 621 1.1 kre expect 063 '%#o' 063 622 1.1 kre 623 1.1 kre # negative numbers are allowed, but printed as unsigned. 624 1.1 kre # Since we have no fixed integer width, we don't know 625 1.1 kre # how many upper 1 bits there will be, so only check the 626 1.1 kre # low 21 bits ... 627 1.1 kre expect '*7777777' '%o' -1 628 1.1 kre expect '*7777776' '%04o' -2 629 1.1 kre expect '*7777770' '%7o' -8 630 1.1 kre expect '0*7777700' '%#o' -0100 631 1.1 kre expect '*7777663' '%o' -77 632 1.1 kre 633 1.1 kre return $RVAL 634 1.1 kre } 635 1.1 kre define o_octal '%o (octal integer) conversions' 636 1.1 kre 637 1.1 kre x_hex() 638 1.1 kre { 639 1.1 kre setmsg x_hex 640 1.1 kre 641 1.1 kre expect 0 '%x' 0 642 1.1 kre expect 1 '%x' 1 643 1.1 kre expect 3e7 '%x' 999 644 1.1 kre expect 33 '%x' 0x33 645 1.1 kre expect 33 '%x' 063 646 1.1 kre 647 1.1 kre expect ' 2' '%4x' 2 648 1.1 kre expect '0002' '%04x' 2 649 1.1 kre expect '2 ' '%-4x' 2 650 1.1 kre expect ' 02' '%4.2x' 2 651 1.1 kre expect '02 ' '%-4.2x' 2 652 1.1 kre expect 1 '%.0x' 1 653 1.1 kre expect '' '%.0x' 0 654 1.1 kre 655 1.8 kre expect 41 '%x' "'A" 656 1.8 kre expect 041 '%03x' "'A" 657 1.1 kre expect 31 '%x' "'1" 658 1.1 kre expect_fail 2d '%x' "'-1" 659 1.1 kre expect_fail 2b '%x' "'+1" 660 1.1 kre 661 1.1 kre expect ' face ' '%5x ' 64206 662 1.1 kre 663 1.1 kre # The 'alternate representation' (# flag) inserts 0x unless value==0 664 1.1 kre 665 1.1 kre expect 0 %#x 0 666 1.1 kre expect 0x1 %#x 1 667 1.1 kre 668 1.1 kre # We can also print negative numbers (treated as unsigned) 669 1.1 kre # but as there is no defined integer width for printf(1) 670 1.1 kre # we don't know how many F's in FFF...FFF for -1, so just 671 1.1 kre # validate the bottom 24 bits, and assume the rest will be OK. 672 1.1 kre # (tests above will fail if printf can't handle at least 32 bits) 673 1.1 kre 674 1.1 kre expect '*ffffff' %x -1 675 1.1 kre expect '*fffff0' %x -16 676 1.1 kre expect '*fff00f' %x -4081 677 1.1 kre expect '*fff00d' %x -4083 678 1.1 kre expect '*fffabc' %x -1348 679 1.1 kre expect '*ff3502' %x -0xCAFE 680 1.1 kre 681 1.1 kre expect_fail '0 1 2' %x%2x%2x junk 1 2 682 1.1 kre expect_fail '3 1 2' %x%2x%2x 3 1+1 2 683 1.1 kre 684 1.1 kre return $RVAL 685 1.1 kre } 686 1.1 kre define x_hex '%x (hexadecimal output) conversions' 687 1.1 kre 688 1.1 kre X_hex() 689 1.1 kre { 690 1.1 kre setmsg X_hex 691 1.1 kre 692 1.1 kre # The only difference between %x and %X ix the case of 693 1.8 kre # the alpha digits, so just do minimal testing of that... 694 1.8 kre 695 1.1 kre expect 3E7 %X 999 696 1.1 kre expect_fail 2D %X "'-1" 697 1.1 kre expect_fail 2B %X "'+1" 698 1.1 kre expect ' FACE ' '%5X ' 64206 699 1.1 kre expect DEADBEEF %X 3735928559 700 1.1 kre 701 1.1 kre expect 1234FEDC %X 0x1234fedc 702 1.1 kre 703 1.1 kre expect '*FFCAFE' %X -13570 704 1.1 kre expect '*FFFFFE' %X -2 705 1.1 kre 706 1.1 kre return $RVAL 707 1.1 kre } 708 1.1 kre define X_hex '%X (hexadecimal output) conversions' 709 1.1 kre 710 1.1 kre f_floats() 711 1.1 kre { 712 1.1 kre setmsg f_floats 713 1.1 kre 714 1.1 kre supported f || { 715 1.1 kre atf_skip "%f conversion not supported" 716 1.1 kre return $RVAL 717 1.1 kre } 718 1.1 kre 719 1.1 kre expect 0.000000 %f 0 720 1.1 kre expect 1.000000 %f 1 721 1.1 kre expect 1.500000 %f 1.5 722 1.1 kre expect -1.000000 %f -1 723 1.1 kre expect -1.500000 %f -1.5 724 1.1 kre 725 1.1 kre expect 44.000000 %f 44 726 1.1 kre expect -43.000000 %f -43 727 1.1 kre expect '3.33333?' %f 3.333333333333333 728 1.1 kre expect '0.78539?' %f .7853981633974483 729 1.1 kre expect '0.00012?' %f .000123456789 730 1.1 kre expect '1234.56789?' %f 1234.56789 731 1.1 kre 732 1.1 kre expect 0 %.0f 0 733 1.1 kre expect 1 %.0f 1 734 1.1 kre expect 1. %#.0f 1.1 735 1.1 kre expect 0. %#.0f 0 736 1.1 kre expect 1. %#.0f 1 737 1.1 kre expect 1. %#.0f 1.2 738 1.1 kre 739 1.1 kre expect 0.0 %.1f 0 740 1.1 kre expect 1.0 %.1f 1 741 1.1 kre expect 1.1 %#.1f 1.1 742 1.1 kre expect 0.0 %#.1f 0 743 1.1 kre expect 1.2 %#.1f 1.2 744 1.1 kre 745 1.1 kre expect ' 0.0' %6.1f 0 746 1.1 kre expect ' 1.0' %6.1f 1 747 1.1 kre expect ' -1.0' %6.1f -1 748 1.1 kre 749 1.1 kre expect '0000.0' %06.1f 0 750 1.1 kre expect '0001.0' %06.1f 1 751 1.1 kre expect '-001.0' %06.1f -1 752 1.1 kre 753 1.1 kre expect ' +0.0' %+6.1f 0 754 1.1 kre expect ' +1.0' %+6.1f 1 755 1.1 kre expect ' -1.0' %+6.1f -1 756 1.1 kre 757 1.1 kre expect ' 0.0' '% 6.1f' 0 758 1.1 kre expect ' 1.0' '% 6.1f' 1 759 1.1 kre expect ' -1.0' '% 6.1f' -1 760 1.1 kre 761 1.1 kre expect ' 000.0' '%0 6.1f' 0 762 1.1 kre expect ' 001.0' '% 06.1f' 1 763 1.1 kre expect '-001.0' '%0 6.1f' -1 764 1.1 kre 765 1.1 kre expect '+000.0' '%0+6.1f' 0 766 1.1 kre expect '+001.0' '%+06.1f' 1 767 1.1 kre expect '-001.0' '%0+6.1f' -1 768 1.1 kre 769 1.1 kre expect '0000000.00' %010.2f 0 770 1.1 kre expect '-000009.00' %010.2f -9 771 1.1 kre 772 1.1 kre expect '0.0 ' %-10.1f 0 773 1.1 kre expect '1.0 ' %-10.1f 1 774 1.1 kre expect '-1.0 ' %-10.1f -1 775 1.1 kre 776 1.1 kre expect '0.00 ' %-10.2f 0 777 1.1 kre expect '-9.00 ' %-10.2f -9 778 1.1 kre 779 1.1 kre expect '0.0 ' %-010.1f 0 780 1.1 kre expect '1.0 ' %-010.1f 1 781 1.1 kre expect '-1.0 ' %-010.1f -1 782 1.1 kre 783 1.1 kre expect '0.00 ' %-6.2f 0 784 1.1 kre expect '-9.00 ' %-6.2f -9 785 1.1 kre 786 1.1 kre expect '0.00 ' %-010.2f 0 787 1.1 kre expect '-9.00 ' %-010.2f -9 788 1.1 kre 789 1.1 kre expect ' 0' %7.0f 0 790 1.1 kre expect '1 ' %-7.0f 1 791 1.1 kre expect ' 0.' %#7.0f 0 792 1.1 kre expect ' 1.' %#7.0f 1 793 1.1 kre expect ' 1.' %#7.0f 1.1 794 1.1 kre expect ' 1.' %#7.0f 1.2 795 1.1 kre expect ' -1.' %#7.0f -1.2 796 1.1 kre expect '1. ' %-#7.0f 1.1 797 1.1 kre expect '0. ' %#-7.0f 0 798 1.1 kre expect '1. ' %-#7.0f 1 799 1.1 kre expect '1. ' %#-7.0f 1.2 800 1.1 kre expect '-1. ' %#-7.0f -1.2 801 1.1 kre expect ' +0' %+7.0f 0 802 1.1 kre expect '+1 ' %-+7.0f 1 803 1.1 kre expect ' +1.' %+#7.0f 1.1 804 1.1 kre expect ' +0.' %#+7.0f 0 805 1.1 kre expect ' +1.' %+#7.0f 1 806 1.1 kre expect ' +1.' %#+7.0f 1.2 807 1.1 kre expect ' -1.' %#+7.0f -1.2 808 1.1 kre expect ' 0' '% 7.0f' 0 809 1.1 kre expect ' 1 ' '%- 7.0f' 1 810 1.1 kre expect '-1 ' '%- 7.0f' -1 811 1.1 kre expect ' 1.' '% #7.0f' 1.1 812 1.1 kre expect ' 0.' '%# 7.0f' 0 813 1.1 kre expect ' 1.' '% #7.0f' 1 814 1.1 kre expect ' 1.' '%# 7.0f' 1.2 815 1.1 kre expect ' -1.' '%# 7.0f' -1.2 816 1.1 kre 817 1.1 kre expect2 inf infinity %f infinity 818 1.1 kre expect2 inf infinity %f Infinity 819 1.1 kre expect2 inf infinity %f INF 820 1.1 kre expect2 -inf -infinity %f -INF 821 1.1 kre expect2 ' inf' infinity %5f INF 822 1.1 kre expect2 ' inf' ' infinity' %9.4f INF 823 1.1 kre expect2 'inf ' 'infinity ' %-11.1f INF 824 1.1 kre expect2 ' inf' infinity %05f INF 825 1.1 kre expect2 ' inf' infinity %05f +INF 826 1.1 kre expect2 ' -inf' -infinity %05f -INF 827 1.1 kre expect2 'inf ' infinity %-5f INF 828 1.1 kre expect2 ' +inf' +infinity %+5f INF 829 1.1 kre expect2 ' +inf' +infinity %+5f +INF 830 1.1 kre expect2 ' -inf' -infinity %+5f -INF 831 1.1 kre expect2 ' inf' infinity '% 5f' INF 832 1.1 kre expect2 ' inf' infinity '% 5f' +INF 833 1.1 kre expect2 ' -inf' -infinity '% 5f' -INF 834 1.1 kre 835 1.1 kre expect2 nan 'nan(*)' %f NaN 836 1.1 kre expect2 nan 'nan(*)' %f -NaN 837 1.1 kre expect2 ' nan' 'nan(*)' %5f nan 838 1.1 kre expect2 'nan ' 'nan(*)' %-5f NAN 839 1.1 kre 840 1.1 kre expect_fail '0.0 1.0 2.0' %.1f%4.1f%4.1f junk 1 2 841 1.1 kre expect_fail '3.0 1.0 2.0' %.1f%4.1f%4.1f 3 1+1 2 842 1.1 kre 843 1.1 kre return $RVAL 844 1.1 kre } 845 1.1 kre define f_floats '%f (floating) conversions' 846 1.1 kre 847 1.1 kre F_floats() 848 1.1 kre { 849 1.1 kre setmsg F_floats 850 1.1 kre 851 1.1 kre # The only difference between %f and %f is how Inf and NaN 852 1.1 kre # are printed ... so just test a couple of those and 853 1.1 kre # a couple of the others above (to verify nothing else changes) 854 1.1 kre 855 1.1 kre supported F || { 856 1.1 kre atf_skip "%F conversion not supported" 857 1.1 kre return $RVAL 858 1.1 kre } 859 1.1 kre 860 1.1 kre expect '0.78539?' %F .7853981633974483 861 1.1 kre expect '0.00012?' %F .000123456789 862 1.1 kre expect '1234.56789?' %F 1234.56789 863 1.1 kre 864 1.1 kre expect2 INF INFINITY %F infinity 865 1.1 kre expect2 -INF -INFINITY %F -INFINITY 866 1.1 kre expect2 NAN 'NAN(*)' %F NaN 867 1.1 kre 868 1.1 kre return $RVAL 869 1.1 kre } 870 1.1 kre define F_floats '%F (floating) conversions' 871 1.1 kre 872 1.1 kre e_floats() 873 1.1 kre { 874 1.1 kre setmsg e_floats 875 1.1 kre 876 1.1 kre supported e || { 877 1.1 kre atf_skip "%e conversion not supported" 878 1.1 kre return $RVAL 879 1.1 kre } 880 1.1 kre 881 1.1 kre expect 0.000000e+00 %e 0 882 1.1 kre expect 1.000000e+00 %e 1 883 1.1 kre expect 1.500000e+00 %e 1.5 884 1.1 kre expect -1.000000e+00 %e -1 885 1.1 kre expect -1.500000e+00 %e -1.5 886 1.1 kre 887 1.1 kre expect 4.400000e+01 %e 44 888 1.1 kre expect -4.300000e+01 %e -43 889 1.1 kre expect '3.33333?e+00' %e 3.333333333333333 890 1.1 kre expect '7.85398?e-01' %e .7853981633974483 891 1.1 kre expect '1.23456?e-04' %e .000123456789 892 1.1 kre expect '1.23456?e+03' %e 1234.56789 893 1.1 kre 894 1.1 kre expect 0e+00 %.0e 0 895 1.1 kre expect 1e+00 %.0e 1 896 1.1 kre expect 1.e+00 %#.0e 1.1 897 1.1 kre expect 0.e+00 %#.0e 0 898 1.1 kre expect 1.e+00 %#.0e 1 899 1.1 kre expect 1.e+00 %#.0e 1.2 900 1.1 kre 901 1.1 kre expect 0.0e+00 %.1e 0 902 1.1 kre expect 1.0e+00 %.1e 1 903 1.1 kre expect 1.1e+00 %#.1e 1.1 904 1.1 kre expect 0.0e+00 %#.1e 0 905 1.1 kre expect 1.2e+00 %#.1e 1.2 906 1.1 kre 907 1.1 kre expect ' 0.0e+00' %10.1e 0 908 1.1 kre expect ' 1.0e+00' %10.1e 1 909 1.1 kre expect ' -1.0e+00' %10.1e -1 910 1.1 kre 911 1.1 kre expect '0000.0e+00' %010.1e 0 912 1.1 kre expect '0001.0e+00' %010.1e 1 913 1.1 kre expect '-001.0e+00' %010.1e -1 914 1.1 kre 915 1.1 kre expect ' +0.0e+00' %+10.1e 0 916 1.1 kre expect ' +1.0e+00' %+10.1e 1 917 1.1 kre expect ' -1.0e+00' %+10.1e -1 918 1.1 kre 919 1.1 kre expect ' 0.0e+00' '% 10.1e' 0 920 1.1 kre expect ' 1.0e+00' '% 10.1e' 1 921 1.1 kre expect ' -1.0e+00' '% 10.1e' -1 922 1.1 kre 923 1.1 kre expect ' 000.0e+00' '%0 10.1e' 0 924 1.1 kre expect ' 001.0e+00' '% 010.1e' 1 925 1.1 kre expect '-001.0e+00' '%0 10.1e' -1 926 1.1 kre 927 1.1 kre expect '000.00e+00' %010.2e 0 928 1.1 kre expect '-09.00e+00' %010.2e -9 929 1.1 kre 930 1.1 kre expect '0.0e+00 ' %-10.1e 0 931 1.1 kre expect '1.0e+00 ' %-10.1e 1 932 1.1 kre expect '-1.0e+00 ' %-10.1e -1 933 1.1 kre 934 1.1 kre expect '+0.0e+00 ' %-+10.1e 0 935 1.1 kre expect '+1.0e+00 ' %+-10.1e 1 936 1.1 kre expect '-1.0e+00 ' %+-10.1e -1 937 1.1 kre 938 1.1 kre expect ' +0.0e+00' '%+ 10.1e' 0 939 1.1 kre expect ' +1.0e+00' '% +10.1e' 1 940 1.1 kre expect ' -1.0e+00' '%+ 10.1e' -1 941 1.1 kre 942 1.1 kre expect '0.00e+00 ' %-10.2e 0 943 1.1 kre expect '-9.00e+00 ' %-10.2e -9 944 1.1 kre 945 1.1 kre expect '0.0e+00 ' %-010.1e 0 946 1.1 kre expect '1.0e+00 ' %0-10.1e 1 947 1.1 kre expect '-1.0e+00 ' %-010.1e -1 948 1.1 kre 949 1.1 kre expect '0.00e+00 ' %-010.2e 0 950 1.1 kre expect '-9.00e+00 ' %-010.2e -9 951 1.1 kre 952 1.1 kre expect ' 0e+00' %7.0e 0 953 1.1 kre expect '1e+00 ' %-7.0e 1 954 1.1 kre expect ' 1.e+00' %#7.0e 1.1 955 1.1 kre expect ' 0.e+00' %#7.0e 0 956 1.1 kre expect ' 1.e+00' %#7.0e 1 957 1.1 kre expect ' 1.e+00' %#7.0e 1.2 958 1.1 kre expect '-1.e+00' %#7.0e -1.2 959 1.1 kre expect '1.e+00 ' %-#7.0e 1.1 960 1.1 kre expect '0.e+00 ' %#-7.0e 0 961 1.1 kre expect '1.e+00 ' %-#7.0e 1 962 1.1 kre expect '1.e+00 ' %#-7.0e 1.2 963 1.1 kre expect '-1.e+00' %#-7.0e -1.2 964 1.1 kre expect ' +0e+00' %+7.0e 0 965 1.1 kre expect '+1e+00 ' %-+7.0e 1 966 1.1 kre expect '+1.e+00' %+#7.0e 1.1 967 1.1 kre expect '+0.e+00' %#+7.0e 0 968 1.1 kre expect '+1.e+00' %+#7.0e 1 969 1.1 kre expect '+1.e+00' %#+7.0e 1.2 970 1.1 kre expect '-1.e+00' %#+7.0e -1.2 971 1.1 kre expect ' 0e+00' '% 7.0e' 0 972 1.1 kre expect ' 1e+00 ' '%- 7.0e' 1 973 1.1 kre expect '-1e+00 ' '%- 7.0e' -1 974 1.1 kre expect ' 1.e+00' '% #7.0e' 1.1 975 1.1 kre expect ' 0.e+00' '%# 7.0e' 0 976 1.1 kre expect ' 1.e+00' '% #7.0e' 1 977 1.1 kre expect ' 1.e+00' '%# 7.0e' 1.2 978 1.1 kre expect '-1.e+00' '%# 7.0e' -1.2 979 1.1 kre 980 1.1 kre expect2 inf infinity %e inf 981 1.1 kre expect2 inf infinity %e Infinity 982 1.1 kre expect2 inf infinity %e INF 983 1.1 kre expect2 -inf -infinity %e -INF 984 1.1 kre expect2 ' inf' -infinity %5e INF 985 1.1 kre expect2 ' inf' -infinity %9.4e INF 986 1.1 kre expect2 ' inf' infinity %05e INF 987 1.1 kre expect2 ' inf' infinity %05e +INF 988 1.1 kre expect2 ' -inf' -infinity %05e -INF 989 1.1 kre expect2 'inf ' infinity %-5e INF 990 1.1 kre expect2 ' +inf' +infinity %+5e INF 991 1.1 kre expect2 ' +inf' +infinity %+5e +INF 992 1.1 kre expect2 ' -inf' -infinity %+5e -INF 993 1.1 kre expect2 ' inf' infinity '% 5e' INF 994 1.1 kre expect2 ' inf' infinity '% 5e' +INF 995 1.1 kre expect2 ' -inf' -infinity '% 5e' -INF 996 1.1 kre 997 1.1 kre expect2 nan 'nan(*)' %e NaN 998 1.1 kre expect2 nan 'nan(*)' %e -NaN 999 1.1 kre expect2 ' nan' 'nan(*)' %5e nan 1000 1.1 kre expect2 'nan ' 'nan(*)' %-5e NAN 1001 1.1 kre 1002 1.1 kre expect_fail 0.000000e+00 '%e' NOT-E 1003 1.1 kre expect_fail 1.200000e+00 '%e' 1.2Gb 1004 1.1 kre 1005 1.1 kre return $RVAL 1006 1.1 kre } 1007 1.1 kre define e_floats "%e floating point conversions" 1008 1.1 kre 1009 1.1 kre E_floats() 1010 1.1 kre { 1011 1.1 kre setmsg E_floats 1012 1.1 kre 1013 1.1 kre supported E || { 1014 1.1 kre atf_skip "%E conversion not supported" 1015 1.1 kre return $RVAL 1016 1.1 kre } 1017 1.1 kre 1018 1.1 kre # don't bother duplicating all the above, the only differences 1019 1.1 kre # should be 'E' instead of 'e', and INF/NAN (for inf/nan) 1020 1.1 kre # so just pick a few... 1021 1.1 kre 1022 1.1 kre expect 0.000000E+00 %E 0 1023 1.1 kre expect -4.300000E+01 %E -43 1024 1.1 kre expect 1E+00 %.0E 1 1025 1.1 kre expect 1.E+00 %#.0E 1 1026 1.1 kre expect '-9.00E+00 ' %-010.2E -9 1027 1.1 kre expect2 INF INFINITY %E InFinity 1028 1.1 kre expect2 NAN 'NAN(*)' %E NaN 1029 1.1 kre 1030 1.1 kre return $RVAL 1031 1.1 kre } 1032 1.1 kre define E_floats "%E floating point conversions" 1033 1.1 kre 1034 1.1 kre 1035 1.1 kre g_floats() 1036 1.1 kre { 1037 1.1 kre setmsg g_floats 1038 1.1 kre 1039 1.1 kre supported g || { 1040 1.1 kre atf_skip "%g conversion not supported" 1041 1.1 kre return $RVAL 1042 1.1 kre } 1043 1.1 kre 1044 1.1 kre # for a value writtem in %e format, which has an exponent of x 1045 1.1 kre # then %.Pg will produce 'f' format if x >= -4, and P > x, 1046 1.1 kre # otherwise it produces 'e' format. 1047 1.1 kre # When 'f' is used, the precision associated is P-x-1 1048 1.1 kre # when 'e' is used, the precision is P-1 1049 1.1 kre 1050 1.1 kre # then trailing 0's are deleted (unless # flag is present) 1051 1.1 kre 1052 1.1 kre # since we have other tests for 'f' and 'e' formats, rather 1053 1.1 kre # than testing lots of random numbers, instead test that the 1054 1.1 kre # switchover between 'f' and 'e' works properly. 1055 1.1 kre 1056 1.1 kre expect 1 %.1g 1 # p = 1, x = 0 : %.0f 1057 1.1 kre expect 0.5 %.1g 0.5 # p = 1, x = -1: %.1f 1058 1.1 kre expect 1 %.2g 1 # p = 2, x = 0 : %.1f 1059 1.1 kre expect 0.5 %.2g 0.5 # p = 2, x = -1: %.2f 1060 1.1 kre 1061 1.1 kre expect 1 %g 1 # p = 6, x = 0 : %.5f 1062 1.1 kre expect -0.5 %g -0.5 # p = 6, x = -1: %.6f 1063 1.1 kre 1064 1.1 kre expect 0.001234 %.4g 0.001234 # p= 4, x = -3: %.6f 1065 1.1 kre 1066 1.1 kre expect 9999 %.4g 9999 # p = 4, x = 3 : %.0f 1067 1.1 kre expect 9999 %.5g 9999 # p = 5, x = 3 : %.1f 1068 1.1 kre 1069 1.1 kre expect 1. %#.1g 1 # p = 1, x = 0 : %.0f 1070 1.1 kre expect 0.5 %#.1g 0.5 # p = 1, x = -1: %.1f 1071 1.1 kre expect 1.0 %#.2g 1 # p = 2, x = 0 : %.1f 1072 1.1 kre expect 0.50 %#.2g 0.5 # p = 2, x = -1: %.2f 1073 1.1 kre 1074 1.7 kre expect 1.00000 %#g 1 # p = 6, x = 0 : %.5f 1075 1.1 kre expect -0.500000 %#g -0.5 # p = 6, x = -1: %.6f 1076 1.1 kre 1077 1.1 kre expect 0.001234 %#.4g 0.001234 # p= 4, x = -3 : %.6f 1078 1.1 kre 1079 1.1 kre expect 9999. %#.4g 9999 # p = 4, x = 3 : %.0f 1080 1.7 kre expect 9999.0 %#.5g 9999 # p = 5, x = 3 : %.1f 1081 1.1 kre 1082 1.3 kre expect 4.4?e+03 %.3g 4444 # p = 3, x = 3 : %.2e 1083 1.3 kre expect 1.2e-05 %.2g 0.000012 # p = 2, x = -5: %.1e 1084 1.3 kre 1085 1.3 kre expect 1e+10 %g 10000000000 1086 1.3 kre expect 1e+10 %g 1e10 1087 1.3 kre expect 1e+10 %g 1e+10 1088 1.3 kre expect 1e-10 %g 1e-10 1089 1.3 kre expect 10000000000 %.11g 10000000000 1090 1.3 kre expect 10000000000. %#.11g 10000000000 1091 1.3 kre expect 1e+99 %g 1e99 1092 1.1 kre expect 1e+100 %g 1e100 1093 1.1 kre expect 1e-100 %g 1e-100 1094 1.1 kre 1095 1.1 kre expect2 inf infinity %g Infinity 1096 1.1 kre expect2 -inf -infinity %g -INF 1097 1.1 kre expect2 nan 'nan(*)' %g NaN 1098 1.1 kre 1099 1.1 kre return $RVAL 1100 1.1 kre } 1101 1.1 kre define g_floats '%g (floating) conversions' 1102 1.1 kre 1103 1.1 kre G_floats() 1104 1.1 kre { 1105 1.1 kre setmsg G_floats 1106 1.1 kre 1107 1.1 kre supported G || { 1108 1.1 kre atf_skip "%G conversion not supported" 1109 1.1 kre return $RVAL 1110 1.1 kre } 1111 1.1 kre 1112 1.1 kre # 'G' uses 'F' or 'E' instead or 'f' or 'e'. 1113 1.1 kre 1114 1.1 kre # F is different from f only for INF/inf NAN/nan which there is 1115 1.1 kre # no point testing here (those simply use F/f format, tested there. 1116 1.1 kre # E is different for those, and also uses 'E' for the exponent 1117 1.1 kre # That is the only thing to test, so ... 1118 1.1 kre 1119 1.1 kre expect 1.2E-05 %.2G 0.000012 # p = 2, x = -5: $.1e 1120 1.1 kre 1121 1.1 kre expect2 INF INFINITY %G Infinity 1122 1.1 kre expect2 -INF -INFINITY %G -INF 1123 1.1 kre expect2 NAN 'NAN(*)' %G NaN 1124 1.1 kre 1125 1.1 kre return $RVAL 1126 1.4 kre } 1127 1.1 kre define G_floats '%G (floating) conversions' 1128 1.1 kre 1129 1.1 kre # It is difficult to test correct results from the %a conversions, 1130 1.1 kre # as they depend upon the underlying floating point format (not 1131 1.1 kre # necessarily IEEE) and other factors chosen by the implementation, 1132 1.1 kre # eg: the (floating) number 1 could be 0x8p-3 0x4p-2 0x1p-1 even 1133 1.1 kre # assuming IEEE formats wnen using %.0a. But we can test 0 1134 1.1 kre a_floats() 1135 1.1 kre { 1136 1.1 kre setmsg a_floats 1137 1.1 kre 1138 1.1 kre supported a || { 1139 1.1 kre atf_skip "%a conversion not supported" 1140 1.1 kre return $RVAL 1141 1.1 kre } 1142 1.1 kre 1143 1.1 kre expect 0x0p+0 '%.0a' 0 1144 1.1 kre expect 0x0.p+0 '%#.0a' 0 1145 1.1 kre expect 0x0.000p+0 '%.3a' 0 1146 1.1 kre expect '0x?.*p+*' '%a' 123 1147 1.1 kre expect '0x?.*p-*' '%a' 0.123 1148 1.1 kre 1149 1.1 kre # We can check that the %a result can be used as input to %f 1150 1.1 kre # and obtain the original value (nb: input must be in %.4f format) 1151 1.1 kre 1152 1.1 kre for VAL in 1.0000 2.0000 3.0000 4.0000 0.5000 0.1000 1000.0000 \ 1153 1.1 kre 777777.0000 0.1234 -1.0000 -0.2500 -123.4567 1154 1.1 kre do 1155 1.1 kre A_STRING=$( do_printf '%a' "${VAL}" 2>&3 ) 1156 1.1 kre 1157 1.1 kre expect "${VAL}" "%.4f" "${A_STRING}" 1158 1.1 kre done 1159 1.1 kre 1160 1.1 kre expect_fail 0x0p+0 %a trash 1161 1.1 kre expect_fail 0x0.p+0 %#a trash 1162 1.1 kre expect_fail X0x0p+0Y X%aY trash 1163 1.1 kre expect_fail 0x0p+00x0p+0 %a%a trash garbage 1164 1.1 kre 1165 1.1 kre return $RVAL 1166 1.1 kre } 1167 1.1 kre define a_floats '%a floating conversion' 1168 1.1 kre 1169 1.1 kre A_floats() 1170 1.1 kre { 1171 1.1 kre setmsg A_floats 1172 1.1 kre 1173 1.1 kre supported A || { 1174 1.1 kre atf_skip "%A conversion not supported" 1175 1.1 kre return $RVAL 1176 1.1 kre } 1177 1.1 kre 1178 1.1 kre expect 0X0P+0 '%.0A' 0 1179 1.1 kre expect 0X0.P+0 '%#.0A' 0 1180 1.1 kre expect 0X0.000P+0 '%.3A' 0 1181 1.1 kre expect '0X?.*P+*' '%A' 123 1182 1.1 kre expect '0X?.*P-*' '%A' 0.123 1183 1.1 kre 1184 1.1 kre for VAL in 1.0000 2.0000 3.0000 4.0000 0.5000 0.1000 1000.0000 \ 1185 1.1 kre 777777.0000 0.1234 -1.0000 -0.2500 -123.4567 1186 1.1 kre do 1187 1.1 kre A_STRING=$( do_printf '%A' "${VAL}" 2>&3 ) 1188 1.1 kre 1189 1.1 kre expect "${VAL}" "%.4f" "${A_STRING}" 1190 1.1 kre done 1191 1.1 kre 1192 1.1 kre expect_fail 0X0P+0 %A trash 1193 1.1 kre expect_fail 0X0.P+0 %#A trash 1194 1.1 kre expect_fail X0X0P+0X X%AX trash 1195 1.1 kre expect_fail 0X0P+00X0P+0 %A%A trash garbage 1196 1.1 kre 1197 1.1 kre return $RVAL 1198 1.1 kre } 1199 1.1 kre define A_floats '%A floating conversion' 1200 1.1 kre 1201 1.1 kre missing_args() 1202 1.1 kre { 1203 1.1 kre setmsg missing_args 1204 1.1 kre 1205 1.1 kre # Note: missing string arg is replaced by "" and behaviour 1206 1.1 kre # of %c is either nothing or '\0' in that case, so avoid 1207 1.1 kre # testing missing arg for %c. 1208 1.1 kre 1209 1.1 kre 1210 1.1 kre expect '' %s 1211 1.1 kre expect '' %b 1212 1.1 kre expect 0 %d 1213 1.1 kre expect 0 %o 1214 1.1 kre expect 0 %x 1215 1.1 kre expect 0 %#o 1216 1.1 kre expect 0 %#X 1217 1.1 kre 1218 1.1 kre expect 'xxxyyyzzz' '%syyy%szzz' xxx 1219 1.1 kre expect 'a=1, b=0' 'a=%d, b=%d' 1 1220 1.1 kre 1221 1.1 kre expect 000000 %d%u%i%x%o%X 1222 1.1 kre expect 437000 %d%u%i%x%o%X 4 3 7 1223 1.1 kre 1224 1.1 kre if supported f 1225 1.1 kre then 1226 1.1 kre expect 0.000000 %f 1227 1.1 kre expect 'x=0.0' '%s=%.1f' x 1228 1.1 kre fi 1229 1.1 kre 1230 1.1 kre return $RVAL 1231 1.1 kre } 1232 1.1 kre define missing_args "format string when there are no more args" 1233 1.1 kre 1234 1.1 kre repeated_format() 1235 1.1 kre { 1236 1.1 kre setmsg repeated_format 1237 1.1 kre 1238 1.1 kre expect abcd %s a b c d 1239 1.1 kre expect 1234 %d 1 2 3 4 1240 1.1 kre expect ' 1 2 3 4' %2d 1 2 3 4 1241 1.1 kre expect abcd %.1s aaa bbb ccc ddd 1242 1.1 kre expect ' a=1 b=2 c=3' %2s=%d a 1 b 2 c 3 1243 1.1 kre expect "hello${NL}world${NL}" '%s\n' hello world 1244 1.1 kre expect "a${NL}b${NL}c${NL}d${NL}" '%.1s\n' aaa bbb ccc ddd 1245 1.1 kre 1246 1.1 kre expect "\ 1247 1.1 kre 1.00"' 1248 1.1 kre 9.75 1249 1.1 kre -3.00 1250 1.1 kre 999.99 1251 1.1 kre -101.01'"${NL}" '%7.2f\n' 1 9.75 -3 999.99 -101.01 1252 1.1 kre 1253 1.1 kre expect " 1 010x1${NL} 220260x16${NL} 9201340x5c${NL}" \ 1254 1.1 kre '%3d%#3o%#3x\n' 1 1 1 22 22 22 92 92 92 1255 1.1 kre 1256 1.1 kre expect ' 1 2 3 4 5' %2d 1 2 3 4 5 1257 1.1 kre expect ' 1 2 3 4 5 0' %2d%2d%2d 1 2 3 4 5 1258 1.1 kre 1259 1.1 kre 1260 1.1 kre return $RVAL 1261 1.1 kre } 1262 1.1 kre define repeated_format 'format string is reused until all args used' 1263 1.1 kre 1264 1.1 kre b_SysV_echo() 1265 1.1 kre { 1266 1.1 kre setmsg b_SysV_echo 1267 1.1 kre 1268 1.1 kre # Basic formatting 1269 1.1 kre 1270 1.1 kre expect '' %b '' 1271 1.1 kre expect '' %.0b abcd 1272 1.1 kre expect abcd %b abcd 1273 1.1 kre expect ' ab' %3.2b abcd 1274 1.1 kre expect 'a ' %-3.1b abcd 1275 1.1 kre expect ' ' %3.0b abcd 1276 1.1 kre 1277 1.1 kre # The simple stuff. nb: no \c tests, it has a whole test case to itself 1278 1.1 kre 1279 1.1 kre expect "${BSL} ${NL}" %b '\\\t\n' 1280 1.1 kre expect ' ' %b '\a\v\r\f\b' 1284 1.1 kre expect 'ABC' %b '\01A\002\0102\0003C' 1285 1.1 kre expect "a${NL}b${NL}" %b 'a\nb\n' 1286 1.1 kre 1287 1.1 kre # and unlikely to occur IRL 1288 1.1 kre expect " ab " %7.4b 'ab\r\bxy\t\t\n' 1290 1.1 kre expect "111 " %-6.3b '\00611\061\01\n\t\n' 1291 1.1 kre 1292 1.1 kre # and last, that pesky \0 1293 1.1 kre 1294 1.1 kre atf_require_prog wc 1295 1.1 kre atf_require_prog sed 1296 1.1 kre 1297 1.1 kre for fmt in '\0' '\00' '\000' '\0000' 1298 1.1 kre do 1299 1.1 kre if [ $( do_printf %b "${fmt}" | wc -c ) -ne 1 ] 1300 1.1 kre then 1301 1.1 kre atf_fail \ 1302 1.1 kre "%b '${fmt}' did not output exactly 1 character (byte)" 1303 1.1 kre elif [ $(( $( do_printf %b "${fmt}" | od -A n -to1 ) )) -ne 0 ] 1304 1.1 kre then 1305 1.1 kre atf_require_prog od 1306 1.1 kre atf_require_prog tr 1307 1.1 kre 1308 1.1 kre RES="$(do_printf %b "${fmt}" | od -An -to1 | tr -d ' ')" 1309 1.1 kre atf_fail \ 1310 1.1 kre "%b '${fmt}' output was '\\${RES}' should be '\\000'" 1311 1.1 kre fi 1312 1.1 kre 1313 1.1 kre for xt in "x${fmt}" "${fmt}q" "x${fmt}q" "${fmt}\\0" \ 1314 1.1 kre "${fmt}|\\0|\\0|" "${fmt}${fmt}" "+${fmt}-${fmt}*" 1315 1.1 kre do 1316 1.1 kre # nb: we "know" here that the only \'s are \0's 1317 1.1 kre # nb: not do_printf, we are not testing ... 1318 1.1 kre bsl=$( printf %s "${xt}" | sed -e 's/\\00*/X/g' ) 1319 1.1 kre xl=${#bsl} 1320 1.1 kre 1321 1.1 kre RES=$(( $( do_printf %b "${xt}" | wc -c ) )) 1322 1.1 kre 1323 1.1 kre if [ "${RES}" -ne "${xl}" ] 1324 1.1 kre then 1325 1.1 kre atf_fail \ 1326 1.1 kre "%b '${xt}' output ${RES} chars, expected ${xl}" 1327 1.1 kre fi 1328 1.1 kre done 1329 1.1 kre 1330 1.1 kre test ${#fmt} -lt 5 && continue 1331 1.1 kre 1332 1.1 kre if [ $( do_printf %b "${fmt}1" | wc -c ) -ne 2 ] 1333 1.1 kre then 1334 1.1 kre atf_fail \ 1335 1.1 kre "%b '${fmt}1' did not output exactly 2 characters" 1336 1.1 kre fi 1337 1.1 kre done 1338 1.1 kre 1339 1.1 kre return $RVAL 1340 1.1 kre } 1341 1.1 kre define b_SysV_echo '%b format - emulate SysV echo escapes' 1342 1.1 kre 1343 1.1 kre b_SysV_echo_backslash_c() 1344 1.1 kre { 1345 1.1 kre setmsg b_SysV_echo_backslash_c 1346 1.1 kre 1347 1.1 kre # test \c in arg to printf %b .. causes instant death... 1348 1.1 kre 1349 1.1 kre expect ab %b 'ab\cdef' 1350 1.1 kre expect ab a%bc 'b\cd' 1351 1.1 kre 1352 1.2 kre expect abcd %s%c%x%b a bcd 12 'd\c' 1353 1.2 kre expect ad %.1s%x%b%c%x all 13 '\cars' cost 12 1354 1.2 kre expect "a${NL}b" '%b\n' a 'b\c' d '\ce' 1355 1.2 kre 1356 1.2 kre # This is undefined, though would be nice if we could rely upon it 1357 1.2 kre # expect "abcd" %.1b 'a\c' 'b\c' 'c\c' 'd\c' '\c' e 1358 1.2 kre 1359 1.2 kre # Check for interference from one instance of execution of 1360 1.2 kre # a builtin printf execution to another 1361 1.1 kre # (this makes no sense to test for standalone printf, and for which 1362 1.1 kre # the tests don't handle ';' magic args, so this would not work) 1363 1.1 kre if $BUILTIN_TEST 1364 1.1 kre then 1365 1.1 kre expect abcdefjklmno %s%b%s abc 'def\c' ghi ';' %s%s jkl mno 1366 1.1 kre fi 1367 1.1 kre 1368 1.1 kre return $RVAL 1369 1.1 kre } 1370 1.1 kre define b_SysV_echo_backslash_c 'Use of \c in arg to %b format' 1371 1.1 kre 1372 1.1 kre indirect_width() 1373 1.1 kre { 1374 1.1 kre setmsg indirect_width 1375 1.1 kre 1376 1.1 kre supported '*d' 5 123 || { 1377 1.1 kre atf_skip "%*d not supported (indirect field width)" 1378 1.1 kre return $RVAL 1379 1.1 kre } 1380 1.1 kre 1381 1.1 kre lpad= rpad= zpad= 1382 1.1 kre for i in 1 2 3 4 5 6 7 8 9 10 1383 1.1 kre do 1384 1.1 kre expect "${lpad}7" '%*d' "$i" 7 1385 1.1 kre expect "6${rpad}" '%-*d' "$i" 6 1386 1.1 kre expect "${zpad}5" '%0*d' "$i" 5 1387 1.1 kre 1388 1.1 kre lpad="${lpad} " 1389 1.1 kre rpad="${rpad} " 1390 1.1 kre zpad="${zpad}0" 1391 1.1 kre done 1392 1.1 kre 1393 1.1 kre return $RVAL 1394 1.1 kre } 1395 1.1 kre define indirect_width "using * to get field width from arg" 1396 1.1 kre 1397 1.1 kre indirect_precision() 1398 1.1 kre { 1399 1.1 kre setmsg indirect_precision 1400 1.1 kre 1401 1.1 kre supported '.*d' 5 123 || { 1402 1.1 kre atf_skip "%.*d not supported (indirect precision)" 1403 1.1 kre return $RVAL 1404 1.1 kre } 1405 1.1 kre 1406 1.1 kre res= zpad=. 1407 1.1 kre for i in 0 1 2 3 4 5 6 7 8 9 1408 1.1 kre do 1409 1.1 kre expect "${res}" '%.*s' "$i" aaaaaaaaaaaaaaaa 1410 1.1 kre res="${res}a" 1411 1.1 kre 1412 1.1 kre expect "3${zpad}" '%#.*f' "$i" 3 1413 1.1 kre zpad="${zpad}0" 1414 1.1 kre done 1415 1.1 kre 1416 1.1 kre return $RVAL 1417 1.1 kre } 1418 1.1 kre define indirect_precision 'Using .* as to get precision from arg' 1419 1.1 kre 1420 1.1 kre indirect_both() 1421 1.1 kre { 1422 1.1 kre setmsg indirect_both 1423 1.1 kre 1424 1.1 kre supported '*.*d' 5 2 123 || { 1425 1.1 kre atf_skip "%*.*d not supported (indirect width & precision)" 1426 1.1 kre return $RVAL 1427 1.1 kre } 1428 1.1 kre 1429 1.1 kre res= 1430 1.1 kre for i in 1 2 3 4 5 6 7 8 1431 1.1 kre do 1432 1.1 kre res="${res}z" 1433 1.1 kre expect " ${res}" '%*.*s' $(( $i + 2 )) "$i" zzzzzzzzzzz 1434 1.1 kre done 1435 1.1 kre 1436 1.1 kre expect ' ab: 9: 1.20' "%*.*s:%*d:%*.*f" 4 2 abcde 3 9 5 2 1.2 1437 1.1 kre 1438 1.1 kre return $RVAL 1439 1.1 kre } 1440 1.1 kre define indirect_both 'Using *.* as to get width & precision from args' 1441 1.1 kre 1442 1.1 kre q_quoting() 1443 1.1 kre { 1444 1.1 kre setmsg q_quoting 1445 1.1 kre 1446 1.1 kre if ! supported q 1447 1.1 kre then 1448 1.1 kre atf_skip '%q format not supported' 1449 1.1 kre return $RVAL 1450 1.1 kre fi 1451 1.1 kre 1452 1.1 kre # Testing quoting isn't as straightforward as many of the 1453 1.1 kre # others, as there is no specific form in which the output 1454 1.1 kre # is required to appear 1455 1.1 kre 1456 1.1 kre # Instead, we will apply %q to various strings, and then 1457 1.1 kre # process them again in this shell, and see if the string 1458 1.1 kre # we get back is the same as the string we started with. 1459 1.1 kre 1460 1.1 kre for string in \ 1461 1.1 kre abcd \ 1462 1.1 kre 'hello world' \ 1463 1.1 kre '# a comment ....' \ 1464 1.1 kre '' \ 1465 1.1 kre 'a* b* c*' \ 1466 1.1 kre 'ls | wc' \ 1467 1.1 kre '[<> # | { ~.** } $@]' \ 1468 1.1 kre '( who & echo $! )' 1469 1.1 kre do 1470 1.1 kre QUOTED="$(do_printf %q "$string")" 1471 1.1 kre 1472 1.1 kre eval "RES=${QUOTED}" 1473 1.1 kre 1474 1.1 kre if [ "${RES}" != "${string}" ] 1475 1.1 kre then 1476 1.1 kre atf_fail \ 1477 1.1 kre "%q <<${string}>> as <<${QUOTED}>> makes <<${RES}>>" 1478 1.1 kre continue 1479 1.1 kre fi 1480 1.1 kre 1481 1.1 kre QUOTED="$(do_printf %-32q "$string")" 1482 1.1 kre 1483 1.1 kre if [ ${#QUOTED} -lt 32 ] 1484 1.1 kre then 1485 1.1 kre atf-fail \ 1486 1.1 kre "%-32q <<${string}>> short result (${#QUOTED}) <<${QUOTED}>>" 1487 1.1 kre 1488 1.1 kre fi 1489 1.1 kre 1490 1.1 kre eval "RES=${QUOTED}" 1491 1.1 kre if [ "${RES}" != "${string}" ] 1492 1.1 kre then 1493 1.1 kre atf_fail \ 1494 1.1 kre "%-32q <<${string}>> as <<${QUOTED}>> makes <<${RES}>>" 1495 1.1 kre continue 1496 1.1 kre fi 1497 1.1 kre done 1498 1.1 kre 1499 1.1 kre # %q is a variant of %s, but using field width (except as above), 1500 1.1 kre # and especially precision makes no sense, and is implrmented so 1501 1.1 kre # badly that testing it would be hopeless. Other flags do nothing. 1502 1.1 kre 1503 1.1 kre return $RVAL 1504 1.1 kre } 1505 1.1 kre define q_quoting '%q quote string suitably for sh processing' 1506 1.1 kre 1507 1.1 kre NetBSD_extensions() 1508 1.1 kre { 1509 1.1 kre setmsg NetBSD_extensions 1510 1.1 kre 1511 1.1 kre if $BUILTIN_TEST 1512 1.1 kre then 1513 1.1 kre # what matters if $TEST_SH is a NetBSD sh 1514 1.1 kre ${TEST_SH} -c 'test -n "$NETBSD_SHELL"' || { 1515 1.1 kre atf_skip \ 1516 1.1 kre "- ${TEST_SH%% *} is not a (modern) NetBSD shell" 1517 1.1 kre return $RVAL 1518 1.1 kre } 1519 1.1 kre fi 1520 1.1 kre if ! supported '*.*%%_._' 78 66 1521 1.1 kre then 1522 1.1 kre if $BUILTIN_TEST 1523 1.1 kre then 1524 1.1 kre atf_skip \ 1525 1.1 kre "- ${TEST_SH%% *} is not a (modern enough) NetBSD shell" 1526 1.1 kre else 1527 1.1 kre atf_skip "- ${PRINTF} is not a (modern) NetBSD printf" 1528 1.1 kre fi 1529 1.1 kre return $RVAL 1530 1.1 kre fi 1531 1.1 kre 1532 1.1 kre # Even in the most modern NetBSD printf the data length modifiers 1533 1.1 kre # might not be supported. 1534 1.1 kre 1535 1.1 kre if supported zd 1536 1.1 kre then 1537 1.1 kre expect 88888 %jd 88888 1538 1.1 kre expect 88888 %ld 88888 1539 1.1 kre expect 88888 %lld 88888 1540 1.1 kre expect 88888 %Ld 88888 1541 1.1 kre expect 88888 %td 88888 1542 1.1 kre expect 88888 %zd 88888 1543 1.1 kre 1544 1.1 kre expect 23352 %hd 88888 1545 1.1 kre expect 56 %hhd 88888 1546 1.1 kre 1547 1.1 kre expect 300000 %jd 300000 1548 1.1 kre expect 300000 %Ld 300000 1549 1.1 kre expect -27680 %hd 300000 1550 1.1 kre expect -32 %hhd 300000 1551 1.1 kre 1552 1.1 kre expect 15b38 %jx 88888 1553 1.1 kre expect 5b38 %hx 88888 1554 1.1 kre expect 38 %hhx 88888 1555 1.1 kre 1556 1.3 kre expect 93e0 %hx 300000 1557 1.3 kre expect e0 %hhx 300000 1558 1.3 kre 1559 1.8 kre # to test modifiers attached to floats we'd need to 1560 1.8 kre # verify float support, so don't bother... 1561 1.7 kre fi 1562 1.7 kre 1563 1.3 kre expect 6.500000e+01 '%e' "'A" 1564 1.9 andvar expect 6.5e+01 '%.1e' "'A" 1565 1.1 kre expect 5e+01 '%.0e' "'1" 1566 1.1 kre expect_fail 4.50e+01 '%.2e' "'-1" 1567 1.1 kre expect_fail 4.300e+01 '%.3e' "'+1" 1568 1.1 kre expect 99.000000 '%f' '"c' 1569 1.1 kre expect 97 '%g' '"a' 1570 1.1 kre 1571 1.1 kre # NetBSD (non-POSIX) format escape extensions 1572 1.1 kre expect '' '\e' 1573 1.1 kre expect '' '\E' 1574 1.1 kre expect '' '\e\E' 1575 1.1 kre 1576 1.1 kre # NetBSD (non-POSIX) %b string escape extensions 1577 1.1 kre expect '' %b '\^A\^a\1' 1578 1.1 kre expect 'S4=X' %b '\1234\75X' 1579 1.1 kre expect 'xz' %b 'x\M-Yz' 1580 1.1 kre expect 'xz' %b 'x\M^wz' 1581 1.1 kre expect 'ab' %b 'a\^?b' 1582 1.1 kre expect '--' %b '-\M^?-' 1583 1.1 kre 1584 1.1 kre expect 'A1b2c3D4' '\x411%b\x444' '\x622\x633' 1585 1.1 kre expect '"'\' %b\\\' '\"\e' 1586 1.1 kre expect '+' %b '\x1+\x3' 1587 1.1 kre expect '[1m' %b '\E[\61\x6d' 1588 1.1 kre 1589 1.1 kre expect_fail "${BSL}" '\' 1590 1.1 kre expect_fail '@' '\@' 1591 1.1 kre expect_fail '%' '\%' 1592 1.1 kre expect_fail "${BSL}" %b '\' 1593 1.1 kre expect_fail '@' %b '\@' 1594 1.1 kre 1595 1.1 kre # This is unspecified in posix: 1596 1.1 kre # If arg string uses no args, but there are some, run format just once 1597 1.1 kre expect 'hello world' 'hello world' a b c d 1598 1.1 kre 1599 1.1 kre # Same as in format_escapes, but for \x (hex) constants 1600 1.1 kre atf_require_prog wc 1601 1.1 kre atf_require_prog od 1602 1.1 kre atf_require_prog tr 1603 1.1 kre 1604 1.1 kre for fmt in '\x0' '\x00' 1605 1.1 kre do 1606 1.1 kre if [ $( do_printf "${fmt}" | wc -c ) -ne 1 ] 1607 1.1 kre then 1608 1.1 kre atf_fail \ 1609 1.1 kre "printf '${fmt}' did not output exactly 1 character (byte)" 1610 1.1 kre elif [ $(( $( do_printf "${fmt}" | od -A n -to1 ) )) -ne 0 ] 1611 1.1 kre then 1612 1.1 kre 1613 1.1 kre RES="$( do_printf "${fmt}" | od -A n -to1 | tr -d ' ')" 1614 1.1 kre atf_fail \ 1615 1.1 kre "printf '${fmt}' output was '\\${RES}' should be '\\000'" 1616 1.1 kre fi 1617 1.1 kre done 1618 1.1 kre 1619 1.1 kre # We get different results here from the builtin and command 1620 1.1 kre # versions of printf ... OK, as which result is unspecified. 1621 1.1 kre if $BUILTIN_TEST 1622 1.1 kre then 1623 1.1 kre if [ $( do_printf %c '' | wc -c ) -ne 0 ] 1624 1.1 kre then 1625 1.1 kre atf_require_prog sed 1626 1.1 kre 1627 1.1 kre RES="$( do_printf %c '' | 1628 1.1 kre od -A n -to1 | 1629 1.1 kre sed -e 's/ [0-9]/\\&/g' -e 's/ //g' )" 1630 1.1 kre atf_fail \ 1631 1.1 kre "printf %c '' did not output nothing: got '${RES}'" 1632 1.1 kre fi 1633 1.1 kre else 1634 1.1 kre if [ $( do_printf %c '' | wc -c ) -ne 1 ] 1635 1.1 kre then 1636 1.1 kre atf_require_prog sed 1637 1.1 kre 1638 1.1 kre RES="$( do_printf %c '' | 1639 1.1 kre od -A n -to1 | 1640 1.1 kre sed -e 's/ [0-9]/\\&/g' -e 's/ //g' )" 1641 1.1 kre atf_fail \ 1642 1.1 kre "printf %c '' did not output nothing: got '${RES}'" 1643 1.1 kre elif [ $(( $( do_printf %c '' | od -A n -to1 ) )) -ne 0 ] 1644 1.1 kre then 1645 1.1 kre RES="$( do_printf %c '' | od -A n -to1 | tr -d ' ')" 1646 1.1 kre atf_fail \ 1647 1.1 kre "printf %c '' output was '\\${RES}' should be '\\000'" 1648 1.1 kre fi 1649 1.1 kre fi 1650 1.1 kre 1651 1.1 kre return $RVAL 1652 1.1 kre } 1653 1.1 kre define NetBSD_extensions "Local NetBSD additions to printf" 1654 1.1 kre 1655 1.1 kre B_string_expand() 1656 1.1 kre { 1657 1.1 kre setmsg B_string_expand 1658 1.1 kre 1659 1.1 kre if ! supported B 1660 1.1 kre then 1661 1.1 kre atf_skip "%B format not supported" 1662 1.1 kre return $RVAL 1663 1.1 kre fi 1664 1.1 kre 1665 1.1 kre # Even if %B is supported, it is not necessarily *our* %B ... 1666 1.1 kre 1667 1.1 kre if $BUILTIN_TEST 1668 1.1 kre then 1669 1.1 kre # what matters if $TEST_SH is a NetBSD sh 1670 1.1 kre ${TEST_SH} -c 'test -n "$NETBSD_SHELL"' || { 1671 1.1 kre atf_skip \ 1672 1.1 kre "- ${TEST_SH%% *} is not a (modern) NetBSD shell" 1673 1.1 kre return $RVAL 1674 1.1 kre } 1675 1.1 kre else 1676 1.1 kre atf_require_prog uname 1677 1.1 kre 1678 1.1 kre SYS="$(uname -s)" 1679 1.1 kre case "${SYS}" in 1680 1.1 kre (NetBSD) ;; 1681 1.1 kre (*) atf_skip "- Not NetBSD (is $SYS), %B format unspecified" 1682 1.1 kre return $RVAL 1683 1.1 kre ;; 1684 1.1 kre esac 1685 1.1 kre fi 1686 1.1 kre 1687 1.1 kre # The trivial stuff... 1688 1.1 kre expect abcd %B abcd 1689 1.1 kre expect ' abcd' %5B abcd 1690 1.1 kre expect 'abcd ' %-5B abcd 1691 1.1 kre expect ab %.2B abcd 1692 1.1 kre expect ' ab' %5.2B abcd 1693 1.1 kre expect 'ab ' %-5.2B abcd 1694 1.1 kre 1695 1.1 kre # Next the semi-trivial 1696 1.1 kre expect "abcd${BSL}n" %B "abcd${NL}" 1697 1.1 kre expect "ab${BSL}tcd" %B "ab cd" 1698 1.1 kre expect "${BSL}\"${BSL}e${BSL}a${BSL}b${BSL}f${BSL}r${BSL}v" \ 1699 1.1 kre %B '" ' 1703 1.1 kre expect "${BSL}'${BSL}^?" %B \''' 1704 1.1 kre expect "${BSL}^A${BSL}^B" %B '' 1705 1.1 kre expect "x${BSL}M-Yz" %B 'xz' 1706 1.1 kre expect "-${BSL}M^W-" %B '--' 1707 1.1 kre expect ":${BSL}M^?:" %B '::' 1708 1.1 kre 1709 1.1 kre # Then, more or less nonsense 1710 1.1 kre expect " abcd${BSL}n" %9B "abcd${NL}" 1711 1.1 kre expect "ab${BSL}tcd " %-9B "ab cd" 1712 1.1 kre expect " ${BSL}'${BSL}^?" %6B \''' 1713 1.1 kre expect "${BSL}^A${BSL}^B " %-7B '' 1714 1.1 kre expect " -${BSL}M^W-" %8B '--' 1715 1.1 kre expect ":${BSL}M^?: " %-8B '::' 1716 1.1 kre 1717 1.1 kre # and finally, the absurd, ridiculous, and bizarre (useless) 1718 1.1 kre expect "abcd${BSL}" %.5B "abcd${NL}" 1719 1.1 kre expect "ab${BSL}" %.3B "ab cd" 1720 1.1 kre expect "${BSL}\"${BSL}" %.3B '" ' 1724 1.1 kre expect "${BSL}" %.1B \''' 1725 1.1 kre expect "${BSL}^" %.2B '' 1726 1.1 kre expect "x${BSL}M-" %.4B 'xz' 1727 1.1 kre expect "-${BSL}M^" %.4B '--' 1728 1.1 kre expect ":${BSL}M" %.3B '::' 1729 1.1 kre 1730 1.1 kre return $RVAL 1731 1.1 kre } 1732 1.1 kre define B_string_expand "NetBSD specific %B string expansion" 1733 1.1 kre 1734 1.1 kre 1735 1.1 kre ############################################################################# 1736 1.1 kre ############################################################################# 1737 1.1 kre # 1738 1.1 kre # The code to make the tests above actually run starts here... 1739 1.1 kre # 1740 1.1 kre 1741 1.1 kre # if setup fails, then ignore any test names on command line 1742 1.1 kre # Just run the (one) test that setup() established 1743 1.1 kre setup || set -- 1744 1.1 kre 1745 1.1 kre NL=' 1746 1.1 kre ' 1747 1.1 kre # test how the shell we're running handles quoted patterns in vars 1748 1.1 kre # Note: it is not our task here to diagnose the broken shell 1749 1.1 kre B1='\' 1750 1.1 kre B2='\\' 1751 1.1 kre case "${B1}" in 1752 1.1 kre (${B2}) BSL="${B2}";; # This one is correct 1753 1.1 kre (${B1}) BSL="${B1}";; # but some shells can't handle that 1754 1.1 kre (*) BSL=BROKEN_SHELL;; # !!! 1755 1.1 kre esac 1756 1.1 kre 1757 1.1 kre if $Running_under_ATF 1758 1.1 kre then 1759 1.1 kre # When in ATF, just add the test cases, and finish, and ATF 1760 1.1 kre # will take care of running everything 1761 1.1 kre 1762 1.1 kre atf_init_test_cases() { 1763 1.1 kre 1764 1.1 kre for T in $Tests 1765 1.3 kre do 1766 1.1 kre atf_add_test_case "$T" 1767 1.1 kre done 1768 1.1 kre return 0 1769 1.1 kre } 1770 1.1 kre exec 3>&2 1771 1.1 kre else 1772 1.1 kre # When not in AFT, we need to do it all here... 1773 1.1 kre 1774 1.1 kre Failed= 1775 1.1 kre Failures=0 1776 1.1 kre 1777 1.1 kre STDERR=$(mktemp ${TMPDIR:-/tmp}/Test-XXXXXX) 1778 1.1 kre trap "rm -f '${STDERR}'" EXIT 1779 1.1 kre exec 3>"${STDERR}" 1780 1.1 kre 1781 1.1 kre case "$#" in 1782 1.1 kre (0) set -- $Tests ;; 1783 1.1 kre esac 1784 1.1 kre 1785 1.1 kre for T 1786 1.1 kre do 1787 1.1 kre $T || { 1788 1.1 kre Failed="${Failed}${Failed:+${NL}} ${T} : " 1789 1.1 kre eval Failed='${Failed}${TEST_'"${T}"'_MSG}' 1790 1.1 kre Failures=$(( $Failures + 1 )) 1791 1.1 kre } 1792 1.1 kre done 1793 1.1 kre if [ $Failures -gt 0 ] 1794 1.1 kre then 1795 1.1 kre s=s 1796 1.1 kre test $Failures -eq 1 && s= 1797 1.1 kre 1798 1.1 kre exec >&2 1799 1.1 kre echo 1800 1.1 kre echo ================================================= 1801 1.1 kre echo 1802 1.1 kre echo "$Failures test$s failed:" 1803 echo "$Failed" 1804 echo 1805 echo ================================================= 1806 1807 if test -s "${STDERR}" 1808 then 1809 echo 1810 echo The following appeared on stderr during the tests: 1811 echo 1812 cat "${STDERR}" 1813 fi 1814 fi 1815 fi 1816