Browse Source

add uClibc-ng test directory

Waldemar Brodkorb 7 years ago
commit
7988979a72
100 changed files with 6694 additions and 0 deletions
  1. 334 0
      test/.gitignore
  2. 91 0
      test/Makefile
  3. 87 0
      test/README
  4. 165 0
      test/Rules.mak
  5. 155 0
      test/Test.mak
  6. 8 0
      test/argp/Makefile
  7. 10 0
      test/argp/Makefile.in
  8. 15 0
      test/argp/argp-ex1.c
  9. 45 0
      test/argp/argp-ex2.c
  10. 153 0
      test/argp/argp-ex3.c
  11. 167 0
      test/argp/argp-ex4.c
  12. 208 0
      test/argp/argp-test.c
  13. 26 0
      test/argp/bug-argp1.c
  14. 117 0
      test/argp/tst-argp1.c
  15. 100 0
      test/argp/tst-argp2.c
  16. 8 0
      test/args/Makefile
  17. 9 0
      test/args/Makefile.in
  18. 40 0
      test/args/arg_test.c
  19. 13 0
      test/args/arg_test.out.good
  20. 13 0
      test/args/arg_test_glibc.out.good
  21. 8 0
      test/assert/Makefile
  22. 5 0
      test/assert/Makefile.in
  23. 47 0
      test/assert/assert.c
  24. 8 0
      test/build/Makefile
  25. 21 0
      test/build/check_config_options.sh
  26. 8 0
      test/crypt/Makefile
  27. 15 0
      test/crypt/Makefile.in
  28. 103 0
      test/crypt/crypt.c
  29. 171 0
      test/crypt/crypt.input
  30. 172 0
      test/crypt/crypt.out.good
  31. 19 0
      test/crypt/md5c-test.c
  32. 62 0
      test/crypt/sha256c-test.c
  33. 63 0
      test/crypt/sha512c-test.c
  34. 8 0
      test/ctype/Makefile
  35. 4 0
      test/ctype/Makefile.in
  36. 250 0
      test/ctype/ctype.c
  37. 8 0
      test/dlopen/Makefile
  38. 84 0
      test/dlopen/Makefile.in
  39. 25 0
      test/dlopen/dladdr.c
  40. 36 0
      test/dlopen/dlafk.c
  41. 43 0
      test/dlopen/dlstatic.c
  42. 41 0
      test/dlopen/dltest.c
  43. 1 0
      test/dlopen/dltest2.c
  44. 29 0
      test/dlopen/dlundef.c
  45. 7 0
      test/dlopen/libA.c
  46. 7 0
      test/dlopen/libB.c
  47. 30 0
      test/dlopen/libC.c
  48. 1 0
      test/dlopen/libafk-temp.c
  49. 1 0
      test/dlopen/libafk.c
  50. 15 0
      test/dlopen/libstatic.c
  51. 11 0
      test/dlopen/libtest.c
  52. 40 0
      test/dlopen/libtest1.c
  53. 38 0
      test/dlopen/libtest2.c
  54. 1 0
      test/dlopen/libtest3.c
  55. 1 0
      test/dlopen/libundef.c
  56. 205 0
      test/dlopen/nodelete.c
  57. 59 0
      test/dlopen/nodelete1.c
  58. 10 0
      test/dlopen/nodelmod1.c
  59. 10 0
      test/dlopen/nodelmod2.c
  60. 8 0
      test/dlopen/nodelmod3.c
  61. 10 0
      test/dlopen/nodelmod4.c
  62. 33 0
      test/dlopen/test1.c
  63. 39 0
      test/dlopen/test2.c
  64. 13 0
      test/dlopen/test3.c
  65. 29 0
      test/dlopen/testscope.c
  66. 37 0
      test/dlopen/tst-origin.c
  67. 8 0
      test/inet/Makefile
  68. 17 0
      test/inet/Makefile.in
  69. 53 0
      test/inet/bug-if1.c
  70. 40 0
      test/inet/gethost.c
  71. 50 0
      test/inet/gethost_r-align.c
  72. 6 0
      test/inet/gethostid.c
  73. 17 0
      test/inet/getnetent.c
  74. 61 0
      test/inet/if_nameindex.c
  75. 80 0
      test/inet/tst-aton.c
  76. 46 0
      test/inet/tst-ether_aton.c
  77. 55 0
      test/inet/tst-ethers-line.c
  78. 37 0
      test/inet/tst-ethers.c
  79. 99 0
      test/inet/tst-ifaddrs.c
  80. 104 0
      test/inet/tst-network.c
  81. 36 0
      test/inet/tst-ntoa.c
  82. 44 0
      test/inet/tst-res.c
  83. 53 0
      test/inet/tst-sock-nonblock.c
  84. 8 0
      test/librt/Makefile
  85. 8 0
      test/librt/Makefile.in
  86. 104 0
      test/librt/shmtest.c
  87. 8 0
      test/locale-mbwc/Makefile
  88. 30 0
      test/locale-mbwc/Makefile.in
  89. 37 0
      test/locale-mbwc/dat_isw-funcs.h
  90. 196 0
      test/locale-mbwc/dat_iswalnum.c
  91. 169 0
      test/locale-mbwc/dat_iswalpha.c
  92. 125 0
      test/locale-mbwc/dat_iswcntrl.c
  93. 667 0
      test/locale-mbwc/dat_iswctype.c
  94. 125 0
      test/locale-mbwc/dat_iswdigit.c
  95. 167 0
      test/locale-mbwc/dat_iswgraph.c
  96. 96 0
      test/locale-mbwc/dat_iswlower.c
  97. 170 0
      test/locale-mbwc/dat_iswprint.c
  98. 155 0
      test/locale-mbwc/dat_iswpunct.c
  99. 129 0
      test/locale-mbwc/dat_iswspace.c
  100. 94 0
      test/locale-mbwc/dat_iswupper.c

+ 334 - 0
test/.gitignore

@@ -0,0 +1,334 @@
+#
+# Never ignore these
+#
+!.gitignore
+#
+# Generated files
+#
+*.out
+#
+# Executable test
+#
+*_glibc
+argp/argp-ex[1-4]
+argp/argp-test
+argp/bug-argp1
+argp/tst-argp[12]
+args/arg_test
+assert/assert
+crypt/crypt
+crypt/md5c-test
+crypt/sha256c-test
+crypt/sha512c-test
+ctype/ctype
+dlopen/dladdr
+dlopen/dlafk
+dlopen/dlstatic
+dlopen/dltest
+dlopen/dltest2
+dlopen/dlundef
+dlopen/libafk.so
+dlopen/libafk-temp.so
+dlopen/libA.so
+dlopen/libB.so
+dlopen/libC.so
+dlopen/libstatic.so
+dlopen/libtest[123].so
+dlopen/libtest.so
+dlopen/libundef.so
+dlopen/test[1-3]
+dlopen/testscope
+inet/bug-if1
+inet/gethost_r-align
+inet/gethostid
+inet/getnetent
+inet/if_nameindex
+inet/tst-aton
+inet/tst-ether_aton
+inet/tst-ethers
+inet/tst-ethers-line
+inet/tst-network
+inet/tst-ntoa
+inet/tst-res
+inet/tst-sock-nonblock
+librt/shmtest
+locale/bug-iconv-trans
+locale/bug-usesetlocale
+locale/C
+locale/collate-test
+locale/dump-ctype
+locale/gen-unicode-ctype
+locale/show-ucs-data
+locale/tst-digits
+locale/tst-langinfo
+locale/tst-mbswcs[1-6]
+locale/tst_nl_langinfo
+locale/tst-numeric
+locale/tst-setlocale
+locale/tst-sscanf
+locale/tst-trans
+locale/tst-wctype
+locale/tst-xlocale1
+locale/tst-xlocale2
+locale/xfrm-test
+locale-mbwc/tst_iswalnum
+locale-mbwc/tst_iswalpha
+locale-mbwc/tst_iswcntrl
+locale-mbwc/tst_iswctype
+locale-mbwc/tst_iswdigit
+locale-mbwc/tst_iswgraph
+locale-mbwc/tst_iswlower
+locale-mbwc/tst_iswprint
+locale-mbwc/tst_iswpunct
+locale-mbwc/tst_iswspace
+locale-mbwc/tst_iswupper
+locale-mbwc/tst_iswxdigit
+locale-mbwc/tst_mblen
+locale-mbwc/tst_mbrlen
+locale-mbwc/tst_mbrtowc
+locale-mbwc/tst_mbsrtowcs
+locale-mbwc/tst_mbstowcs
+locale-mbwc/tst_mbtowc
+locale-mbwc/tst_strcoll
+locale-mbwc/tst_strxfrm
+locale-mbwc/tst_swscanf
+locale-mbwc/tst_towctrans
+locale-mbwc/tst_towlower
+locale-mbwc/tst_towupper
+locale-mbwc/tst_wcrtomb
+locale-mbwc/tst_wcscat
+locale-mbwc/tst_wcschr
+locale-mbwc/tst_wcscmp
+locale-mbwc/tst_wcscoll
+locale-mbwc/tst_wcscpy
+locale-mbwc/tst_wcscspn
+locale-mbwc/tst_wcslen
+locale-mbwc/tst_wcsncat
+locale-mbwc/tst_wcsncmp
+locale-mbwc/tst_wcsncpy
+locale-mbwc/tst_wcspbrk
+locale-mbwc/tst_wcsrtombs
+locale-mbwc/tst_wcsspn
+locale-mbwc/tst_wcsstr
+locale-mbwc/tst_wcstod
+locale-mbwc/tst_wcstok
+locale-mbwc/tst_wcstombs
+locale-mbwc/tst_wcswidth
+locale-mbwc/tst_wcsxfrm
+locale-mbwc/tst_wctob
+locale-mbwc/tst_wctomb
+locale-mbwc/tst_wctrans
+locale-mbwc/tst_wctype
+locale-mbwc/tst_wcwidth
+locale-mbwc/tst2_mbrtowc
+malloc/malloc
+malloc/mallocbug
+malloc/malloc-standard-alignment
+malloc/realloc0
+malloc/realloc-can-shrink
+malloc/testmalloc
+malloc/tst-[cmv]alloc
+malloc/tst-mallocfork
+malloc/tst-mcheck
+malloc/tst-obstack
+math/basic-test
+math/compile_test
+math/c99_test
+math/ilogb
+math/libm-test-ulps.h
+math/libm-test.c
+math/rint
+math/signgam
+math/test-double
+math/test-ildoubl
+math/test-ldouble
+math/test-float
+math/test-fpucw
+math/test-idouble
+math/test-ifloat
+math/tst-definitions
+misc/bug-glob2
+misc/bug-readdir1
+misc/dirent
+misc/dirent64
+misc/fdopen
+misc/opendir-tst1
+misc/popen
+misc/seek
+misc/sem
+misc/stdarg
+misc/tst-inotify
+misc/tst-scandir
+misc/tst-seekdir
+misc/tst-statfs
+misc/tst-statvfs
+misc/tst-utmp
+misc/tst-utmpx
+mmap/mmap
+mmap/mmap2
+mmap/mmap64
+nptl/tst-align
+nptl/tst-align2
+nptl/tst-align3
+nptl/tst-atfork1
+nptl/tst-attr[1-3]
+nptl/tst-barrier[1-4]
+nptl/tst-basic[1-7]
+nptl/tst-cancel[1-9]
+nptl/tst-cancelx[2-4]
+nptl/tst-cancelx[6-9]
+nptl/tst-cancelx1[0-8]
+nptl/tst-cancelx2[0-1]
+nptl/tst-cancel[1-3][0-9]
+nptl/tst-cleanup[0-4]
+nptl/tst-cleanupx[0-4]
+nptl/tst-clock
+nptl/tst-clock[12]
+nptl/tst-clock_nanosleep
+nptl/tst-cond[1-9]
+nptl/tst-cond[1-2][0-9]
+nptl/tst-cpuclock[12]
+nptl/tst-cputimer[1-3]
+nptl/tst-detach1
+nptl/tst-dlsym1
+nptl/tst-eintr[1-5]
+nptl/tst-exec[2-4]
+nptl/tst-exit[1-3]
+nptl/tst-fini1
+nptl/tst-fini1mod.so
+nptl/tst-flock[1-2]
+nptl/tst-fork[1-4]
+nptl/tst-getpid[1-3]
+nptl/tst-initializers1
+nptl/tst-initializers1-c[89]9
+nptl/tst-initializers1-gnu[89]9
+nptl/tst-join[1-6]
+nptl/tst-key[1-4]
+nptl/tst-kill[1-6]
+nptl/tst-mqueue[1-9]
+nptl/tst-mutex[1-9]
+nptl/tst-mutex[57]a
+nptl/tst-once[1-4]
+nptl/tst-oncex[3-4]
+nptl/tst-popen1
+nptl/tst-oddstacklimit
+nptl/tst-raise1
+nptl/tst-rwlock[1-9]
+nptl/tst-rwlock1[0-4]
+nptl/tst-rwlock2a
+nptl/tst-sched1
+nptl/tst-sem[1-9]
+nptl/tst-sem1[0-2]
+nptl/tst-signal[1-7]
+nptl/tst-spin[1-3]
+nptl/tst-stack[12]
+nptl/tst-stdio[12]
+nptl/tst-sysconf
+nptl/tst-timer[2-5]
+nptl/tst-tls[1-5]
+nptl/tst-tls4mod.so
+nptl/tst-tls?mod[a-f].so
+nptl/tst-tls4modb.so
+nptl/tst-tls[35]mod.so
+nptl/tst-tls6.sh
+nptl/tst-tsd[1-6]
+nptl/tst-typesizes
+nptl/tst-umask1
+nptl/tst-unload
+nptl/tst-vfork[12]x
+pthread/cancellation-points
+pthread/ex[1-7]
+pthread/tst-too-many-cleanups
+pwd_grp/getgroups
+pwd_grp/grcat
+pwd_grp/pwcat
+pwd_grp/test_grp
+pwd_grp/test_pwd
+regex/testregex
+regex/tst-regex2
+regex/tst-regexloc
+rpc/getrpcent
+rpc/getrpcent_r
+setjmp/bug269-setjmp
+setjmp/jmpbug
+setjmp/sigjmpbug
+setjmp/tst-setjmp
+setjmp/tst-vfork-longjmp
+signal/sigchld
+signal/signal
+signal/tst-raise
+signal/tst-signal
+signal/tst-signalfd
+signal/tst-sigset
+signal/tst-sigsimple
+silly/hello
+silly/tiny
+silly/tst-atomic
+silly/tst-atomic-long
+stat/memcmp-stat
+stat/stat
+stat/stat64
+stat/stat-loop256
+stdio/64bit
+stdio/fclose-loop
+stdlib/ptytest
+stdlib/qsort
+stdlib/testarc4random
+stdlib/testatexit
+stdlib/test-canon
+stdlib/test-canon2
+stdlib/test-mkostemp-O_CLOEXEC
+stdlib/test-mkostemp-child
+stdlib/teston_exit
+stdlib/teststrtol
+stdlib/teststrtoq
+string/bug-strcoll1
+string/bug-strncat1
+string/bug-strpbrk1
+string/bug-strspn1
+string/stratcliff
+string/testcopy
+string/tester
+string/test-ffs
+string/tst-bswap
+string/tst-inlcall
+string/tst-strlen
+string/tst-strtok
+string/tst-strxfrm
+termios/termios
+time/clocktest
+time/test_time
+time/tst-ctime
+time/tst-ftime_l
+time/tst-futimens1
+time/tst-mktime
+time/tst-mktime3
+time/tst-strptime2
+time/tst-timerfd
+time/tst_wcsftime
+tls/tst-tls[1-9]
+tls/tst-tls1[0-8]
+tls/tst-tls-at-ctor
+tls/tst-tlsmod[1-9].so
+tls/tst-tlsmod1[0-9].so
+tls/tst-tlsmod1[0-9][ab].so
+tls/tst-tlsmod1[78]a[0-9].so
+tls/tst-tlsmod1[78]a1[0-9].so
+tls/tst-tlsmod-at-ctor.so
+unistd/clone
+unistd/errno
+unistd/exec-null
+unistd/fork
+unistd/getconf
+unistd/getconf.c
+unistd/getcwd
+unistd/getopt
+unistd/getopt_long
+unistd/tstgetopt
+unistd/tst-fallocate
+unistd/tst-fallocate64
+unistd/tst-posix_fallocate
+unistd/tst-posix_fallocate64
+unistd/tst-preadwrite
+unistd/tst-preadwrite64
+unistd/vfork

+ 91 - 0
test/Makefile

@@ -0,0 +1,91 @@
+# Makefile for uClibc
+#
+# Copyright (C) 2000-2005 Erik Andersen <andersen@uclibc.org>
+#
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+#
+
+top_srcdir=../
+top_builddir=../
+include Rules.mak
+
+ALL_SUBDIRS := $(patsubst %/Makefile,%,$(wildcard */Makefile))
+
+DIRS := $(ALL_SUBDIRS)
+ifneq ($(HAVE_SHARED)$(UCLIBC_HAS_THREADS),yy)
+	DIRS := $(filter-out dlopen,$(DIRS))
+endif
+ifneq ($(findstring -static,$(LDFLAGS)),)
+	DIRS := $(filter-out dlopen,$(DIRS))
+endif
+ifneq ($(UCLIBC_HAS_THREADS)$(ARCH_USE_MMU),yy)
+	DIRS := $(filter-out pthread,$(DIRS))
+endif
+ifneq ($(UCLIBC_HAS_FLOATS),y)
+	DIRS := $(filter-out math,$(DIRS))
+endif
+ifneq ($(UCLIBC_HAS_FULL_RPC),y)
+	DIRS := $(filter-out rpc,$(DIRS))
+endif
+ifneq ($(UCLIBC_HAS_REGEX),y)
+	DIRS := $(filter-out regex,$(DIRS))
+endif
+ifneq ($(HAVE_SHARED)$(UCLIBC_HAS_THREADS_NATIVE),yy)
+	DIRS := $(filter-out tls nptl,$(DIRS))
+endif
+ifneq ($(UCLIBC_HAS_WCHAR),y)
+	DIRS := $(filter-out locale-mbwc,$(DIRS))
+endif
+ifneq ($(UCLIBC_HAS_LOCALE),y)
+	DIRS := $(filter-out locale,$(DIRS))
+endif
+ifneq ($(UCLIBC_HAS_CRYPT_IMPL),y)
+	DIRS := $(filter-out crypt,$(DIRS))
+endif
+ifeq ($(HAS_NO_THREADS),y)
+	DIRS := $(filter-out pthread,$(DIRS))
+endif
+ifneq ($(UCLIBC_HAS_ARGP),y)
+	DIRS := $(filter-out argp,$(DIRS))
+endif
+
+test check all: run
+
+run: subdirs_run
+
+gen:
+	-rm -f $(top_builddir)/test/uclibcng-testrunner.in
+	$(MAKE) run UCLIBCNG_GENERATE_TESTRUNNER=1
+
+compile: $(top_builddir)$(LOCAL_INSTALL_PATH) subdirs_compile
+
+$(top_builddir)$(LOCAL_INSTALL_PATH):
+	$(Q)$(MAKE) -C $(top_builddir) $(LOCAL_INSTALL_PATH)
+
+tags:
+	ctags -R
+
+clean: subdirs_clean
+
+subdirs: $(patsubst %, _dir_%, $(DIRS))
+subdirs_compile: $(patsubst %, _dircompile_%, $(DIRS))
+subdirs_run: $(patsubst %, _dirrun_%, $(DIRS))
+subdirs_clean: $(patsubst %, _dirclean_%, $(ALL_SUBDIRS))
+
+$(patsubst %, _dir_%, $(DIRS)) : dummy
+	$(Q)$(MAKE) -C $(patsubst _dir_%, %, $@) \
+		KCONFIG_CONFIG=$(KCONFIG_CONFIG)
+
+$(patsubst %, _dirrun_%, $(DIRS)) : dummy
+	$(Q)$(MAKE) -C $(patsubst _dirrun_%, %, $@) run \
+		UCLIBCNG_TEST_SUBDIR=$(strip $(patsubst _dirrun_%, %, $@)) \
+		KCONFIG_CONFIG=$(KCONFIG_CONFIG)
+
+$(patsubst %, _dircompile_%, $(DIRS)) : dummy
+	$(Q)$(MAKE) -C $(patsubst _dircompile_%, %, $@) compile \
+		KCONFIG_CONFIG=$(KCONFIG_CONFIG)
+
+$(patsubst %, _dirclean_%, $(ALL_SUBDIRS)) : dummy
+	$(Q)$(MAKE) -C $(patsubst _dirclean_%, %, $@) clean
+
+.PHONY: all check clean dummy subdirs_compile subdirs_run subdirs subdirs_clean test run compile

+ 87 - 0
test/README

@@ -0,0 +1,87 @@
+-----------
+ For: User
+-----------
+Following make targets are avaialable
+
+make compile
+
+This will compile and link the tests.
+
+make run
+
+This will execute all the tests.
+
+make check
+make all
+
+This will build and run tests.
+
+The following make variables may help you in testing:
+
+ - UCLIBC_ONLY  - only run tests against uClibc
+ - GLIBC_ONLY   - only run tests against glibc
+ - V / VERBOSE  - run tests with a lot of output
+ - TEST_INSTALLED_UCLIBC - Test installed libraries
+                           under /lib and /usr/lib.
+ - TIMEOUTFACTOR=nn - increase test timeout nn times.
+                  At least REGEX_OLD + regex/tst-regex2 needs it increased.
+
+So, to just run the uClibc tests, try this:
+make check UCLIBC_ONLY=1
+
+You can pass the following 2 environment variables to "make run":
+ - make run SIMULATOR_uclibc=qemu-sh4 SIMULATOR_glibc=qemu-x86_64
+
+If you need to test just a subset of all test, delete subdirectories
+you do not need.
+
+As of 2009-07, build machinery does not track dependencies on uclibc.
+If you edit a header and re-run "make compile", it does not re-install it
+into ../install_dir. If you delete ../install_dir, "make compile"
+rebuilds uclibc as needed and re-installs ../install_dir,
+but still does not rebuild testcases.
+(You can work around it by "touch */*.c" for now).
+
+----------------
+ For: Developer
+----------------
+
+The structure of this test system is:
+ test/                    toplevel dir containing common test code
+ test/Rules.mak           Common build code
+ test/Test.mak            Runtime test make code
+ test/subdir/             code specific to a subsystem is stored in a subdir
+ test/subdir/Makefile.in  describe the tests to run
+ test/subdir/Makefile     test entry point, includes needed upper-level
+                          makefiles plus Makefile.in
+ test/subdir/*.c          the tests
+
+Each subdir has a Makefile (same for any subdir) that must include in strict order:
+  - the upper-level Rules.mak file
+  - the Makefile.in
+  - the upper-level Test.mak file
+Makefile.in may be used to define the TESTS and TESTS_DISABLED variables.
+If you do not, TESTS is built automatically based upon all the .c files in the subdir.
+TESTS := foo
+TESTS_DISABLED := bar
+Each test must use a similar .c name; so the "foo" test needs a "foo.c".
+
+Additionally, the following options further control specific test behavior:
+CFLAGS_foo    := extra cflags to use to compile test
+DODIFF_foo    := compare the output of the glibc and uClibc tests (see below)
+LDFLAGS_foo   := extra ldflags to use to link test
+OPTS_foo      := extra options to pass to test
+RET_foo       := expected exit code of test; default is 0
+WRAPPER_foo   := execute stuff just before test
+
+Or to control all tests in a subdir:
+EXTRA_CLEAN   := extra files to remove in the clean target
+EXTRA_DIRS    := extra directories to remove in the clean target
+EXTRA_CFLAGS  := -DFOO
+EXTRA_LDFLAGS := -lpthread
+OPTS          :=
+WRAPPER       :=
+
+If you want to compare the output of a test with known good output, then just
+create a local file named "foo.out.good" and the output generated by the test
+"foo" will be automatically stored in "foo.out" and compared to "foo.out.good".

+ 165 - 0
test/Rules.mak

@@ -0,0 +1,165 @@
+# Rules.mak for uClibc test subdirs
+#
+# Copyright (C) 2000-2006 Erik Andersen <andersen@uclibc.org>
+#
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+#
+
+.SUFFIXES:
+
+top_builddir ?= ../
+abs_top_builddir ?= $(shell cd $(top_builddir); pwd)/
+
+TESTDIR=$(top_builddir)test/
+
+include $(top_srcdir)Rules.mak
+ifeq ($(filter $(clean_targets) CLEAN_%,$(MAKECMDGOALS)),)
+ifeq ($(HAVE_DOT_CONFIG),)
+$(error no HAVE_DOT_CONFIG, failed to read .config)
+endif
+endif
+
+ifdef UCLIBC_LDSO
+ifeq (,$(findstring /,$(UCLIBC_LDSO)))
+UCLIBC_LDSO := $(UCLIBC_LDSO)
+else
+UCLIBC_LDSO := $(notdir $(UCLIBC_LDSO))
+endif
+else
+UCLIBC_LDSO := $(notdir $(firstword $(wildcard $(top_builddir)lib/ld*)))
+endif
+ifndef TEST_INSTALLED_UCLIBC
+ifeq ($(LDSO_SAFE_RUNPATH),y)
+UCLIBC_PATH := $(abs_top_builddir)lib
+else
+UCLIBC_PATH := $(top_builddir)lib
+endif
+else
+UCLIBC_PATH := $(RUNTIME_PREFIX)$(MULTILIB_DIR)
+endif
+#--------------------------------------------------------
+# Ensure consistent sort order, 'gcc -print-search-dirs' behavior, etc.
+LC_ALL:= C
+export LC_ALL
+
+ifeq ($(strip $(TARGET_ARCH)),)
+TARGET_ARCH:=$(shell $(CC) -dumpmachine | sed -e s'/-.*//' \
+	-e 's/i.86/i386/' \
+	-e 's/sun.*/sparc/' -e 's/sparc.*/sparc/' \
+	-e 's/sa110/arm/' -e 's/arm.*/arm/g' \
+	-e 's/m68k.*/m68k/' \
+	-e 's/parisc.*/hppa/' \
+	-e 's/ppc/powerpc/g' \
+	-e 's/sh[234]/sh/' \
+	-e 's/mips.*/mips/' \
+	-e 's/cris.*/cris/' \
+	-e 's/xtensa.*/xtensa/' \
+	)
+endif
+export TARGET_ARCH
+
+RM_R = $(Q)$(RM) -r
+LN_S = $(Q)$(LN) -fs
+
+ifneq ($(KERNEL_HEADERS),)
+ifeq ($(patsubst /%,/,$(KERNEL_HEADERS)),/)
+# Absolute path in KERNEL_HEADERS
+KERNEL_INCLUDES += -I$(KERNEL_HEADERS)
+else
+# Relative path in KERNEL_HEADERS
+KERNEL_INCLUDES += -I$(top_builddir)$(KERNEL_HEADERS)
+endif
+endif
+
+XCOMMON_CFLAGS := -I$(top_builddir)test -D_GNU_SOURCE
+XWARNINGS      += $(CFLAG_-Wstrict-prototypes)
+CFLAGS         := -nostdinc -I$(top_builddir)$(LOCAL_INSTALL_PATH)/usr/include
+CFLAGS         += $(XCOMMON_CFLAGS) $(KERNEL_INCLUDES) $(CC_INC)
+CFLAGS         += $(OPTIMIZATION) $(CPU_CFLAGS) $(XWARNINGS)
+
+$(eval $(call check-gcc-var,-Wno-missing-field-initializers))
+CFLAGS         += $(CFLAG_-Wno-missing-field-initializers)
+
+# Can't add $(OPTIMIZATION) here, it may be target-specific.
+# Just adding -Os for now.
+HOST_CFLAGS    += $(XCOMMON_CFLAGS) -Os $(XWARNINGS) -std=gnu99
+
+LDFLAGS        := $(CPU_LDFLAGS-y) -Wl,-z,now
+ifeq ($(DODEBUG),y)
+	CFLAGS        += -g
+	HOST_CFLAGS   += -g
+	LDFLAGS       += -Wl,-g
+	HOST_LDFLAGS  += -Wl,-g
+endif
+
+ifeq ($(DOSTRIP),y)
+	LDFLAGS       += -Wl,-s
+	HOST_LDFLAGS  += -Wl,-s
+endif
+
+ifneq ($(HAVE_SHARED),y)
+	LDFLAGS       += -Wl,-static -static-libgcc
+endif
+
+ifndef TEST_INSTALLED_UCLIBC
+LDFLAGS += -B$(UCLIBC_PATH) -Wl,-rpath,$(UCLIBC_PATH):$(shell pwd) -Wl,-rpath-link,$(UCLIBC_PATH):$(shell pwd)
+else
+LDFLAGS += -Wl,-rpath,$(shell pwd)
+endif
+
+ifeq ($(findstring -static,$(LDFLAGS)),)
+LDFLAGS += -Wl,--dynamic-linker,$(UCLIBC_PATH)/$(UCLIBC_LDSO)
+endif
+
+ifeq ($(LDSO_GNU_HASH_SUPPORT),y)
+# Check for binutils support is done on root Rules.mak
+LDFLAGS += $(CFLAG_-Wl--hash-style=gnu)
+endif
+
+ifneq ($(strip $(UCLIBC_EXTRA_CFLAGS)),"")
+CFLAGS += $(call qstrip,$(UCLIBC_EXTRA_CFLAGS))
+endif
+ifneq ($(strip $(UCLIBC_EXTRA_LDFLAGS)),"")
+LDFLAGS += $(call qstrip,$(UCLIBC_EXTRA_LDFLAGS))
+endif
+
+ifneq ($(findstring -s,$(MAKEFLAGS)),)
+DISP := sil
+Q    := @
+SCAT := -@true
+else
+ifneq ($(V)$(VERBOSE),)
+DISP := ver
+Q    :=
+SCAT := cat
+else
+DISP := pur
+Q    := @
+SCAT := -@true
+endif
+endif
+ifneq ($(Q),)
+MAKEFLAGS += --no-print-directory
+endif
+
+banner := ---------------------------------
+pur_showclean = echo "  "CLEAN $(notdir $(CURDIR))
+pur_showdiff  = echo "  "TEST_DIFF $(notdir $(CURDIR))/
+pur_showlink  = echo "  "TEST_LINK $(notdir $(CURDIR))/ $@
+pur_showtest  = echo "  "TEST_EXEC $(notdir $(CURDIR))/ $(@:.exe=)
+sil_showclean =
+sil_showdiff  = true
+sil_showlink  = true
+sil_showtest  = true
+ver_showclean =
+ver_showdiff  = true echo
+ver_showlink  = true echo
+ver_showtest  = printf "\n$(banner)\nTEST $(notdir $(CURDIR))/ $(@:.exe=)\n$(banner)\n"
+do_showclean  = $($(DISP)_showclean)
+do_showdiff   = $($(DISP)_showdiff)
+do_showlink   = $($(DISP)_showlink)
+do_showtest   = $($(DISP)_showtest)
+showclean = @$(do_showclean)
+showdiff  = @$(do_showdiff)
+showlink  = @$(do_showlink)
+showtest  = @$(do_showtest)

+ 155 - 0
test/Test.mak

@@ -0,0 +1,155 @@
+# Common makefile rules for tests
+#
+# Copyright (C) 2000-2006 Erik Andersen <andersen@uclibc.org>
+#
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+
+shellescape='$(subst ','\'',$(1))'
+
+ifeq ($(TESTS),)
+TESTS := $(patsubst %.c,%,$(wildcard *.c))
+endif
+ifneq ($(TESTS_DISABLED),)
+TESTS := $(filter-out $(TESTS_DISABLED),$(TESTS))
+endif
+ifeq ($(SHELL_TESTS),)
+SHELL_TESTS := $(patsubst %.sh,shell_%,$(wildcard *.sh))
+endif
+
+ifneq ($(filter-out test,$(strip $(TESTS))),$(strip $(TESTS)))
+$(error Sanity check: cannot have a test named "test.c")
+endif
+
+U_TARGETS := $(TESTS)
+G_TARGETS := $(addsuffix _glibc,$(U_TARGETS))
+
+ifneq ($(GLIBC_TESTS_DISABLED),)
+G_TARGETS := $(filter-out $(GLIBC_TESTS_DISABLED),$(G_TARGETS))
+endif
+
+ifeq ($(GLIBC_ONLY),)
+TARGETS   += $(U_TARGETS)
+endif
+ifeq ($(UCLIBC_ONLY),)
+TARGETS   += $(G_TARGETS)
+endif
+
+CLEAN_TARGETS := $(U_TARGETS) $(G_TARGETS)
+CLEAN_TARGETS += $(TESTS_DISABLED) $(addsuffix _glibc,$(TESTS_DISABLED)) $(GLIBC_TESTS_DISABLED)
+COMPILE_TARGETS :=  $(TARGETS)
+# We sort the targets so uClibc and host-libc tests are run adjacent
+RUN_TARGETS := $(sort $(addsuffix .exe,$(TARGETS)))
+COMPILE_TARGETS :=  $(sort $(COMPILE_TARGETS))
+# provide build rules even for disabled tests:
+U_TARGETS += $(TESTS_DISABLED)
+G_TARGETS += $(addsuffix _glibc,$(TESTS_DISABLED)) $(GLIBC_TESTS_DISABLED)
+TARGETS += $(SHELL_TESTS)
+CFLAGS += $(CFLAGS_$(notdir $(CURDIR)))
+ifeq (1,$(UCLIBCNG_GENERATE_TESTRUNNER))
+UCLIBCNG_TEST_SUBDIR ?= $(patsubst $(realpath $(TESTDIR))/%,%,$(CURDIR))
+endif
+
+define binary_name
+$(patsubst %.exe,%,$@)
+endef
+define tst_src_name
+$(patsubst %_glibc,%,$(binary_name))
+endef
+
+define diff_test
+	$(Q)\
+	for x in "$(binary_name).out" "$(tst_src_name).out" ; do \
+		test -e "$$x.good" && $(do_showdiff) "$(binary_name).out" "$$x.good" && exec diff -u "$(binary_name).out" "$$x.good" ; \
+	done ; \
+	true
+endef
+define uclibc_glibc_diff_test
+	$(Q)\
+	test -z "$(DODIFF_$(tst_src_name))" && exec true ; \
+	uclibc_out="$(binary_name).out" ; \
+	glibc_out="$(tst_src_name).out" ; \
+	$(do_showdiff) $$uclibc_out $$glibc_out ; \
+	exec diff -u "$$uclibc_out" "$$glibc_out"
+endef
+define exec_test
+	$(showtest)
+	$(Q)\
+	$(SIMULATOR) $(WRAPPER) $(WRAPPER_$(tst_src_name)) \
+	./$(binary_name) $(OPTS) $(OPTS_$(tst_src_name)) > "$(binary_name).out" 2>&1 ; \
+		ret=$$? ; \
+		expected_ret="$(RET_$(tst_src_name))" ; \
+		test -z "$$expected_ret" && export expected_ret=0 ; \
+	if ! test $$ret -eq $$expected_ret ; then \
+		echo "ret == $$ret ; expected_ret == $$expected_ret" ; \
+		echo "The output of the failed test is:"; \
+		cat "$(binary_name).out"; \
+		exit 1 ; \
+	fi
+	$(SCAT) "$(binary_name).out"
+endef
+
+test check all: run
+run: $(RUN_TARGETS)
+
+$(addsuffix .exe,$(U_TARGETS)): SIMULATOR:=$(SIMULATOR_uclibc)
+$(addsuffix .exe,$(G_TARGETS)): SIMULATOR:=$(SIMULATOR_glibc)
+$(RUN_TARGETS):
+ifeq (1,$(UCLIBCNG_GENERATE_TESTRUNNER))
+	$(Q)\
+	expected_ret="$(RET_$(tst_src_name))"; echo \
+	    "$${expected_ret:-0}" \
+	    $(call shellescape,$(tst_src_name)) \
+	    $(call shellescape,$(binary_name)) \
+	    $(call shellescape,$(UCLIBCNG_TEST_SUBDIR)) \
+	    $(call shellescape,$(WRAPPER) $(WRAPPER_$(tst_src_name)) ./$(binary_name) $(OPTS) $(OPTS_$(tst_src_name))) \
+	    >>$(top_builddir)/test/uclibcng-testrunner.in
+else
+	$(exec_test)
+	$(diff_test)
+ifeq ($(UCLIBC_ONLY),)
+	$(uclibc_glibc_diff_test)
+endif
+endif
+
+compile: $(COMPILE_TARGETS)
+
+G_TARGET_SRCS := $(addsuffix .c,$(G_TARGETS))
+U_TARGET_SRCS := $(addsuffix .c,$(U_TARGETS))
+
+MAKE_SRCS := $(wildcard Makefile.in) $(TESTDIR)Makefile $(TESTDIR)Rules.mak $(TESTDIR)Test.mak
+
+$(U_TARGETS): $(U_TARGET_SRCS) $(MAKE_SRCS)
+	$(showlink)
+	$(Q)$(CC) $(filter-out $(CFLAGS-OMIT-$@),$(CFLAGS)) $(EXTRA_CFLAGS) $(CFLAGS_$(notdir $(CURDIR))) $(CFLAGS_$@) -c $@.c -o $@.o
+	$(Q)$(CC) $(filter-out $(LDFLAGS-OMIT-$@),$(LDFLAGS)) $@.o -o $@ $(EXTRA_LDFLAGS) $(LDFLAGS_$@)
+
+$(G_TARGETS): $(U_TARGET_SRCS) $(MAKE_SRCS)
+	$(showlink)
+	$(Q)$(HOSTCC) $(filter-out $(HOST_CFLAGS-OMIT-$(patsubst %_glibc,%,$@)),$(HOST_CFLAGS)) \
+	$(CFLAGS_$(notdir $(CURDIR))) $(CFLAGS_$(patsubst %_glibc,%,$@)) \
+	-c $(patsubst %_glibc,%,$@).c -o $@.o
+	$(Q)$(HOSTCC) $(filter-out $(LDFLAGS-OMIT-$(patsubst %_glibc,%,$@)),$(HOST_LDFLAGS)) \
+	$@.o -o $@ $(EXTRA_LDFLAGS) $(LDFLAGS_$(patsubst %_glibc,%,$@)) $(LDFLAGS_$@)
+
+
+shell_%:
+	$(showtest)
+	$(Q)$(if $(PRE_RUN_$(@)),$(PRE_RUN_$(@)))
+	$(Q)$(SHELL) $(patsubst shell_%,%.sh,$(binary_name))
+	$(Q)$(if $(POST_RUN_$(@)),$(POST_RUN_$(@)))
+
+%.so: %.c
+	$(showlink)
+	$(Q)$(CC) \
+		$(filter-out $(CFLAGS-OMIT-$<),$(CFLAGS)) $(EXTRA_CFLAGS) \
+		$(CFLAGS_$(patsubst %_glibc,%,$@)) \
+		-fPIC -shared $< -o $@ -Wl,-soname,$@ \
+		$(filter-out $(LDFLAGS-OMIT-$<),$(LDFLAGS)) $(EXTRA_LIBS) \
+		$(LDFLAGS_$(patsubst %_glibc,%,$@))
+
+clean:
+	$(showclean)
+	$(Q)$(RM) *.a *.o *.so *~ core *.out *.gdb $(CLEAN_TARGETS) $(EXTRA_CLEAN)
+	$(Q)$(RM_R) $(EXTRA_DIRS)
+
+.PHONY: all check clean test run compile

+ 8 - 0
test/argp/Makefile

@@ -0,0 +1,8 @@
+# uClibc argp tests
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+
+top_builddir=../../
+top_srcdir=../../
+include ../Rules.mak
+-include Makefile.in
+include ../Test.mak

+ 10 - 0
test/argp/Makefile.in

@@ -0,0 +1,10 @@
+# uClibc argp tests
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+
+TESTS := $(addprefix argp-, ex1 ex2 ex3 ex4 test) \
+         bug-argp1 tst-argp1 tst-argp2
+
+OPTS_argp-ex3 = ARG1 ARG2
+OPTS_argp-ex4 = ARG1 string1 string2 string3
+OPTS_bug-argp1 = -- --help
+

+ 15 - 0
test/argp/argp-ex1.c

@@ -0,0 +1,15 @@
+/* Argp example #1 -- a minimal program using argp */
+
+/* This is (probably) the smallest possible program that
+   uses argp.  It won't do much except give an error
+   messages and exit when there are any arguments, and print
+   a (rather pointless) messages for --help.  */
+
+#include <stdlib.h>
+#include <argp.h>
+
+int main (int argc, char **argv)
+{
+  argp_parse (0, argc, argv, 0, 0, 0);
+  exit (0);
+}

+ 45 - 0
test/argp/argp-ex2.c

@@ -0,0 +1,45 @@
+/* Argp example #2 -- a pretty minimal program using argp */
+
+/* This program doesn't use any options or arguments, but uses
+   argp to be compliant with the GNU standard command line
+   format.
+
+   In addition to making sure no arguments are given, and
+   implementing a --help option, this example will have a
+   --version option, and will put the given documentation string
+   and bug address in the --help output, as per GNU standards.
+
+   The variable ARGP contains the argument parser specification;
+   adding fields to this structure is the way most parameters are
+   passed to argp_parse (the first three fields are usually used,
+   but not in this small program).  There are also two global
+   variables that argp knows about defined here,
+   ARGP_PROGRAM_VERSION and ARGP_PROGRAM_BUG_ADDRESS (they are
+   global variables because they will almost always be constant
+   for a given program, even if it uses different argument
+   parsers for various tasks).  */
+
+#include <stdlib.h>
+#include <argp.h>
+
+const char *argp_program_version =
+  "argp-ex2 1.0";
+const char *argp_program_bug_address =
+  "<bug-gnu-utils@@gnu.org>";
+
+/* Program documentation.  */
+static char doc[] =
+  "Argp example #2 -- a pretty minimal program using argp";
+
+/* Our argument parser.  The @code{options}, @code{parser}, and
+   @code{args_doc} fields are zero because we have neither options or
+   arguments; @code{doc} and @code{argp_program_bug_address} will be
+   used in the output for @samp{--help}, and the @samp{--version}
+   option will print out @code{argp_program_version}.  */
+static struct argp argp = { 0, 0, 0, doc };
+
+int main (int argc, char **argv)
+{
+  argp_parse (&argp, argc, argv, 0, 0, 0);
+  exit (0);
+}

+ 153 - 0
test/argp/argp-ex3.c

@@ -0,0 +1,153 @@
+/* Argp example #3 -- a program with options and arguments using argp */
+
+/* This program uses the same features as example 2, and uses options and
+   arguments.
+
+   We now use the first four fields in ARGP, so here's a description of them:
+     OPTIONS  -- A pointer to a vector of struct argp_option (see below)
+     PARSER   -- A function to parse a single option, called by argp
+     ARGS_DOC -- A string describing how the non-option arguments should look
+     DOC      -- A descriptive string about this program; if it contains a
+                 vertical tab character (\v), the part after it will be
+                 printed *following* the options
+
+   The function PARSER takes the following arguments:
+     KEY  -- An integer specifying which option this is (taken
+             from the KEY field in each struct argp_option), or
+             a special key specifying something else; the only
+             special keys we use here are ARGP_KEY_ARG, meaning
+             a non-option argument, and ARGP_KEY_END, meaning
+             that all arguments have been parsed
+     ARG  -- For an option KEY, the string value of its
+             argument, or NULL if it has none
+     STATE-- A pointer to a struct argp_state, containing
+             various useful information about the parsing state; used here
+             are the INPUT field, which reflects the INPUT argument to
+             argp_parse, and the ARG_NUM field, which is the number of the
+             current non-option argument being parsed
+   It should return either 0, meaning success, ARGP_ERR_UNKNOWN, meaning the
+   given KEY wasn't recognized, or an errno value indicating some other
+   error.
+
+   Note that in this example, main uses a structure to communicate with the
+   parse_opt function, a pointer to which it passes in the INPUT argument to
+   argp_parse.  Of course, it's also possible to use global variables
+   instead, but this is somewhat more flexible.
+
+   The OPTIONS field contains a pointer to a vector of struct argp_option's;
+   that structure has the following fields (if you assign your option
+   structures using array initialization like this example, unspecified
+   fields will be defaulted to 0, and need not be specified):
+     NAME   -- The name of this option's long option (may be zero)
+     KEY    -- The KEY to pass to the PARSER function when parsing this option,
+               *and* the name of this option's short option, if it is a
+               printable ascii character
+     ARG    -- The name of this option's argument, if any
+     FLAGS  -- Flags describing this option; some of them are:
+                 OPTION_ARG_OPTIONAL -- The argument to this option is optional
+                 OPTION_ALIAS        -- This option is an alias for the
+                                        previous option
+                 OPTION_HIDDEN       -- Don't show this option in --help output
+     DOC    -- A documentation string for this option, shown in --help output
+
+   An options vector should be terminated by an option with all fields zero. */
+
+#include <stdlib.h>
+#include <argp.h>
+
+const char *argp_program_version =
+  "argp-ex3 1.0";
+const char *argp_program_bug_address =
+  "<bug-gnu-utils@@gnu.org>";
+
+/* Program documentation.  */
+static char doc[] =
+  "Argp example #3 -- a program with options and arguments using argp";
+
+/* A description of the arguments we accept.  */
+static char args_doc[] = "ARG1 ARG2";
+
+/* The options we understand.  */
+static struct argp_option options[] = {
+  {"verbose",  'v', 0,      0,  "Produce verbose output" },
+  {"quiet",    'q', 0,      0,  "Don't produce any output" },
+  {"silent",   's', 0,      OPTION_ALIAS },
+  {"output",   'o', "FILE", 0,
+   "Output to FILE instead of standard output" },
+  { 0 }
+};
+
+/* Used by @code{main} to communicate with @code{parse_opt}.  */
+struct arguments
+{
+  char *args[2];               /* @var{arg1} & @var{arg2} */
+  int silent, verbose;
+  char *output_file;
+};
+
+/* Parse a single option.  */
+static error_t
+parse_opt (int key, char *arg, struct argp_state *state)
+{
+  /* Get the @var{input} argument from @code{argp_parse}, which we
+     know is a pointer to our arguments structure.  */
+  struct arguments *arguments = state->input;
+
+  switch (key)
+    {
+    case 'q': case 's':
+      arguments->silent = 1;
+      break;
+    case 'v':
+      arguments->verbose = 1;
+      break;
+    case 'o':
+      arguments->output_file = arg;
+      break;
+
+    case ARGP_KEY_ARG:
+      if (state->arg_num >= 2)
+       /* Too many arguments.  */
+       argp_usage (state);
+
+      arguments->args[state->arg_num] = arg;
+
+      break;
+
+    case ARGP_KEY_END:
+      if (state->arg_num < 2)
+       /* Not enough arguments.  */
+       argp_usage (state);
+      break;
+
+    default:
+      return ARGP_ERR_UNKNOWN;
+    }
+  return 0;
+}
+
+/* Our argp parser.  */
+static struct argp argp = { options, parse_opt, args_doc, doc };
+
+int main (int argc, char **argv)
+{
+  struct arguments arguments;
+
+  /* Default values.  */
+  arguments.silent = 0;
+  arguments.verbose = 0;
+  arguments.output_file = "-";
+
+  /* Parse our arguments; every option seen by @code{parse_opt} will
+     be reflected in @code{arguments}.  */
+  argp_parse (&argp, argc, argv, 0, 0, &arguments);
+
+  printf ("ARG1 = %s\nARG2 = %s\nOUTPUT_FILE = %s\n"
+         "VERBOSE = %s\nSILENT = %s\n",
+         arguments.args[0], arguments.args[1],
+         arguments.output_file,
+         arguments.verbose ? "yes" : "no",
+         arguments.silent ? "yes" : "no");
+
+  exit (0);
+}

+ 167 - 0
test/argp/argp-ex4.c

@@ -0,0 +1,167 @@
+/* Argp example #4 -- a program with somewhat more complicated options */
+
+/* This program uses the same features as example 3, but has more
+   options, and somewhat more structure in the -help output.  It
+   also shows how you can `steal' the remainder of the input
+   arguments past a certain point, for programs that accept a
+   list of items.  It also shows the special argp KEY value
+   ARGP_KEY_NO_ARGS, which is only given if no non-option
+   arguments were supplied to the program.
+
+   For structuring the help output, two features are used,
+   *headers* which are entries in the options vector with the
+   first four fields being zero, and a two part documentation
+   string (in the variable DOC), which allows documentation both
+   before and after the options; the two parts of DOC are
+   separated by a vertical-tab character ('\v', or '\013').  By
+   convention, the documentation before the options is just a
+   short string saying what the program does, and that afterwards
+   is longer, describing the behavior in more detail.  All
+   documentation strings are automatically filled for output,
+   although newlines may be included to force a line break at a
+   particular point.  All documentation strings are also passed to
+   the `gettext' function, for possible translation into the
+   current locale.  */
+
+#include <stdlib.h>
+#include <error.h>
+#include <argp.h>
+
+const char *argp_program_version =
+  "argp-ex4 1.0";
+const char *argp_program_bug_address =
+  "<bug-gnu-utils@@prep.ai.mit.edu>";
+
+/* Program documentation.  */
+static char doc[] =
+  "Argp example #4 -- a program with somewhat more complicated\
+options\
+\vThis part of the documentation comes *after* the options;\
+ note that the text is automatically filled, but it's possible\
+ to force a line-break, e.g.\n<-- here.";
+
+/* A description of the arguments we accept.  */
+static char args_doc[] = "ARG1 [STRING...]";
+
+/* Keys for options without short-options.  */
+#define OPT_ABORT  1           /* --abort */
+
+/* The options we understand.  */
+static struct argp_option options[] = {
+  {"verbose",  'v', 0,       0, "Produce verbose output" },
+  {"quiet",    'q', 0,       0, "Don't produce any output" },
+  {"silent",   's', 0,       OPTION_ALIAS },
+  {"output",   'o', "FILE",  0,
+   "Output to FILE instead of standard output" },
+
+  {0,0,0,0, "The following options should be grouped together:" },
+  {"repeat",   'r', "COUNT", OPTION_ARG_OPTIONAL,
+   "Repeat the output COUNT (default 10) times"},
+  {"abort",    OPT_ABORT, 0, 0, "Abort before showing any output"},
+
+  { 0 }
+};
+
+/* Used by @code{main} to communicate with @code{parse_opt}.  */
+struct arguments
+{
+  char *arg1;                  /* @var{arg1} */
+  char **strings;              /* [@var{string}@dots{}] */
+  int silent, verbose, abort;  /* @samp{-s}, @samp{-v}, @samp{--abort} */
+  char *output_file;           /* @var{file} arg to @samp{--output} */
+  int repeat_count;            /* @var{count} arg to @samp{--repeat} */
+};
+
+/* Parse a single option.  */
+static error_t
+parse_opt (int key, char *arg, struct argp_state *state)
+{
+  /* Get the @code{input} argument from @code{argp_parse}, which we
+     know is a pointer to our arguments structure.  */
+  struct arguments *arguments = state->input;
+
+  switch (key)
+    {
+    case 'q': case 's':
+      arguments->silent = 1;
+      break;
+    case 'v':
+      arguments->verbose = 1;
+      break;
+    case 'o':
+      arguments->output_file = arg;
+      break;
+    case 'r':
+      arguments->repeat_count = arg ? atoi (arg) : 10;
+      break;
+    case OPT_ABORT:
+      arguments->abort = 1;
+      break;
+
+    case ARGP_KEY_NO_ARGS:
+      argp_usage (state);
+
+    case ARGP_KEY_ARG:
+      /* Here we know that @code{state->arg_num == 0}, since we
+        force argument parsing to end before any more arguments can
+        get here.  */
+      arguments->arg1 = arg;
+
+      /* Now we consume all the rest of the arguments.
+        @code{state->next} is the index in @code{state->argv} of the
+        next argument to be parsed, which is the first @var{string}
+        we're interested in, so we can just use
+        @code{&state->argv[state->next]} as the value for
+        arguments->strings.
+
+        @emph{In addition}, by setting @code{state->next} to the end
+        of the arguments, we can force argp to stop parsing here and
+        return.  */
+      arguments->strings = &state->argv[state->next];
+      state->next = state->argc;
+
+      break;
+
+    default:
+      return ARGP_ERR_UNKNOWN;
+    }
+  return 0;
+}
+
+/* Our argp parser.  */
+static struct argp argp = { options, parse_opt, args_doc, doc };
+
+int main (int argc, char **argv)
+{
+  int i, j;
+  struct arguments arguments;
+
+  /* Default values.  */
+  arguments.silent = 0;
+  arguments.verbose = 0;
+  arguments.output_file = "-";
+  arguments.repeat_count = 1;
+  arguments.abort = 0;
+
+  /* Parse our arguments; every option seen by @code{parse_opt} will be
+     reflected in @code{arguments}.  */
+  argp_parse (&argp, argc, argv, 0, 0, &arguments);
+
+  if (arguments.abort)
+    error (10, 0, "ABORTED");
+
+  for (i = 0; i < arguments.repeat_count; i++)
+    {
+      printf ("ARG1 = %s\n", arguments.arg1);
+      printf ("STRINGS = ");
+      for (j = 0; arguments.strings[j]; j++)
+       printf (j == 0 ? "%s" : ", %s", arguments.strings[j]);
+      printf ("\n");
+      printf ("OUTPUT_FILE = %s\nVERBOSE = %s\nSILENT = %s\n",
+             arguments.output_file,
+             arguments.verbose ? "yes" : "no",
+             arguments.silent ? "yes" : "no");
+    }
+
+  exit (0);
+}

+ 208 - 0
test/argp/argp-test.c

@@ -0,0 +1,208 @@
+/* Test program for argp argument parser
+   Copyright (C) 1997 Free Software Foundation, Inc.
+   This file is part of the GNU C Library.
+   Written by Miles Bader <miles at gnu.ai.mit.edu>.
+
+   The GNU C Library is free software; you can redistribute it and/or
+   modify it under the terms of the GNU Lesser General Public
+   License as published by the Free Software Foundation; either
+   version 2.1 of the License, or (at your option) any later version.
+
+   The GNU C Library is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+   Lesser General Public License for more details.
+
+   You should have received a copy of the GNU Lesser General Public
+   License along with the GNU C Library; see the file COPYING.LIB.  If
+   not, see <http://www.gnu.org/licenses/>.  */
+
+#ifdef HAVE_CONFIG_H
+#include <config.h>
+#endif
+
+#include <stdlib.h>
+#include <time.h>
+#include <string.h>
+#include <argp.h>
+
+const char *argp_program_version = "argp-test 1.0";
+
+struct argp_option sub_options[] =
+{
+  {"subopt1",       's',     0,  0, "Nested option 1"},
+  {"subopt2",       'S',     0,  0, "Nested option 2"},
+
+  { 0, 0, 0, 0, "Some more nested options:", 10},
+  {"subopt3",       'p',     0,  0, "Nested option 3"},
+
+  {"subopt4",       'q',     0,  0, "Nested option 4", 1},
+
+  {0}
+};
+
+static const char sub_args_doc[] = "STRING...\n-";
+static const char sub_doc[] = "\vThis is the doc string from the sub-arg-parser.";
+
+static error_t
+sub_parse_opt (int key, char *arg, struct argp_state *state)
+{
+  switch (key)
+    {
+    case ARGP_KEY_NO_ARGS:
+      printf ("NO SUB ARGS\n");
+      break;
+    case ARGP_KEY_ARG:
+      printf ("SUB ARG: %s\n", arg);
+      break;
+
+    case 's' : case 'S': case 'p': case 'q':
+      printf ("SUB KEY %c\n", key);
+      break;
+
+    default:
+      return ARGP_ERR_UNKNOWN;
+    }
+  return 0;
+}
+
+static char *
+sub_help_filter (int key, const char *text, void *input)
+{
+  if (key == ARGP_KEY_HELP_EXTRA)
+    return strdup ("This is some extra text from the sub parser (note that it \
+is preceded by a blank line).");
+  else
+    return (char *)text;
+}
+
+static struct argp sub_argp = {
+  sub_options, sub_parse_opt, sub_args_doc, sub_doc, 0, sub_help_filter
+};
+
+/* Structure used to communicate with the parsing functions.  */
+struct params
+{
+  unsigned foonly;             /* Value parsed for foonly.  */
+  unsigned foonly_default;     /* Default value for it.  */
+};
+
+#define OPT_PGRP 1
+#define OPT_SESS 2
+
+struct argp_option options[] =
+{
+  {"pid",       'p',     "PID", 0, "List the process PID"},
+  {"pgrp",      OPT_PGRP,"PGRP",0, "List processes in the process group PGRP"},
+  {"no-parent", 'P',    0,     0, "Include processes without parents"},
+  {0,           'x',     0,     OPTION_ALIAS},
+  {"all-fields",'Q',     0,     0, "Don't elide unusable fields (normally"
+                                  " if there's some reason ps can't"
+                                  " print a field for any process, it's"
+                                  " removed from the output entirely)" },
+  {"reverse",   'r',    0,      0, "Reverse the order of any sort"},
+  {"gratuitously-long-reverse-option", 0, 0, OPTION_ALIAS},
+  {"session",  OPT_SESS,"SID",  OPTION_ARG_OPTIONAL,
+                                  "Add the processes from the session"
+                                  " SID (which defaults to the sid of"
+                                  " the current process)" },
+
+  {0,0,0,0, "Here are some more options:"},
+  {"foonly", 'f', "ZOT", OPTION_ARG_OPTIONAL, "Glork a foonly"},
+  {"zaza", 'z', 0, 0, "Snit a zar"},
+
+  {0}
+};
+
+static const char args_doc[] = "STRING";
+static const char doc[] = "Test program for argp."
+ "\vThis doc string comes after the options."
+ "\nHey!  Some manual formatting!"
+ "\nThe current time is: %s";
+
+static void
+popt (int key, char *arg)
+{
+  char buf[10];
+  if (isprint (key))
+    sprintf (buf, "%c", key);
+  else
+    sprintf (buf, "%d", key);
+  if (arg)
+    printf ("KEY %s: %s\n", buf, arg);
+  else
+    printf ("KEY %s\n", buf);
+}
+
+static error_t
+parse_opt (int key, char *arg, struct argp_state *state)
+{
+  struct params *params = state->input;
+
+  switch (key)
+    {
+    case ARGP_KEY_NO_ARGS:
+      printf ("NO ARGS\n");
+      break;
+
+    case ARGP_KEY_ARG:
+      if (state->arg_num > 0)
+       return ARGP_ERR_UNKNOWN; /* Leave it for the sub-arg parser.  */
+      printf ("ARG: %s\n", arg);
+      break;
+
+    case 'f':
+      if (arg)
+       params->foonly = atoi (arg);
+      else
+       params->foonly = params->foonly_default;
+      popt (key, arg);
+      break;
+
+    case 'p': case 'P': case OPT_PGRP: case 'x': case 'Q':
+    case 'r': case OPT_SESS: case 'z':
+      popt (key, arg);
+      break;
+
+    default:
+      return ARGP_ERR_UNKNOWN;
+    }
+  return 0;
+}
+
+static char *
+help_filter (int key, const char *text, void *input)
+{
+  char *new_text;
+  struct params *params = input;
+
+  if (key == ARGP_KEY_HELP_POST_DOC && text)
+    {
+      time_t now = time (0);
+      asprintf (&new_text, text, ctime (&now));
+    }
+  else if (key == 'f')
+    /* Show the default for the --foonly option.  */
+    asprintf (&new_text, "%s (ZOT defaults to %x)",
+             text, params->foonly_default);
+  else
+    new_text = (char *)text;
+
+  return new_text;
+}
+
+static struct argp_child argp_children[] = { { &sub_argp }, { 0 } };
+static struct argp argp = {
+  options, parse_opt, args_doc, doc, argp_children, help_filter
+};
+
+int
+main (int argc, char **argv)
+{
+  struct params params;
+  params.foonly = 0;
+  params.foonly_default = random ();
+  argp_parse (&argp, argc, argv, 0, 0, &params);
+  printf ("After parsing: foonly = %x\n", params.foonly);
+  return 0;
+}

+ 26 - 0
test/argp/bug-argp1.c

@@ -0,0 +1,26 @@
+#include <argp.h>
+
+
+static const struct argp_option test_options[] =
+{
+  { NULL, 'a', NULL, OPTION_DOC, NULL },
+  { NULL, 'b', NULL, OPTION_DOC, NULL },
+  { NULL, 0, NULL, 0, NULL }
+};
+
+static struct argp test_argp =
+{
+  test_options
+};
+
+
+static int
+do_test (int argc, char *argv[])
+{
+  int i;
+  argp_parse (&test_argp, argc, argv, 0, &i, NULL);
+  return 0;
+}
+
+#define TEST_FUNCTION do_test (argc, argv)
+#include "../test-skeleton.c"

+ 117 - 0
test/argp/tst-argp1.c

@@ -0,0 +1,117 @@
+/* Copyright (C) 2002, 2003 Free Software Foundation, Inc.
+   This file is part of the GNU C Library.
+   Contributed by Ulrich Drepper <drepper at redhat.com>, 2002.
+
+   The GNU C Library is free software; you can redistribute it and/or
+   modify it under the terms of the GNU Lesser General Public
+   License as published by the Free Software Foundation; either
+   version 2.1 of the License, or (at your option) any later version.
+
+   The GNU C Library is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+   Lesser General Public License for more details.
+
+   You should have received a copy of the GNU Lesser General Public
+   License along with the GNU C Library; see the file COPYING.LIB.  If
+   not, see <http://www.gnu.org/licenses/>.  */
+
+#include <argp.h>
+
+
+
+
+#define OPT_TO_THREAD          300
+#define OPT_TO_PROCESS         301
+#define OPT_SYNC_SIGNAL                302
+#define OPT_SYNC_JOIN          303
+#define OPT_TOPLEVEL           304
+
+
+static const struct argp_option test_options[] =
+  {
+    { NULL, 0, NULL, 0, "\
+This is a test for threads so we allow ther user to selection the number of \
+threads which are used at any one time.  Independently the total number of \
+rounds can be selected.  This is the total number of threads which will have \
+run when the process terminates:" },
+    { "threads", 't', "NUMBER", 0, "Number of threads used at once" },
+    { "starts", 's', "NUMBER", 0, "Total number of working threads" },
+    { "toplevel", OPT_TOPLEVEL, "NUMBER", 0,
+      "Number of toplevel threads which start the other threads; this \
+implies --sync-join" },
+
+    { NULL, 0, NULL, 0, "\
+Each thread can do one of two things: sleep or do work.  The latter is 100% \
+CPU bound.  The work load is the probability a thread does work.  All values \
+from zero to 100 (inclusive) are valid.  How often each thread repeats this \
+can be determined by the number of rounds.  The work cost determines how long \
+each work session (not sleeping) takes.  If it is zero a thread would \
+effectively nothing.  By setting the number of rounds to zero the thread \
+does no work at all and pure thread creation times can be measured." },
+    { "workload", 'w', "PERCENT", 0, "Percentage of time spent working" },
+    { "workcost", 'c', "NUMBER", 0,
+      "Factor in the cost of each round of working" },
+    { "rounds", 'r', "NUMBER", 0, "Number of rounds each thread runs" },
+
+    { NULL, 0, NULL, 0, "\
+There are a number of different methods how thread creation can be \
+synchronized.  Synchronization is necessary since the number of concurrently \
+running threads is limited." },
+    { "sync-signal", OPT_SYNC_SIGNAL, NULL, 0,
+      "Synchronize using a signal (default)" },
+    { "sync-join", OPT_SYNC_JOIN, NULL, 0, "Synchronize using pthread_join" },
+
+    { NULL, 0, NULL, 0, "\
+One parameter for each threads execution is the size of the stack.  If this \
+parameter is not used the system's default stack size is used.  If many \
+threads are used the stack size should be chosen quite small." },
+    { "stacksize", 'S', "BYTES", 0, "Size of threads stack" },
+    { "guardsize", 'g', "BYTES", 0,
+      "Size of stack guard area; must fit into the stack" },
+
+    { NULL, 0, NULL, 0, "Signal options:" },
+    { "to-thread", OPT_TO_THREAD, NULL, 0, "Send signal to main thread" },
+    { "to-process", OPT_TO_PROCESS, NULL, 0,
+      "Send signal to process (default)" },
+
+    { NULL, 0, NULL, 0, "Administrative options:" },
+    { "progress", 'p', NULL, 0, "Show signs of progress" },
+    { "timing", 'T', NULL, 0,
+      "Measure time from startup to the last thread finishing" },
+    { NULL, 0, NULL, 0, NULL }
+  };
+
+/* Prototype for option handler.  */
+static error_t parse_opt (int key, char *arg, struct argp_state *state);
+
+/* Data structure to communicate with argp functions.  */
+static struct argp argp =
+{
+  test_options, parse_opt
+};
+
+
+static int
+do_test (void)
+{
+  int argc = 2;
+  char *argv[3] = { (char *) "tst-argp1", (char *) "--help", NULL };
+  int remaining;
+
+  /* Parse and process arguments.  */
+  argp_parse (&argp, argc, argv, 0, &remaining, NULL);
+
+  return 0;
+}
+
+
+/* Handle program arguments.  */
+static error_t
+parse_opt (int key, char *arg, struct argp_state *state)
+{
+  return ARGP_ERR_UNKNOWN;
+}
+
+#define TEST_FUNCTION do_test ()
+#include "../test-skeleton.c"

+ 100 - 0
test/argp/tst-argp2.c

@@ -0,0 +1,100 @@
+/* Copyright (C) 2007 Free Software Foundation, Inc.
+   This file is part of the GNU C Library.
+   Contributed by Jakub Jelinek <jakub at redhat.com>, 2007.
+
+   The GNU C Library is free software; you can redistribute it and/or
+   modify it under the terms of the GNU Lesser General Public
+   License as published by the Free Software Foundation; either
+   version 2.1 of the License, or (at your option) any later version.
+
+   The GNU C Library is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+   Lesser General Public License for more details.
+
+   You should have received a copy of the GNU Lesser General Public
+   License along with the GNU C Library; see the file COPYING.LIB.  If
+   not, see <http://www.gnu.org/licenses/>.  */
+
+#include <argp.h>
+
+static const struct argp_option opt1[] =
+  {
+    { "opt1", '1', "NUMBER", 0, "Option 1" },
+    { NULL, 0, NULL, 0, NULL }
+  };
+
+static const struct argp_option opt2[] =
+  {
+    { "opt2", '2', "NUMBER", 0, "Option 2" },
+    { NULL, 0, NULL, 0, NULL }
+  };
+
+static const struct argp_option opt3[] =
+  {
+    { "opt3", '3', "NUMBER", 0, "Option 3" },
+    { NULL, 0, NULL, 0, NULL }
+  };
+
+static const struct argp_option opt4[] =
+  {
+    { "opt4", '4', "NUMBER", 0, "Option 4" },
+    { NULL, 0, NULL, 0, NULL }
+  };
+
+static const struct argp_option opt5[] =
+  {
+    { "opt5", '5', "NUMBER", 0, "Option 5" },
+    { NULL, 0, NULL, 0, NULL }
+  };
+
+static struct argp argp5 =
+  {
+    opt5, NULL, "args doc5", "doc5", NULL, NULL, NULL
+  };
+
+static struct argp argp4 =
+  {
+    opt4, NULL, "args doc4", "doc4", NULL, NULL, NULL
+  };
+
+static struct argp argp3 =
+  {
+    opt3, NULL, "args doc3", "doc3", NULL, NULL, NULL
+  };
+
+static struct argp_child children2[] =
+  {
+    { &argp4, 0, "child3", 3 },
+    { &argp5, 0, "child4", 4 },
+    { NULL, 0, NULL, 0 }
+  };
+
+static struct argp argp2 =
+  {
+    opt2, NULL, "args doc2", "doc2", children2, NULL, NULL
+  };
+
+static struct argp_child children1[] =
+  {
+    { &argp2, 0, "child1", 1 },
+    { &argp3, 0, "child2", 2 },
+    { NULL, 0, NULL, 0 }
+  };
+
+static struct argp argp1 =
+  {
+    opt1, NULL, "args doc1", "doc1", children1, NULL, NULL
+  };
+
+
+static int
+do_test (void)
+{
+  argp_help (&argp1, stdout, ARGP_HELP_LONG, (char *) "tst-argp2");
+  return 0;
+}
+
+
+#define TEST_FUNCTION do_test ()
+#include "../test-skeleton.c"

+ 8 - 0
test/args/Makefile

@@ -0,0 +1,8 @@
+# uClibc args tests
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+
+top_builddir=../../
+top_srcdir=../../
+include ../Rules.mak
+-include Makefile.in
+include ../Test.mak

+ 9 - 0
test/args/Makefile.in

@@ -0,0 +1,9 @@
+# uClibc args tests
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+
+OPTS_arg_test = a b c d e f g h
+WRAPPER_arg_test = \
+	env -i \
+	ENVVAR=123 \
+	SOMETHING=sldajfasdf \
+	BLAHBLAH=" hi hi "

+ 40 - 0
test/args/arg_test.c

@@ -0,0 +1,40 @@
+/* vi: set sw=4 ts=4: */
+/*
+ * Test application for argc and argv handling
+ * Copyright (C) 2000-2006 by Erik Andersen <andersen@uclibc.org>
+ *
+ * Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+
+int main(int argc, char **argv)
+{
+	int i=0;
+	char** index=__environ;
+
+#ifdef __powerpc__
+	{
+		unsigned long sp;
+		sp = (unsigned long) __builtin_frame_address(0);
+		if(sp&0xf){
+			printf("stack pointer is unaligned! (%08lx)\n", sp);
+		}
+	}
+#endif
+
+	printf("argc=%d\n", argc);
+
+	for(i=0;i<argc;i++) {
+		printf("argv[%d]='%s'\n", i, argv[i]);
+	}
+
+	i=0;
+	while(*index) {
+		printf("environ[%d]='%s'\n", i++, *index++);
+	}
+
+	exit(0);
+}

+ 13 - 0
test/args/arg_test.out.good

@@ -0,0 +1,13 @@
+argc=9
+argv[0]='./arg_test'
+argv[1]='a'
+argv[2]='b'
+argv[3]='c'
+argv[4]='d'
+argv[5]='e'
+argv[6]='f'
+argv[7]='g'
+argv[8]='h'
+environ[0]='ENVVAR=123'
+environ[1]='SOMETHING=sldajfasdf'
+environ[2]='BLAHBLAH= hi hi '

+ 13 - 0
test/args/arg_test_glibc.out.good

@@ -0,0 +1,13 @@
+argc=9
+argv[0]='./arg_test_glibc'
+argv[1]='a'
+argv[2]='b'
+argv[3]='c'
+argv[4]='d'
+argv[5]='e'
+argv[6]='f'
+argv[7]='g'
+argv[8]='h'
+environ[0]='ENVVAR=123'
+environ[1]='SOMETHING=sldajfasdf'
+environ[2]='BLAHBLAH= hi hi '

+ 8 - 0
test/assert/Makefile

@@ -0,0 +1,8 @@
+# uClibc assert tests
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+
+top_builddir=../../
+top_srcdir=../../
+include ../Rules.mak
+-include Makefile.in
+include ../Test.mak

+ 5 - 0
test/assert/Makefile.in

@@ -0,0 +1,5 @@
+# uClibc assert tests
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+
+RET_assert     := 134
+WRAPPER_assert := trap ":" ABRT ;

+ 47 - 0
test/assert/assert.c

@@ -0,0 +1,47 @@
+/* vi: set sw=4 ts=4: */
+/*
+ * Test application for functions defined in ctype.h
+ * Copyright (C) 2000-2006 by Erik Andersen <andersen@uclibc.org>
+ *
+ * Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+ */
+
+#undef NDEBUG
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <assert.h>
+#include <signal.h>
+#include "../testsuite.h"
+
+int got_abort;
+
+static void aborthandler(int junk)
+{
+	got_abort = 1;
+}
+
+int main(int argc, char *argv[])
+{
+	signal(SIGABRT, aborthandler);
+
+	init_testsuite("Testing functions defined in assert.h:\n\t");
+
+	got_abort=0;
+	assert(0 == 0);
+	TEST_NUMERIC(got_abort, 0);
+
+#define NDEBUG
+	got_abort = 0;
+	printf("Don't worry -- This next test is supposed to print an assert message:\n");
+	fprintf(stderr, "\t");
+	assert(0 == 1);
+	TEST_NUMERIC(got_abort, 0);
+
+#undef NDEBUG
+	got_abort = 0;
+	assert(0 == 1);
+	TEST_NUMERIC(got_abort, 1);
+
+	exit(0);
+}

+ 8 - 0
test/build/Makefile

@@ -0,0 +1,8 @@
+# uClibc build tests
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+
+top_builddir=../../
+top_srcdir=../../
+include ../Rules.mak
+-include Makefile.in
+include ../Test.mak

+ 21 - 0
test/build/check_config_options.sh

@@ -0,0 +1,21 @@
+#!/bin/sh
+
+ret=0
+
+# Make sure nothing uses the ARCH_HAS_MMU option anymore
+result=$(
+find ../.. \
+	| grep -v \
+		-e include/bits/uClibc_config.h \
+		-e /test/ \
+		-e /.svn/ \
+	| xargs grep -sHI \
+		__ARCH_HAS_MMU__
+)
+if [ -n "$result" ] ; then
+	echo "The build system is incorrectly using ARCH_HAS_MMU:"
+	echo "$result"
+	ret=1
+fi
+
+exit $ret

+ 8 - 0
test/crypt/Makefile

@@ -0,0 +1,8 @@
+# uClibc crypt tests
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+
+top_builddir=../../
+top_srcdir=../../
+include ../Rules.mak
+-include Makefile.in
+include ../Test.mak

+ 15 - 0
test/crypt/Makefile.in

@@ -0,0 +1,15 @@
+# uClibc crypt tests
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+
+EXTRA_LDFLAGS := -lcrypt
+
+OPTS_crypt = < crypt.input
+
+ifneq ($(UCLIBC_HAS_SHA512_CRYPT_IMPL),y)
+TESTS_DISABLED += sha512c-test
+endif
+ifneq ($(UCLIBC_HAS_SHA256_CRYPT_IMPL),y)
+TESTS_DISABLED += sha256c-test
+endif
+
+WRAPPER := env TIMEOUTFACTOR=50

+ 103 - 0
test/crypt/crypt.c

@@ -0,0 +1,103 @@
+
+/*
+ * This crypt(3) validation program shipped with UFC-crypt
+ * is derived from one distributed with Phil Karns PD DES package.
+ *
+ * @(#)cert.c	1.8 11 Aug 1996
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include "crypt.h"
+
+static int totfails = 0;
+
+static void good_bye (void) __attribute__ ((noreturn));
+static void good_bye (void)
+{
+  if(totfails == 0) {
+    printf("Passed DES validation suite\n");
+    exit(0);
+  } else {
+    printf("%d failures during DES validation suite!!!\n", totfails);
+    exit(1);
+  }
+}
+
+static void get8(char *cp)
+{
+	int i,j,t;
+
+	for(i=0;i<8;i++){
+		scanf("%2x",&t);
+		if(feof(stdin))
+		  good_bye();
+		for(j=0; j<8 ; j++) {
+		  *cp++ = (t & (0x01 << (7-j))) != 0;
+		}
+	}
+}
+
+static void put8(char *cp)
+{
+	int i,j,t;
+
+	for(i=0;i<8;i++){
+	  t = 0;
+	  for(j = 0; j<8; j++)
+	    t = (t<<1) | *cp++;
+	  printf("%02x", t);
+	}
+}
+
+int main(void)
+{
+	char key[64],plain[64],cipher[64],answer[64];
+	int i;
+	int test;
+	int fail;
+
+	for(test=0;!feof(stdin);test++){
+
+		get8(key);
+		printf(" K: "); put8(key);
+		setkey(key);
+
+		get8(plain);
+		printf(" P: "); put8(plain);
+
+		get8(answer);
+		printf(" C: "); put8(answer);
+
+		for(i=0;i<64;i++)
+			cipher[i] = plain[i];
+		encrypt(cipher, 0);
+
+		for(i=0;i<64;i++) {
+			if(cipher[i] != answer[i])
+				break;
+		}
+		fail = 0;
+		if(i != 64){
+			printf(" Encrypt FAIL");
+			fail++; totfails++;
+		}
+
+		encrypt(cipher, 1);
+
+		for(i=0;i<64;i++)
+			if(cipher[i] != plain[i])
+				break;
+		if(i != 64){
+			printf(" Decrypt FAIL");
+			fail++; totfails++;
+		}
+
+		if(fail == 0)
+			printf(" OK");
+		printf("\n");
+	}
+	good_bye();
+}
+
+

+ 171 - 0
test/crypt/crypt.input

@@ -0,0 +1,171 @@
+0101010101010101 95f8a5e5dd31d900 8000000000000000
+0101010101010101 dd7f121ca5015619 4000000000000000
+0101010101010101 2e8653104f3834ea 2000000000000000
+0101010101010101 4bd388ff6cd81d4f 1000000000000000
+0101010101010101 20b9e767b2fb1456 0800000000000000
+0101010101010101 55579380d77138ef 0400000000000000
+0101010101010101 6cc5defaaf04512f 0200000000000000
+0101010101010101 0d9f279ba5d87260 0100000000000000
+0101010101010101 d9031b0271bd5a0a 0080000000000000
+0101010101010101 424250b37c3dd951 0040000000000000
+0101010101010101 b8061b7ecd9a21e5 0020000000000000
+0101010101010101 f15d0f286b65bd28 0010000000000000
+0101010101010101 add0cc8d6e5deba1 0008000000000000
+0101010101010101 e6d5f82752ad63d1 0004000000000000
+0101010101010101 ecbfe3bd3f591a5e 0002000000000000
+0101010101010101 f356834379d165cd 0001000000000000
+0101010101010101 2b9f982f20037fa9 0000800000000000
+0101010101010101 889de068a16f0be6 0000400000000000
+0101010101010101 e19e275d846a1298 0000200000000000
+0101010101010101 329a8ed523d71aec 0000100000000000
+0101010101010101 e7fce22557d23c97 0000080000000000
+0101010101010101 12a9f5817ff2d65d 0000040000000000
+0101010101010101 a484c3ad38dc9c19 0000020000000000
+0101010101010101 fbe00a8a1ef8ad72 0000010000000000
+0101010101010101 750d079407521363 0000008000000000
+0101010101010101 64feed9c724c2faf 0000004000000000
+0101010101010101 f02b263b328e2b60 0000002000000000
+0101010101010101 9d64555a9a10b852 0000001000000000
+0101010101010101 d106ff0bed5255d7 0000000800000000
+0101010101010101 e1652c6b138c64a5 0000000400000000
+0101010101010101 e428581186ec8f46 0000000200000000
+0101010101010101 aeb5f5ede22d1a36 0000000100000000
+0101010101010101 e943d7568aec0c5c 0000000080000000
+0101010101010101 df98c8276f54b04b 0000000040000000
+0101010101010101 b160e4680f6c696f 0000000020000000
+0101010101010101 fa0752b07d9c4ab8 0000000010000000
+0101010101010101 ca3a2b036dbc8502 0000000008000000
+0101010101010101 5e0905517bb59bcf 0000000004000000
+0101010101010101 814eeb3b91d90726 0000000002000000
+0101010101010101 4d49db1532919c9f 0000000001000000
+0101010101010101 25eb5fc3f8cf0621 0000000000800000
+0101010101010101 ab6a20c0620d1c6f 0000000000400000
+0101010101010101 79e90dbc98f92cca 0000000000200000
+0101010101010101 866ecedd8072bb0e 0000000000100000
+0101010101010101 8b54536f2f3e64a8 0000000000080000
+0101010101010101 ea51d3975595b86b 0000000000040000
+0101010101010101 caffc6ac4542de31 0000000000020000
+0101010101010101 8dd45a2ddf90796c 0000000000010000
+0101010101010101 1029d55e880ec2d0 0000000000008000
+0101010101010101 5d86cb23639dbea9 0000000000004000
+0101010101010101 1d1ca853ae7c0c5f 0000000000002000
+0101010101010101 ce332329248f3228 0000000000001000
+0101010101010101 8405d1abe24fb942 0000000000000800
+0101010101010101 e643d78090ca4207 0000000000000400
+0101010101010101 48221b9937748a23 0000000000000200
+0101010101010101 dd7c0bbd61fafd54 0000000000000100
+0101010101010101 2fbc291a570db5c4 0000000000000080
+0101010101010101 e07c30d7e4e26e12 0000000000000040
+0101010101010101 0953e2258e8e90a1 0000000000000020
+0101010101010101 5b711bc4ceebf2ee 0000000000000010
+0101010101010101 cc083f1e6d9e85f6 0000000000000008
+0101010101010101 d2fd8867d50d2dfe 0000000000000004
+0101010101010101 06e7ea22ce92708f 0000000000000002
+0101010101010101 166b40b44aba4bd6 0000000000000001
+8001010101010101 0000000000000000 95a8d72813daa94d
+4001010101010101 0000000000000000 0eec1487dd8c26d5
+2001010101010101 0000000000000000 7ad16ffb79c45926
+1001010101010101 0000000000000000 d3746294ca6a6cf3
+0801010101010101 0000000000000000 809f5f873c1fd761
+0401010101010101 0000000000000000 c02faffec989d1fc
+0201010101010101 0000000000000000 4615aa1d33e72f10
+0180010101010101 0000000000000000 2055123350c00858
+0140010101010101 0000000000000000 df3b99d6577397c8
+0120010101010101 0000000000000000 31fe17369b5288c9
+0110010101010101 0000000000000000 dfdd3cc64dae1642
+0108010101010101 0000000000000000 178c83ce2b399d94
+0104010101010101 0000000000000000 50f636324a9b7f80
+0102010101010101 0000000000000000 a8468ee3bc18f06d
+0101800101010101 0000000000000000 a2dc9e92fd3cde92
+0101400101010101 0000000000000000 cac09f797d031287
+0101200101010101 0000000000000000 90ba680b22aeb525
+0101100101010101 0000000000000000 ce7a24f350e280b6
+0101080101010101 0000000000000000 882bff0aa01a0b87
+0101040101010101 0000000000000000 25610288924511c2
+0101020101010101 0000000000000000 c71516c29c75d170
+0101018001010101 0000000000000000 5199c29a52c9f059
+0101014001010101 0000000000000000 c22f0a294a71f29f
+0101012001010101 0000000000000000 ee371483714c02ea
+0101011001010101 0000000000000000 a81fbd448f9e522f
+0101010801010101 0000000000000000 4f644c92e192dfed
+0101010401010101 0000000000000000 1afa9a66a6df92ae
+0101010201010101 0000000000000000 b3c1cc715cb879d8
+0101010180010101 0000000000000000 19d032e64ab0bd8b
+0101010140010101 0000000000000000 3cfaa7a7dc8720dc
+0101010120010101 0000000000000000 b7265f7f447ac6f3
+0101010110010101 0000000000000000 9db73b3c0d163f54
+0101010108010101 0000000000000000 8181b65babf4a975
+0101010104010101 0000000000000000 93c9b64042eaa240
+0101010102010101 0000000000000000 5570530829705592
+0101010101800101 0000000000000000 8638809e878787a0
+0101010101400101 0000000000000000 41b9a79af79ac208
+0101010101200101 0000000000000000 7a9be42f2009a892
+0101010101100101 0000000000000000 29038d56ba6d2745
+0101010101080101 0000000000000000 5495c6abf1e5df51
+0101010101040101 0000000000000000 ae13dbd561488933
+0101010101020101 0000000000000000 024d1ffa8904e389
+0101010101018001 0000000000000000 d1399712f99bf02e
+0101010101014001 0000000000000000 14c1d7c1cffec79e
+0101010101012001 0000000000000000 1de5279dae3bed6f
+0101010101011001 0000000000000000 e941a33f85501303
+0101010101010801 0000000000000000 da99dbbc9a03f379
+0101010101010401 0000000000000000 b7fc92f91d8e92e9
+0101010101010201 0000000000000000 ae8e5caa3ca04e85
+0101010101010180 0000000000000000 9cc62df43b6eed74
+0101010101010140 0000000000000000 d863dbb5c59a91a0
+0101010101010120 0000000000000000 a1ab2190545b91d7
+0101010101010110 0000000000000000 0875041e64c570f7
+0101010101010108 0000000000000000 5a594528bebef1cc
+0101010101010104 0000000000000000 fcdb3291de21f0c0
+0101010101010102 0000000000000000 869efd7f9f265a09
+1046913489980131 0000000000000000 88d55e54f54c97b4
+1007103489988020 0000000000000000 0c0cc00c83ea48fd
+10071034c8980120 0000000000000000 83bc8ef3a6570183
+1046103489988020 0000000000000000 df725dcad94ea2e9
+1086911519190101 0000000000000000 e652b53b550be8b0
+1086911519580101 0000000000000000 af527120c485cbb0
+5107b01519580101 0000000000000000 0f04ce393db926d5
+1007b01519190101 0000000000000000 c9f00ffc74079067
+3107915498080101 0000000000000000 7cfd82a593252b4e
+3107919498080101 0000000000000000 cb49a2f9e91363e3
+10079115b9080140 0000000000000000 00b588be70d23f56
+3107911598080140 0000000000000000 406a9a6ab43399ae
+1007d01589980101 0000000000000000 6cb773611dca9ada
+9107911589980101 0000000000000000 67fd21c17dbb5d70
+9107d01589190101 0000000000000000 9592cb4110430787
+1007d01598980120 0000000000000000 a6b7ff68a318ddd3
+1007940498190101 0000000000000000 4d102196c914ca16
+0107910491190401 0000000000000000 2dfa9f4573594965
+0107910491190101 0000000000000000 b46604816c0e0774
+0107940491190401 0000000000000000 6e7e6221a4f34e87
+19079210981a0101 0000000000000000 aa85e74643233199
+1007911998190801 0000000000000000 2e5a19db4d1962d6
+10079119981a0801 0000000000000000 23a866a809d30894
+1007921098190101 0000000000000000 d812d961f017d320
+100791159819010b 0000000000000000 055605816e58608f
+1004801598190101 0000000000000000 abd88e8b1b7716f1
+1004801598190102 0000000000000000 537ac95be69da1e1
+1004801598190108 0000000000000000 aed0f6ae3c25cdd8
+1002911598100104 0000000000000000 b3e35a5ee53e7b8d
+1002911598190104 0000000000000000 61c79c71921a2ef8
+1002911598100201 0000000000000000 e2f5728f0995013c
+1002911698100101 0000000000000000 1aeac39a61f0a464
+7ca110454a1a6e57 01a1d6d039776742 690f5b0d9a26939b
+0131d9619dc1376e 5cd54ca83def57da 7a389d10354bd271
+07a1133e4a0b2686 0248d43806f67172 868ebb51cab4599a
+3849674c2602319e 51454b582ddf440a 7178876e01f19b2a
+04b915ba43feb5b6 42fd443059577fa2 af37fb421f8c4095
+0113b970fd34f2ce 059b5e0851cf143a 86a560f10ec6d85b
+0170f175468fb5e6 0756d8e0774761d2 0cd3da020021dc09
+43297fad38e373fe 762514b829bf486a ea676b2cb7db2b7a
+07a7137045da2a16 3bdd119049372802 dfd64a815caf1a0f
+04689104c2fd3b2f 26955f6835af609a 5c513c9c4886c088
+37d06bb516cb7546 164d5e404f275232 0a2aeeae3ff4ab77
+1f08260d1ac2465e 6b056e18759f5cca ef1bf03e5dfa575a
+584023641aba6176 004bd6ef09176062 88bf0db6d70dee56
+025816164629b007 480d39006ee762f2 a1f9915541020b56
+49793ebc79b3258f 437540c8698f3cfa 6fbf1cafcffd0556
+4fb05e1515ab73a7 072d43a077075292 2f22e49bab7ca1ac
+49e95d6d4ca229bf 02fe55778117f12a 5a6b612cc26cce4a
+018310dc409b26d6 1d9d5c5018f728c2 5f4c038ed12b2e41
+1c587f1c13924fef 305532286d6f295a 63fac0d034d9f793

+ 172 - 0
test/crypt/crypt.out.good

@@ -0,0 +1,172 @@
+ K: 0101010101010101 P: 95f8a5e5dd31d900 C: 8000000000000000 OK
+ K: 0101010101010101 P: dd7f121ca5015619 C: 4000000000000000 OK
+ K: 0101010101010101 P: 2e8653104f3834ea C: 2000000000000000 OK
+ K: 0101010101010101 P: 4bd388ff6cd81d4f C: 1000000000000000 OK
+ K: 0101010101010101 P: 20b9e767b2fb1456 C: 0800000000000000 OK
+ K: 0101010101010101 P: 55579380d77138ef C: 0400000000000000 OK
+ K: 0101010101010101 P: 6cc5defaaf04512f C: 0200000000000000 OK
+ K: 0101010101010101 P: 0d9f279ba5d87260 C: 0100000000000000 OK
+ K: 0101010101010101 P: d9031b0271bd5a0a C: 0080000000000000 OK
+ K: 0101010101010101 P: 424250b37c3dd951 C: 0040000000000000 OK
+ K: 0101010101010101 P: b8061b7ecd9a21e5 C: 0020000000000000 OK
+ K: 0101010101010101 P: f15d0f286b65bd28 C: 0010000000000000 OK
+ K: 0101010101010101 P: add0cc8d6e5deba1 C: 0008000000000000 OK
+ K: 0101010101010101 P: e6d5f82752ad63d1 C: 0004000000000000 OK
+ K: 0101010101010101 P: ecbfe3bd3f591a5e C: 0002000000000000 OK
+ K: 0101010101010101 P: f356834379d165cd C: 0001000000000000 OK
+ K: 0101010101010101 P: 2b9f982f20037fa9 C: 0000800000000000 OK
+ K: 0101010101010101 P: 889de068a16f0be6 C: 0000400000000000 OK
+ K: 0101010101010101 P: e19e275d846a1298 C: 0000200000000000 OK
+ K: 0101010101010101 P: 329a8ed523d71aec C: 0000100000000000 OK
+ K: 0101010101010101 P: e7fce22557d23c97 C: 0000080000000000 OK
+ K: 0101010101010101 P: 12a9f5817ff2d65d C: 0000040000000000 OK
+ K: 0101010101010101 P: a484c3ad38dc9c19 C: 0000020000000000 OK
+ K: 0101010101010101 P: fbe00a8a1ef8ad72 C: 0000010000000000 OK
+ K: 0101010101010101 P: 750d079407521363 C: 0000008000000000 OK
+ K: 0101010101010101 P: 64feed9c724c2faf C: 0000004000000000 OK
+ K: 0101010101010101 P: f02b263b328e2b60 C: 0000002000000000 OK
+ K: 0101010101010101 P: 9d64555a9a10b852 C: 0000001000000000 OK
+ K: 0101010101010101 P: d106ff0bed5255d7 C: 0000000800000000 OK
+ K: 0101010101010101 P: e1652c6b138c64a5 C: 0000000400000000 OK
+ K: 0101010101010101 P: e428581186ec8f46 C: 0000000200000000 OK
+ K: 0101010101010101 P: aeb5f5ede22d1a36 C: 0000000100000000 OK
+ K: 0101010101010101 P: e943d7568aec0c5c C: 0000000080000000 OK
+ K: 0101010101010101 P: df98c8276f54b04b C: 0000000040000000 OK
+ K: 0101010101010101 P: b160e4680f6c696f C: 0000000020000000 OK
+ K: 0101010101010101 P: fa0752b07d9c4ab8 C: 0000000010000000 OK
+ K: 0101010101010101 P: ca3a2b036dbc8502 C: 0000000008000000 OK
+ K: 0101010101010101 P: 5e0905517bb59bcf C: 0000000004000000 OK
+ K: 0101010101010101 P: 814eeb3b91d90726 C: 0000000002000000 OK
+ K: 0101010101010101 P: 4d49db1532919c9f C: 0000000001000000 OK
+ K: 0101010101010101 P: 25eb5fc3f8cf0621 C: 0000000000800000 OK
+ K: 0101010101010101 P: ab6a20c0620d1c6f C: 0000000000400000 OK
+ K: 0101010101010101 P: 79e90dbc98f92cca C: 0000000000200000 OK
+ K: 0101010101010101 P: 866ecedd8072bb0e C: 0000000000100000 OK
+ K: 0101010101010101 P: 8b54536f2f3e64a8 C: 0000000000080000 OK
+ K: 0101010101010101 P: ea51d3975595b86b C: 0000000000040000 OK
+ K: 0101010101010101 P: caffc6ac4542de31 C: 0000000000020000 OK
+ K: 0101010101010101 P: 8dd45a2ddf90796c C: 0000000000010000 OK
+ K: 0101010101010101 P: 1029d55e880ec2d0 C: 0000000000008000 OK
+ K: 0101010101010101 P: 5d86cb23639dbea9 C: 0000000000004000 OK
+ K: 0101010101010101 P: 1d1ca853ae7c0c5f C: 0000000000002000 OK
+ K: 0101010101010101 P: ce332329248f3228 C: 0000000000001000 OK
+ K: 0101010101010101 P: 8405d1abe24fb942 C: 0000000000000800 OK
+ K: 0101010101010101 P: e643d78090ca4207 C: 0000000000000400 OK
+ K: 0101010101010101 P: 48221b9937748a23 C: 0000000000000200 OK
+ K: 0101010101010101 P: dd7c0bbd61fafd54 C: 0000000000000100 OK
+ K: 0101010101010101 P: 2fbc291a570db5c4 C: 0000000000000080 OK
+ K: 0101010101010101 P: e07c30d7e4e26e12 C: 0000000000000040 OK
+ K: 0101010101010101 P: 0953e2258e8e90a1 C: 0000000000000020 OK
+ K: 0101010101010101 P: 5b711bc4ceebf2ee C: 0000000000000010 OK
+ K: 0101010101010101 P: cc083f1e6d9e85f6 C: 0000000000000008 OK
+ K: 0101010101010101 P: d2fd8867d50d2dfe C: 0000000000000004 OK
+ K: 0101010101010101 P: 06e7ea22ce92708f C: 0000000000000002 OK
+ K: 0101010101010101 P: 166b40b44aba4bd6 C: 0000000000000001 OK
+ K: 8001010101010101 P: 0000000000000000 C: 95a8d72813daa94d OK
+ K: 4001010101010101 P: 0000000000000000 C: 0eec1487dd8c26d5 OK
+ K: 2001010101010101 P: 0000000000000000 C: 7ad16ffb79c45926 OK
+ K: 1001010101010101 P: 0000000000000000 C: d3746294ca6a6cf3 OK
+ K: 0801010101010101 P: 0000000000000000 C: 809f5f873c1fd761 OK
+ K: 0401010101010101 P: 0000000000000000 C: c02faffec989d1fc OK
+ K: 0201010101010101 P: 0000000000000000 C: 4615aa1d33e72f10 OK
+ K: 0180010101010101 P: 0000000000000000 C: 2055123350c00858 OK
+ K: 0140010101010101 P: 0000000000000000 C: df3b99d6577397c8 OK
+ K: 0120010101010101 P: 0000000000000000 C: 31fe17369b5288c9 OK
+ K: 0110010101010101 P: 0000000000000000 C: dfdd3cc64dae1642 OK
+ K: 0108010101010101 P: 0000000000000000 C: 178c83ce2b399d94 OK
+ K: 0104010101010101 P: 0000000000000000 C: 50f636324a9b7f80 OK
+ K: 0102010101010101 P: 0000000000000000 C: a8468ee3bc18f06d OK
+ K: 0101800101010101 P: 0000000000000000 C: a2dc9e92fd3cde92 OK
+ K: 0101400101010101 P: 0000000000000000 C: cac09f797d031287 OK
+ K: 0101200101010101 P: 0000000000000000 C: 90ba680b22aeb525 OK
+ K: 0101100101010101 P: 0000000000000000 C: ce7a24f350e280b6 OK
+ K: 0101080101010101 P: 0000000000000000 C: 882bff0aa01a0b87 OK
+ K: 0101040101010101 P: 0000000000000000 C: 25610288924511c2 OK
+ K: 0101020101010101 P: 0000000000000000 C: c71516c29c75d170 OK
+ K: 0101018001010101 P: 0000000000000000 C: 5199c29a52c9f059 OK
+ K: 0101014001010101 P: 0000000000000000 C: c22f0a294a71f29f OK
+ K: 0101012001010101 P: 0000000000000000 C: ee371483714c02ea OK
+ K: 0101011001010101 P: 0000000000000000 C: a81fbd448f9e522f OK
+ K: 0101010801010101 P: 0000000000000000 C: 4f644c92e192dfed OK
+ K: 0101010401010101 P: 0000000000000000 C: 1afa9a66a6df92ae OK
+ K: 0101010201010101 P: 0000000000000000 C: b3c1cc715cb879d8 OK
+ K: 0101010180010101 P: 0000000000000000 C: 19d032e64ab0bd8b OK
+ K: 0101010140010101 P: 0000000000000000 C: 3cfaa7a7dc8720dc OK
+ K: 0101010120010101 P: 0000000000000000 C: b7265f7f447ac6f3 OK
+ K: 0101010110010101 P: 0000000000000000 C: 9db73b3c0d163f54 OK
+ K: 0101010108010101 P: 0000000000000000 C: 8181b65babf4a975 OK
+ K: 0101010104010101 P: 0000000000000000 C: 93c9b64042eaa240 OK
+ K: 0101010102010101 P: 0000000000000000 C: 5570530829705592 OK
+ K: 0101010101800101 P: 0000000000000000 C: 8638809e878787a0 OK
+ K: 0101010101400101 P: 0000000000000000 C: 41b9a79af79ac208 OK
+ K: 0101010101200101 P: 0000000000000000 C: 7a9be42f2009a892 OK
+ K: 0101010101100101 P: 0000000000000000 C: 29038d56ba6d2745 OK
+ K: 0101010101080101 P: 0000000000000000 C: 5495c6abf1e5df51 OK
+ K: 0101010101040101 P: 0000000000000000 C: ae13dbd561488933 OK
+ K: 0101010101020101 P: 0000000000000000 C: 024d1ffa8904e389 OK
+ K: 0101010101018001 P: 0000000000000000 C: d1399712f99bf02e OK
+ K: 0101010101014001 P: 0000000000000000 C: 14c1d7c1cffec79e OK
+ K: 0101010101012001 P: 0000000000000000 C: 1de5279dae3bed6f OK
+ K: 0101010101011001 P: 0000000000000000 C: e941a33f85501303 OK
+ K: 0101010101010801 P: 0000000000000000 C: da99dbbc9a03f379 OK
+ K: 0101010101010401 P: 0000000000000000 C: b7fc92f91d8e92e9 OK
+ K: 0101010101010201 P: 0000000000000000 C: ae8e5caa3ca04e85 OK
+ K: 0101010101010180 P: 0000000000000000 C: 9cc62df43b6eed74 OK
+ K: 0101010101010140 P: 0000000000000000 C: d863dbb5c59a91a0 OK
+ K: 0101010101010120 P: 0000000000000000 C: a1ab2190545b91d7 OK
+ K: 0101010101010110 P: 0000000000000000 C: 0875041e64c570f7 OK
+ K: 0101010101010108 P: 0000000000000000 C: 5a594528bebef1cc OK
+ K: 0101010101010104 P: 0000000000000000 C: fcdb3291de21f0c0 OK
+ K: 0101010101010102 P: 0000000000000000 C: 869efd7f9f265a09 OK
+ K: 1046913489980131 P: 0000000000000000 C: 88d55e54f54c97b4 OK
+ K: 1007103489988020 P: 0000000000000000 C: 0c0cc00c83ea48fd OK
+ K: 10071034c8980120 P: 0000000000000000 C: 83bc8ef3a6570183 OK
+ K: 1046103489988020 P: 0000000000000000 C: df725dcad94ea2e9 OK
+ K: 1086911519190101 P: 0000000000000000 C: e652b53b550be8b0 OK
+ K: 1086911519580101 P: 0000000000000000 C: af527120c485cbb0 OK
+ K: 5107b01519580101 P: 0000000000000000 C: 0f04ce393db926d5 OK
+ K: 1007b01519190101 P: 0000000000000000 C: c9f00ffc74079067 OK
+ K: 3107915498080101 P: 0000000000000000 C: 7cfd82a593252b4e OK
+ K: 3107919498080101 P: 0000000000000000 C: cb49a2f9e91363e3 OK
+ K: 10079115b9080140 P: 0000000000000000 C: 00b588be70d23f56 OK
+ K: 3107911598080140 P: 0000000000000000 C: 406a9a6ab43399ae OK
+ K: 1007d01589980101 P: 0000000000000000 C: 6cb773611dca9ada OK
+ K: 9107911589980101 P: 0000000000000000 C: 67fd21c17dbb5d70 OK
+ K: 9107d01589190101 P: 0000000000000000 C: 9592cb4110430787 OK
+ K: 1007d01598980120 P: 0000000000000000 C: a6b7ff68a318ddd3 OK
+ K: 1007940498190101 P: 0000000000000000 C: 4d102196c914ca16 OK
+ K: 0107910491190401 P: 0000000000000000 C: 2dfa9f4573594965 OK
+ K: 0107910491190101 P: 0000000000000000 C: b46604816c0e0774 OK
+ K: 0107940491190401 P: 0000000000000000 C: 6e7e6221a4f34e87 OK
+ K: 19079210981a0101 P: 0000000000000000 C: aa85e74643233199 OK
+ K: 1007911998190801 P: 0000000000000000 C: 2e5a19db4d1962d6 OK
+ K: 10079119981a0801 P: 0000000000000000 C: 23a866a809d30894 OK
+ K: 1007921098190101 P: 0000000000000000 C: d812d961f017d320 OK
+ K: 100791159819010b P: 0000000000000000 C: 055605816e58608f OK
+ K: 1004801598190101 P: 0000000000000000 C: abd88e8b1b7716f1 OK
+ K: 1004801598190102 P: 0000000000000000 C: 537ac95be69da1e1 OK
+ K: 1004801598190108 P: 0000000000000000 C: aed0f6ae3c25cdd8 OK
+ K: 1002911598100104 P: 0000000000000000 C: b3e35a5ee53e7b8d OK
+ K: 1002911598190104 P: 0000000000000000 C: 61c79c71921a2ef8 OK
+ K: 1002911598100201 P: 0000000000000000 C: e2f5728f0995013c OK
+ K: 1002911698100101 P: 0000000000000000 C: 1aeac39a61f0a464 OK
+ K: 7ca110454a1a6e57 P: 01a1d6d039776742 C: 690f5b0d9a26939b OK
+ K: 0131d9619dc1376e P: 5cd54ca83def57da C: 7a389d10354bd271 OK
+ K: 07a1133e4a0b2686 P: 0248d43806f67172 C: 868ebb51cab4599a OK
+ K: 3849674c2602319e P: 51454b582ddf440a C: 7178876e01f19b2a OK
+ K: 04b915ba43feb5b6 P: 42fd443059577fa2 C: af37fb421f8c4095 OK
+ K: 0113b970fd34f2ce P: 059b5e0851cf143a C: 86a560f10ec6d85b OK
+ K: 0170f175468fb5e6 P: 0756d8e0774761d2 C: 0cd3da020021dc09 OK
+ K: 43297fad38e373fe P: 762514b829bf486a C: ea676b2cb7db2b7a OK
+ K: 07a7137045da2a16 P: 3bdd119049372802 C: dfd64a815caf1a0f OK
+ K: 04689104c2fd3b2f P: 26955f6835af609a C: 5c513c9c4886c088 OK
+ K: 37d06bb516cb7546 P: 164d5e404f275232 C: 0a2aeeae3ff4ab77 OK
+ K: 1f08260d1ac2465e P: 6b056e18759f5cca C: ef1bf03e5dfa575a OK
+ K: 584023641aba6176 P: 004bd6ef09176062 C: 88bf0db6d70dee56 OK
+ K: 025816164629b007 P: 480d39006ee762f2 C: a1f9915541020b56 OK
+ K: 49793ebc79b3258f P: 437540c8698f3cfa C: 6fbf1cafcffd0556 OK
+ K: 4fb05e1515ab73a7 P: 072d43a077075292 C: 2f22e49bab7ca1ac OK
+ K: 49e95d6d4ca229bf P: 02fe55778117f12a C: 5a6b612cc26cce4a OK
+ K: 018310dc409b26d6 P: 1d9d5c5018f728c2 C: 5f4c038ed12b2e41 OK
+ K: 1c587f1c13924fef P: 305532286d6f295a C: 63fac0d034d9f793 OK
+Passed DES validation suite

+ 19 - 0
test/crypt/md5c-test.c

@@ -0,0 +1,19 @@
+#include <stdlib.h>
+#include <stdio.h>
+#include <string.h>
+#include <crypt.h>
+
+int
+main (int argc, char *argv[])
+{
+  const char salt[] = "$1$saltstring";
+  char *cp;
+
+  cp = crypt ("Hello world!", salt);
+  if (strcmp ("$1$saltstri$YMyguxXMBpd2TEZ.vS/3q1", cp)) {
+      fprintf(stderr, "Failed md5 crypt test!\n");
+      return EXIT_FAILURE;
+  }
+  fprintf(stderr, "Passed md5 crypt test!\n");
+  return EXIT_SUCCESS;
+}

+ 62 - 0
test/crypt/sha256c-test.c

@@ -0,0 +1,62 @@
+#include <crypt.h>
+#include <stdio.h>
+#include <string.h>
+
+static const struct
+{
+  const char *salt;
+  const char *input;
+  const char *expected;
+} tests[] =
+{
+  { "$5$saltstring", "Hello world!",
+    "$5$saltstring$5B8vYYiY.CVt1RlTTf8KbXBH3hsxY/GNooZaBBGWEc5" },
+  { "$5$rounds=10000$saltstringsaltstring", "Hello world!",
+    "$5$rounds=10000$saltstringsaltst$3xv.VbSHBb41AL9AvLeujZkZRBAwqFMz2."
+    "opqey6IcA" },
+  { "$5$rounds=5000$toolongsaltstring", "This is just a test",
+    "$5$rounds=5000$toolongsaltstrin$Un/5jzAHMgOGZ5.mWJpuVolil07guHPvOW8"
+    "mGRcvxa5" },
+  { "$5$rounds=1400$anotherlongsaltstring",
+    "a very much longer text to encrypt.  This one even stretches over more"
+    "than one line.",
+    "$5$rounds=1400$anotherlongsalts$Rx.j8H.h8HjEDGomFU8bDkXm3XIUnzyxf12"
+    "oP84Bnq1" },
+  { "$5$rounds=77777$short",
+    "we have a short salt string but not a short password",
+    "$5$rounds=77777$short$JiO1O3ZpDAxGJeaDIuqCoEFysAe1mZNJRs3pw0KQRd/" },
+  { "$5$rounds=123456$asaltof16chars..", "a short string",
+    "$5$rounds=123456$asaltof16chars..$gP3VQ/6X7UUEW3HkBn2w1/Ptq2jxPyzV/"
+    "cZKmF/wJvD" },
+  { "$5$rounds=10$roundstoolow", "the minimum number is still observed",
+    "$5$rounds=1000$roundstoolow$yfvwcWrQ8l/K0DAWyuPMDNHpIVlTQebY9l/gL97"
+    "2bIC" },
+};
+#define ntests (sizeof (tests) / sizeof (tests[0]))
+
+
+
+static int
+do_test (void)
+{
+  int result = 0;
+  int i;
+
+  for (i = 0; i < ntests; ++i)
+    {
+      char *cp = crypt (tests[i].input, tests[i].salt);
+
+      if (strcmp (cp, tests[i].expected) != 0)
+	{
+	  printf ("test %d: expected \"%s\", got \"%s\"\n",
+		  i, tests[i].expected, cp);
+	  result = 1;
+	}
+    }
+
+  return result;
+}
+
+#define TIMEOUT 6
+#define TEST_FUNCTION do_test ()
+#include "../test-skeleton.c"

+ 63 - 0
test/crypt/sha512c-test.c

@@ -0,0 +1,63 @@
+#include <crypt.h>
+#include <stdio.h>
+#include <string.h>
+
+static const struct
+{
+  const char *salt;
+  const char *input;
+  const char *expected;
+} tests[] =
+{
+  { "$6$saltstring", "Hello world!",
+    "$6$saltstring$svn8UoSVapNtMuq1ukKS4tPQd8iKwSMHWjl/O817G3uBnIFNjnQJu"
+    "esI68u4OTLiBFdcbYEdFCoEOfaS35inz1" },
+  { "$6$rounds=10000$saltstringsaltstring", "Hello world!",
+    "$6$rounds=10000$saltstringsaltst$OW1/O6BYHV6BcXZu8QVeXbDWra3Oeqh0sb"
+    "HbbMCVNSnCM/UrjmM0Dp8vOuZeHBy/YTBmSK6H9qs/y3RnOaw5v." },
+  { "$6$rounds=5000$toolongsaltstring", "This is just a test",
+    "$6$rounds=5000$toolongsaltstrin$lQ8jolhgVRVhY4b5pZKaysCLi0QBxGoNeKQ"
+    "zQ3glMhwllF7oGDZxUhx1yxdYcz/e1JSbq3y6JMxxl8audkUEm0" },
+  { "$6$rounds=1400$anotherlongsaltstring",
+    "a very much longer text to encrypt.  This one even stretches over more"
+    "than one line.",
+    "$6$rounds=1400$anotherlongsalts$POfYwTEok97VWcjxIiSOjiykti.o/pQs.wP"
+    "vMxQ6Fm7I6IoYN3CmLs66x9t0oSwbtEW7o7UmJEiDwGqd8p4ur1" },
+  { "$6$rounds=77777$short",
+    "we have a short salt string but not a short password",
+    "$6$rounds=77777$short$WuQyW2YR.hBNpjjRhpYD/ifIw05xdfeEyQoMxIXbkvr0g"
+    "ge1a1x3yRULJ5CCaUeOxFmtlcGZelFl5CxtgfiAc0" },
+  { "$6$rounds=123456$asaltof16chars..", "a short string",
+    "$6$rounds=123456$asaltof16chars..$BtCwjqMJGx5hrJhZywWvt0RLE8uZ4oPwc"
+    "elCjmw2kSYu.Ec6ycULevoBK25fs2xXgMNrCzIMVcgEJAstJeonj1" },
+  { "$6$rounds=10$roundstoolow", "the minimum number is still observed",
+    "$6$rounds=1000$roundstoolow$kUMsbe306n21p9R.FRkW3IGn.S9NPN0x50YhH1x"
+    "hLsPuWGsUSklZt58jaTfF4ZEQpyUNGc0dqbpBYYBaHHrsX." },
+};
+#define ntests (sizeof (tests) / sizeof (tests[0]))
+
+
+static int
+do_test (void)
+{
+  int result = 0;
+  int i;
+
+  for (i = 0; i < ntests; ++i)
+    {
+      char *cp = crypt (tests[i].input, tests[i].salt);
+
+      if (strcmp (cp, tests[i].expected) != 0)
+	{
+	  printf ("test %d: expected \"%s\", got \"%s\"\n",
+		  i, tests[i].expected, cp);
+	  result = 1;
+	}
+    }
+
+  return result;
+}
+
+#define TIMEOUT 6
+#define TEST_FUNCTION do_test ()
+#include "../test-skeleton.c"

+ 8 - 0
test/ctype/Makefile

@@ -0,0 +1,8 @@
+# uClibc ctype tests
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+
+top_builddir=../../
+top_srcdir=../../
+include ../Rules.mak
+-include Makefile.in
+include ../Test.mak

+ 4 - 0
test/ctype/Makefile.in

@@ -0,0 +1,4 @@
+# uClibc ctype tests
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+
+TESTS := ctype

+ 250 - 0
test/ctype/ctype.c

@@ -0,0 +1,250 @@
+/* vi: set sw=4 ts=4: */
+/*
+ * Test application for functions defined in ctype.h
+ * Copyright (C) 2000-2006 by Erik Andersen <andersen@uclibc.org>
+ *
+ * Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <stdarg.h>
+#include <ctype.h>
+#include "../testsuite.h"
+
+
+int main( int argc, char **argv)
+{
+	int i, c;
+
+
+    init_testsuite("Testing functions defined in ctype.h\n");
+
+	/* isalnum() */
+	{
+		int buffer[]={ '1', '4', 'a', 'z', 'A', 'Z', '5', -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( isalnum(c)!=0);
+		}
+	}
+	{
+		int buffer[]={  2, 128, 254, '\n', -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( isalnum(c)==0);
+		}
+	}
+
+
+
+	/* isalpha() */
+	{
+		int buffer[]={ 'a', 'z', 'A', 'Z', -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( isalpha(c)!=0);
+		}
+	}
+	{
+		int buffer[]={  2, 63, 128, 254, '\n', -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( isalpha(c)==0);
+		}
+	}
+
+
+
+#ifdef __UCLIBC_SUSV4_LEGACY__
+	/* isascii() */
+	{
+		int buffer[]={ 'a', 'z', 'A', 'Z', '\n', -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( isascii(c)!=0);
+		}
+	}
+	{
+		int buffer[]={  128, 254, -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( isascii(c)==0);
+		}
+	}
+#endif
+
+
+	/* iscntrl() */
+	{
+		int buffer[]={ 0x7F, 6, '\t', '\n', 0x7F, -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( iscntrl(c)!=0);
+		}
+	}
+	{
+		int buffer[]={  63, 128, 254, -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( iscntrl(c)==0);
+		}
+	}
+
+
+	/* isdigit() */
+	{
+		int buffer[]={ '1', '5', '7', '9', -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( isdigit(c)!=0);
+		}
+	}
+	{
+		int buffer[]={  2, 'a', 'z', 'A', 'Z', 63, 128, 254, '\n', -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( isdigit(c)==0);
+		}
+	}
+
+
+
+	/* isgraph() */
+	{
+		int buffer[]={ ')', '~', '9', -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( isgraph(c)!=0);
+		}
+	}
+	{
+		int buffer[]={ 9, ' ', '\t', '\n', 200, 0x7F, -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( isgraph(c)==0);
+		}
+	}
+
+
+	/* islower() */
+	{
+		int buffer[]={ 'a', 'g', 'z', -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( islower(c)!=0);
+		}
+	}
+	{
+		int buffer[]={ 9, 'A', 'Z', 128, 254, ' ', '\t', '\n', 0x7F, -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( islower(c)==0);
+		}
+	}
+
+
+	/* isprint() */
+	{
+		int buffer[]={ ' ', ')', '~', '9', -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( isprint(c)!=0);
+		}
+	}
+	{
+		int buffer[]={ '\b', '\t', '\n', 9, 128, 254, 200, 0x7F, -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( isprint(c)==0);
+		}
+	}
+
+
+	/* ispunct() */
+	{
+		int buffer[]={ '.', '#', '@', ';', -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( ispunct(c)!=0);
+		}
+	}
+	{
+		int buffer[]={  2, 'a', 'Z', '1', 128, 254, '\n', -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( ispunct(c)==0);
+		}
+	}
+
+
+	/* isspace() */
+	{
+		int buffer[]={ ' ', '\t', '\r', '\v', '\n', -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( isspace(c)!=0);
+		}
+	}
+	{
+		int buffer[]={  2, 'a', 'Z', '1', 128, 254, -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( isspace(c)==0);
+		}
+	}
+
+
+	/* isupper() */
+	{
+		int buffer[]={ 'A', 'G', 'Z', -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( isupper(c)!=0);
+		}
+	}
+	{
+		int buffer[]={  2, 'a', 'z', '1', 128, 254, -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( isupper(c)==0);
+		}
+	}
+
+
+
+	/* isxdigit() */
+	{
+		int buffer[]={ 'f', 'A', '1', '8', -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( isxdigit(c)!=0);
+		}
+	}
+	{
+		int buffer[]={  2, 'g', 'G', 'x', '\n', -1};
+		for(i=0; buffer[i]!=-1; i++) {
+			c = buffer[i];
+			TEST( isxdigit(c)==0);
+		}
+	}
+
+
+	/* tolower() */
+	c='A';
+	TEST_NUMERIC( tolower(c), 'a');
+	c='a';
+	TEST_NUMERIC( tolower(c), 'a');
+	c='#';
+	TEST_NUMERIC( tolower(c), c);
+
+	/* toupper() */
+	c='a';
+	TEST_NUMERIC( toupper(c), 'A');
+	c='A';
+	TEST_NUMERIC( toupper(c), 'A');
+	c='#';
+	TEST_NUMERIC( toupper(c), c);
+
+	exit(0);
+}

+ 8 - 0
test/dlopen/Makefile

@@ -0,0 +1,8 @@
+# uClibc dlopen tests
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+
+top_builddir=../../
+top_srcdir=../../
+include ../Rules.mak
+-include Makefile.in
+include ../Test.mak

+ 84 - 0
test/dlopen/Makefile.in

@@ -0,0 +1,84 @@
+# uClibc dlopen tests
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+
+# rules need a little love to work with glibc ...
+export UCLIBC_ONLY := 1
+
+TESTS := dltest dltest2 dlstatic test1 test2 test3 dlundef dlafk dladdr \
+	testscope nodelete nodelete1 tst-origin
+
+ifneq ($(HAVE_SHARED),y)
+TESTS_DISABLED := test3
+LDFLAGS_libtest.so := -lpthread
+endif
+
+CFLAGS_dltest    := -DLIBNAME="\"./libtest.so\""
+CFLAGS_dltest2   := -DLIBNAME="\"./libtest3.so\""
+
+LDFLAGS_dlstatic := -ldl
+LDFLAGS_dltest   := -ldl
+LDFLAGS_dltest2  := -ldl
+LDFLAGS_dlundef  := -ldl
+LDFLAGS_dlafk    := -ldl ./libafk.so -Wl,-rpath,.
+LDFLAGS_test1    := -ldl
+LDFLAGS_test2    := -ldl
+LDFLAGS_test3    := -ldl ./libtest1.so ./libtest2.so -Wl,-rpath,.
+LDFLAGS_dladdr   := -ldl
+LDFLAGS_testscope:= -ldl
+LDFLAGS_tst-origin:= -ldl -Wl,-rpath,\$$ORIGIN/testlib
+
+DEBUG_LIBS := X
+WRAPPER := env $(DEBUG_LIBS)=all LD_LIBRARY_PATH="$$PWD:.:$(LD_LIBRARY_PATH)"
+
+testlib:
+	@mkdir $@
+
+testlib/libtest31.so: libtest3.so | testlib
+	@cp $^ $@
+
+EXTRA_DIRS := testlib
+
+# Build libC.so without -mprefergot compilation flag to force a
+# R_SH_JMP_SLOT relocation instead of R_SH_GLOB_DAT for _libC_fini. This is
+# needed to resolve the _libC_fini symbol when used (by libC.so destructor),
+# whereas with GLOB_DAT relocation the resolution happens in the GOT entry
+# when the libC is loaded, for the same reason remove also the "-z now"
+# linker flag.
+# These are needed to spot the issue test case want raise.
+
+ifeq ($(TARGET_ARCH),sh)
+CFLAGS-OMIT-libC.c = -mprefergot
+endif
+LDFLAGS-OMIT-libC.c = -Wl,-z,now
+
+dltest: libtest.so
+dltest2: libtest3.so
+dlstatic: libstatic.so
+dlundef: libundef.so
+dlafk: libafk.so
+testscope:libA.so
+libafk.so: libafk-temp.so
+LDFLAGS_libafk.so := ./libafk-temp.so -Wl,-rpath,.
+test1: libtest1.so
+test2: libtest1.so libtest2.so
+test3: libtest1.so libtest2.so
+tst-origin: testlib/libtest31.so
+libtest1.so: libtest2.so
+libB.so: libC.so
+libA.so: libB.so
+LDFLAGS_libtest.so := -lpthread
+LDFLAGS_libtest1.so := ./libtest2.so -Wl,-rpath,.
+LDFLAGS_libtest2.so := -Wl,-rpath,.
+LDFLAGS_libtest3.so := -lpthread -Wl,-rpath,.
+LDFLAGS_libC.so := -ldl
+LDFLAGS_libB.so := ./libC.so -Wl,-rpath,.
+LDFLAGS_libA.so := ./libB.so -Wl,-rpath,.
+
+nodelete: nodelmod1.so nodelmod2.so nodelmod3.so
+nodelmod3.so: nodelmod4.so
+LDFLAGS_nodelete := -rdynamic -ldl
+LDFLAGS_nodelmod1.so := -Wl,-z,nodelete
+LDFLAGS_nodelmod3.so := ./nodelmod4.so
+LDFLAGS_nodelmod4.so := -Wl,-z,nodelete
+nodelete1: nodelmod1.so nodelmod2.so
+LDFLAGS_nodelete1 := -rdynamic -ldl

+ 25 - 0
test/dlopen/dladdr.c

@@ -0,0 +1,25 @@
+#include <dlfcn.h>
+#include <stdlib.h>
+#include <stdio.h>
+#include <string.h>
+
+int main(int argc, char **argv)
+{
+	Dl_info info;
+	int res = 0;
+
+	memset(&info, '\0', sizeof(Dl_info));
+	res = dladdr((void *)1, &info);
+	if (res != 0) {
+		fprintf(stderr, "dladdr() should fail\n");
+		fprintf(stderr, "dli_fname = %s\n", info.dli_fname);
+		fprintf(stderr, "dli_fbase = 0x%08x\n", (unsigned int)info.dli_fbase);
+		fprintf(stderr, "dli_sname = %s\n", info.dli_sname);
+		fprintf(stderr, "dli_saddr = 0x%08x\n", (unsigned int)info.dli_saddr);
+		exit(1);
+        }
+
+	fprintf(stderr, "dladdr() failed as expected\n");
+	return EXIT_SUCCESS;
+}
+

+ 36 - 0
test/dlopen/dlafk.c

@@ -0,0 +1,36 @@
+#include <fcntl.h>
+#include <stdlib.h>
+#include <stdio.h>
+#include <dlfcn.h>
+#include <stdint.h>
+#include <unistd.h>
+#include <errno.h>
+#include <string.h>
+
+#define LIBNAME "libafk.so"
+
+#define LIBAFK "libafk-temp.so"
+#define LIBAFK_BAK ".libafk-temp.so.temp"
+
+int main(int argc, char **argv)
+{
+	void *handle;
+
+	if (rename(LIBAFK, LIBAFK_BAK)) {
+		fprintf(stderr, "Unable to rename %s: %s\n", LIBAFK, strerror(errno));
+		return EXIT_FAILURE;
+	}
+
+	handle = dlopen(LIBNAME, RTLD_NOW);
+	if (!handle) {
+		fprintf(stderr, "Could not open ./%s: %s\n", LIBNAME, dlerror());
+		return EXIT_FAILURE;
+	}
+
+	if (rename(LIBAFK_BAK, LIBAFK)) {
+		fprintf(stderr, "Unable to rename %s: %s\n", LIBAFK_BAK, strerror(errno));
+		return EXIT_FAILURE;
+	}
+
+	return EXIT_SUCCESS;
+}

+ 43 - 0
test/dlopen/dlstatic.c

@@ -0,0 +1,43 @@
+#include <fcntl.h>
+#include <stdlib.h>
+#include <stdio.h>
+#include <dlfcn.h>
+#include <stdint.h>
+
+#define LIBNAME "libstatic.so"
+
+int load_and_test(void)
+{
+	void *handle;
+	int (*mystatic)(void);
+
+	handle = dlopen(LIBNAME, RTLD_LAZY);
+	if (!handle) {
+		fprintf(stderr, "Could not open ./%s: %s\n", LIBNAME, dlerror());
+		return 1;
+	}
+
+	mystatic = dlsym(handle, "static_test");
+	if (mystatic == NULL) {
+		fprintf(stderr, "Could not locate symbol 'static_test': %s\n", dlerror());
+		return 1;
+	}
+
+	if (!mystatic()) {
+		fprintf(stderr, "mystatic() failed: static vars were not setup properly\n");
+		return 1;
+	}
+
+	dlclose(handle);
+
+	return 0;
+}
+
+int main(int argc, char **argv)
+{
+	int count = 5;
+	while (count-- > 0)
+		if (load_and_test())
+			return EXIT_FAILURE;
+	return EXIT_SUCCESS;
+}

+ 41 - 0
test/dlopen/dltest.c

@@ -0,0 +1,41 @@
+#include <fcntl.h>
+#include <stdlib.h>
+#include <stdio.h>
+#include <dlfcn.h>
+#include <stdint.h>
+
+int main(int argc, char **argv)
+{
+	int ret = EXIT_SUCCESS;
+	void *handle;
+	void (*mydltest)(void *value1, void *value2);
+	char *error;
+	uint32_t *value1, *value2;
+
+	handle = dlopen (LIBNAME, RTLD_LAZY);
+	if (!handle) {
+		fprintf(stderr, "Could not open ./%s: %s\n", LIBNAME, dlerror());
+		exit(1);
+	}
+
+	mydltest = dlsym(handle, "dltest");
+	if ((error = dlerror()) != NULL)  {
+		fprintf(stderr, "Could not locate symbol 'dltest': %s\n", error);
+		exit(1);
+	}
+
+	mydltest(&value1, &value2);
+	printf("dltest: pthread_once=%p\n", value1);
+	printf("dltest: pthread_self=%p\n", value2);
+	if (value1 == value2) {
+	    ret = EXIT_FAILURE;
+	    printf("dltest: values should NOT be equal  Weak values resolved incorrectly!\n");
+	} else {
+	    printf("dltest: weak symbols resolved correctly.\n");
+	}
+
+	dlclose(handle);
+
+	return ret;
+}
+

+ 1 - 0
test/dlopen/dltest2.c

@@ -0,0 +1 @@
+#include "dltest.c"

+ 29 - 0
test/dlopen/dlundef.c

@@ -0,0 +1,29 @@
+#include <fcntl.h>
+#include <stdlib.h>
+#include <stdio.h>
+#include <dlfcn.h>
+#include <stdint.h>
+
+#define LIBNAME "libundef.so"
+
+int main(int argc, char **argv)
+{
+	void *handle;
+	int (*myundefined)(void);
+
+	handle = dlopen(LIBNAME, RTLD_LAZY);
+	if (!handle) {
+		fprintf(stderr, "Could not open ./%s: %s\n", LIBNAME, dlerror());
+		return EXIT_FAILURE;
+	}
+
+	myundefined = dlsym(handle, "__booga_booga_you_cant_touch_this__");
+	if (myundefined != NULL) {
+		fprintf(stderr, "dlsym() found a symbol that does not exist!\n");
+		return EXIT_FAILURE;
+	}
+
+	dlclose(handle);
+
+	return EXIT_SUCCESS;
+}

+ 7 - 0
test/dlopen/libA.c

@@ -0,0 +1,7 @@
+extern void libB_func(void);
+
+void libA_func(void);
+void libA_func(void)
+{
+	libB_func();
+}

+ 7 - 0
test/dlopen/libB.c

@@ -0,0 +1,7 @@
+extern void libC_func(void);
+
+void libB_func(void);
+void libB_func(void)
+{
+	libC_func();
+}

+ 30 - 0
test/dlopen/libC.c

@@ -0,0 +1,30 @@
+#include <dlfcn.h>
+#include <stdio.h>
+#include <stdlib.h>
+
+#define LIBNAME "libB.so"
+void _libC_fini(void);
+void _libC_fini(void)
+{
+	printf("libC_fini():finish - atexit()\n");
+}
+
+void libC_fini(void);
+void libC_fini(void)
+{
+	_libC_fini();
+}
+
+void libC_func(void);
+void libC_func(void)
+{
+	void *libB;
+
+	libB = dlopen(LIBNAME, RTLD_LAZY);
+	if (!libB) {
+		fprintf(stderr, "Could not open ./%s: %s\n", LIBNAME, dlerror());
+		exit(1);
+	}
+
+	atexit(libC_fini);
+}

+ 1 - 0
test/dlopen/libafk-temp.c

@@ -0,0 +1 @@
+/* the actual contents doesnt matter */

+ 1 - 0
test/dlopen/libafk.c

@@ -0,0 +1 @@
+/* the actual contents doesnt matter */

+ 15 - 0
test/dlopen/libstatic.c

@@ -0,0 +1,15 @@
+#include <stdio.h>
+
+static int global_static = -1;
+
+int static_test(void)
+{
+	static int local_static = -2;
+
+	if (global_static != -1)
+		printf("FAIL: global_static is not -1\n");
+	if (local_static != -2)
+		printf("FAIL: local_static is not -2\n");
+
+	return (global_static == -1 && local_static == -2);
+}

+ 11 - 0
test/dlopen/libtest.c

@@ -0,0 +1,11 @@
+#include <stdio.h>
+#include <pthread.h>
+#include <stdint.h>
+
+void dltest(uint32_t **value1, uint32_t **value2);
+void dltest(uint32_t **value1, uint32_t **value2)
+{
+	*value1 = (uint32_t *) pthread_once;
+	*value2 = (uint32_t *) pthread_self;
+}
+

+ 40 - 0
test/dlopen/libtest1.c

@@ -0,0 +1,40 @@
+#include <stdio.h>
+
+extern int libtest2_func(const char *s);
+
+void __attribute__((constructor)) libtest1_ctor(void);
+void libtest1_ctor(void)
+{
+    printf("libtest1: constructor!\n");
+}
+
+void __attribute__((destructor)) libtest1_dtor(void);
+void libtest1_dtor(void)
+{
+    printf("libtest1: destructor!\n");
+}
+
+void __attribute__((weak)) function1(void);
+void function1(void)
+{
+    printf("libtest1: I am weak function1!\n");
+}
+
+void function2(void);
+void function2(void)
+{
+    printf("libtest1: I am function2!\n");
+}
+
+int dltest(const char *s);
+int dltest(const char *s)
+{
+    printf( "libtest1: function1 = %p\n"
+	    "libtest1: function2 = %p\n",
+	    function1, function2);
+    function1();
+    function2();
+    return(libtest2_func(s));
+}
+
+

+ 38 - 0
test/dlopen/libtest2.c

@@ -0,0 +1,38 @@
+#include <stdio.h>
+#include <pthread.h>
+
+void __attribute__((constructor)) libtest2_ctor(void);
+void libtest2_ctor(void)
+{
+    printf("libtest2: constructor!\n");
+}
+
+void __attribute__((destructor)) libtest2_dtor(void);
+void libtest2_dtor(void)
+{
+    printf("libtest2: destructor!\n");
+}
+
+void function1(void);
+void function1(void)
+{
+    printf("libtest2: I am function1!\n");
+}
+
+void __attribute__((weak)) function2(void);
+void function2(void)
+{
+    printf("libtest2: I am weak function2!\n");
+}
+
+
+int libtest2_func(const char *s);
+int libtest2_func(const char *s)
+{
+    printf( "libtest2: function1 = %p\n"
+	    "libtest2: function2 = %p\n",
+	    function1, function2);
+    function1();
+    function2();
+    return 0;
+}

+ 1 - 0
test/dlopen/libtest3.c

@@ -0,0 +1 @@
+#include "libtest.c"

+ 1 - 0
test/dlopen/libundef.c

@@ -0,0 +1 @@
+/* the actual contents doesnt matter */

+ 205 - 0
test/dlopen/nodelete.c

@@ -0,0 +1,205 @@
+#include <dlfcn.h>
+#include <setjmp.h>
+#include <signal.h>
+#include <stdio.h>
+#include <stdlib.h>
+
+
+static sigjmp_buf jmpbuf;
+
+
+int fini_ran;
+
+
+static void
+__attribute__ ((noreturn))
+handler (int sig)
+{
+  siglongjmp (jmpbuf, 1);
+}
+
+
+#define TEST_FUNCTION do_test ()
+static int
+do_test (void)
+{
+  /* We are testing the two possibilities to mark an object as not deletable:
+     - marked on the linker commandline with `-z nodelete'
+     - with the RTLD_NODELETE flag at dlopen()-time.
+
+     The test we are performing should be safe.  We are loading the objects,
+     get the address of variables in the respective object, unload the object
+     and then try to read the variable.  If the object is unloaded this
+     should lead to an segmentation fault.  */
+  void *p;
+  struct sigaction sa;
+
+  sa.sa_handler = handler;
+  sigfillset (&sa.sa_mask);
+  sa.sa_flags = SA_RESTART;
+
+  if (sigaction (SIGSEGV, &sa, NULL) == -1)
+    puts ("cannot install signal handler: %m");
+
+  p = dlopen ("nodelmod1.so", RTLD_LAZY);
+  if (p == NULL)
+    {
+      printf ("failed to load \"nodelmod1.so\": %s\n", dlerror ());
+      exit (1);
+    }
+  else
+    {
+      int *varp;
+
+      varp = dlsym (p, "var1");
+      if (varp == NULL)
+	{
+	  puts ("failed to get address of \"var1\" in \"nodelmod1.so\"");
+	  exit (1);
+	}
+      else
+	{
+	  *varp = 20000720;
+
+	  /* Now close the object.  */
+	  fini_ran = 0;
+	  if (dlclose (p) != 0)
+	    {
+	      puts ("failed to close \"nodelmod1.so\"");
+	      exit (1);
+	    }
+	  else if (! sigsetjmp (jmpbuf, 1))
+	    {
+	      /* Access the variable again.  */
+	      if (*varp != 20000720)
+		{
+		  puts ("\"var1\" value not correct");
+		  exit (1);
+		}
+	      else if (fini_ran != 0)
+		{
+		  puts ("destructor of \"nodelmod1.so\" ran");
+		  exit (1);
+		}
+	      else
+		puts ("-z nodelete test succeeded");
+	    }
+	  else
+	    {
+	      /* We caught an segmentation fault.  */
+	      puts ("\"nodelmod1.so\" got deleted!");
+	      exit (1);
+	    }
+	}
+    }
+
+  p = dlopen ("nodelmod2.so", RTLD_LAZY | RTLD_NODELETE);
+  if (p == NULL)
+    {
+      printf ("failed to load \"nodelmod2.so\": %s\n", dlerror ());
+      exit (1);
+    }
+  else
+    {
+      int *varp;
+
+      varp = dlsym (p, "var2");
+      if (varp == NULL)
+	{
+	  puts ("failed to get address of \"var2\" in \"nodelmod2.so\"");
+	  exit (1);
+	}
+      else
+	{
+	  *varp = 42;
+
+	  /* Now close the object.  */
+	  fini_ran = 0;
+	  if (dlclose (p) != 0)
+	    {
+	      puts ("failed to close \"nodelmod2.so\"");
+	      exit (1);
+	    }
+	  else if (! sigsetjmp (jmpbuf, 1))
+	    {
+	      /* Access the variable again.  */
+	      if (*varp != 42)
+		{
+		  puts ("\"var2\" value not correct");
+		  exit (1);
+		}
+	      else if (fini_ran != 0)
+		{
+		  puts ("destructor of \"nodelmod2.so\" ran");
+		  exit (1);
+		}
+	      else
+		puts ("RTLD_NODELETE test succeeded");
+	    }
+	  else
+	    {
+	      /* We caught an segmentation fault.  */
+	      puts ("\"nodelmod2.so\" got deleted!");
+	      exit (1);
+	    }
+	}
+    }
+
+  p = dlopen ("nodelmod3.so", RTLD_LAZY);
+  if (p == NULL)
+    {
+      printf ("failed to load \"nodelmod3.so\": %s\n", dlerror ());
+      exit (1);
+    }
+  else
+    {
+      int *(*fctp) (void);
+
+      fctp = dlsym (p, "addr");
+      if (fctp == NULL)
+	{
+	  puts ("failed to get address of \"addr\" in \"nodelmod3.so\"");
+	  exit (1);
+	}
+      else
+	{
+	  int *varp = fctp ();
+
+	  *varp = -1;
+
+	  /* Now close the object.  */
+	  fini_ran = 0;
+	  if (dlclose (p) != 0)
+	    {
+	      puts ("failed to close \"nodelmod3.so\"");
+	      exit (1);
+	    }
+	  else if (! sigsetjmp (jmpbuf, 1))
+	    {
+	      /* Access the variable again.  */
+	      if (*varp != -1)
+		{
+		  puts ("\"var_in_mod4\" value not correct");
+		  exit (1);
+		}
+	      else if (fini_ran != 0)
+		{
+		  puts ("destructor of \"nodelmod4.so\" ran");
+		  exit (1);
+		}
+	      else
+		puts ("-z nodelete in dependency succeeded");
+	    }
+	  else
+	    {
+	      /* We caught an segmentation fault.  */
+	      puts ("\"nodelmod4.so\" got deleted!");
+	      exit (1);
+	    }
+	}
+    }
+
+  return 0;
+}
+
+#include "../test-skeleton.c"

+ 59 - 0
test/dlopen/nodelete1.c

@@ -0,0 +1,59 @@
+#include <dlfcn.h>
+#include <stdio.h>
+#include <stdlib.h>
+
+
+int fini_ran;
+
+#define LIBNAME1	"nodelmod1.so"
+
+static int
+do_test (void)
+{
+  /* Verify ability to reload RTLD_NODELETE libraries.
+   */
+  void *p;
+
+  p = dlopen (LIBNAME1, RTLD_NOW);
+  if (p == NULL)
+  {
+      printf ("failed to load "LIBNAME1": %s\n", dlerror ());
+      exit (1);
+  }
+
+  if (dlclose (p) != 0)
+  {
+      puts ("failed to close "LIBNAME1"");
+      exit (1);
+  }
+
+  p = dlopen (LIBNAME1, RTLD_LAZY);
+  if (p == NULL)
+  {
+      printf ("failed to load "LIBNAME1": %s\n", dlerror ());
+      exit (1);
+  }
+
+  if (dlclose (p) != 0)
+  {
+      puts ("failed to close "LIBNAME1"");
+      exit (1);
+  }
+
+  p = dlopen ("nodelmod2.so", RTLD_LAZY);
+  if (p == NULL)
+  {
+      printf ("failed to load \"nodelmod2.so\": %s\n", dlerror ());
+      exit (1);
+  }
+  if (dlclose (p) != 0)
+  {
+      puts ("failed to close \"nodelmod2.so\"");
+      exit (1);
+  }
+
+  return 0;
+}
+
+#define TEST_FUNCTION do_test ()
+#include "../test-skeleton.c"

+ 10 - 0
test/dlopen/nodelmod1.c

@@ -0,0 +1,10 @@
+extern int fini_ran;
+
+int var1 = 42;
+
+static void
+__attribute__ ((__destructor__))
+destr (void)
+{
+  fini_ran = 1;
+}

+ 10 - 0
test/dlopen/nodelmod2.c

@@ -0,0 +1,10 @@
+extern int fini_ran;
+
+int var2 = 100;
+
+static void
+__attribute__ ((__destructor__))
+destr (void)
+{
+  fini_ran = 1;
+}

+ 8 - 0
test/dlopen/nodelmod3.c

@@ -0,0 +1,8 @@
+extern int var_in_mod4;
+extern int *addr (void);
+
+int *
+addr (void)
+{
+  return &var_in_mod4;
+}

+ 10 - 0
test/dlopen/nodelmod4.c

@@ -0,0 +1,10 @@
+extern int fini_ran;
+
+int var_in_mod4 = 99;
+
+static void
+__attribute__ ((__destructor__))
+destr (void)
+{
+  fini_ran = 1;
+}

+ 33 - 0
test/dlopen/test1.c

@@ -0,0 +1,33 @@
+#include <fcntl.h>
+#include <stdlib.h>
+#include <stdio.h>
+#include <dlfcn.h>
+
+#ifdef __UCLIBC__
+extern void _dlinfo(void);
+#endif
+
+int main(int argc, char **argv) {
+	void *handle;
+	int (*mydltest)(const char *s);
+	char *error;
+
+	handle = dlopen ("./libtest1.so", RTLD_LAZY);
+	if (!handle) {
+		fprintf(stderr, "Could not open ./libtest1.so: %s\n", dlerror());
+		exit(1);
+	}
+
+	mydltest = dlsym(handle, "dltest");
+	if ((error = dlerror()) != NULL)  {
+		fprintf(stderr, "Could not locate symbol 'dltest': %s\n", error);
+		exit(1);
+	}
+
+	mydltest("hello world!");
+
+	dlclose(handle);
+
+	return EXIT_SUCCESS;
+}
+

+ 39 - 0
test/dlopen/test2.c

@@ -0,0 +1,39 @@
+#include <fcntl.h>
+#include <stdlib.h>
+#include <stdio.h>
+#include <dlfcn.h>
+
+#ifdef __UCLIBC__
+extern void _dlinfo(void);
+#endif
+
+int main(int argc, char **argv) {
+	void *handle;
+	int (*mydltest)(const char *s);
+	char *error;
+
+	handle = dlopen ("./libtest2.so", RTLD_LAZY);
+	if (!handle) {
+		fprintf(stderr, "Could not open ./libtest2.so: %s\n", dlerror());
+		exit(1);
+	}
+
+	handle = dlopen ("./libtest1.so", RTLD_LAZY);
+	if (!handle) {
+		fprintf(stderr, "Could not open ./libtest1.so: %s\n", dlerror());
+		exit(1);
+	}
+
+	mydltest = dlsym(handle, "dltest");
+	if ((error = dlerror()) != NULL)  {
+		fprintf(stderr, "Could not locate symbol 'dltest': %s\n", error);
+		exit(1);
+	}
+
+	mydltest("hello world!");
+
+	dlclose(handle);
+
+	return EXIT_SUCCESS;
+}
+

+ 13 - 0
test/dlopen/test3.c

@@ -0,0 +1,13 @@
+#include <fcntl.h>
+#include <stdlib.h>
+#include <stdio.h>
+#include <dlfcn.h>
+
+extern int dltest(const char *s);
+
+int main(int argc, char **argv)
+{
+	dltest("hello world!");
+	return EXIT_SUCCESS;
+}
+

+ 29 - 0
test/dlopen/testscope.c

@@ -0,0 +1,29 @@
+#include <dlfcn.h>
+#include <stdio.h>
+#include <stdlib.h>
+
+#define LIBNAME "libA.so"
+int main(int argc, char **argv)
+{
+	void *libA;
+	void (*libAfn)(void);
+	char *error;
+
+	libA = dlopen(LIBNAME, RTLD_LAZY);
+	if (!libA) {
+		fprintf(stderr, "Could not open ./%s: %s\n", LIBNAME, dlerror());
+		exit(1);
+	}
+
+	libAfn = dlsym(libA, "libA_func");
+	if ((error = dlerror()) != NULL)  {
+		fprintf(stderr, "Could not locate symbol 'libA_func': %s\n", error);
+		exit(1);
+	}
+
+	libAfn();
+
+	dlclose(libA);
+
+	return EXIT_SUCCESS;
+}

+ 37 - 0
test/dlopen/tst-origin.c

@@ -0,0 +1,37 @@
+#include <fcntl.h>
+#include <stdlib.h>
+#include <stdio.h>
+#include <dlfcn.h>
+
+#ifdef __UCLIBC__
+extern void _dlinfo(void);
+#endif
+
+int main(int argc, char **argv) {
+	void *h1, *h2;
+	int __attribute__((unused))(*mydltest)(const char *s);
+	char *error;
+
+	h1 = dlopen ("libtest31.so", RTLD_LAZY);
+	if (!h1) {
+		fprintf(stderr, "Could not open libtest31.so: %s\n", dlerror());
+		exit(1);
+	}
+
+	h2 = dlopen ("libtest31.so", RTLD_NOLOAD);
+	if (!h2) {
+		fprintf(stderr, "Could not open libtest31.so(RTLD_NOLOAD): %s\n", dlerror());
+		exit(1);
+	}
+
+	mydltest = dlsym(h1, "dltest");
+	if ((error = dlerror()) != NULL)  {
+		fprintf(stderr, "Could not locate symbol 'dltest': %s\n", error);
+		exit(1);
+	}
+
+	dlclose(h2);
+	dlclose(h1);
+
+	return EXIT_SUCCESS;
+}

+ 8 - 0
test/inet/Makefile

@@ -0,0 +1,8 @@
+# uClibc inet tests
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+
+top_builddir=../../
+top_srcdir=../../
+include ../Rules.mak
+-include Makefile.in
+include ../Test.mak

+ 17 - 0
test/inet/Makefile.in

@@ -0,0 +1,17 @@
+# uClibc inet tests
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+#
+ifeq ($(UCLIBC_HAS_IPV4)$(UCLIBC_HAS_IPV6),)
+TESTS_DISABLED := bug-if1 gethost_r-align gethostid if_nameindex tst-aton \
+	tst-network tst-ntoa test-ifaddrs
+endif
+
+ifeq ($(UCLIBC_HAS_SOCKET)$(UCLIBC_HAS_IPV4)$(UCLIBC_HAS_IPV6),)
+TESTS_DISABLED += tst-ether_aton tst-ethers tst-ethers-line
+endif
+
+ifeq ($(UCLIBC_HAS_RESOLVER_SUPPORT),)
+TESTS_DISABLED += tst-res
+else
+LDFLAGS_tst-res_glibc := -lresolv # assume it's glibc or somebody with that lib
+endif

+ 53 - 0
test/inet/bug-if1.c

@@ -0,0 +1,53 @@
+/* Copyright (C) 2004 Free Software Foundation, Inc.
+   This file is part of the GNU C Library.
+   Contributed by Ulrich Drepper <drepper@redhat.com>, 2004.
+
+   The GNU C Library is free software; you can redistribute it and/or
+   modify it under the terms of the GNU Lesser General Public
+   License as published by the Free Software Foundation; either
+   version 2.1 of the License, or (at your option) any later version.
+
+   The GNU C Library is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+   Lesser General Public License for more details.
+
+   You should have received a copy of the GNU Lesser General Public
+   License along with the GNU C Library; if not, see
+   <http://www.gnu.org/licenses/>.  */
+
+#include <errno.h>
+#include <limits.h>
+#include <stdio.h>
+#include <string.h>
+#include <net/if.h>
+
+
+static int
+do_test (void)
+{
+  char buf[IF_NAMESIZE];
+  /* Index 0 is always invalid (see RFC 3493).  */
+  char *cp = if_indextoname (0, buf);
+  if (cp != NULL)
+    {
+      printf ("invalid index returned result \"%s\"\n", cp);
+      return 1;
+    }
+  else if (errno != ENXIO)
+    {
+      int err = errno;
+      char errbuf1[256];
+      char errbuf2[256];
+
+      printf ("errno = %d (%s), expected %d (%s)\n",
+	      err, strerror_r (err, errbuf1, sizeof (errbuf1)),
+	      ENXIO, strerror_r (ENXIO, errbuf2, sizeof (errbuf2)));
+      return 1;
+    }
+
+  return 0;
+}
+
+#define TEST_FUNCTION do_test ()
+#include "../test-skeleton.c"

+ 40 - 0
test/inet/gethost.c

@@ -0,0 +1,40 @@
+#include <errno.h>
+#include <netdb.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <arpa/inet.h>
+#include <sys/socket.h>
+
+int main(void)
+{
+       in_addr_t addr = inet_addr("127.0.0.1");
+       struct hostent *hent;
+
+       hent = gethostent();
+       if (hent == NULL) {
+               printf("gethostent(%d):%s\n", errno, hstrerror(h_errno));
+               exit(1);
+       }
+
+       hent = gethostbyname("localhost");
+       if (hent == NULL) {
+               printf("gethostbyname(%d):%s\n", errno, hstrerror(h_errno));
+               exit(1);
+       }
+
+       hent = gethostbyname2("localhost", AF_INET);
+       if (hent == NULL) {
+               printf("gethostbyname2(%d):%s\n", errno, hstrerror(h_errno));
+               exit(1);
+       }
+
+       hent = gethostbyaddr(&addr, sizeof(addr), AF_INET);
+       if (hent == NULL) {
+               printf("gethostbyaddr(%d):%s\n", errno, hstrerror(h_errno));
+               exit(1);
+       }
+
+       return 0;
+}
+

+ 50 - 0
test/inet/gethost_r-align.c

@@ -0,0 +1,50 @@
+/* Since the reentrant gethost functions take a char * buffer,
+ * we have to make sure they internally do not assume alignment.
+ * The actual return values are not relevant.  If the test fails,
+ * it'll be due to an alignment exception which means the test
+ * app is killed by the kernel.
+ */
+
+#include <errno.h>
+#include <netdb.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <arpa/inet.h>
+#include <sys/socket.h>
+
+int main(int argc, char *argv[])
+{
+	size_t i;
+	char buf[1024];
+	in_addr_t addr;
+
+	addr = inet_addr("127.0.0.1");
+
+	for (i = 0; i < sizeof(size_t) * 2; ++i) {
+		struct hostent hent, *hentres;
+		int ret, herr;
+
+		printf("Testing misalignment of %2zi bytes: ", i);
+
+		memset(&hent, 0x00, sizeof(hent));
+		ret = gethostent_r(&hent, buf + i, sizeof(buf) - i, &hentres, &herr);
+		printf("%sgethostent_r() ", (ret ? "!!!" : ""));
+
+		memset(&hent, 0x00, sizeof(hent));
+		ret = gethostbyname_r("localhost", &hent, buf + i, sizeof(buf) - i, &hentres, &herr);
+		printf("%sgethostbyname_r() ", (ret ? "!!!" : ""));
+
+		memset(&hent, 0x00, sizeof(hent));
+		ret = gethostbyname2_r("localhost", AF_INET, &hent, buf + i, sizeof(buf) - i, &hentres, &herr);
+		printf("%sgethostbyname2_r() ", (ret ? "!!!" : ""));
+
+		memset(&hent, 0x00, sizeof(hent));
+		ret = gethostbyaddr_r(&addr, sizeof(addr), AF_INET, &hent, buf + i, sizeof(buf) - i, &hentres, &herr);
+		printf("%sgethostbyaddr_r() ", (ret ? "!!!" : ""));
+
+		puts("OK!");
+	}
+
+	return 0;
+}

+ 6 - 0
test/inet/gethostid.c

@@ -0,0 +1,6 @@
+#include <unistd.h>
+#include <stdio.h>
+int main(void) {
+	printf("hostid=%ld\n", gethostid());
+	return 0;
+}

+ 17 - 0
test/inet/getnetent.c

@@ -0,0 +1,17 @@
+#include <stdio.h>
+#include <netdb.h>
+int main(void)
+{
+	struct netent *net;
+	setnetent(0);
+	while ((net = getnetent())) {
+		while (net->n_net && !((net->n_net >> 24) & 0xff)) {
+			net->n_net <<= 8;
+		}
+		printf("%u.%u.%u.%u\n",
+			   (net->n_net >> 24) & 0xff, (net->n_net >> 16) & 0xff,
+			   (net->n_net >> 8) & 0xff, net->n_net & 0xff);
+	}
+	endnetent();
+	return 0;
+}

+ 61 - 0
test/inet/if_nameindex.c

@@ -0,0 +1,61 @@
+/* if_nameindex.c: test the if_nameindex() function
+ *
+ * Copyright (C) 2006 Erik Andersen <andersen@uclibc.org>
+ *
+ * Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <net/if.h>
+
+static char ifname[IF_NAMESIZE];
+
+static void test_if_nameindex(void)
+{
+	size_t i;
+	struct if_nameindex *ret;
+
+	ret = if_nameindex();
+
+	if (ret == NULL) {
+		perror("if_nameindex()");
+		exit(1);
+	}
+
+	printf("--- if_nameindex()\n");
+	for (i=0; ret[i].if_name; ++i)
+		printf("%i: %s\n", ret[i].if_index, ret[i].if_name);
+
+	if_freenameindex(ret);
+}
+
+static void test_if_indextoname(void)
+{
+	if (if_indextoname(1, ifname) == NULL) {
+		perror("if_nameindex()");
+		exit(1);
+	}
+
+	printf("if_indextoname(1) = %s\n", ifname);
+}
+
+static void test_if_nametoindex(void)
+{
+	int ifindex = if_nametoindex(ifname);
+
+	if (ifindex == 0) {
+		perror("if_nametoindex()");
+		exit(1);
+	}
+
+	printf("if_nametoindex(%s) = %i\n", ifname, ifindex);
+}
+
+int main(void)
+{
+	test_if_nameindex();
+	test_if_indextoname();
+	test_if_nametoindex();
+	return 0;
+}

+ 80 - 0
test/inet/tst-aton.c

@@ -0,0 +1,80 @@
+#include <stdio.h>
+#include <sys/socket.h>
+#include <netinet/in.h>
+#include <arpa/inet.h>
+
+/* Note: uClibc only supports the standard notation 'a.b.c.d' */
+
+static struct tests
+{
+  const char *input;
+  int valid;
+  uint32_t result;
+} tests[] =
+{
+  { "", 0, 0 },
+  { "-1", 0, 0 },
+/*
+  { "256", 1, 0x00000100 },
+*/
+  { "256.", 0, 0 },
+  { "256a", 0, 0 },
+/*
+  { "0x100", 1, 0x00000100 },
+  { "0200.0x123456", 1, 0x80123456 },
+  { "0300.0x89123456.", 0 ,0 },
+  { "0100.-0xffff0000", 0, 0 },
+  { "0.0xffffff", 1, 0x00ffffff },
+  { "0.0x1000000", 0, 0 },
+  { "0377.16777215", 1, 0xffffffff },
+  { "0377.16777216", 0, 0 },
+  { "0x87.077777777", 1, 0x87ffffff },
+  { "0x87.0100000000", 0, 0 },
+  { "0.1.3", 1, 0x00010003 },
+*/
+  { "0.256.3", 0, 0 },
+  { "256.1.3", 0, 0 },
+/*
+  { "0.1.0x10000", 0, 0 },
+  { "0.1.0xffff", 1, 0x0001ffff },
+*/
+  { "0.1a.3", 0, 0 },
+  { "0.1.a3", 0, 0 },
+  { "1.2.3.4", 1, 0x01020304 },
+  { "0400.2.3.4", 0, 0 },
+  { "1.0x100.3.4", 0, 0 },
+  { "1.2.256.4", 0, 0 },
+  { "1.2.3.0x100", 0, 0 },
+  { "323543357756889", 0, 0 },
+  { "10.1.2.3.4", 0, 0},
+};
+
+
+int
+main (int argc, char *argv[])
+{
+  int result = 0;
+  size_t cnt;
+
+  for (cnt = 0; cnt < sizeof (tests) / sizeof (tests[0]); ++cnt)
+    {
+      struct in_addr addr;
+
+      if ((int) inet_aton (tests[cnt].input, &addr) != tests[cnt].valid)
+	{
+	  if (tests[cnt].valid)
+	    printf ("\"%s\" not seen as valid IP address\n", tests[cnt].input);
+	  else
+	    printf ("\"%s\" seen as valid IP address\n", tests[cnt].input);
+	  result = 1;
+	}
+      else if (tests[cnt].valid && addr.s_addr != ntohl (tests[cnt].result))
+	{
+	  printf ("\"%s\" not converted correctly: is %08x, should be %08x\n",
+		  tests[cnt].input, addr.s_addr, tests[cnt].result);
+	  result = 1;
+	}
+    }
+
+  return result;
+}

+ 46 - 0
test/inet/tst-ether_aton.c

@@ -0,0 +1,46 @@
+#include <stdio.h>
+#include <stdint.h>
+#include <string.h>
+#include <netinet/ether.h>
+
+static struct tests
+{
+  const char *input;
+  int valid;
+  uint8_t result[6];
+} tests[] =
+{
+  { "", 0, {0, 0, 0, 0, 0, 0} },
+  { "AB:CD:EF:01:23:45", 1, {171, 205, 239, 1, 35, 69} },
+  { "\022B:BB:BB:BB:BB:BB", 0, {0, 0, 0, 0, 0, 0} }
+};
+
+
+int
+main (int argc, char *argv[])
+{
+  int result = 0;
+  size_t cnt;
+
+  for (cnt = 0; cnt < sizeof (tests) / sizeof (tests[0]); ++cnt)
+    {
+      struct ether_addr *addr;
+
+      if (!!(addr = ether_aton (tests[cnt].input)) != tests[cnt].valid)
+      {
+        if (tests[cnt].valid)
+          printf ("\"%s\" not seen as valid MAC address\n", tests[cnt].input);
+        else
+          printf ("\"%s\" seen as valid MAC address\n", tests[cnt].input);
+        result = 1;
+      }
+      else if (tests[cnt].valid
+               && memcmp(addr, &tests[cnt].result, sizeof(struct ether_addr)))
+      {
+        printf ("\"%s\" not converted correctly\n", tests[cnt].input);
+        result = 1;
+      }
+    }
+
+  return result;
+}

+ 55 - 0
test/inet/tst-ethers-line.c

@@ -0,0 +1,55 @@
+#include <netinet/ether.h>
+#include <stdio.h>
+#include <sys/mman.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#include <stdlib.h>
+
+/* glibc 2.4 has no ETHER_FILE_NAME, host compile fails without this */
+#ifndef ETHER_FILE_NAME
+#define ETHER_FILE_NAME "/etc/ethers"
+#endif
+
+#define ETHER_LINE_LEN 256
+
+/* This test requires /etc/ethers to exist
+ * and to have nonzero length. You should create it manually,
+ * if it doesn't exist.
+ */
+
+int main(void)
+{
+	struct ether_addr addr;
+	char hostname[ETHER_LINE_LEN];
+	int fd, i;
+	const char *ethers;
+	struct stat statb;
+
+	if ((fd = open(ETHER_FILE_NAME, O_RDONLY)) == -1) {
+		perror ("Cannot open file /etc/ethers");
+		exit(1);
+	}
+
+	if (fstat(fd, &statb)) {
+		perror("Stat failed");
+		exit(1);
+	}
+	ethers = mmap(NULL, statb.st_size, PROT_READ, MAP_SHARED, fd, 0);
+
+	if (ethers == MAP_FAILED) {
+		perror("File mapping failed");
+		exit(1);
+	}
+
+	ether_line(ethers, &addr, hostname);
+
+	for (i = 0; i < 6; i++) {
+		printf("%02x", addr.ether_addr_octet[i]);
+		if (i < 5)
+			printf(":");
+	}
+	printf(" %s\n", hostname);
+
+	return 0;
+}

+ 37 - 0
test/inet/tst-ethers.c

@@ -0,0 +1,37 @@
+#include <netinet/ether.h>
+#include <stdio.h>
+
+#define ETHER_LINE_LEN 256
+
+/* This test requires /etc/ethers to exist
+ * and to have host "teeth". For example:
+ * 00:11:22:33:44:55 teeth
+ * You should create /etc/ethers file with
+ * host "teeth" manually, if it doesn't exist.
+ */
+
+int main(void)
+{
+	struct ether_addr addr;
+	char host[ETHER_LINE_LEN];
+	int i;
+	int res = ether_hostton("teeth", &addr);
+
+	if (res) {
+		printf("Either /etc/ethers is missing or it has incorrect contents\n");
+		return 1;
+	}
+
+	for (i = 0; i < 6; i++) {
+		printf("%02x", addr.ether_addr_octet[i]);
+		if (i < 5)
+			printf(":");
+	}
+
+	res = ether_ntohost(host, &addr);
+	if (res)
+		return 1;
+	printf(" %s\n", host);
+
+	return 0;
+}

+ 99 - 0
test/inet/tst-ifaddrs.c

@@ -0,0 +1,99 @@
+/* Test listing of network interface addresses.
+   Copyright (C) 2002-2015 Free Software Foundation, Inc.
+   This file is part of the GNU C Library.
+
+   The GNU C Library is free software; you can redistribute it and/or
+   modify it under the terms of the GNU Lesser General Public
+   License as published by the Free Software Foundation; either
+   version 2.1 of the License, or (at your option) any later version.
+
+   The GNU C Library is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+   Lesser General Public License for more details.
+
+   You should have received a copy of the GNU Lesser General Public
+   License along with the GNU C Library; if not, see
+   <http://www.gnu.org/licenses/>.  */
+
+#include <errno.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <ifaddrs.h>
+#include <netinet/in.h>
+#include <arpa/inet.h>
+
+static int failures;
+
+static const char *
+addr_string (struct sockaddr *sa, char *buf, size_t size)
+{
+  if (sa == NULL)
+    return "<none>";
+
+  switch (sa->sa_family)
+    {
+    case AF_INET:
+      return inet_ntop (AF_INET, &((struct sockaddr_in *) sa)->sin_addr,
+			buf, size);
+    case AF_INET6:
+      return inet_ntop (AF_INET6, &((struct sockaddr_in6 *) sa)->sin6_addr,
+			buf, size);
+#ifdef AF_LINK
+    case AF_LINK:
+      return "<link>";
+#endif
+    case AF_UNSPEC:
+      return "---";
+
+#ifdef AF_PACKET
+    case AF_PACKET:
+      return "<packet>";
+#endif
+
+    default:
+      ++failures;
+      printf ("sa_family=%d %08x\n", sa->sa_family,
+	      *(int*)&((struct sockaddr_in *) sa)->sin_addr.s_addr);
+      return "<unexpected sockaddr family>";
+    }
+}
+
+
+static int
+do_test (void)
+{
+  struct ifaddrs *ifaces, *ifa;
+
+  if (getifaddrs (&ifaces) < 0)
+    {
+      if (errno != ENOSYS)
+	{
+	  printf ("Couldn't get any interfaces: %s.\n", strerror (errno));
+	  exit (1);
+	}
+      /* The function is simply not implemented.  */
+      exit (0);
+    }
+
+  puts ("\
+Name           Flags   Address         Netmask         Broadcast/Destination");
+
+  for (ifa = ifaces; ifa != NULL; ifa = ifa->ifa_next)
+    {
+      char abuf[64], mbuf[64], dbuf[64];
+      printf ("%-15s%#.4x  %-15s %-15s %-15s\n",
+	      ifa->ifa_name, ifa->ifa_flags,
+	      addr_string (ifa->ifa_addr, abuf, sizeof (abuf)),
+	      addr_string (ifa->ifa_netmask, mbuf, sizeof (mbuf)),
+	      addr_string (ifa->ifa_broadaddr, dbuf, sizeof (dbuf)));
+    }
+
+  freeifaddrs (ifaces);
+
+  return failures ? 1 : 0;
+}
+
+#define TEST_FUNCTION do_test ()
+#include "../test-skeleton.c"

+ 104 - 0
test/inet/tst-network.c

@@ -0,0 +1,104 @@
+/* Test for inet_network.
+   Copyright (C) 2000, 2002 Free Software Foundation, Inc.
+   This file is part of the GNU C Library.
+   Contributed by Andreas Jaeger <aj@suse.de>, 2000.
+
+   The GNU C Library is free software; you can redistribute it and/or
+   modify it under the terms of the GNU Lesser General Public
+   License as published by the Free Software Foundation; either
+   version 2.1 of the License, or (at your option) any later version.
+
+   The GNU C Library is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+   Lesser General Public License for more details.
+
+   You should have received a copy of the GNU Lesser General Public
+   License along with the GNU C Library; if not, see
+   <http://www.gnu.org/licenses/>.  */
+
+#include <stdio.h>
+#include <sys/socket.h>
+#include <netinet/in.h>
+#include <arpa/inet.h>
+
+struct
+{
+  const char *network;
+  uint32_t number;
+} tests [] =
+{
+  {"1.0.0.0", 0x1000000},
+  {"1.0.0", 0x10000},
+  {"1.0", 0x100},
+  {"1", 0x1},
+  {"192.168.0.0", 0xC0A80000},
+  /* Now some invalid addresses.  */
+  {"141.30.225.2800", INADDR_NONE},
+  {"141.76.1.1.1", INADDR_NONE},
+  {"141.76.1.11.", INADDR_NONE},
+  {"1410", INADDR_NONE},
+  {"1.1410", INADDR_NONE},
+  {"1.1410.", INADDR_NONE},
+  {"1.1410", INADDR_NONE},
+  {"141.76.1111", INADDR_NONE},
+  {"141.76.1111.", INADDR_NONE},
+  {"1.1.1.257", INADDR_NONE},
+  /* Now some from BSD */
+  {"0x12", 0x00000012},
+  {"127.1", 0x00007f01},
+  {"127.1.2.3", 0x7f010203},
+  {"0x123456", INADDR_NONE},
+  {"0x12.0x34", 0x00001234},
+  {"0x12.0x345", INADDR_NONE},
+  {"1.2.3.4.5", INADDR_NONE},
+  {"1..3.4", INADDR_NONE},
+  {".", INADDR_NONE},
+  {"1.", INADDR_NONE},
+  {".1", INADDR_NONE},
+  {"x", INADDR_NONE},
+  {"0x", INADDR_NONE},
+  {"0", 0x00000000},
+  {"0x0", 0x00000000},
+  {"01.02.07.077", 0x0102073f},
+  {"0x1.23.045.0", 0x01172500},
+  {"", INADDR_NONE},
+  {" ", INADDR_NONE},
+  {"bar", INADDR_NONE},
+  {"1.2bar", INADDR_NONE},
+  {"1.", INADDR_NONE},
+  {"ÊÃÕËÅÎ", INADDR_NONE},
+  {"255.255.255.255", INADDR_NONE},
+  {"x", INADDR_NONE},
+  {"0X12", 0x00000012},
+  {"078", INADDR_NONE},
+  {"1 bar", INADDR_NONE},
+  {"127.0xfff", INADDR_NONE},
+};
+
+
+int
+main (void)
+{
+  int errors = 0;
+  size_t i;
+  uint32_t res;
+
+  for (i = 0; i < sizeof (tests) / sizeof (tests[0]); ++i)
+    {
+      printf ("Testing: %s\n", tests[i].network);
+      res = inet_network (tests[i].network);
+
+      if (res != tests[i].number)
+	{
+	  ++errors;
+	  printf ("Test failed for inet_network (\"%s\"):\n",
+		  tests[i].network);
+	  printf ("Expected return value %u (0x%x) but got %u (0x%x).\n",
+		  tests[i].number, tests[i].number, res, res);
+	}
+
+    }
+
+  return errors != 0;
+}

+ 36 - 0
test/inet/tst-ntoa.c

@@ -0,0 +1,36 @@
+#include <stdio.h>
+#include <string.h>
+#include <arpa/inet.h>
+#include <netinet/in.h>
+
+
+static int
+test (unsigned int inaddr, const char *expected)
+{
+  struct in_addr addr;
+  char *res;
+  int fail;
+
+  addr.s_addr = htonl (inaddr);
+  res = inet_ntoa (addr);
+  fail = strcmp (res, expected);
+
+  printf ("%#010x -> \"%s\" -> %s%s\n", inaddr, res,
+	  fail ? "fail, expected" : "ok", fail ? expected : "");
+
+  return fail;
+}
+
+
+int
+main (void)
+{
+  int result = 0;
+
+  result |= test (INADDR_LOOPBACK, "127.0.0.1");
+  result |= test (INADDR_BROADCAST, "255.255.255.255");
+  result |= test (INADDR_ANY, "0.0.0.0");
+  result |= test (0xc0060746, "192.6.7.70");
+
+  return result;
+}

+ 44 - 0
test/inet/tst-res.c

@@ -0,0 +1,44 @@
+#include <stdlib.h>
+#include <assert.h>
+#include <sys/types.h>
+#include <netinet/in.h>
+#include <arpa/nameser.h>
+#include <resolv.h>
+#include <netdb.h>
+
+int main(int argc, char **argv)
+{
+    int r;
+    struct __res_state state;
+
+    r = res_ninit(&state);
+    if (r) {
+        herror("ninit");
+		abort();
+	}
+    r = res_init();
+    if (r) {
+        herror("init");
+		abort();
+	}
+
+#ifdef __UCLIBC_HAS_BSD_RES_CLOSE__
+    res_close();
+#endif
+#ifdef __UCLIBC__
+	/* assume there is at least one resolver configured */
+	assert (state._u._ext.nscount > 0);
+#else
+	assert (state._u._ext.nscount == 0);
+#endif
+	assert (state.options & RES_INIT);
+    res_nclose(&state);
+#ifdef __UCLIBC__
+	/* We wipe the whole thing */
+	assert ((state.options & RES_INIT) == 0);
+#endif
+	assert (state._u._ext.nscount == 0);
+
+    return 0;
+}
+

+ 53 - 0
test/inet/tst-sock-nonblock.c

@@ -0,0 +1,53 @@
+/* vi: set sw=4 ts=4 sts=4: */
+/*
+ * Nonblocking socket test for uClibc
+ * Copyright (C) 2012 by Kevin Cernekee <cernekee@gmail.com>
+ *
+ * Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <unistd.h>
+#include <errno.h>
+#include <error.h>
+#include <sys/types.h>
+#include <sys/socket.h>
+#include <sys/un.h>
+#include <sys/fcntl.h>
+
+static int
+do_test(void)
+{
+	int fd, ret, result = 0;
+	struct sockaddr_un sa;
+	char buf;
+
+	fd = socket(AF_UNIX, SOCK_DGRAM | SOCK_NONBLOCK, 0);
+	if (fd < 0) {
+		perror("socket()");
+		result = 1;
+	}
+
+	memset(&sa, 0, sizeof(sa));
+	sa.sun_family = AF_UNIX;
+	strcpy(sa.sun_path, "socktest");
+	unlink("socktest");
+	if (bind(fd, (const struct sockaddr *)&sa, sizeof(sa)) < 0) {
+		perror("bind()");
+		result = 1;
+	}
+
+	ret = read(fd, &buf, sizeof(buf));
+	if (ret != -1 || errno != EAGAIN) {
+		error(0, 0, "Nonblocking read returned %d", ret);
+		result = 1;
+	}
+
+	return result;
+}
+
+#define TIMEOUT 5
+#define TEST_FUNCTION do_test ()
+#include "../test-skeleton.c"

+ 8 - 0
test/librt/Makefile

@@ -0,0 +1,8 @@
+# uClibc shm tests
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+
+top_builddir=../../
+top_srcdir=../../
+include ../Rules.mak
+-include Makefile.in
+include ../Test.mak

+ 8 - 0
test/librt/Makefile.in

@@ -0,0 +1,8 @@
+# uClibc shm tests
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+
+LDFLAGS_shmtest := -lrt
+
+ifeq ($(ARCH_USE_MMU),)
+TESTS_DISABLED := shmtest
+endif

+ 104 - 0
test/librt/shmtest.c

@@ -0,0 +1,104 @@
+/* Copyright (C) 2009 Mikael Lund Jepsen <mlj@iccc.dk>
+ *
+ * Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+ */
+
+#include <errno.h>
+#include <fcntl.h>
+#include <string.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <sys/types.h>
+#include <sys/mman.h>
+#include <sys/stat.h>
+#include <sys/wait.h>
+
+#define ARRAY_SIZE(arr) (sizeof(arr) / sizeof((arr)[0]))
+
+char shared_name[] = "/sharetest";
+int test_data[11] = {0,1,2,3,4,5,6,7,8,9,10};
+
+int main(void) {
+	int pfds[2];
+	pid_t pid;
+	int fd;
+	int test_data_fails = 0;
+	char *ptest_data;
+	unsigned int i;
+	char buf[30];
+	int rv;
+
+	pipe(pfds);
+
+	switch(pid = fork()) {
+	case -1:
+		perror("fork");
+		exit(1);	/* parent exits */
+
+	case 0:
+		/* Child */
+
+		/* wait for parent */
+		read(pfds[0], buf, 5);
+
+		fd =  shm_open(shared_name, O_RDWR, DEFFILEMODE);
+		if (fd == -1) {
+			perror("CHILD - shm_open(existing):");
+			exit(1);
+		} else {
+			ptest_data = mmap(0, sizeof(test_data), PROT_READ + PROT_WRITE, MAP_SHARED, fd, 0);
+			if (ptest_data != MAP_FAILED) {
+				for (i=0; i < ARRAY_SIZE(test_data); i++) {
+					if (ptest_data[i] != test_data[i]) {
+						printf("%-40s: Offset %d, local %d, shm %d\n", "Compare memory error", i, test_data[i], ptest_data[i]);
+						test_data_fails++;
+					}
+				}
+				if (test_data_fails == 0)
+					printf("%-40s: %s\n", "Compare memory", "Success");
+
+				munmap(ptest_data, sizeof(test_data));
+			}
+		}
+		exit(0);
+
+	default:
+		/* Parent */
+		fd = shm_open(shared_name, O_RDWR+O_CREAT+O_EXCL, DEFFILEMODE );
+		if (fd == -1) {
+			perror("PARENT - shm_open(create):");
+		} else {
+			if ((ftruncate(fd, sizeof(test_data))) == -1)
+			{
+				printf("%-40s: %s", "ftruncate", strerror(errno));
+				shm_unlink(shared_name);
+				return 0;
+			}
+
+			ptest_data = mmap(0, sizeof(test_data), PROT_READ + PROT_WRITE, MAP_SHARED, fd, 0);
+			if (ptest_data == MAP_FAILED)
+			{
+				perror("PARENT - mmap:");
+				if (shm_unlink(shared_name) == -1) {
+					perror("PARENT - shm_unlink:");
+				}
+				return 0;
+			}
+			for (i=0; i < ARRAY_SIZE(test_data); i++)
+				ptest_data[i] = test_data[i];
+
+			/* signal child */
+			write(pfds[1], "rdy", 5);
+			/* wait for child */
+			wait(&rv);
+
+			/* Cleanup */
+			munmap(ptest_data, sizeof(test_data));
+			if (shm_unlink(shared_name) == -1) {
+				perror("PARENT - shm_unlink:");
+			}
+		}
+	}
+	return 0;
+}

+ 8 - 0
test/locale-mbwc/Makefile

@@ -0,0 +1,8 @@
+# uClibc locale tests
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+
+top_builddir=../../
+top_srcdir=../../
+include ../Rules.mak
+-include Makefile.in
+include ../Test.mak

+ 30 - 0
test/locale-mbwc/Makefile.in

@@ -0,0 +1,30 @@
+# uClibc locale tests
+# Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
+#	 tst_mbtowc tst_strcoll tst_strfmon tst_strxfrm    \
+
+TESTS := tst_iswalnum tst_iswalpha tst_iswcntrl          \
+	 tst_iswctype tst_iswdigit tst_iswgraph          \
+	 tst_iswlower tst_iswprint tst_iswpunct          \
+	 tst_iswspace tst_iswupper tst_iswxdigit         \
+	 tst_mblen tst_mbrlen tst_mbrtowc tst_mbsrtowcs  \
+	 tst_mbstowcs tst_mbtowc tst_strcoll tst_strxfrm \
+	 tst_swscanf tst_towctrans tst_towlower          \
+	 tst_towupper tst_wcrtomb tst_wcscat tst_wcschr  \
+	 tst_wcscmp tst_wcscoll tst_wcscpy tst_wcscspn   \
+	 tst_wcslen tst_wcsncat tst_wcsncmp tst_wcsncpy  \
+	 tst_wcspbrk tst_wcsrtombs tst_wcsspn tst_wcsstr \
+	 tst_wcstod tst_wcstok tst_wcstombs tst_wcswidth \
+	 tst_wcsxfrm tst_wctob tst_wctomb tst_wctrans    \
+	 tst_wctype tst_wcwidth tst_strfmon \
+	 tst2_mbrtowc
+
+# NOTE: For now disabled tst_strfmon to avoid build failure.
+TESTS_DISABLED := tst_strfmon
+
+ifneq ($(UCLIBC_HAS_FLOATS),y)
+TESTS_DISABLED += tst_swscanf tst_wcstod
+endif
+
+DODIFF_rint     := 1
+
+EXTRA_CFLAGS    := -D__USE_GNU -fno-builtin

+ 37 - 0
test/locale-mbwc/dat_isw-funcs.h

@@ -0,0 +1,37 @@
+/*
+ *  TEST SUITE FOR MB/WC FUNCTIONS IN C LIBRARY
+ *
+ *	 FILE:	dat_isw-funcs.h
+ *
+ *	 ISW*:	int isw* (wint_t wc);
+ */
+
+#include <errno.h>
+#include <stdlib.h>
+#include <wctype.h>
+#include "tst_types.h"
+#include "tgn_locdef.h"
+
+#define TST_ISW_LOC(FUNC, func) \
+	TST_ISW## FUNC	  tst_isw## func ##_loc []
+
+#define TST_ISW_REC(locale, func) \
+	{  Tisw## func,	   TST_LOC_## locale  },
+
+/*
+ *  NOTE:
+ *    Set ret_flg = 1, when a return value is expected to be 0 (FALSE).
+ *    Set ret_flg = 0, when a return value is expected to be non-zero (TRUE).
+ *
+ *    Since the functions return *non*-zero value for TRUE, can't
+ *    compare an actual return value with an expected return value.
+ *    Set the ret_flg=0 for TRUE cases and the tst_isw*() will check
+ *    the non-zero value.
+ *
+ *    { { WEOF }, { 0,1,0 } },
+ *		      | |
+ *		      | ret_val: an expected return value
+ *		      ret_flg: if 1, compare an actual return value with the
+ *			       ret_val; if 0, the test program
+ *			       checks the actual return value.
+ */

+ 196 - 0
test/locale-mbwc/dat_iswalnum.c

@@ -0,0 +1,196 @@
+/*
+ *  TEST SUITE FOR MB/WC FUNCTIONS IN C LIBRARY
+ *
+ *	 FILE:	dat_iswalnum.c
+ *
+ *	 ISW*:	int iswalnum (wint_t wc);
+ */
+
+
+#include "dat_isw-funcs.h"
+
+
+TST_ISW_LOC (ALNUM, alnum) = {
+
+    {	TST_ISW_REC (de, alnum)
+	{
+	  {  { 0x0080 }, { 0,1,0 }  },  /* CTRL     */
+	  {  { 0x009F }, { 0,1,0 }  },  /* CTRL     */
+	  {  { 0x00A0 }, { 0,1,0 }  },  /* NB SPACE */
+	  {  { 0x00A1 }, { 0,1,0 }  },  /* UD !     */
+	  {  { 0x00B0 }, { 0,1,0 }  },  /* Degree   */
+	  {  { 0x00B1 }, { 0,1,0 }  },  /* +- sign  */
+	  {  { 0x00B2 }, { 0,1,0 }  },  /* SUP 2    */
+	  {  { 0x00B3 }, { 0,1,0 }  },  /* SUP 3    */
+	  {  { 0x00B4 }, { 0,1,0 }  },  /* ACUTE    */
+	  {  { 0x00B8 }, { 0,1,0 }  },  /* CEDILLA  */
+	  {  { 0x00B9 }, { 0,1,0 }  },  /* SUP 1    */
+	  {  { 0x00BB }, { 0,1,0 }  },  /* >>	      */
+	  {  { 0x00BC }, { 0,1,0 }  },  /* 1/4      */
+	  {  { 0x00BD }, { 0,1,0 }  },  /* 1/2      */
+	  {  { 0x00BE }, { 0,1,0 }  },  /* 3/4      */
+	  {  { 0x00BF }, { 0,1,0 }  },  /* UD ?     */
+	  {  { 0x00C0 }, { 0,0,0 }  },  /* A Grave  */
+	  {  { 0x00D6 }, { 0,0,0 }  },  /* O dia    */
+	  {  { 0x00D7 }, { 0,1,0 }  },  /* multipl. */
+	  {  { 0x00D8 }, { 0,0,0 }  },  /* O stroke */
+	  {  { 0x00DF }, { 0,0,0 }  },  /* small Sh */
+	  {  { 0x00E0 }, { 0,0,0 }  },  /* a grave  */
+	  {  { 0x00F6 }, { 0,0,0 }  },  /* o dia    */
+	  {  { 0x00F7 }, { 0,1,0 }  },  /* division */
+	  {  { 0x00F8 }, { 0,0,0 }  },  /* o stroke */
+	  {  { 0x00FF }, { 0,0,0 }  },  /* y dia    */
+	  {  .is_last = 1 }		  /* last element    */
+	}
+    },
+    {	TST_ISW_REC (de_UTF8, alnum)
+	{
+	  {  { 0x0080 }, { 0,1,0 }  },  /* CTRL     */
+	  {  { 0x009F }, { 0,1,0 }  },  /* CTRL     */
+	  {  { 0x00A0 }, { 0,1,0 }  },  /* NB SPACE */
+	  {  { 0x00A1 }, { 0,1,0 }  },  /* UD !     */
+	  {  { 0x00B0 }, { 0,1,0 }  },  /* Degree   */
+	  {  { 0x00B1 }, { 0,1,0 }  },  /* +- sign  */
+	  {  { 0x00B2 }, { 0,1,0 }  },  /* SUP 2    */
+	  {  { 0x00B3 }, { 0,1,0 }  },  /* SUP 3    */
+	  {  { 0x00B4 }, { 0,1,0 }  },  /* ACUTE    */
+	  {  { 0x00B8 }, { 0,1,0 }  },  /* CEDILLA  */
+	  {  { 0x00B9 }, { 0,1,0 }  },  /* SUP 1    */
+	  {  { 0x00BB }, { 0,1,0 }  },  /* >>	      */
+	  {  { 0x00BC }, { 0,1,0 }  },  /* 1/4      */
+	  {  { 0x00BD }, { 0,1,0 }  },  /* 1/2      */
+	  {  { 0x00BE }, { 0,1,0 }  },  /* 3/4      */
+	  {  { 0x00BF }, { 0,1,0 }  },  /* UD ?     */
+	  {  { 0x00C0 }, { 0,0,0 }  },  /* A Grave  */
+	  {  { 0x00D6 }, { 0,0,0 }  },  /* O dia    */
+	  {  { 0x00D7 }, { 0,1,0 }  },  /* multipl. */
+	  {  { 0x00D8 }, { 0,0,0 }  },  /* O stroke */
+	  {  { 0x00DF }, { 0,0,0 }  },  /* small Sh */
+	  {  { 0x00E0 }, { 0,0,0 }  },  /* a grave  */
+	  {  { 0x00F6 }, { 0,0,0 }  },  /* o dia    */
+	  {  { 0x00F7 }, { 0,1,0 }  },  /* division */
+	  {  { 0x00F8 }, { 0,0,0 }  },  /* o stroke */
+	  {  { 0x00FF }, { 0,0,0 }  },  /* y dia    */
+	  {  .is_last = 1 }		  /* last element    */
+	}
+    },
+    {	TST_ISW_REC (enUS, alnum)
+	{
+	  {  { WEOF   }, { 0,1,0 }  },
+	  {  { 0x0000 }, { 0,1,0 }  },
+	  {  { 0x001F }, { 0,1,0 }  },
+	  {  { 0x0020 }, { 0,1,0 }  },
+	  {  { 0x0021 }, { 0,1,0 }  },
+	  {  { 0x002F }, { 0,1,0 }  },
+	  {  { 0x0030 }, { 0,0,0 }  },
+	  {  { 0x0039 }, { 0,0,0 }  },
+	  {  { 0x003A }, { 0,1,0 }  },
+	  {  { 0x0040 }, { 0,1,0 }  },
+	  {  { 0x0041 }, { 0,0,0 }  },
+	  {  { 0x005A }, { 0,0,0 }  },
+	  {  { 0x005B }, { 0,1,0 }  },
+	  {  { 0x0060 }, { 0,1,0 }  },
+	  {  { 0x0061 }, { 0,0,0 }  },
+	  {  { 0x007A }, { 0,0,0 }  },
+	  {  { 0x007B }, { 0,1,0 }  },
+	  {  { 0x007E }, { 0,1,0 }  },
+	  {  { 0x007F }, { 0,1,0 }  },
+	  {  { 0x0080 }, { 0,1,0 }  },
+	  {  .is_last = 1 }		  /* last element    */
+	}
+    },
+#if 0
+    {	TST_ISW_REC (eucJP, alnum)
+#else
+    {	TST_ISW_REC (ja_UTF8, alnum)
+#endif
+	{
+	  {  { 0x3000 }, { 0,1,0 }  },  /* IDEO. SPACE	*/
+	  {  { 0x3020 }, { 0,1,0 }  },  /* POSTAL MARK FACE	*/
+#ifdef SHOJI_IS_RIGHT
+	  {  { 0x3029 }, { 0,1,0 }  },  /* Hangzhou NUM9	*/
+#else
+	  {  { 0x3029 }, { 0,0,0 }  },  /* Hangzhou NUM9	*/
+#endif
+	  {  { 0x302F }, { 0,1,0 }  },  /* Diacritics(Hangul) */
+	  {  { 0x3037 }, { 0,1,0 }  },  /* Separator Symbol	*/
+	  {  { 0x303F }, { 0,1,0 }  },  /* IDEO. HALF SPACE	*/
+#ifdef SHOJI_IS_RIGHT
+	  {  { 0x3041 }, { 0,1,0 }  },  /* HIRAGANA a		*/
+	  {  { 0x3094 }, { 0,1,0 }  },  /* HIRAGANA u"		*/
+#else
+	  {  { 0x3041 }, { 0,0,0 }  },  /* HIRAGANA a		*/
+	  {  { 0x3094 }, { 0,0,0 }  },  /* HIRAGANA u"		*/
+#endif
+	  {  { 0x3099 }, { 0,1,0 }  },  /* SOUND MARK		*/
+#ifdef SHOJI_IS_RIGHT
+	  {  { 0x309E }, { 0,1,0 }  },  /* ITERATION MARK	*/
+	  {  { 0x30A1 }, { 0,1,0 }  },  /* KATAKANA a		*/
+	  {  { 0x30FA }, { 0,1,0 }  },  /* KATAKANA wo"	*/
+#else
+	  {  { 0x309E }, { 0,0,0 }  },  /* ITERATION MARK	*/
+	  {  { 0x30A1 }, { 0,0,0 }  },  /* KATAKANA a		*/
+	  {  { 0x30FA }, { 0,0,0 }  },  /* KATAKANA wo"	*/
+#endif
+	  {  { 0x30FB }, { 0,1,0 }  },  /* KATAKANA MID.DOT	*/
+#ifdef SHOJI_IS_RIGHT
+	  {  { 0x30FE }, { 0,1,0 }  },  /* KATAKANA ITERATION	*/
+#else
+	  {  { 0x30FE }, { 0,0,0 }  },  /* KATAKANA ITERATION	*/
+#endif
+	  {  { 0x3191 }, { 0,1,0 }  },  /* KANBUN REV.MARK	*/
+	  {  { 0x3243 }, { 0,1,0 }  },  /* IDEO. MARK (reach) */
+	  {  { 0x32CB }, { 0,1,0 }  },  /* IDEO.TEL.SYM.DEC12 */
+	  {  { 0x32FE }, { 0,1,0 }  },  /* MARU KATAKANA wo	*/
+	  {  { 0x33FE }, { 0,1,0 }  },  /* CJK IDEO.TEL.31th	*/
+#ifdef SHOJI_IS_RIGHT
+	  {  { 0x4E00 }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x4E05 }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x4E06 }, { 0,1,0 }  },  /* CJK UNI.IDEO.NON-J	*/
+	  {  { 0x4E07 }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x4FFF }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x9000 }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x9006 }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x9007 }, { 0,1,0 }  },  /* CJK UNI.IDEO.NON-J	*/
+	  {  { 0x9FA4 }, { 0,1,0 }  },  /* CJK UNI.IDEO.NON-J	*/
+	  {  { 0x9FA5 }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+#else
+	  {  { 0x4E00 }, { 0,0,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x4E05 }, { 0,0,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x4E06 }, { 0,0,0 }  },  /* CJK UNI.IDEO.NON-J	*/
+	  {  { 0x4E07 }, { 0,0,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x4FFF }, { 0,0,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x9000 }, { 0,0,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x9006 }, { 0,0,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x9007 }, { 0,0,0 }  },  /* CJK UNI.IDEO.NON-J	*/
+	  {  { 0x9FA4 }, { 0,0,0 }  },  /* CJK UNI.IDEO.NON-J	*/
+	  {  { 0x9FA5 }, { 0,0,0 }  },  /* CJK UNI.IDEO.	*/
+#endif
+	  {  { 0xFE4F }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0xFF0F }, { 0,1,0 }  },  /* FULL SLASH		*/
+	  {  { 0xFF19 }, { 0,0,0 }  },  /* FULL 9		*/
+	  {  { 0xFF20 }, { 0,1,0 }  },  /* FULL @		*/
+	  {  { 0xFF3A }, { 0,0,0 }  },  /* FULL Z		*/
+	  {  { 0xFF40 }, { 0,1,0 }  },  /* FULL GRAVE ACC.	*/
+	  {  { 0xFF5A }, { 0,0,0 }  },  /* FULL z		*/
+	  {  { 0xFF5E }, { 0,1,0 }  },  /* FULL ~ (tilde)	*/
+	  {  { 0xFF61 }, { 0,1,0 }  },  /* HALF IDEO.STOP. .	*/
+	  {  { 0xFF65 }, { 0,1,0 }  },  /* HALF KATA MID.DOT	*/
+#ifdef SHOJI_IS_RIGHT
+	  {  { 0xFF66 }, { 0,1,0 }  },  /* HALF KATA WO		*/
+	  {  { 0xFF6F }, { 0,1,0 }  },  /* HALF KATA tu		*/
+	  {  { 0xFF70 }, { 0,1,0 }  },  /* HALF KATA PL -	*/
+	  {  { 0xFF71 }, { 0,1,0 }  },  /* HALF KATA A		*/
+	  {  { 0xFF9E }, { 0,1,0 }  },  /* HALF KATA MI		*/
+#else
+	  {  { 0xFF66 }, { 0,0,0 }  },  /* HALF KATA WO		*/
+	  {  { 0xFF6F }, { 0,0,0 }  },  /* HALF KATA tu		*/
+	  {  { 0xFF70 }, { 0,0,0 }  },  /* HALF KATA PL -	*/
+	  {  { 0xFF71 }, { 0,0,0 }  },  /* HALF KATA A		*/
+	  {  { 0xFF9E }, { 0,0,0 }  },  /* HALF KATA MI		*/
+#endif
+	  {  .is_last = 1 }		  /* last element    */
+	}
+    },
+    {	TST_ISW_REC (end, alnum) }
+};

+ 169 - 0
test/locale-mbwc/dat_iswalpha.c

@@ -0,0 +1,169 @@
+/*
+ *  TEST SUITE FOR MB/WC FUNCTIONS IN C LIBRARY
+ *
+ *	 FILE:	dat_iswalpha.c
+ *
+ *	 ISW*:	int iswalpha (wint_t wc);
+ */
+
+
+#include "dat_isw-funcs.h"
+
+
+TST_ISW_LOC (ALPHA, alpha)  = {
+
+    {	TST_ISW_REC (de, alpha)
+	{
+	  {  { 0x0080 }, { 0,1,0 }  },  /* CTRL     */
+	  {  { 0x009F }, { 0,1,0 }  },  /* CTRL     */
+	  {  { 0x00A0 }, { 0,1,0 }  },  /* NB SPACE */
+	  {  { 0x00A1 }, { 0,1,0 }  },  /* UD !     */
+	  {  { 0x00B0 }, { 0,1,0 }  },  /* Degree   */
+	  {  { 0x00B1 }, { 0,1,0 }  },  /* +- sign  */
+	  {  { 0x00B2 }, { 0,1,0 }  },  /* SUP 2    */
+	  {  { 0x00B3 }, { 0,1,0 }  },  /* SUP 3    */
+	  {  { 0x00B4 }, { 0,1,0 }  },  /* ACUTE    */
+	  {  { 0x00B8 }, { 0,1,0 }  },  /* CEDILLA  */
+	  {  { 0x00B9 }, { 0,1,0 }  },  /* SUP 1    */
+	  {  { 0x00BB }, { 0,1,0 }  },  /* >>	      */
+	  {  { 0x00BC }, { 0,1,0 }  },  /* 1/4      */
+	  {  { 0x00BD }, { 0,1,0 }  },  /* 1/2      */
+	  {  { 0x00BE }, { 0,1,0 }  },  /* 3/4      */
+	  {  { 0x00BF }, { 0,1,0 }  },  /* UD ?     */
+	  {  { 0x00C0 }, { 0,0,0 }  },  /* A Grave  */
+	  {  { 0x00D6 }, { 0,0,0 }  },  /* O dia    */
+	  {  { 0x00D7 }, { 0,1,0 }  },  /* multipl. */
+	  {  { 0x00D8 }, { 0,0,0 }  },  /* O stroke */
+	  {  { 0x00DF }, { 0,0,0 }  },  /* small Sh */
+	  {  { 0x00E0 }, { 0,0,0 }  },  /* a grave  */
+	  {  { 0x00F6 }, { 0,0,0 }  },  /* o dia    */
+	  {  { 0x00F7 }, { 0,1,0 }  },  /* division */
+	  {  { 0x00F8 }, { 0,0,0 }  },  /* o stroke */
+	  {  { 0x00FF }, { 0,0,0 }  },  /* y dia    */
+	  {  .is_last = 1 }		  /* last element    */
+	}
+    },
+    {	TST_ISW_REC (enUS, alpha)
+	{
+	  {  { WEOF   }, { 0,1,0 }  },
+	  {  { 0x0000 }, { 0,1,0 }  },
+	  {  { 0x001F }, { 0,1,0 }  },
+	  {  { 0x0020 }, { 0,1,0 }  },
+	  {  { 0x0021 }, { 0,1,0 }  },
+	  {  { 0x002F }, { 0,1,0 }  },
+	  {  { 0x0030 }, { 0,1,0 }  },
+	  {  { 0x0039 }, { 0,1,0 }  },
+	  {  { 0x003A }, { 0,1,0 }  },
+	  {  { 0x0040 }, { 0,1,0 }  },
+	  {  { 0x0041 }, { 0,0,0 }  },
+	  {  { 0x005A }, { 0,0,0 }  },
+	  {  { 0x005B }, { 0,1,0 }  },
+	  {  { 0x0060 }, { 0,1,0 }  },
+	  {  { 0x0061 }, { 0,0,0 }  },
+	  {  { 0x007A }, { 0,0,0 }  },
+	  {  { 0x007B }, { 0,1,0 }  },
+	  {  { 0x007E }, { 0,1,0 }  },
+	  {  { 0x007F }, { 0,1,0 }  },
+	  {  { 0x0080 }, { 0,1,0 }  },  /* 20 */
+	  {  .is_last = 1 }		  /* last element    */
+	}
+    },
+#if 0
+    {	TST_ISW_REC (eucJP, alpha)
+#else
+    {	TST_ISW_REC (ja_UTF8, alpha)
+#endif
+	{
+	  {  { 0x3000 }, { 0,1,0 }  },  /* IDEO. SPACE	*/
+	  {  { 0x3020 }, { 0,1,0 }  },  /* POSTAL MARK FACE	*/
+#ifdef SHOJI_IS_RIGHT
+	  {  { 0x3029 }, { 0,1,0 }  },  /* Hangzhou NUM9	*/
+#else
+	  {  { 0x3029 }, { 0,0,0 }  },  /* Hangzhou NUM9	*/
+#endif
+	  {  { 0x302F }, { 0,1,0 }  },  /* Diacritics(Hangul) */
+	  {  { 0x3037 }, { 0,1,0 }  },  /* Separator Symbol	*/
+	  {  { 0x303F }, { 0,1,0 }  },  /* IDEO. HALF SPACE	*/
+#ifdef SHOJI_IS_RIGHT
+	  {  { 0x3041 }, { 0,1,0 }  },  /* HIRAGANA a		*/
+	  {  { 0x3094 }, { 0,1,0 }  },  /* HIRAGANA u"		*/
+#else
+	  {  { 0x3041 }, { 0,0,0 }  },  /* HIRAGANA a		*/
+	  {  { 0x3094 }, { 0,0,0 }  },  /* HIRAGANA u"		*/
+#endif
+	  {  { 0x3099 }, { 0,1,0 }  },  /* SOUND MARK		*/
+#ifdef SHOJI_IS_RIGHT
+	  {  { 0x309E }, { 0,1,0 }  },  /* ITERATION MARK	*/
+	  {  { 0x30A1 }, { 0,1,0 }  },  /* KATAKANA a		*/
+	  {  { 0x30FA }, { 0,1,0 }  },  /* KATAKANA wo"		*/
+#else
+	  {  { 0x309E }, { 0,0,0 }  },  /* ITERATION MARK	*/
+	  {  { 0x30A1 }, { 0,0,0 }  },  /* KATAKANA a		*/
+	  {  { 0x30FA }, { 0,0,0 }  },  /* KATAKANA wo"		*/
+#endif
+	  {  { 0x30FB }, { 0,1,0 }  },  /* KATAKANA MID.DOT	*/
+#ifdef SHOJI_IS_RIGHT
+	  {  { 0x30FE }, { 0,1,0 }  },  /* KATAKANA ITERATION	*/
+#else
+	  {  { 0x30FE }, { 0,0,0 }  },  /* KATAKANA ITERATION	*/
+#endif
+	  {  { 0x3191 }, { 0,1,0 }  },  /* KANBUN REV.MARK	*/
+	  {  { 0x3243 }, { 0,1,0 }  },  /* IDEO. MARK (reach) */
+	  {  { 0x32CB }, { 0,1,0 }  },  /* IDEO.TEL.SYM.DEC12 */
+	  {  { 0x32FE }, { 0,1,0 }  },  /* MARU KATAKANA wo	*/
+	  {  { 0x33FE }, { 0,1,0 }  },  /* CJK IDEO.TEL.31th	*/
+#ifdef SHOJI_IS_RIGHT
+	  {  { 0x4E00 }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x4E05 }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x4E06 }, { 0,1,0 }  },  /* CJK UNI.IDEO.NON-J	*/
+	  {  { 0x4E07 }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x4FFF }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x9000 }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x9006 }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x9007 }, { 0,1,0 }  },  /* CJK UNI.IDEO.NON-J	*/
+	  {  { 0x9FA4 }, { 0,1,0 }  },  /* CJK UNI.IDEO.NON-J	*/
+	  {  { 0x9FA5 }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+#else
+	  {  { 0x4E00 }, { 0,0,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x4E05 }, { 0,0,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x4E06 }, { 0,0,0 }  },  /* CJK UNI.IDEO.NON-J	*/
+	  {  { 0x4E07 }, { 0,0,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x4FFF }, { 0,0,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x9000 }, { 0,0,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x9006 }, { 0,0,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x9007 }, { 0,0,0 }  },  /* CJK UNI.IDEO.NON-J	*/
+	  {  { 0x9FA4 }, { 0,0,0 }  },  /* CJK UNI.IDEO.NON-J	*/
+	  {  { 0x9FA5 }, { 0,0,0 }  },  /* CJK UNI.IDEO.	*/
+#endif
+	  {  { 0xFE4F }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0xFF0F }, { 0,1,0 }  },  /* FULL SLASH		*/
+#ifdef SHOJI_IS_RIGHT
+	  {  { 0xFF19 }, { 0,1,0 }  },  /* FULL 9		*/
+#else
+	  {  { 0xFF19 }, { 0,0,0 }  },  /* FULL 9		*/
+#endif
+	  {  { 0xFF20 }, { 0,1,0 }  },  /* FULL @		*/
+	  {  { 0xFF3A }, { 0,0,0 }  },  /* FULL Z		*/
+	  {  { 0xFF40 }, { 0,1,0 }  },  /* FULL GRAVE ACC.	*/
+	  {  { 0xFF5A }, { 0,0,0 }  },  /* FULL z		*/
+	  {  { 0xFF5E }, { 0,1,0 }  },  /* FULL ~ (tilde)	*/
+	  {  { 0xFF61 }, { 0,1,0 }  },  /* HALF IDEO.STOP. .	*/
+	  {  { 0xFF65 }, { 0,1,0 }  },  /* HALF KATA MID.DOT	*/
+#ifdef SHOJI_IS_RIGHT
+	  {  { 0xFF66 }, { 0,1,0 }  },  /* HALF KATA WO		*/
+	  {  { 0xFF6F }, { 0,1,0 }  },  /* HALF KATA tu		*/
+	  {  { 0xFF70 }, { 0,1,0 }  },  /* HALF KATA PL -	*/
+	  {  { 0xFF71 }, { 0,1,0 }  },  /* HALF KATA A		*/
+	  {  { 0xFF9E }, { 0,1,0 }  },  /* HALF KATA MI		*/
+#else
+	  {  { 0xFF66 }, { 0,0,0 }  },  /* HALF KATA WO		*/
+	  {  { 0xFF6F }, { 0,0,0 }  },  /* HALF KATA tu		*/
+	  {  { 0xFF70 }, { 0,0,0 }  },  /* HALF KATA PL -	*/
+	  {  { 0xFF71 }, { 0,0,0 }  },  /* HALF KATA A		*/
+	  {  { 0xFF9E }, { 0,0,0 }  },  /* HALF KATA MI		*/
+#endif
+	  {  .is_last = 1 }		  /* last element    */
+	}
+    },
+    {	TST_ISW_REC (end, alpha) }
+};

+ 125 - 0
test/locale-mbwc/dat_iswcntrl.c

@@ -0,0 +1,125 @@
+/*
+ *  TEST SUITE FOR MB/WC FUNCTIONS IN C LIBRARY
+ *
+ *	 FILE:	dat_iswcntrl.c
+ *
+ *	 ISW*:	int iswcntrl (wint_t wc);
+ */
+
+
+#include "dat_isw-funcs.h"
+
+
+TST_ISW_LOC (CNTRL, cntrl) = {
+
+    {	TST_ISW_REC (de, cntrl)
+	{
+	  {  { 0x0080 }, { 0,0,0 }  },  /* CTRL     */
+	  {  { 0x009F }, { 0,0,0 }  },  /* CTRL     */
+	  {  { 0x00A0 }, { 0,1,0 }  },  /* NB SPACE */
+	  {  { 0x00A1 }, { 0,1,0 }  },  /* UD !     */
+	  {  { 0x00B0 }, { 0,1,0 }  },  /* Degree   */
+	  {  { 0x00B1 }, { 0,1,0 }  },  /* +- sign  */
+	  {  { 0x00B2 }, { 0,1,0 }  },  /* SUP 2    */
+	  {  { 0x00B3 }, { 0,1,0 }  },  /* SUP 3    */
+	  {  { 0x00B4 }, { 0,1,0 }  },  /* ACUTE    */
+	  {  { 0x00B8 }, { 0,1,0 }  },  /* CEDILLA  */
+	  {  { 0x00B9 }, { 0,1,0 }  },  /* SUP 1    */
+	  {  { 0x00BB }, { 0,1,0 }  },  /* >>	      */
+	  {  { 0x00BC }, { 0,1,0 }  },  /* 1/4      */
+	  {  { 0x00BD }, { 0,1,0 }  },  /* 1/2      */
+	  {  { 0x00BE }, { 0,1,0 }  },  /* 3/4      */
+	  {  { 0x00BF }, { 0,1,0 }  },  /* UD ?     */
+	  {  { 0x00C0 }, { 0,1,0 }  },  /* A Grave  */
+	  {  { 0x00D6 }, { 0,1,0 }  },  /* O dia    */
+	  {  { 0x00D7 }, { 0,1,0 }  },  /* multipl. */
+	  {  { 0x00D8 }, { 0,1,0 }  },  /* O stroke */
+	  {  { 0x00DF }, { 0,1,0 }  },  /* small Sh */
+	  {  { 0x00E0 }, { 0,1,0 }  },  /* a grave  */
+	  {  { 0x00F6 }, { 0,1,0 }  },  /* o dia    */
+	  {  { 0x00F7 }, { 0,1,0 }  },  /* division */
+	  {  { 0x00F8 }, { 0,1,0 }  },  /* o stroke */
+	  {  { 0x00FF }, { 0,1,0 }  },  /* y dia    */
+	  { .is_last = 1 }		  /* Last element.  */
+	}
+    },
+    {	TST_ISW_REC (enUS, cntrl)
+	{
+	  {  { WEOF   }, { 0,1,0 }  },
+	  {  { 0x0000 }, { 0,0,0 }  },
+	  {  { 0x001F }, { 0,0,0 }  },
+	  {  { 0x0020 }, { 0,1,0 }  },
+	  {  { 0x0021 }, { 0,1,0 }  },
+	  {  { 0x002F }, { 0,1,0 }  },
+	  {  { 0x0030 }, { 0,1,0 }  },
+	  {  { 0x0039 }, { 0,1,0 }  },
+	  {  { 0x003A }, { 0,1,0 }  },
+	  {  { 0x0040 }, { 0,1,0 }  },
+	  {  { 0x0041 }, { 0,1,0 }  },
+	  {  { 0x005A }, { 0,1,0 }  },
+	  {  { 0x005B }, { 0,1,0 }  },
+	  {  { 0x0060 }, { 0,1,0 }  },
+	  {  { 0x0061 }, { 0,1,0 }  },
+	  {  { 0x007A }, { 0,1,0 }  },
+	  {  { 0x007B }, { 0,1,0 }  },
+	  {  { 0x007E }, { 0,1,0 }  },
+	  {  { 0x007F }, { 0,0,0 }  },
+	  {  { 0x0080 }, { 0,1,0 }  },
+	  { .is_last = 1 }		  /* Last element.  */
+	}
+    },
+#if 0
+    {	TST_ISW_REC (eucJP, cntrl)
+#else
+    {	TST_ISW_REC (ja_UTF8, cntrl)
+#endif
+	{
+	  {  { 0x3000 }, { 0,1,0 }  },  /* IDEO. SPACE	*/
+	  {  { 0x3020 }, { 0,1,0 }  },  /* POSTAL MARK FACE	*/
+	  {  { 0x3029 }, { 0,1,0 }  },  /* Hangzhou NUM9	*/
+	  {  { 0x302F }, { 0,1,0 }  },  /* Diacritics(Hangul) */
+	  {  { 0x3037 }, { 0,1,0 }  },  /* Separator Symbol	*/
+	  {  { 0x303F }, { 0,1,0 }  },  /* IDEO. HALF SPACE	*/
+	  {  { 0x3041 }, { 0,1,0 }  },  /* HIRAGANA a		*/
+	  {  { 0x3094 }, { 0,1,0 }  },  /* HIRAGANA u"	*/
+	  {  { 0x3099 }, { 0,1,0 }  },  /* SOUND MARK		*/
+	  {  { 0x309E }, { 0,1,0 }  },  /* ITERATION MARK	*/
+	  {  { 0x30A1 }, { 0,1,0 }  },  /* KATAKANA a		*/
+	  {  { 0x30FA }, { 0,1,0 }  },  /* KATAKANA wo"	*/
+	  {  { 0x30FB }, { 0,1,0 }  },  /* KATAKANA MID.DOT	*/
+	  {  { 0x30FE }, { 0,1,0 }  },  /* KATAKANA ITERATION */
+	  {  { 0x3191 }, { 0,1,0 }  },  /* KANBUN REV.MARK	*/
+	  {  { 0x3243 }, { 0,1,0 }  },  /* IDEO. MARK (reach) */
+	  {  { 0x32CB }, { 0,1,0 }  },  /* IDEO.TEL.SYM.DEC12 */
+	  {  { 0x32FE }, { 0,1,0 }  },  /* MARU KATAKANA wo	*/
+	  {  { 0x33FE }, { 0,1,0 }  },  /* CJK IDEO.TEL.31th	*/
+	  {  { 0x4E00 }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x4E05 }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x4E06 }, { 0,1,0 }  },  /* CJK UNI.IDEO.NON-J */
+	  {  { 0x4E07 }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x4FFF }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x9000 }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x9006 }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0x9007 }, { 0,1,0 }  },  /* CJK UNI.IDEO.NON-J */
+	  {  { 0x9FA4 }, { 0,1,0 }  },  /* CJK UNI.IDEO.NON-J */
+	  {  { 0x9FA5 }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0xFE4F }, { 0,1,0 }  },  /* CJK UNI.IDEO.	*/
+	  {  { 0xFF0F }, { 0,1,0 }  },  /* FULL SLASH		*/
+	  {  { 0xFF19 }, { 0,1,0 }  },  /* FULL 9		*/
+	  {  { 0xFF20 }, { 0,1,0 }  },  /* FULL @		*/
+	  {  { 0xFF3A }, { 0,1,0 }  },  /* FULL Z		*/
+	  {  { 0xFF40 }, { 0,1,0 }  },  /* FULL GRAVE ACC.	*/
+	  {  { 0xFF5A }, { 0,1,0 }  },  /* FULL z		*/
+	  {  { 0xFF5E }, { 0,1,0 }  },  /* FULL ~ (tilde)	*/
+	  {  { 0xFF61 }, { 0,1,0 }  },  /* HALF IDEO.STOP. .	*/
+	  {  { 0xFF65 }, { 0,1,0 }  },  /* HALF KATA MID.DOT	*/
+	  {  { 0xFF66 }, { 0,1,0 }  },  /* HALF KATA WO	*/
+	  {  { 0xFF6F }, { 0,1,0 }  },  /* HALF KATA tu	*/
+	  {  { 0xFF70 }, { 0,1,0 }  },  /* HALF KATA PL -	*/
+	  {  { 0xFF71 }, { 0,1,0 }  },  /* HALF KATA A	*/
+	  {  { 0xFF9E }, { 0,1,0 }  },  /* HALF KATA MI	*/
+	  { .is_last = 1 }		  /* Last element.  */
+	}
+    },
+    {	TST_ISW_REC(end, cntrl) }
+};

+ 667 - 0
test/locale-mbwc/dat_iswctype.c

@@ -0,0 +1,667 @@
+/*
+ *  TEST SUITE FOR MB/WC FUNCTIONS IN C LIBRARY
+ *
+ *	 FILE:	dat_iswctype.c
+ *
+ *	 ISWCTYPE:  int iswctype( wint_t wc, wctype_t charclass );
+ */
+
+#include <errno.h>
+#include <stdlib.h>
+#include <wctype.h>
+#include "tst_types.h"
+#include "tgn_locdef.h"
+
+/*
+ *  NOTE:
+ *   Set ret_flg = 1, when a return value is expected to be 0 (FALSE).
+ *   Set ret_flg = 0, when a return value is expected to be non-zero (TRUE).
+ *
+ *   Since the functions return *non*-zero value for TRUE, can't
+ *   compare an actual return value with an expected return value.
+ *   Set the ret_flg=0 for TRUE cases and the tst_isw*() will check
+ *   the non-zero value.
+ *
+ * { { WEOF }, { 0,1,0 } },
+ *		   | |
+ *		   | ret_val: an expected return value
+ *		   ret_flg: if 1, compare an actual return value with the
+ *			    ret_val; if 0, the test program checks
+ *			    the actual return value.
+ */
+
+TST_ISWCTYPE tst_iswctype_loc [] = {
+  {
+    { Tiswctype, TST_LOC_de },
+    {
+      {	 { 0x009F, "alnum"  }, { 0,1,0 }  },	   /* CTRL     */
+      {	 { 0x00A0, "alnum"  }, { 0,1,0 }  },	   /* NB SPACE */
+      {	 { 0x00A1, "alnum"  }, { 0,1,0 }  },	   /* UD !     */
+      {	 { 0x00B1, "alnum"  }, { 0,1,0 }  },	   /* +- sign  */
+      {	 { 0x00B3, "alnum"  }, { 0,1,0 }  },	   /* SUP 3    */
+      {	 { 0x00B4, "alnum"  }, { 0,1,0 }  },	   /* ACUTE    */
+      {	 { 0x00BB, "alnum"  }, { 0,1,0 }  },	   /* >>       */
+      {	 { 0x00BE, "alnum"  }, { 0,1,0 }  },	   /* 3/4      */
+      {	 { 0x00BF, "alnum"  }, { 0,1,0 }  },	   /* UD ?     */
+      {	 { 0x00C0, "alnum"  }, { 0,0,0 }  },	   /* A Grave  */
+      {	 { 0x00D6, "alnum"  }, { 0,0,0 }  },	   /* O dia    */
+      {	 { 0x00D7, "alnum"  }, { 0,1,0 }  },	   /* multipl. */
+      {	 { 0x00D8, "alnum"  }, { 0,0,0 }  },	   /* O stroke */
+      {	 { 0x00DF, "alnum"  }, { 0,0,0 }  },	   /* small Sh */
+      {	 { 0x00E0, "alnum"  }, { 0,0,0 }  },	   /* a grave  */
+      {	 { 0x00F6, "alnum"  }, { 0,0,0 }  },	   /* o dia    */
+      {	 { 0x00F7, "alnum"  }, { 0,1,0 }  },	   /* division */
+      {	 { 0x00F8, "alnum"  }, { 0,0,0 }  },	   /* o stroke */
+      {	 { 0x00FF, "alnum"  }, { 0,0,0 }  },	   /* y dia    */
+      {	 { 0x0080, "alpha"  }, { 0,1,0 }  },	   /* CTRL     */
+      {	 { 0x00A0, "alpha"  }, { 0,1,0 }  },	   /* NB SPACE */
+      {	 { 0x00A1, "alpha"  }, { 0,1,0 }  },	   /* UD !     */
+      {	 { 0x00B1, "alpha"  }, { 0,1,0 }  },	   /* +- sign  */
+      {	 { 0x00B4, "alpha"  }, { 0,1,0 }  },	   /* ACUTE    */
+      {	 { 0x00B8, "alpha"  }, { 0,1,0 }  },	   /* CEDILLA  */
+      {	 { 0x00B9, "alpha"  }, { 0,1,0 }  },	   /* SUP 1    */
+      {	 { 0x00BB, "alpha"  }, { 0,1,0 }  },	   /* >>       */
+      {	 { 0x00BE, "alpha"  }, { 0,1,0 }  },	   /* 3/4      */
+      {	 { 0x00BF, "alpha"  }, { 0,1,0 }  },	   /* UD ?     */
+      {	 { 0x00C0, "alpha"  }, { 0,0,0 }  },	   /* A Grave  */
+      {	 { 0x00D6, "alpha"  }, { 0,0,0 }  },	   /* O dia    */
+      {	 { 0x00D7, "alpha"  }, { 0,1,0 }  },	   /* multipl. */
+      {	 { 0x00D8, "alpha"  }, { 0,0,0 }  },	   /* O stroke */
+      {	 { 0x00DF, "alpha"  }, { 0,0,0 }  },	   /* small Sh */
+      {	 { 0x00E0, "alpha"  }, { 0,0,0 }  },	   /* a grave  */
+      {	 { 0x00F6, "alpha"  }, { 0,0,0 }  },	   /* o dia    */
+      {	 { 0x00F7, "alpha"  }, { 0,1,0 }  },	   /* division */
+      {	 { 0x00F8, "alpha"  }, { 0,0,0 }  },	   /* o stroke */
+      {	 { 0x00FF, "alpha"  }, { 0,0,0 }  },	   /* y dia    */
+      {	 { 0x0080, "cntrl"  }, { 0,0,0 }  },	   /* CTRL     */
+      {	 { 0x009F, "cntrl"  }, { 0,0,0 }  },	   /* CTRL     */
+      {	 { 0x00A0, "cntrl"  }, { 0,1,0 }  },	   /* NB SPACE */
+      {	 { 0x00F6, "cntrl"  }, { 0,1,0 }  },	   /* o dia    */
+      {	 { 0x00FF, "cntrl"  }, { 0,1,0 }  },	   /* y dia    */
+      {	 { 0x00B9, "digit"  }, { 0,1,0 }  },	   /* SUP 1    */
+      {	 { 0x00BE, "digit"  }, { 0,1,0 }  },	   /* 3/4      */
+      {	 { 0x009F, "graph"  }, { 0,1,0 }  },	   /* CTRL     */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0x00A0, "graph"  }, { 0,1,0 }  },	   /* NB SPACE */
+#else
+      {	 { 0x00A0, "graph"  }, { 0,0,0 }  },	   /* NB SPACE */
+#endif
+      {	 { 0x00A1, "graph"  }, { 0,0,0 }  },	   /* UD !     */
+      {	 { 0x00B1, "graph"  }, { 0,0,0 }  },	   /* +- sign  */
+      {	 { 0x00B3, "graph"  }, { 0,0,0 }  },	   /* SUP 3    */
+      {	 { 0x00B4, "graph"  }, { 0,0,0 }  },	   /* ACUTE    */
+      {	 { 0x00BB, "graph"  }, { 0,0,0 }  },	   /* >>       */
+      {	 { 0x00BE, "graph"  }, { 0,0,0 }  },	   /* 3/4      */
+      {	 { 0x00C0, "graph"  }, { 0,0,0 }  },	   /* A Grave  */
+      {	 { 0x00D6, "graph"  }, { 0,0,0 }  },	   /* O dia    */
+      {	 { 0x00D7, "graph"  }, { 0,0,0 }  },	   /* multipl. */
+      {	 { 0x00D8, "graph"  }, { 0,0,0 }  },	   /* O stroke */
+      {	 { 0x00DF, "graph"  }, { 0,0,0 }  },	   /* small Sh */
+      {	 { 0x00F7, "graph"  }, { 0,0,0 }  },	   /* division */
+      {	 { 0x00F8, "graph"  }, { 0,0,0 }  },	   /* o stroke */
+      {	 { 0x00FF, "graph"  }, { 0,0,0 }  },	   /* y dia    */
+      {	 { 0x009F, "print"  }, { 0,1,0 }  },	   /* CTRL     */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0x00A0, "print"  }, { 0,1,0 }  },	   /* NB SPACE */
+#else
+      {	 { 0x00A0, "print"  }, { 0,0,0 }  },	   /* NB SPACE */
+#endif
+      {	 { 0x00A1, "print"  }, { 0,0,0 }  },	   /* UD !     */
+      {	 { 0x00B1, "print"  }, { 0,0,0 }  },	   /* +- sign  */
+      {	 { 0x00B4, "print"  }, { 0,0,0 }  },	   /* ACUTE    */
+      {	 { 0x00B8, "print"  }, { 0,0,0 }  },	   /* CEDILLA  */
+      {	 { 0x00B9, "print"  }, { 0,0,0 }  },	   /* SUP 1    */
+      {	 { 0x00BB, "print"  }, { 0,0,0 }  },	   /* >>       */
+      {	 { 0x00BE, "print"  }, { 0,0,0 }  },	   /* 3/4      */
+      {	 { 0x00C0, "print"  }, { 0,0,0 }  },	   /* A Grave  */
+      {	 { 0x00DF, "print"  }, { 0,0,0 }  },	   /* small Sh */
+      {	 { 0x00F6, "print"  }, { 0,0,0 }  },	   /* o dia    */
+      {	 { 0x00F7, "print"  }, { 0,0,0 }  },	   /* division */
+      {	 { 0x00F8, "print"  }, { 0,0,0 }  },	   /* o stroke */
+      {	 { 0x00FF, "print"  }, { 0,0,0 }  },	   /* y dia    */
+      {	 { 0x009F, "punct"  }, { 0,1,0 }  },	   /* CTRL     */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0x00A0, "punct"  }, { 0,1,0 }  },	   /* NB SPACE */
+#else
+      {	 { 0x00A0, "punct"  }, { 0,0,0 }  },	   /* NB SPACE */
+#endif
+      {	 { 0x00A1, "punct"  }, { 0,0,0 }  },	   /* UD !     */
+      {	 { 0x00B0, "punct"  }, { 0,0,0 }  },	   /* Degree   */
+      {	 { 0x00B1, "punct"  }, { 0,0,0 }  },	   /* +- sign  */
+      {	 { 0x00B2, "punct"  }, { 0,0,0 }  },	   /* SUP 2    */
+      {	 { 0x00B3, "punct"  }, { 0,0,0 }  },	   /* SUP 3    */
+      {	 { 0x00B4, "punct"  }, { 0,0,0 }  },	   /* ACUTE    */
+      {	 { 0x00B8, "punct"  }, { 0,0,0 }  },	   /* CEDILLA  */
+      {	 { 0x00B9, "punct"  }, { 0,0,0 }  },	   /* SUP 1    */
+      {	 { 0x00BB, "punct"  }, { 0,0,0 }  },	   /* >>       */
+      {	 { 0x00BC, "punct"  }, { 0,0,0 }  },	   /* 1/4      */
+      {	 { 0x00BD, "punct"  }, { 0,0,0 }  },	   /* 1/2      */
+      {	 { 0x00BE, "punct"  }, { 0,0,0 }  },	   /* 3/4      */
+      {	 { 0x00BF, "punct"  }, { 0,0,0 }  },	   /* UD ?     */
+      {	 { 0x00C0, "punct"  }, { 0,1,0 }  },	   /* A Grave  */
+      {	 { 0x00D7, "punct"  }, { 0,0,0 }  },	   /* multipl. */
+      {	 { 0x00DF, "punct"  }, { 0,1,0 }  },	   /* small Sh */
+      {	 { 0x00F6, "punct"  }, { 0,1,0 }  },	   /* o dia    */
+      {	 { 0x00F7, "punct"  }, { 0,0,0 }  },	   /* division */
+      {	 { 0x00FF, "punct"  }, { 0,1,0 }  },	   /* y dia    */
+      {	 { 0x009F, "space"  }, { 0,1,0 }  },	   /* CTRL     */
+      {	 { 0x00A0, "space"  }, { 0,1,0 }  },	   /* NB SPACE */
+      {	 { 0x00A1, "space"  }, { 0,1,0 }  },	   /* UD !     */
+      {	 { 0x00B1, "space"  }, { 0,1,0 }  },	   /* +- sign  */
+      {	 { 0x00F8, "space"  }, { 0,1,0 }  },	   /* o stroke */
+      {	 { 0x00B3, "lower"  }, { 0,1,0 }  },	   /* SUP 3    */
+      {	 { 0x00B8, "lower"  }, { 0,1,0 }  },	   /* CEDILLA  */
+      {	 { 0x00BE, "lower"  }, { 0,1,0 }  },	   /* 3/4      */
+      {	 { 0x00C0, "lower"  }, { 0,1,0 }  },	   /* A Grave  */
+      {	 { 0x00D6, "lower"  }, { 0,1,0 }  },	   /* O dia    */
+      {	 { 0x00D8, "lower"  }, { 0,1,0 }  },	   /* O stroke */
+      {	 { 0x00DF, "lower"  }, { 0,0,0 }  },	   /* small Sh */
+      {	 { 0x00E0, "lower"  }, { 0,0,0 }  },	   /* a grave  */
+      {	 { 0x00F6, "lower"  }, { 0,0,0 }  },	   /* o dia    */
+      {	 { 0x00F7, "lower"  }, { 0,1,0 }  },	   /* division */
+      {	 { 0x00F8, "lower"  }, { 0,0,0 }  },	   /* o stroke */
+      {	 { 0x00FF, "lower"  }, { 0,0,0 }  },	   /* y dia    */
+      {	 { 0x00B4, "upper"  }, { 0,1,0 }  },	   /* ACUTE    */
+      {	 { 0x00B8, "upper"  }, { 0,1,0 }  },	   /* CEDILLA  */
+      {	 { 0x00B9, "upper"  }, { 0,1,0 }  },	   /* SUP 1    */
+      {	 { 0x00BE, "upper"  }, { 0,1,0 }  },	   /* 3/4      */
+      {	 { 0x00BF, "upper"  }, { 0,1,0 }  },	   /* UD ?     */
+      {	 { 0x00C0, "upper"  }, { 0,0,0 }  },	   /* A Grave  */
+      {	 { 0x00D6, "upper"  }, { 0,0,0 }  },	   /* O dia    */
+      {	 { 0x00D7, "upper"  }, { 0,1,0 }  },	   /* multipl. */
+      {	 { 0x00D8, "upper"  }, { 0,0,0 }  },	   /* O stroke */
+      {	 { 0x00DF, "upper"  }, { 0,1,0 }  },	   /* small Sh */
+      {	 { 0x00FF, "upper"  }, { 0,1,0 }  },	   /* y dia    */
+      {	 { 0x00B9, "xdigit" }, { 0,1,0 }  },	   /* SUP 1    */
+      {	 { 0x00BC, "xdigit" }, { 0,1,0 }  },	   /* 1/4      */
+      { .is_last = 1 }
+    }
+  },
+  {
+    { Tiswctype, TST_LOC_enUS },
+    {
+      {	 { WEOF,   "alnum"  }, { 0,1,0 }  },
+      {	 { 0x0000, "alnum"  }, { 0,1,0 }  },
+      {	 { 0x001F, "alnum"  }, { 0,1,0 }  },
+      {	 { 0x0020, "alnum"  }, { 0,1,0 }  },
+      {	 { 0x0021, "alnum"  }, { 0,1,0 }  },
+      {	 { 0x002F, "alnum"  }, { 0,1,0 }  },
+      {	 { 0x0030, "alnum"  }, { 0,0,0 }  },
+      {	 { 0x0039, "alnum"  }, { 0,0,0 }  },
+      {	 { 0x003A, "alnum"  }, { 0,1,0 }  },
+      {	 { 0x0040, "alnum"  }, { 0,1,0 }  },
+      {	 { 0x0041, "alnum"  }, { 0,0,0 }  },
+      {	 { 0x005A, "alnum"  }, { 0,0,0 }  },
+      {	 { 0x005B, "alnum"  }, { 0,1,0 }  },
+      {	 { 0x0060, "alnum"  }, { 0,1,0 }  },
+      {	 { 0x0061, "alnum"  }, { 0,0,0 }  },
+      {	 { 0x007A, "alnum"  }, { 0,0,0 }  },
+      {	 { 0x007B, "alnum"  }, { 0,1,0 }  },
+      {	 { 0x007E, "alnum"  }, { 0,1,0 }  },
+      {	 { 0x007F, "alnum"  }, { 0,1,0 }  },
+      {	 { 0x0080, "alnum"  }, { 0,1,0 }  },
+      {	 { 0x0000, "alpha"  }, { 0,1,0 }  },
+      {	 { 0x001F, "alpha"  }, { 0,1,0 }  },
+      {	 { 0x0020, "alpha"  }, { 0,1,0 }  },
+      {	 { 0x0021, "alpha"  }, { 0,1,0 }  },
+      {	 { 0x002F, "alpha"  }, { 0,1,0 }  },
+      {	 { 0x0030, "alpha"  }, { 0,1,0 }  },
+      {	 { 0x0039, "alpha"  }, { 0,1,0 }  },
+      {	 { 0x003A, "alpha"  }, { 0,1,0 }  },
+      {	 { 0x0040, "alpha"  }, { 0,1,0 }  },
+      {	 { 0x0041, "alpha"  }, { 0,0,0 }  },
+      {	 { 0x005A, "alpha"  }, { 0,0,0 }  },
+      {	 { 0x005B, "alpha"  }, { 0,1,0 }  },
+      {	 { 0x0060, "alpha"  }, { 0,1,0 }  },
+      {	 { 0x0061, "alpha"  }, { 0,0,0 }  },
+      {	 { 0x007A, "alpha"  }, { 0,0,0 }  },
+      {	 { 0x007B, "alpha"  }, { 0,1,0 }  },
+      {	 { 0x007E, "alpha"  }, { 0,1,0 }  },
+      {	 { 0x007F, "alpha"  }, { 0,1,0 }  },
+      {	 { 0x0080, "alpha"  }, { 0,1,0 }  },
+      {	 { 0x0009, "blank"  }, { 0,0,0 }  },
+      {	 { 0x000B, "blank"  }, { 0,1,0 }  },
+      {	 { 0x0020, "blank"  }, { 0,0,0 }  },
+      {	 { 0x0000, "cntrl"  }, { 0,0,0 }  },
+      {	 { 0x001F, "cntrl"  }, { 0,0,0 }  },
+      {	 { 0x0020, "cntrl"  }, { 0,1,0 }  },
+      {	 { 0x0021, "cntrl"  }, { 0,1,0 }  },
+      {	 { 0x002F, "cntrl"  }, { 0,1,0 }  },
+      {	 { 0x0030, "cntrl"  }, { 0,1,0 }  },
+      {	 { 0x0039, "cntrl"  }, { 0,1,0 }  },
+      {	 { 0x003A, "cntrl"  }, { 0,1,0 }  },
+      {	 { 0x0040, "cntrl"  }, { 0,1,0 }  },
+      {	 { 0x0041, "cntrl"  }, { 0,1,0 }  },
+      {	 { 0x005A, "cntrl"  }, { 0,1,0 }  },
+      {	 { 0x005B, "cntrl"  }, { 0,1,0 }  },
+      {	 { 0x0060, "cntrl"  }, { 0,1,0 }  },
+      {	 { 0x0061, "cntrl"  }, { 0,1,0 }  },
+      {	 { 0x007A, "cntrl"  }, { 0,1,0 }  },
+      {	 { 0x007B, "cntrl"  }, { 0,1,0 }  },
+      {	 { 0x007E, "cntrl"  }, { 0,1,0 }  },
+      {	 { 0x007F, "cntrl"  }, { 0,0,0 }  },
+      {	 { 0x0080, "cntrl"  }, { 0,1,0 }  },
+      {	 { 0x0000, "digit"  }, { 0,1,0 }  },
+      {	 { 0x001F, "digit"  }, { 0,1,0 }  },
+      {	 { 0x0020, "digit"  }, { 0,1,0 }  },
+      {	 { 0x0021, "digit"  }, { 0,1,0 }  },
+      {	 { 0x002F, "digit"  }, { 0,1,0 }  },
+      {	 { 0x0030, "digit"  }, { 0,0,0 }  },
+      {	 { 0x0039, "digit"  }, { 0,0,0 }  },
+      {	 { 0x003A, "digit"  }, { 0,1,0 }  },
+      {	 { 0x0040, "digit"  }, { 0,1,0 }  },
+      {	 { 0x0041, "digit"  }, { 0,1,0 }  },
+      {	 { 0x005A, "digit"  }, { 0,1,0 }  },
+      {	 { 0x005B, "digit"  }, { 0,1,0 }  },
+      {	 { 0x0060, "digit"  }, { 0,1,0 }  },
+      {	 { 0x0061, "digit"  }, { 0,1,0 }  },
+      {	 { 0x007A, "digit"  }, { 0,1,0 }  },
+      {	 { 0x007B, "digit"  }, { 0,1,0 }  },
+      {	 { 0x007E, "digit"  }, { 0,1,0 }  },
+      {	 { 0x007F, "digit"  }, { 0,1,0 }  },
+      {	 { 0x0080, "digit"  }, { 0,1,0 }  },
+      {	 { 0x0000, "graph"  }, { 0,1,0 }  },
+      {	 { 0x001F, "graph"  }, { 0,1,0 }  },
+      {	 { 0x0020, "graph"  }, { 0,1,0 }  },
+      {	 { 0x0021, "graph"  }, { 0,0,0 }  },
+      {	 { 0x002F, "graph"  }, { 0,0,0 }  },
+      {	 { 0x0030, "graph"  }, { 0,0,0 }  },
+      {	 { 0x0039, "graph"  }, { 0,0,0 }  },
+      {	 { 0x003A, "graph"  }, { 0,0,0 }  },
+      {	 { 0x0040, "graph"  }, { 0,0,0 }  },
+      {	 { 0x0041, "graph"  }, { 0,0,0 }  },
+      {	 { 0x005A, "graph"  }, { 0,0,0 }  },
+      {	 { 0x005B, "graph"  }, { 0,0,0 }  },
+      {	 { 0x0060, "graph"  }, { 0,0,0 }  },
+      {	 { 0x0061, "graph"  }, { 0,0,0 }  },
+      {	 { 0x007A, "graph"  }, { 0,0,0 }  },
+      {	 { 0x007B, "graph"  }, { 0,0,0 }  },
+      {	 { 0x007E, "graph"  }, { 0,0,0 }  },
+      {	 { 0x007F, "graph"  }, { 0,1,0 }  },
+      {	 { 0x0080, "graph"  }, { 0,1,0 }  },
+      {	 { 0x0000, "print"  }, { 0,1,0 }  },
+      {	 { 0x001F, "print"  }, { 0,1,0 }  },
+      {	 { 0x0020, "print"  }, { 0,0,0 }  },
+      {	 { 0x0021, "print"  }, { 0,0,0 }  },
+      {	 { 0x002F, "print"  }, { 0,0,0 }  },
+      {	 { 0x0030, "print"  }, { 0,0,0 }  },
+      {	 { 0x0039, "print"  }, { 0,0,0 }  },
+      {	 { 0x003A, "print"  }, { 0,0,0 }  },
+      {	 { 0x0040, "print"  }, { 0,0,0 }  },
+      {	 { 0x0041, "print"  }, { 0,0,0 }  },
+      {	 { 0x005A, "print"  }, { 0,0,0 }  },
+      {	 { 0x005B, "print"  }, { 0,0,0 }  },
+      {	 { 0x0060, "print"  }, { 0,0,0 }  },
+      {	 { 0x0061, "print"  }, { 0,0,0 }  },
+      {	 { 0x007A, "print"  }, { 0,0,0 }  },
+      {	 { 0x007B, "print"  }, { 0,0,0 }  },
+      {	 { 0x007E, "print"  }, { 0,0,0 }  },
+      {	 { 0x007F, "print"  }, { 0,1,0 }  },
+      {	 { 0x0080, "print"  }, { 0,1,0 }  },
+      {	 { 0x0000, "punct"  }, { 0,1,0 }  },
+      {	 { 0x001F, "punct"  }, { 0,1,0 }  },
+      {	 { 0x0020, "punct"  }, { 0,1,0 }  },
+      {	 { 0x0021, "punct"  }, { 0,0,0 }  },
+      {	 { 0x002F, "punct"  }, { 0,0,0 }  },
+      {	 { 0x0030, "punct"  }, { 0,1,0 }  },
+      {	 { 0x0039, "punct"  }, { 0,1,0 }  },
+      {	 { 0x003A, "punct"  }, { 0,0,0 }  },
+      {	 { 0x0040, "punct"  }, { 0,0,0 }  },
+      {	 { 0x0041, "punct"  }, { 0,1,0 }  },
+      {	 { 0x005A, "punct"  }, { 0,1,0 }  },
+      {	 { 0x005B, "punct"  }, { 0,0,0 }  },
+      {	 { 0x0060, "punct"  }, { 0,0,0 }  },
+      {	 { 0x0061, "punct"  }, { 0,1,0 }  },
+      {	 { 0x007A, "punct"  }, { 0,1,0 }  },
+      {	 { 0x007B, "punct"  }, { 0,0,0 }  },
+      {	 { 0x007E, "punct"  }, { 0,0,0 }  },
+      {	 { 0x007F, "punct"  }, { 0,1,0 }  },
+      {	 { 0x0080, "punct"  }, { 0,1,0 }  },
+      {	 { 0x0000, "space"  }, { 0,1,0 }  },
+      {	 { 0x001F, "space"  }, { 0,1,0 }  },
+      {	 { 0x0020, "space"  }, { 0,0,0 }  },
+      {	 { 0x0021, "space"  }, { 0,1,0 }  },
+      {	 { 0x002F, "space"  }, { 0,1,0 }  },
+      {	 { 0x007E, "space"  }, { 0,1,0 }  },
+      {	 { 0x007F, "space"  }, { 0,1,0 }  },
+      {	 { 0x0080, "space"  }, { 0,1,0 }  },
+      {	 { 0x0000, "lower"  }, { 0,1,0 }  },
+      {	 { 0x001F, "lower"  }, { 0,1,0 }  },
+      {	 { 0x0020, "lower"  }, { 0,1,0 }  },
+      {	 { 0x0021, "lower"  }, { 0,1,0 }  },
+      {	 { 0x002F, "lower"  }, { 0,1,0 }  },
+      {	 { 0x0030, "lower"  }, { 0,1,0 }  },
+      {	 { 0x0039, "lower"  }, { 0,1,0 }  },
+      {	 { 0x003A, "lower"  }, { 0,1,0 }  },
+      {	 { 0x0040, "lower"  }, { 0,1,0 }  },
+      {	 { 0x0041, "lower"  }, { 0,1,0 }  },
+      {	 { 0x005A, "lower"  }, { 0,1,0 }  },
+      {	 { 0x005B, "lower"  }, { 0,1,0 }  },
+      {	 { 0x0060, "lower"  }, { 0,1,0 }  },
+      {	 { 0x0061, "lower"  }, { 0,0,0 }  },
+      {	 { 0x007A, "lower"  }, { 0,0,0 }  },
+      {	 { 0x007B, "lower"  }, { 0,1,0 }  },
+      {	 { 0x007E, "lower"  }, { 0,1,0 }  },
+      {	 { 0x007F, "lower"  }, { 0,1,0 }  },
+      {	 { 0x0080, "lower"  }, { 0,1,0 }  },
+      {	 { 0x0000, "upper"  }, { 0,1,0 }  },
+      {	 { 0x001F, "upper"  }, { 0,1,0 }  },
+      {	 { 0x0020, "upper"  }, { 0,1,0 }  },
+      {	 { 0x0021, "upper"  }, { 0,1,0 }  },
+      {	 { 0x002F, "upper"  }, { 0,1,0 }  },
+      {	 { 0x0030, "upper"  }, { 0,1,0 }  },
+      {	 { 0x0039, "upper"  }, { 0,1,0 }  },
+      {	 { 0x003A, "upper"  }, { 0,1,0 }  },
+      {	 { 0x0040, "upper"  }, { 0,1,0 }  },
+      {	 { 0x0041, "upper"  }, { 0,0,0 }  },
+      {	 { 0x005A, "upper"  }, { 0,0,0 }  },
+      {	 { 0x005B, "upper"  }, { 0,1,0 }  },
+      {	 { 0x0060, "upper"  }, { 0,1,0 }  },
+      {	 { 0x0061, "upper"  }, { 0,1,0 }  },
+      {	 { 0x007A, "upper"  }, { 0,1,0 }  },
+      {	 { 0x007B, "upper"  }, { 0,1,0 }  },
+      {	 { 0x007E, "upper"  }, { 0,1,0 }  },
+      {	 { 0x007F, "upper"  }, { 0,1,0 }  },
+      {	 { 0x0080, "upper"  }, { 0,1,0 }  },
+      {	 { 0x0000, "xdigit" }, { 0,1,0 }  },
+      {	 { 0x001F, "xdigit" }, { 0,1,0 }  },
+      {	 { 0x0020, "xdigit" }, { 0,1,0 }  },
+      {	 { 0x0021, "xdigit" }, { 0,1,0 }  },
+      {	 { 0x002F, "xdigit" }, { 0,1,0 }  },
+      {	 { 0x0030, "xdigit" }, { 0,0,0 }  },
+      {	 { 0x0039, "xdigit" }, { 0,0,0 }  },
+      {	 { 0x003A, "xdigit" }, { 0,1,0 }  },
+      {	 { 0x0040, "xdigit" }, { 0,1,0 }  },
+      {	 { 0x0041, "xdigit" }, { 0,0,0 }  },
+      {	 { 0x005A, "xdigit" }, { 0,1,0 }  },
+      {	 { 0x005B, "xdigit" }, { 0,1,0 }  },
+      {	 { 0x0060, "xdigit" }, { 0,1,0 }  },
+      {	 { 0x0061, "xdigit" }, { 0,0,0 }  },
+      {	 { 0x007A, "xdigit" }, { 0,1,0 }  },
+      {	 { 0x007B, "xdigit" }, { 0,1,0 }  },
+      {	 { 0x007E, "xdigit" }, { 0,1,0 }  },
+      {	 { 0x007F, "xdigit" }, { 0,1,0 }  },
+      {	 { 0x0080, "xdigit" }, { 0,1,0 }  },
+      {	 { 0x0061, "xxxxxx" }, { 0,1,0 }  },
+      { .is_last = 1 }
+    }
+  },
+  {
+#if 0
+    { Tiswctype, TST_LOC_eucJP },
+#else
+    { Tiswctype, TST_LOC_ja_UTF8 },
+#endif
+    {
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0x3029, "alnum"  }, { 0,1,0 }  },	   /* Hangzhou NUM9	 */
+#else
+      {	 { 0x3029, "alnum"  }, { 0,0,0 }  },	   /* Hangzhou NUM9	 */
+#endif
+      {	 { 0xFE4F, "alnum"  }, { 0,1,0 }  },	   /* CJK UNI.IDEO.	 */
+      {	 { 0xFF19, "alnum"  }, { 0,0,0 }  },	   /* FULL 9		 */
+      {	 { 0xFF20, "alnum"  }, { 0,1,0 }  },	   /* FULL @		 */
+      {	 { 0xFF3A, "alnum"  }, { 0,0,0 }  },	   /* FULL Z		 */
+      {	 { 0xFF40, "alnum"  }, { 0,1,0 }  },	   /* FULL GRAVE ACC.	 */
+      {	 { 0xFF5A, "alnum"  }, { 0,0,0 }  },	   /* FULL z		 */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0xFF71, "alnum"  }, { 0,1,0 }  },	   /* HALF KATA A	 */
+#else
+      {	 { 0xFF71, "alnum"  }, { 0,0,0 }  },	   /* HALF KATA A	 */
+#endif
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0x3029, "alpha"  }, { 0,1,0 }  },	   /* Hangzhou NUM9	 */
+#else
+      {	 { 0x3029, "alpha"  }, { 0,0,0 }  },	   /* Hangzhou NUM9	 */
+#endif
+      {	 { 0xFE4F, "alpha"  }, { 0,1,0 }  },	   /* CJK UNI.IDEO.	 */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0xFF19, "alpha"  }, { 0,1,0 }  },	   /* FULL 9		 */
+#else
+      {	 { 0xFF19, "alpha"  }, { 0,0,0 }  },	   /* FULL 9		 */
+#endif
+      {	 { 0xFF20, "alpha"  }, { 0,1,0 }  },	   /* FULL @		 */
+      {	 { 0xFF3A, "alpha"  }, { 0,0,0 }  },	   /* FULL Z		 */
+      {	 { 0xFF40, "alpha"  }, { 0,1,0 }  },	   /* FULL GRAVE ACC.	 */
+      {	 { 0xFF5A, "alpha"  }, { 0,0,0 }  },	   /* FULL z		 */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0xFF71, "alpha"  }, { 0,1,0 }  },	   /* HALF KATA A	 */
+#else
+      {	 { 0xFF71, "alpha"  }, { 0,0,0 }  },	   /* HALF KATA A	 */
+#endif
+      {	 { 0x0080, "cntrl"  }, { 0,0,0 }  },	   /* CNTRL		 */
+      {	 { 0x3000, "cntrl"  }, { 0,1,0 }  },	   /* IDEO. SPACE	 */
+      {	 { 0x3029, "digit"  }, { 0,1,0 }  },	   /* Hangzhou NUM9	 */
+      {	 { 0x32CB, "digit"  }, { 0,1,0 }  },	   /* IDEO.TEL.SYM.DEC12 */
+      /* 21: */
+      {	 { 0x33FE, "digit"  }, { 0,1,0 }  },	   /* CJK IDEO.TEL.31th	 */
+      {	 { 0xFF19, "digit"  }, { 0,1,0 }  },	   /* FULL 9		 */
+      {	 { 0x3000, "graph"  }, { 0,1,0 }  },	   /* IDEO. SPACE	 */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0x3020, "graph"  }, { 0,1,0 }  },	   /* POSTAL MARK FACE	 */
+      {	 { 0x3029, "graph"  }, { 0,1,0 }  },	   /* Hangzhou NUM9	 */
+      {	 { 0x302F, "graph"  }, { 0,1,0 }  },	   /* Diacritics(Hangul) */
+      {	 { 0x3037, "graph"  }, { 0,1,0 }  },	   /* Separator Symbol	 */
+      {	 { 0x303F, "graph"  }, { 0,1,0 }  },	   /* IDEO. HALF SPACE	 */
+#else
+      {	 { 0x3020, "graph"  }, { 0,0,0 }  },	   /* POSTAL MARK FACE	 */
+      {	 { 0x3029, "graph"  }, { 0,0,0 }  },	   /* Hangzhou NUM9	 */
+      {	 { 0x302F, "graph"  }, { 0,0,0 }  },	   /* Diacritics(Hangul) */
+      {	 { 0x3037, "graph"  }, { 0,0,0 }  },	   /* Separator Symbol	 */
+      {	 { 0x303F, "graph"  }, { 0,0,0 }  },	   /* IDEO. HALF SPACE	 */
+#endif
+      /* 29: */
+      {	 { 0x3041, "graph"  }, { 0,0,0 }  },	   /* HIRAGANA a	 */
+      /* Non jis: */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0x3094, "graph"  }, { 0,1,0 }  },	   /* HIRAGANA u"	 */
+#else
+      {	 { 0x3094, "graph"  }, { 0,0,0 }  },	   /* HIRAGANA u"	 */
+#endif
+      /* Non jis: */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0x3099, "graph"  }, { 0,1,0 }  },	   /* SOUND MARK	 */
+#else
+      {	 { 0x3099, "graph"  }, { 0,0,0 }  },	   /* SOUND MARK	 */
+#endif
+      {	 { 0x309E, "graph"  }, { 0,0,0 }  },	   /* ITERATION MARK	 */
+      /* 33: */
+      {	 { 0x30A1, "graph"  }, { 0,0,0 }  },	   /* KATAKANA a	 */
+      /* Non jis: */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0x30FA, "graph"  }, { 0,1,0 }  },	   /* KATAKANA wo"	 */
+#else
+      {	 { 0x30FA, "graph"  }, { 0,0,0 }  },	   /* KATAKANA wo"	 */
+#endif
+      {	 { 0x30FB, "graph"  }, { 0,0,0 }  },	   /* KATAKANA MID.DOT	 */
+      {	 { 0x30FE, "graph"  }, { 0,0,0 }  },	   /* KATAKANA ITERATION */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0x3191, "graph"  }, { 0,1,0 }  },	   /* KANBUN REV.MARK	 */
+      {	 { 0x3243, "graph"  }, { 0,1,0 }  },	   /* IDEO. MARK (reach) */
+      {	 { 0x32CB, "graph"  }, { 0,1,0 }  },	   /* IDEO.TEL.SYM.DEC12 */
+      {	 { 0x32FE, "graph"  }, { 0,1,0 }  },	   /* MARU KATAKANA wo	 */
+      {	 { 0x33FE, "graph"  }, { 0,1,0 }  },	   /* CJK IDEO.TEL.31th	 */
+#else
+      {	 { 0x3191, "graph"  }, { 0,0,0 }  },	   /* KANBUN REV.MARK	 */
+      {	 { 0x3243, "graph"  }, { 0,0,0 }  },	   /* IDEO. MARK (reach) */
+      {	 { 0x32CB, "graph"  }, { 0,0,0 }  },	   /* IDEO.TEL.SYM.DEC12 */
+      {	 { 0x32FE, "graph"  }, { 0,0,0 }  },	   /* MARU KATAKANA wo	 */
+      {	 { 0x33FE, "graph"  }, { 0,0,0 }  },	   /* CJK IDEO.TEL.31th	 */
+#endif
+      {	 { 0x4E00, "graph"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.	 */
+      {	 { 0x4E05, "graph"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.	 */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0x4E06, "graph"  }, { 0,1,0 }  },	   /* CJK UNI.IDEO.NON-J */
+#else
+      {	 { 0x4E06, "graph"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.NON-J */
+#endif
+      {	 { 0x4E07, "graph"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.	 */
+      {	 { 0x4FFF, "graph"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.	 */
+      {	 { 0x9000, "graph"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.	 */
+      {	 { 0x9006, "graph"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.	 */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0x9007, "graph"  }, { 0,1,0 }  },	   /* CJK UNI.IDEO.NON-J */
+      {	 { 0x9FA4, "graph"  }, { 0,1,0 }  },	   /* CJK UNI.IDEO.NON-J */
+#else
+      {	 { 0x9007, "graph"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.NON-J */
+      {	 { 0x9FA4, "graph"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.NON-J */
+#endif
+      /* 51 */
+      {	 { 0x9FA5, "graph"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.	 */
+      /* Non jis: */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0xFE4F, "graph"  }, { 0,1,0 }  },	   /* CJK UNI.IDEO.	 */
+#else
+      {	 { 0xFE4F, "graph"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.	 */
+#endif
+      {	 { 0xFF0F, "graph"  }, { 0,0,0 }  },	   /* FULL SLASH	 */
+      {	 { 0xFF19, "graph"  }, { 0,0,0 }  },	   /* FULL 9		 */
+      {	 { 0xFF20, "graph"  }, { 0,0,0 }  },	   /* FULL @		 */
+      {	 { 0xFF3A, "graph"  }, { 0,0,0 }  },	   /* FULL Z		 */
+      {	 { 0xFF40, "graph"  }, { 0,0,0 }  },	   /* FULL GRAVE ACC.	 */
+      {	 { 0xFF5A, "graph"  }, { 0,0,0 }  },	   /* FULL z		 */
+      {	 { 0xFF5E, "graph"  }, { 0,0,0 }  },	   /* FULL ~ (tilde)	 */
+      {	 { 0xFF61, "graph"  }, { 0,0,0 }  },	   /* HALF IDEO.STOP. .	 */
+      {	 { 0xFF65, "graph"  }, { 0,0,0 }  },	   /* HALF KATA MID.DOT	 */
+      {	 { 0xFF66, "graph"  }, { 0,0,0 }  },	   /* HALF KATA WO	 */
+      {	 { 0xFF6F, "graph"  }, { 0,0,0 }  },	   /* HALF KATA tu	 */
+      {	 { 0xFF70, "graph"  }, { 0,0,0 }  },	   /* HALF KATA PL -	 */
+      {	 { 0xFF71, "graph"  }, { 0,0,0 }  },	   /* HALF KATA A	 */
+      {	 { 0xFF9E, "graph"  }, { 0,0,0 }  },	   /* HALF KATA MI	 */
+      {	 { 0x3000, "print"  }, { 0,0,0 }  },	   /* IDEO. SPACE	 */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0x3020, "print"  }, { 0,1,0 }  },	   /* POSTAL MARK FACE	 */
+      {	 { 0x3029, "print"  }, { 0,1,0 }  },	   /* Hangzhou NUM9	 */
+      {	 { 0x302F, "print"  }, { 0,1,0 }  },	   /* Diacritics(Hangul) */
+      {	 { 0x3037, "print"  }, { 0,1,0 }  },	   /* Separator Symbol	 */
+#else
+      {	 { 0x3020, "print"  }, { 0,0,0 }  },	   /* POSTAL MARK FACE	 */
+      {	 { 0x3029, "print"  }, { 0,0,0 }  },	   /* Hangzhou NUM9	 */
+      {	 { 0x302F, "print"  }, { 0,0,0 }  },	   /* Diacritics(Hangul) */
+      {	 { 0x3037, "print"  }, { 0,0,0 }  },	   /* Separator Symbol	 */
+#endif
+      {	 { 0x4E00, "print"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.	 */
+      {	 { 0x4E05, "print"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.	 */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0x4E06, "print"  }, { 0,1,0 }  },	   /* CJK UNI.IDEO.NON-J */
+#else
+      {	 { 0x4E06, "print"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.NON-J */
+#endif
+      {	 { 0x4E07, "print"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.	 */
+      {	 { 0x4FFF, "print"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.	 */
+      {	 { 0x9000, "print"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.	 */
+      {	 { 0x9006, "print"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.	 */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0x9007, "print"  }, { 0,1,0 }  },	   /* CJK UNI.IDEO.NON-J */
+      {	 { 0x9FA4, "print"  }, { 0,1,0 }  },	   /* CJK UNI.IDEO.NON-J */
+#else
+      {	 { 0x9007, "print"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.NON-J */
+      {	 { 0x9FA4, "print"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.NON-J */
+#endif
+      /* 81: */
+      {	 { 0x9FA5, "print"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.	 */
+      /* Non jis: */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0xFE4F, "print"  }, { 0,1,0 }  },	   /* CJK UNI.IDEO.	 */
+#else
+      {	 { 0xFE4F, "print"  }, { 0,0,0 }  },	   /* CJK UNI.IDEO.	 */
+#endif
+      {	 { 0x3000, "punct"  }, { 0,1,0 }  },	   /* IDEO. SPACE	 */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0x3020, "punct"  }, { 0,1,0 }  },	   /* POSTAL MARK FACE	 */
+      {	 { 0x302F, "punct"  }, { 0,1,0 }  },	   /* Diacritics(Hangul) */
+      {	 { 0x3037, "punct"  }, { 0,1,0 }  },	   /* FEED Separator	 */
+      {	 { 0x303F, "punct"  }, { 0,1,0 }  },	   /* IDEO. HALF SPACE	 */
+#else
+      {	 { 0x3020, "punct"  }, { 0,0,0 }  },	   /* POSTAL MARK FACE	 */
+      {	 { 0x302F, "punct"  }, { 0,0,0 }  },	   /* Diacritics(Hangul) */
+      {	 { 0x3037, "punct"  }, { 0,0,0 }  },	   /* FEED Separator	 */
+      {	 { 0x303F, "punct"  }, { 0,0,0 }  },	   /* IDEO. HALF SPACE	 */
+#endif
+      {	 { 0x3041, "punct"  }, { 0,1,0 }  },	   /* HIRAGANA a	 */
+      {	 { 0x3094, "punct"  }, { 0,1,0 }  },	   /* HIRAGANA u"	 */
+      /* 90: */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0x3099, "punct"  }, { 0,1,0 }  },	   /* SOUND MARK	 */
+#else
+      {	 { 0x3099, "punct"  }, { 0,0,0 }  },	   /* SOUND MARK	 */
+#endif
+      {	 { 0x309E, "punct"  }, { 0,1,0 }  },	   /* ITERATION MARK	 */
+      {	 { 0x30A1, "punct"  }, { 0,1,0 }  },	   /* KATAKANA a	 */
+      {	 { 0x30FA, "punct"  }, { 0,1,0 }  },	   /* KATAKANA wo"	 */
+      {	 { 0x30FB, "punct"  }, { 0,0,0 }  },	   /* KATAKANA MID.DOT	 */
+      /* 95: */
+      {	 { 0x30FE, "punct"  }, { 0,1,0 }  },	   /* KATAKANA ITERATION */
+#ifdef SHOJI_IS_RIGHT
+      {	 { 0x3191, "punct"  }, { 0,1,0 }  },	   /* KANBUN REV.MARK	 */
+      {	 { 0x3243, "punct"  }, { 0,1,0 }  },	   /* IDEO. MARK (reach) */
+      {	 { 0x32CB, "punct"  }, { 0,1,0 }  },	   /* IDEO.TEL.SYM.DEC12 */
+      {	 { 0x32FE, "punct"  }, { 0,1,0 }  },	   /* MARU KATAKANA wo	 */
+      {	 { 0x33FE, "punct"  }, { 0,1,0 }  },	   /* CJK IDEO.TEL.31th	 */
+#else
+      {	 { 0x3191, "punct"  }, { 0,0,0 }  },	   /* KANBUN REV.MARK	 */
+      {	 { 0x3243, "punct"  }, { 0,0,0 }  },	   /* IDEO. MARK (reach) */
+      {	 { 0x32CB, "punct"  }, { 0,0,0 }  },	   /* IDEO.TEL.SYM.DEC12 */
+      {	 { 0x32FE, "punct"  }, { 0,0,0 }  },	   /* MARU KATAKANA wo	 */
+      {	 { 0x33FE, "punct"  }, { 0,0,0 }  },	   /* CJK IDEO.TEL.31th	 */
+#endif
+      {	 { 0x9007, "punct"  }, { 0,1,0 }  },	   /* CJK UNI.IDEO.NON-J */
+      {	 { 0x9FA4, "punct"  }, { 0,1,0 }  },	   /* CJK UNI.IDEO.NON-J */
+      {	 { 0x9FA5, "punct"  }, { 0,1,0 }  },	   /* CJK UNI.IDEO.	 */
+      {	 { 0xFF0F, "punct"  }, { 0,0,0 }  },	   /* FULL SLASH	 */
+      /* 105: */
+      {	 { 0xFF19, "punct"  }, { 0,1,0 }  },	   /* FULL 9		 */
+      {	 { 0xFF20, "punct"  }, { 0,0,0 }  },	   /* FULL @		 */
+      {	 { 0xFF3A, "punct"  }, { 0,1,0 }  },	   /* FULL Z		 */
+      {	 { 0xFF40, "punct"  }, { 0,0,0 }  },	   /* FULL GRAVE ACC.	 */
+      {	 { 0xFF5A, "punct"  }, { 0,1,0 }  },	   /* FULL z		 */
+      {	 { 0xFF5E, "punct"  }, { 0,0,0 }  },	   /* FULL ~ (tilde)	 */
+      {	 { 0xFF61, "punct"  }, { 0,0,0 }  },	   /* HALF IDEO.STOP. .	 */
+      {	 { 0xFF65, "punct"  }, { 0,0,0 }  },	   /* HALF KATA MID.DOT	 */
+      {	 { 0xFF70, "punct"  }, { 0,1,0 }  },	   /* HALF KATA PL -	 */
+      {	 { 0xFF9E, "punct"  }, { 0,1,0 }  },	   /* HALF KATA MI	 */
+      /* 115: */
+      {	 { 0x3000, "space"  }, { 0,0,0 }  },	   /* IDEO. SPACE	 */
+      {	 { 0x303F, "space"  }, { 0,1,0 }  },	   /* IDEO. HALF SPACE	 */
+      {	 { 0x3041, "lower"  }, { 0,1,0 }  },	   /* HIRAGANA a	 */
+      {	 { 0x3094, "lower"  }, { 0,1,0 }  },	   /* HIRAGANA u"	 */
+      {	 { 0x30A1, "lower"  }, { 0,1,0 }  },	   /* KATAKANA a	 */
+      {	 { 0x30FA, "lower"  }, { 0,1,0 }  },	   /* KATAKANA wo"	 */
+      {	 { 0xFF66, "lower"  }, { 0,1,0 }  },	   /* HALF KATA WO	 */
+      {	 { 0xFF6F, "lower"  }, { 0,1,0 }  },	   /* HALF KATA tu	 */
+      {	 { 0xFF70, "lower"  }, { 0,1,0 }  },	   /* HALF KATA PL -	 */
+      /* 124: */
+      {	 { 0xFF71, "lower"  }, { 0,1,0 }  },	   /* HALF KATA A	 */
+      {	 { 0xFF9E, "lower"  }, { 0,1,0 }  },	   /* HALF KATA MI	 */
+      {	 { 0xFF71, "upper"  }, { 0,1,0 }  },	   /* HALF KATA A	 */
+      {	 { 0xFF19, "xdigit" }, { 0,1,0 }  },	   /* FULL 9		 */
+      {	 { 0x3000, "jspace" }, { 0,0,0 }  },	   /* IDEO. SPACE	 */
+      /* Non jis? */
+      {	 { 0x303F, "jspace" }, { 0,1,0 }  },	   /* IDEO.HALF SPACE	 */
+      {	 { 0xFF19, "jdigit" }, { 0,0,0 }  },	   /* FULL 9		 */
+      {	 { 0x3041, "jhira"  }, { 0,0,0 }  },	   /* HIRAGANA a	 */
+      {	 { 0x3094, "jhira"  }, { 0,1,0 }  },	   /* HIRAGANA u"	 */
+      {	 { 0x30A1, "jkata"  }, { 0,0,0 }  },	   /* KATAKANA a	 */
+      /* Non jis: */
+      {	 { 0x30FA, "jkata"  }, { 0,1,0 }  },	   /* KATAKANA wo"	 */
+      {	 { 0xFF66, "jkata"  }, { 0,0,0 }  },	   /* HALF KATA WO	 */
+      {	 { 0xFF6F, "jkata"  }, { 0,0,0 }  },	   /* HALF KATA tu	 */
+      {	 { 0x4E05, "jkanji" }, { 0,0,0 }  },	   /* CJK UNI.IDEO.	 */
+#ifdef SHOJI_IS_RIGHT
+      /* <NO_WAIVER>: */
+      {	 { 0x4E06, "jkanji" }, { 0,1,1 }  },	   /* CJK UNI.IDEO.NON-J */
+#else
+      /* XXX This character does not exist in EUC-JP.  */
+      {	 { 0x4E06, "jkanji" }, { 0,1,0 }  },	   /* CJK UNI.IDEO.NON-J */
+#endif
+      {	 { 0x4E07, "jkanji" }, { 0,0,0 }  },	   /* CJK UNI.IDEO.	 */
+      { .is_last = 1 }
+    }
+  },
+  {
+    { Tiswctype, TST_LOC_end }
+  }
+};
+
+
+/* dat_isw-funcs.c */

+ 125 - 0
test/locale-mbwc/dat_iswdigit.c

@@ -0,0 +1,125 @@
+/*
+ *  TEST SUITE FOR MB/WC FUNCTIONS IN C LIBRARY
+ *
+ *	 FILE:	dat_iswdigit.c
+ *
+ *	 ISW*:	int iswdigit (wint_t wc);
+ */
+
+
+#include "dat_isw-funcs.h"
+
+
+TST_ISW_LOC (DIGIT, digit) = {
+
+  {   TST_ISW_REC (de, digit)
+      {
+	{  { 0x0080 }, { 0,1,0 }  },	/* CTRL	    */
+	{  { 0x009F }, { 0,1,0 }  },	/* CTRL	    */
+	{  { 0x00A0 }, { 0,1,0 }  },	/* NB SPACE */
+	{  { 0x00A1 }, { 0,1,0 }  },	/* UD !	    */
+	{  { 0x00B0 }, { 0,1,0 }  },	/* Degree   */
+	{  { 0x00B1 }, { 0,1,0 }  },	/* +- sign  */
+	{  { 0x00B2 }, { 0,1,0 }  },	/* SUP 2    */
+	{  { 0x00B3 }, { 0,1,0 }  },	/* SUP 3    */
+	{  { 0x00B4 }, { 0,1,0 }  },	/* ACUTE    */
+	{  { 0x00B8 }, { 0,1,0 }  },	/* CEDILLA  */
+	{  { 0x00B9 }, { 0,1,0 }  },	/* SUP 1    */
+	{  { 0x00BB }, { 0,1,0 }  },	/* >>	    */
+	{  { 0x00BC }, { 0,1,0 }  },	/* 1/4	    */
+	{  { 0x00BD }, { 0,1,0 }  },	/* 1/2	    */
+	{  { 0x00BE }, { 0,1,0 }  },	/* 3/4	    */
+	{  { 0x00BF }, { 0,1,0 }  },	/* UD ?	    */
+	{  { 0x00C0 }, { 0,1,0 }  },	/* A Grave  */
+	{  { 0x00D6 }, { 0,1,0 }  },	/* O dia    */
+	{  { 0x00D7 }, { 0,1,0 }  },	/* multipl. */
+	{  { 0x00D8 }, { 0,1,0 }  },	/* O stroke */
+	{  { 0x00DF }, { 0,1,0 }  },	/* small Sh */
+	{  { 0x00E0 }, { 0,1,0 }  },	/* a grave  */
+	{  { 0x00F6 }, { 0,1,0 }  },	/* o dia    */
+	{  { 0x00F7 }, { 0,1,0 }  },	/* division */
+	{  { 0x00F8 }, { 0,1,0 }  },	/* o stroke */
+	{  { 0x00FF }, { 0,1,0 }  },	/* y dia    */
+	{ .is_last = 1 }		/* Last element.  */
+      }
+  },
+  {   TST_ISW_REC (enUS, digit)
+      {
+	{  { WEOF   }, { 0,1,0 }  },
+	{  { 0x0000 }, { 0,1,0 }  },
+	{  { 0x001F }, { 0,1,0 }  },
+	{  { 0x0020 }, { 0,1,0 }  },
+	{  { 0x0021 }, { 0,1,0 }  },
+	{  { 0x002F }, { 0,1,0 }  },
+	{  { 0x0030 }, { 0,0,0 }  },
+	{  { 0x0039 }, { 0,0,0 }  },
+	{  { 0x003A }, { 0,1,0 }  },
+	{  { 0x0040 }, { 0,1,0 }  },
+	{  { 0x0041 }, { 0,1,0 }  },
+	{  { 0x005A }, { 0,1,0 }  },
+	{  { 0x005B }, { 0,1,0 }  },
+	{  { 0x0060 }, { 0,1,0 }  },
+	{  { 0x0061 }, { 0,1,0 }  },
+	{  { 0x007A }, { 0,1,0 }  },
+	{  { 0x007B }, { 0,1,0 }  },
+	{  { 0x007E }, { 0,1,0 }  },
+	{  { 0x007F }, { 0,1,0 }  },
+	{  { 0x0080 }, { 0,1,0 }  },
+	{ .is_last = 1 }		/* Last element.  */
+      }
+  },
+#if 0
+  {   TST_ISW_REC (eucJP, digit)
+#else
+  {   TST_ISW_REC (ja_UTF8, digit)
+#endif
+      {
+	{  { 0x3000 }, { 0,1,0 }  },	/* IDEO. SPACE	      */
+	{  { 0x3020 }, { 0,1,0 }  },	/* POSTAL MARK FACE   */
+	{  { 0x3029 }, { 0,1,0 }  },	/* Hangzhou NUM9      */
+	{  { 0x302F }, { 0,1,0 }  },	/* Diacritics(Hangul) */
+	{  { 0x3037 }, { 0,1,0 }  },	/* Separator Symbol   */
+	{  { 0x303F }, { 0,1,0 }  },	/* IDEO. HALF SPACE   */
+	{  { 0x3041 }, { 0,1,0 }  },	/* HIRAGANA a	      */
+	{  { 0x3094 }, { 0,1,0 }  },	/* HIRAGANA u"	      */
+	{  { 0x3099 }, { 0,1,0 }  },	/* SOUND MARK	      */
+	{  { 0x309E }, { 0,1,0 }  },	/* ITERATION MARK     */
+	{  { 0x30A1 }, { 0,1,0 }  },	/* KATAKANA a	      */
+	{  { 0x30FA }, { 0,1,0 }  },	/* KATAKANA wo"	      */
+	{  { 0x30FB }, { 0,1,0 }  },	/* KATAKANA MID.DOT   */
+	{  { 0x30FE }, { 0,1,0 }  },	/* KATAKANA ITERATION */
+	{  { 0x3191 }, { 0,1,0 }  },	/* KANBUN REV.MARK    */
+	{  { 0x3243 }, { 0,1,0 }  },	/* IDEO. MARK (reach) */
+	{  { 0x32CB }, { 0,1,0 }  },	/* IDEO.TEL.SYM.DEC12 */
+	{  { 0x32FE }, { 0,1,0 }  },	/* MARU KATAKANA wo   */
+	{  { 0x33FE }, { 0,1,0 }  },	/* CJK IDEO.TEL.31th  */
+	{  { 0x4E00 }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x4E05 }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x4E06 }, { 0,1,0 }  },	/* CJK UNI.IDEO.NON-J */
+	{  { 0x4E07 }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x4FFF }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x9000 }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x9006 }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x9007 }, { 0,1,0 }  },	/* CJK UNI.IDEO.NON-J */
+	{  { 0x9FA4 }, { 0,1,0 }  },	/* CJK UNI.IDEO.NON-J */
+	{  { 0x9FA5 }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0xFE4F }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0xFF0F }, { 0,1,0 }  },	/* FULL SLASH	      */
+	{  { 0xFF19 }, { 0,1,0 }  },	/* FULL 9	      */
+	{  { 0xFF20 }, { 0,1,0 }  },	/* FULL @	      */
+	{  { 0xFF3A }, { 0,1,0 }  },	/* FULL Z	      */
+	{  { 0xFF40 }, { 0,1,0 }  },	/* FULL GRAVE ACC.    */
+	{  { 0xFF5A }, { 0,1,0 }  },	/* FULL z	      */
+	{  { 0xFF5E }, { 0,1,0 }  },	/* FULL ~ (tilde)     */
+	{  { 0xFF61 }, { 0,1,0 }  },	/* HALF IDEO.STOP. .  */
+	{  { 0xFF65 }, { 0,1,0 }  },	/* HALF KATA MID.DOT  */
+	{  { 0xFF66 }, { 0,1,0 }  },	/* HALF KATA WO	      */
+	{  { 0xFF6F }, { 0,1,0 }  },	/* HALF KATA tu	      */
+	{  { 0xFF70 }, { 0,1,0 }  },	/* HALF KATA PL -     */
+	{  { 0xFF71 }, { 0,1,0 }  },	/* HALF KATA A	      */
+	{  { 0xFF9E }, { 0,1,0 }  },	/* HALF KATA MI	      */
+	{ .is_last = 1 }		/* Last element.  */
+      }
+  },
+  {   TST_ISW_REC (end, digit) }
+};

+ 167 - 0
test/locale-mbwc/dat_iswgraph.c

@@ -0,0 +1,167 @@
+/*
+ *  TEST SUITE FOR MB/WC FUNCTIONS IN C LIBRARY
+ *
+ *	 FILE:	dat_iswgraph.c
+ *
+ *	 ISW*:	int iswgraph (wint_t wc);
+ */
+
+
+#include "dat_isw-funcs.h"
+
+
+TST_ISW_LOC (GRAPH, graph) = {
+
+  {   TST_ISW_REC (de, graph)
+      {
+	{  { 0x0080 }, { 0,1,0 }  },	/* CTRL	    */
+	{  { 0x009F }, { 0,1,0 }  },	/* CTRL	    */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0x00A0 }, { 0,1,0 }  },	/* NB SPACE */
+#else
+	{  { 0x00A0 }, { 0,0,0 }  },	/* NB SPACE */
+#endif
+	{  { 0x00A1 }, { 0,0,0 }  },	/* UD !	    */
+	{  { 0x00B0 }, { 0,0,0 }  },	/* Degree   */
+	{  { 0x00B1 }, { 0,0,0 }  },	/* +- sign  */
+	{  { 0x00B2 }, { 0,0,0 }  },	/* SUP 2    */
+	{  { 0x00B3 }, { 0,0,0 }  },	/* SUP 3    */
+	{  { 0x00B4 }, { 0,0,0 }  },	/* ACUTE    */
+	{  { 0x00B8 }, { 0,0,0 }  },	/* CEDILLA  */
+	{  { 0x00B9 }, { 0,0,0 }  },	/* SUP 1    */
+	{  { 0x00BB }, { 0,0,0 }  },	/* >>	    */
+	{  { 0x00BC }, { 0,0,0 }  },	/* 1/4	    */
+	{  { 0x00BD }, { 0,0,0 }  },	/* 1/2	    */
+	{  { 0x00BE }, { 0,0,0 }  },	/* 3/4	    */
+	{  { 0x00BF }, { 0,0,0 }  },	/* UD ?	    */
+	{  { 0x00C0 }, { 0,0,0 }  },	/* A Grave  */
+	{  { 0x00D6 }, { 0,0,0 }  },	/* O dia    */
+	{  { 0x00D7 }, { 0,0,0 }  },	/* multipl. */
+	{  { 0x00D8 }, { 0,0,0 }  },	/* O stroke */
+	{  { 0x00DF }, { 0,0,0 }  },	/* small Sh */
+	{  { 0x00E0 }, { 0,0,0 }  },	/* a grave  */
+	{  { 0x00F6 }, { 0,0,0 }  },	/* o dia    */
+	{  { 0x00F7 }, { 0,0,0 }  },	/* division */
+	{  { 0x00F8 }, { 0,0,0 }  },	/* o stroke */
+	{  { 0x00FF }, { 0,0,0 }  },	/* y dia    */
+	{ .is_last = 1 }		/* Last element.  */
+      }
+  },
+  {   TST_ISW_REC (enUS, graph)
+      {
+	{  { WEOF   }, { 0,1,0 }  },
+	{  { 0x0000 }, { 0,1,0 }  },
+	{  { 0x001F }, { 0,1,0 }  },
+	{  { 0x0020 }, { 0,1,0 }  },
+	{  { 0x0021 }, { 0,0,0 }  },
+	{  { 0x002F }, { 0,0,0 }  },
+	{  { 0x0030 }, { 0,0,0 }  },
+	{  { 0x0039 }, { 0,0,0 }  },
+	{  { 0x003A }, { 0,0,0 }  },
+	{  { 0x0040 }, { 0,0,0 }  },
+	{  { 0x0041 }, { 0,0,0 }  },
+	{  { 0x005A }, { 0,0,0 }  },
+	{  { 0x005B }, { 0,0,0 }  },
+	{  { 0x0060 }, { 0,0,0 }  },
+	{  { 0x0061 }, { 0,0,0 }  },
+	{  { 0x007A }, { 0,0,0 }  },
+	{  { 0x007B }, { 0,0,0 }  },
+	{  { 0x007E }, { 0,0,0 }  },
+	{  { 0x007F }, { 0,1,0 }  },
+	{  { 0x0080 }, { 0,1,0 }  }, /* 20 */
+	{ .is_last = 1 }		/* Last element.  */
+      }
+  },
+#if 0
+  {   TST_ISW_REC( eucJP, graph )
+#else
+  {   TST_ISW_REC( ja_UTF8, graph )
+#endif
+      {
+	{  { 0x3000 }, { 0,1,0 }  },	/* IDEO. SPACE	      */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0x3020 }, { 0,1,0 }  },	/* POSTAL MARK FACE   */
+	{  { 0x3029 }, { 0,1,0 }  },	/* Hangzhou NUM9      */
+	{  { 0x302F }, { 0,1,0 }  },	/* Diacritics(Hangul) */
+	{  { 0x3037 }, { 0,1,0 }  },	/* Separator Symbol   */
+	{  { 0x303F }, { 0,1,0 }  },	/* IDEO. HALF SPACE   */
+#else
+	{  { 0x3020 }, { 0,0,0 }  },	/* POSTAL MARK FACE   */
+	{  { 0x3029 }, { 0,0,0 }  },	/* Hangzhou NUM9      */
+	{  { 0x302F }, { 0,0,0 }  },	/* Diacritics(Hangul) */
+	{  { 0x3037 }, { 0,0,0 }  },	/* Separator Symbol   */
+	{  { 0x303F }, { 0,0,0 }  },	/* IDEO. HALF SPACE   */
+#endif
+	{  { 0x3041 }, { 0,0,0 }  },	/* HIRAGANA a	      */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0x3094 }, { 0,1,0 }  },	/* HIRAGANA u"	      */  /* non jis */
+	{  { 0x3099 }, { 0,1,0 }  },	/* SOUND MARK	      */
+#else
+	{  { 0x3094 }, { 0,0,0 }  },	/* HIRAGANA u"	      */  /* non jis */
+	{  { 0x3099 }, { 0,0,0 }  },	/* SOUND MARK	      */
+#endif
+	{  { 0x309E }, { 0,0,0 }  },	/* ITERATION MARK     */  /* 10 */
+	{  { 0x30A1 }, { 0,0,0 }  },	/* KATAKANA a	      */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0x30FA }, { 0,1,0 }  },	/* KATAKANA wo"	      */  /* non jis */
+#else
+	{  { 0x30FA }, { 0,0,0 }  },	/* KATAKANA wo"	      */  /* non jis */
+#endif
+	{  { 0x30FB }, { 0,0,0 }  },	/* KATAKANA MID.DOT   */
+	{  { 0x30FE }, { 0,0,0 }  },	/* KATAKANA ITERATION */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0x3191 }, { 0,1,0 }  },	/* KANBUN REV.MARK    */
+	{  { 0x3243 }, { 0,1,0 }  },	/* IDEO. MARK (reach) */
+	{  { 0x32CB }, { 0,1,0 }  },	/* IDEO.TEL.SYM.DEC12 */
+	{  { 0x32FE }, { 0,1,0 }  },	/* MARU KATAKANA wo   */
+	{  { 0x33FE }, { 0,1,0 }  },	/* CJK IDEO.TEL.31th  */
+#else
+	{  { 0x3191 }, { 0,0,0 }  },	/* KANBUN REV.MARK    */
+	{  { 0x3243 }, { 0,0,0 }  },	/* IDEO. MARK (reach) */
+	{  { 0x32CB }, { 0,0,0 }  },	/* IDEO.TEL.SYM.DEC12 */
+	{  { 0x32FE }, { 0,0,0 }  },	/* MARU KATAKANA wo   */
+	{  { 0x33FE }, { 0,0,0 }  },	/* CJK IDEO.TEL.31th  */
+#endif
+	{  { 0x4E00 }, { 0,0,0 }  },	/* CJK UNI.IDEO.      */  /* 20 */
+	{  { 0x4E05 }, { 0,0,0 }  },	/* CJK UNI.IDEO.      */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0x4E06 }, { 0,1,0 }  },	/* CJK UNI.IDEO.NON-J */
+#else
+	{  { 0x4E06 }, { 0,0,0 }  },	/* CJK UNI.IDEO.NON-J */
+#endif
+	{  { 0x4E07 }, { 0,0,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x4FFF }, { 0,0,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x9000 }, { 0,0,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x9006 }, { 0,0,0 }  },	/* CJK UNI.IDEO.      */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0x9007 }, { 0,1,0 }  },	/* CJK UNI.IDEO.NON-J */
+	{  { 0x9FA4 }, { 0,1,0 }  },	/* CJK UNI.IDEO.NON-J */
+#else
+	{  { 0x9007 }, { 0,0,0 }  },	/* CJK UNI.IDEO.NON-J */
+	{  { 0x9FA4 }, { 0,0,0 }  },	/* CJK UNI.IDEO.NON-J */
+#endif
+	{  { 0x9FA5 }, { 0,0,0 }  },	/* CJK UNI.IDEO.      */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0xFE4F }, { 0,1,0 }  },	/* CJK Wave Low Line  */  /* 30 */
+#else
+	{  { 0xFE4F }, { 0,0,0 }  },	/* CJK Wave Low Line  */  /* 30 */
+#endif
+	{  { 0xFF0F }, { 0,0,0 }  },	/* FULL SLASH	      */
+	{  { 0xFF19 }, { 0,0,0 }  },	/* FULL 9	      */
+	{  { 0xFF20 }, { 0,0,0 }  },	/* FULL @	      */
+	{  { 0xFF3A }, { 0,0,0 }  },	/* FULL Z	      */
+	{  { 0xFF40 }, { 0,0,0 }  },	/* FULL GRAVE ACC.    */
+	{  { 0xFF5A }, { 0,0,0 }  },	/* FULL z	      */
+	{  { 0xFF5E }, { 0,0,0 }  },	/* FULL ~ (tilde)     */
+	{  { 0xFF61 }, { 0,0,0 }  },	/* HALF IDEO.STOP. .  */
+	{  { 0xFF65 }, { 0,0,0 }  },	/* HALF KATA MID.DOT  */
+	{  { 0xFF66 }, { 0,0,0 }  },	/* HALF KATA WO	      */
+	{  { 0xFF6F }, { 0,0,0 }  },	/* HALF KATA tu	      */
+	{  { 0xFF70 }, { 0,0,0 }  },	/* HALF KATA PL -     */
+	{  { 0xFF71 }, { 0,0,0 }  },	/* HALF KATA A	      */
+	{  { 0xFF9E }, { 0,0,0 }  },	/* HALF KATA MI	      */
+	{ .is_last = 1 }		/* Last element.  */
+      }
+  },
+  {   TST_ISW_REC (end, graph) }
+};

+ 96 - 0
test/locale-mbwc/dat_iswlower.c

@@ -0,0 +1,96 @@
+/*
+ *  TEST SUITE FOR MB/WC FUNCTIONS IN C LIBRARY
+ *
+ *	 FILE:	dat_iswlower.c
+ *
+ *	 ISW*:	int iswlower (wint_t wc);
+ */
+
+
+#include "dat_isw-funcs.h"
+
+
+TST_ISW_LOC (LOWER, lower) = {
+
+  {   TST_ISW_REC (de, lower)
+      {
+	{  { 0x0080 }, { 0,1,0 }  },	/* CTRL	    */
+	{  { 0x009F }, { 0,1,0 }  },	/* CTRL	    */
+	{  { 0x00A0 }, { 0,1,0 }  },	/* NB SPACE */
+	{  { 0x00A1 }, { 0,1,0 }  },	/* UD !	    */
+	{  { 0x00B0 }, { 0,1,0 }  },	/* Degree   */
+	{  { 0x00B1 }, { 0,1,0 }  },	/* +- sign  */
+	{  { 0x00B2 }, { 0,1,0 }  },	/* SUP 2    */
+	{  { 0x00B3 }, { 0,1,0 }  },	/* SUP 3    */
+	{  { 0x00B4 }, { 0,1,0 }  },	/* ACUTE    */
+	{  { 0x00B8 }, { 0,1,0 }  },	/* CEDILLA  */
+	{  { 0x00B9 }, { 0,1,0 }  },	/* SUP 1    */
+	{  { 0x00BB }, { 0,1,0 }  },	/* >>	    */
+	{  { 0x00BC }, { 0,1,0 }  },	/* 1/4	    */
+	{  { 0x00BD }, { 0,1,0 }  },	/* 1/2	    */
+	{  { 0x00BE }, { 0,1,0 }  },	/* 3/4	    */
+	{  { 0x00BF }, { 0,1,0 }  },	/* UD ?	    */
+	{  { 0x00C0 }, { 0,1,0 }  },	/* A Grave  */
+	{  { 0x00D6 }, { 0,1,0 }  },	/* O dia    */
+	{  { 0x00D7 }, { 0,1,0 }  },	/* multipl. */
+	{  { 0x00D8 }, { 0,1,0 }  },	/* O stroke */
+	{  { 0x00DF }, { 0,0,0 }  },	/* small Sh */
+	{  { 0x00E0 }, { 0,0,0 }  },	/* a grave  */
+	{  { 0x00F6 }, { 0,0,0 }  },	/* o dia    */
+	{  { 0x00F7 }, { 0,1,0 }  },	/* division */
+	{  { 0x00F8 }, { 0,0,0 }  },	/* o stroke */
+	{  { 0x00FF }, { 0,0,0 }  },	/* y dia    */
+	{ .is_last = 1 }		/* Last element.  */
+      }
+  },
+  {   TST_ISW_REC (enUS, lower)
+      {
+	{  { WEOF   }, { 0,1,0 }  },
+	{  { 0x0000 }, { 0,1,0 }  },
+	{  { 0x001F }, { 0,1,0 }  },
+	{  { 0x0020 }, { 0,1,0 }  },
+	{  { 0x0021 }, { 0,1,0 }  },
+	{  { 0x002F }, { 0,1,0 }  },
+	{  { 0x0030 }, { 0,1,0 }  },
+	{  { 0x0039 }, { 0,1,0 }  },
+	{  { 0x003A }, { 0,1,0 }  },
+	{  { 0x0040 }, { 0,1,0 }  },
+	{  { 0x0041 }, { 0,1,0 }  },
+	{  { 0x005A }, { 0,1,0 }  },
+	{  { 0x005B }, { 0,1,0 }  },
+	{  { 0x0060 }, { 0,1,0 }  },
+	{  { 0x0061 }, { 0,0,0 }  },
+	{  { 0x007A }, { 0,0,0 }  },
+	{  { 0x007B }, { 0,1,0 }  },
+	{  { 0x007E }, { 0,1,0 }  },
+	{  { 0x007F }, { 0,1,0 }  },
+	{  { 0x0080 }, { 0,1,0 }  },
+	{ .is_last = 1 }		/* Last element.  */
+      }
+  },
+#if 0
+  {   TST_ISW_REC (eucJP, lower)
+#else
+  {   TST_ISW_REC (ja_UTF8, lower)
+#endif
+      {
+	{  { 0x3000 }, { 0,1,0 }  },	/* IDEO. SPACE	      */
+	{  { 0x303F }, { 0,1,0 }  },	/* IDEO. HALF SPACE   */
+	{  { 0x3041 }, { 0,1,0 }  },	/* HIRAGANA a	      */
+	{  { 0x3094 }, { 0,1,0 }  },	/* HIRAGANA u"	      */
+	{  { 0x3099 }, { 0,1,0 }  },	/* SOUND MARK	      */
+	{  { 0x309E }, { 0,1,0 }  },	/* ITERATION MARK     */
+	{  { 0x30A1 }, { 0,1,0 }  },	/* KATAKANA a	      */
+	{  { 0x30FA }, { 0,1,0 }  },	/* KATAKANA wo"	      */
+	{  { 0xFF3A }, { 0,1,0 }  },	/* FULL Z	      */
+	{  { 0xFF40 }, { 0,1,0 }  },	/* FULL GRAVE ACC.    */
+	{  { 0xFF5A }, { 0,0,0 }  },	/* FULL z	      */
+	{  { 0xFF6F }, { 0,1,0 }  },	/* HALF KATA tu	      */
+	{  { 0xFF71 }, { 0,1,0 }  },	/* HALF KATA A	      */
+	{  { 0xFF9E }, { 0,1,0 }  },	/* HALF KATA MI	      */
+	{ .is_last = 1 }		/* Last element.  */
+      }
+  },
+  {   TST_ISW_REC (end, lower) }
+
+};

+ 170 - 0
test/locale-mbwc/dat_iswprint.c

@@ -0,0 +1,170 @@
+/*
+ *  TEST SUITE FOR MB/WC FUNCTIONS IN C LIBRARY
+ *
+ *       FILE:  dat_iswprint.c
+ *
+ *       ISW*:  int iswprint (wint_t wc);
+ */
+
+
+#include "dat_isw-funcs.h"
+
+
+TST_ISW_LOC (PRINT, print) = {
+
+  {   TST_ISW_REC (de, print)
+      {
+	{  { 0x0080 }, { 0,1,0 }  },  /* CTRL     */
+	{  { 0x009F }, { 0,1,0 }  },  /* CTRL     */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0x00A0 }, { 0,1,0 }  },  /* NB SPACE */
+#else
+	{  { 0x00A0 }, { 0,0,0 }  },  /* NB SPACE */
+#endif
+	{  { 0x00A1 }, { 0,0,0 }  },  /* UD !     */
+	{  { 0x00B0 }, { 0,0,0 }  },  /* Degree   */
+	{  { 0x00B1 }, { 0,0,0 }  },  /* +- sign  */
+	{  { 0x00B2 }, { 0,0,0 }  },  /* SUP 2    */
+	{  { 0x00B3 }, { 0,0,0 }  },  /* SUP 3    */
+	{  { 0x00B4 }, { 0,0,0 }  },  /* ACUTE    */
+	{  { 0x00B8 }, { 0,0,0 }  },  /* CEDILLA  */
+	{  { 0x00B9 }, { 0,0,0 }  },  /* SUP 1    */
+	{  { 0x00BB }, { 0,0,0 }  },  /* >>       */
+	{  { 0x00BC }, { 0,0,0 }  },  /* 1/4      */
+	{  { 0x00BD }, { 0,0,0 }  },  /* 1/2      */
+	{  { 0x00BE }, { 0,0,0 }  },  /* 3/4      */
+	{  { 0x00BF }, { 0,0,0 }  },  /* UD ?     */
+	{  { 0x00C0 }, { 0,0,0 }  },  /* A Grave  */
+	{  { 0x00D6 }, { 0,0,0 }  },  /* O dia    */
+	{  { 0x00D7 }, { 0,0,0 }  },  /* multipl. */
+	{  { 0x00D8 }, { 0,0,0 }  },  /* O stroke */
+	{  { 0x00DF }, { 0,0,0 }  },  /* small Sh */
+	{  { 0x00E0 }, { 0,0,0 }  },  /* a grave  */
+	{  { 0x00F6 }, { 0,0,0 }  },  /* o dia    */
+	{  { 0x00F7 }, { 0,0,0 }  },  /* division */
+	{  { 0x00F8 }, { 0,0,0 }  },  /* o stroke */
+	{  { 0x00FF }, { 0,0,0 }  },  /* y dia    */
+	{ .is_last = 1 }		/* Last element.  */
+      }
+  },
+  {   TST_ISW_REC (enUS, print)
+      {
+	{  { WEOF   }, { 0,1,0 }  }, /* 01 */
+	{  { 0x0000 }, { 0,1,0 }  },
+	{  { 0x001F }, { 0,1,0 }  },
+	{  { 0x0020 }, { 0,0,0 }  },
+	{  { 0x0021 }, { 0,0,0 }  },
+	{  { 0x002F }, { 0,0,0 }  },
+	{  { 0x0030 }, { 0,0,0 }  },
+	{  { 0x0039 }, { 0,0,0 }  },
+	{  { 0x003A }, { 0,0,0 }  },
+	{  { 0x0040 }, { 0,0,0 }  },
+	{  { 0x0041 }, { 0,0,0 }  },
+	{  { 0x005A }, { 0,0,0 }  },
+	{  { 0x005B }, { 0,0,0 }  },
+	{  { 0x0060 }, { 0,0,0 }  },
+	{  { 0x0061 }, { 0,0,0 }  },
+	{  { 0x007A }, { 0,0,0 }  },
+	{  { 0x007B }, { 0,0,0 }  },
+	{  { 0x007E }, { 0,0,0 }  },
+	{  { 0x007F }, { 0,1,0 }  },
+	{  { 0x0080 }, { 0,1,0 }  }, /* 20 */
+#ifdef NO_WAIVER
+	{  { 0x3042 }, { 0,1,0 }  }, /* <WAIVER> */
+#endif
+	{ .is_last = 1 }		/* Last element.  */
+      }
+  },
+#if 0
+  {   TST_ISW_REC (eucJP, print)
+#else
+  {   TST_ISW_REC (ja_UTF8, print)
+#endif
+      {
+	{  { 0x3000 }, { 0,0,0 }  },  /* IDEO. SPACE        */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0x3020 }, { 0,1,0 }  },  /* POSTAL MARK FACE   */
+	{  { 0x3029 }, { 0,1,0 }  },  /* Hangzhou NUM9      */
+	{  { 0x302F }, { 0,1,0 }  },  /* Diacritics(Hangul) */
+	{  { 0x3037 }, { 0,1,0 }  },  /* Separator Symbol   */
+	{  { 0x303F }, { 0,1,0 }  },  /* IDEO. HALF SPACE   */
+#else
+	{  { 0x3020 }, { 0,0,0 }  },  /* POSTAL MARK FACE   */
+	{  { 0x3029 }, { 0,0,0 }  },  /* Hangzhou NUM9      */
+	{  { 0x302F }, { 0,0,0 }  },  /* Diacritics(Hangul) */
+	{  { 0x3037 }, { 0,0,0 }  },  /* Separator Symbol   */
+	{  { 0x303F }, { 0,0,0 }  },  /* IDEO. HALF SPACE   */
+#endif
+	{  { 0x3041 }, { 0,0,0 }  },  /* HIRAGANA a         */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0x3094 }, { 0,1,0 }  },  /* HIRAGANA u"        */  /* non jis */
+	{  { 0x3099 }, { 0,1,0 }  },  /* SOUND MARK         */
+#else
+	{  { 0x3094 }, { 0,0,0 }  },  /* HIRAGANA u"        */  /* non jis */
+	{  { 0x3099 }, { 0,0,0 }  },  /* SOUND MARK         */
+#endif
+	{  { 0x309E }, { 0,0,0 }  },  /* ITERATION MARK     */  /* 10 */
+	{  { 0x30A1 }, { 0,0,0 }  },  /* KATAKANA a         */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0x30FA }, { 0,1,0 }  },  /* KATAKANA wo"       */  /* non jis */
+#else
+	{  { 0x30FA }, { 0,0,0 }  },  /* KATAKANA wo"       */  /* non jis */
+#endif
+	{  { 0x30FB }, { 0,0,0 }  },  /* KATAKANA MID.DOT   */
+	{  { 0x30FE }, { 0,0,0 }  },  /* KATAKANA ITERATION */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0x3191 }, { 0,1,0 }  },  /* KANBUN REV.MARK    */
+	{  { 0x3243 }, { 0,1,0 }  },  /* IDEO. MARK (reach) */
+	{  { 0x32CB }, { 0,1,0 }  },  /* IDEO.TEL.SYM.DEC12 */
+	{  { 0x32FE }, { 0,1,0 }  },  /* MARU KATAKANA wo   */
+	{  { 0x33FE }, { 0,1,0 }  },  /* CJK IDEO.TEL.31th  */
+#else
+	{  { 0x3191 }, { 0,0,0 }  },  /* KANBUN REV.MARK    */
+	{  { 0x3243 }, { 0,0,0 }  },  /* IDEO. MARK (reach) */
+	{  { 0x32CB }, { 0,0,0 }  },  /* IDEO.TEL.SYM.DEC12 */
+	{  { 0x32FE }, { 0,0,0 }  },  /* MARU KATAKANA wo   */
+	{  { 0x33FE }, { 0,0,0 }  },  /* CJK IDEO.TEL.31th  */
+#endif
+	{  { 0x4E00 }, { 0,0,0 }  },  /* CJK UNI.IDEO.      */  /* 20 */
+	{  { 0x4E05 }, { 0,0,0 }  },  /* CJK UNI.IDEO.      */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0x4E06 }, { 0,1,0 }  },  /* CJK UNI.IDEO.NON-J */
+#else
+	{  { 0x4E06 }, { 0,0,0 }  },  /* CJK UNI.IDEO.NON-J */
+#endif
+	{  { 0x4E07 }, { 0,0,0 }  },  /* CJK UNI.IDEO.      */
+	{  { 0x4FFF }, { 0,0,0 }  },  /* CJK UNI.IDEO.      */
+	{  { 0x9000 }, { 0,0,0 }  },  /* CJK UNI.IDEO.      */
+	{  { 0x9006 }, { 0,0,0 }  },  /* CJK UNI.IDEO.      */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0x9007 }, { 0,1,0 }  },  /* CJK UNI.IDEO.NON-J */
+	{  { 0x9FA4 }, { 0,1,0 }  },  /* CJK UNI.IDEO.NON-J */
+#else
+	{  { 0x9007 }, { 0,0,0 }  },  /* CJK UNI.IDEO.NON-J */
+	{  { 0x9FA4 }, { 0,0,0 }  },  /* CJK UNI.IDEO.NON-J */
+#endif
+	{  { 0x9FA5 }, { 0,0,0 }  },  /* CJK UNI.IDEO.      */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0xFE4F }, { 0,1,0 }  },  /* WAVE LOW LINE      */  /* 30 */
+#else
+	{  { 0xFE4F }, { 0,0,0 }  },  /* WAVE LOW LINE      */  /* 30 */
+#endif
+	{  { 0xFF0F }, { 0,0,0 }  },  /* FULL SLASH         */
+	{  { 0xFF19 }, { 0,0,0 }  },  /* FULL 9             */
+	{  { 0xFF20 }, { 0,0,0 }  },  /* FULL @             */
+	{  { 0xFF3A }, { 0,0,0 }  },  /* FULL Z             */
+	{  { 0xFF40 }, { 0,0,0 }  },  /* FULL GRAVE ACC.    */
+	{  { 0xFF5A }, { 0,0,0 }  },  /* FULL z             */
+	{  { 0xFF5E }, { 0,0,0 }  },  /* FULL ~ (tilde)     */
+	{  { 0xFF61 }, { 0,0,0 }  },  /* HALF IDEO.STOP. .  */
+	{  { 0xFF65 }, { 0,0,0 }  },  /* HALF KATA MID.DOT  */
+	{  { 0xFF66 }, { 0,0,0 }  },  /* HALF KATA WO       */  /* 40 */
+	{  { 0xFF6F }, { 0,0,0 }  },  /* HALF KATA tu       */
+	{  { 0xFF70 }, { 0,0,0 }  },  /* HALF KATA PL -     */
+	{  { 0xFF71 }, { 0,0,0 }  },  /* HALF KATA A        */
+	{  { 0xFF9E }, { 0,0,0 }  },  /* HALF KATA MI       */
+	{ .is_last = 1 }		/* Last element.  */
+      }
+  },
+  {   TST_ISW_REC (end, print) }
+};

+ 155 - 0
test/locale-mbwc/dat_iswpunct.c

@@ -0,0 +1,155 @@
+/*
+ *  TEST SUITE FOR MB/WC FUNCTIONS IN C LIBRARY
+ *
+ *	 FILE:	dat_iswpunct.c
+ *
+ *	 ISW*:	int iswpunct (wint_t wc);
+ */
+
+
+#include "dat_isw-funcs.h"
+
+
+TST_ISW_LOC (PUNCT, punct) = {
+
+  {   TST_ISW_REC (de, punct)
+      {
+	{  { 0x0080 }, { 0,1,0 }  },	/* CTRL	    */
+	{  { 0x009F }, { 0,1,0 }  },	/* CTRL	    */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0x00A0 }, { 0,1,0 }  },	/* NB SPACE */
+#else
+	{  { 0x00A0 }, { 0,0,0 }  },	/* NB SPACE */
+#endif
+	{  { 0x00A1 }, { 0,0,0 }  },	/* UD !	    */
+	{  { 0x00B0 }, { 0,0,0 }  },	/* Degree   */
+	{  { 0x00B1 }, { 0,0,0 }  },	/* +- sign  */
+	{  { 0x00B2 }, { 0,0,0 }  },	/* SUP 2    */
+	{  { 0x00B3 }, { 0,0,0 }  },	/* SUP 3    */
+	{  { 0x00B4 }, { 0,0,0 }  },	/* ACUTE    */
+	{  { 0x00B8 }, { 0,0,0 }  },	/* CEDILLA  */
+	{  { 0x00B9 }, { 0,0,0 }  },	/* SUP 1    */
+	{  { 0x00BB }, { 0,0,0 }  },	/* >>	    */
+	{  { 0x00BC }, { 0,0,0 }  },	/* 1/4	    */
+	{  { 0x00BD }, { 0,0,0 }  },	/* 1/2	    */
+	{  { 0x00BE }, { 0,0,0 }  },	/* 3/4	    */
+	{  { 0x00BF }, { 0,0,0 }  },	/* UD ?	    */
+	{  { 0x00C0 }, { 0,1,0 }  },	/* A Grave  */
+	{  { 0x00D6 }, { 0,1,0 }  },	/* O dia    */
+	{  { 0x00D7 }, { 0,0,0 }  },	/* multipl. */
+	{  { 0x00D8 }, { 0,1,0 }  },	/* O stroke */
+	{  { 0x00DF }, { 0,1,0 }  },	/* small Sh */
+	{  { 0x00E0 }, { 0,1,0 }  },	/* a grave  */
+	{  { 0x00F6 }, { 0,1,0 }  },	/* o dia    */
+	{  { 0x00F7 }, { 0,0,0 }  },	/* division */
+	{  { 0x00F8 }, { 0,1,0 }  },	/* o stroke */
+	{  { 0x00FF }, { 0,1,0 }  },	/* y dia    */
+	{ .is_last = 1 }		/* Last element.  */
+      }
+  },
+  {   TST_ISW_REC (enUS, punct)
+      {
+	{  { WEOF   }, { 0,1,0 }  }, /* 01 */
+	{  { 0x0000 }, { 0,1,0 }  },
+	{  { 0x001F }, { 0,1,0 }  },
+	{  { 0x0020 }, { 0,1,0 }  },
+	{  { 0x0021 }, { 0,0,0 }  },
+	{  { 0x002F }, { 0,0,0 }  },
+	{  { 0x0030 }, { 0,1,0 }  },
+	{  { 0x0039 }, { 0,1,0 }  },
+	{  { 0x003A }, { 0,0,0 }  },
+	{  { 0x0040 }, { 0,0,0 }  },
+	{  { 0x0041 }, { 0,1,0 }  },
+	{  { 0x005A }, { 0,1,0 }  },
+	{  { 0x005B }, { 0,0,0 }  },
+	{  { 0x0060 }, { 0,0,0 }  },
+	{  { 0x0061 }, { 0,1,0 }  },
+	{  { 0x007A }, { 0,1,0 }  },
+	{  { 0x007B }, { 0,0,0 }  },
+	{  { 0x007E }, { 0,0,0 }  },
+	{  { 0x007F }, { 0,1,0 }  },
+	{  { 0x0080 }, { 0,1,0 }  }, /* 20 */
+	{ .is_last = 1 }		/* Last element.  */
+      }
+  },
+#if 0
+  {   TST_ISW_REC (eucJP, punct)
+#else
+  {   TST_ISW_REC (ja_UTF8, punct)
+#endif
+      {
+	{  { 0x3000 }, { 0,1,0 }  },	/* IDEO. SPACE	      */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0x3020 }, { 0,1,0 }  },	/* POSTAL MARK FACE   */
+#else
+	{  { 0x3020 }, { 0,0,0 }  },	/* POSTAL MARK FACE   */
+#endif
+	{  { 0x3029 }, { 0,1,0 }  },	/* Hangzhou NUM9      */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0x302F }, { 0,1,0 }  },	/* Diacritics(Hangul) */
+	{  { 0x3037 }, { 0,1,0 }  },	/* Separator Symbol   */
+	{  { 0x303F }, { 0,1,0 }  },	/* IDEO. HALF SPACE   */
+#else
+	{  { 0x302F }, { 0,0,0 }  },	/* Diacritics(Hangul) */
+	{  { 0x3037 }, { 0,0,0 }  },	/* Separator Symbol   */
+	{  { 0x303F }, { 0,0,0 }  },	/* IDEO. HALF SPACE   */
+#endif
+	{  { 0x3041 }, { 0,1,0 }  },	/* HIRAGANA a	      */
+	{  { 0x3094 }, { 0,1,0 }  },	/* HIRAGANA u"	      */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0x3099 }, { 0,1,0 }  },	/* SOUND MARK	      */
+#else
+	{  { 0x3099 }, { 0,0,0 }  },	/* SOUND MARK	      */
+#endif
+	{  { 0x309E }, { 0,1,0 }  },	/* ITERATION MARK     */  /* 10 */
+	{  { 0x30A1 }, { 0,1,0 }  },	/* KATAKANA a	      */
+	{  { 0x30FA }, { 0,1,0 }  },	/* KATAKANA wo"	      */
+	{  { 0x30FB }, { 0,0,0 }  },	/* KATAKANA MID.DOT   */
+	{  { 0x30FE }, { 0,1,0 }  },	/* KATAKANA ITERATION */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0x3191 }, { 0,1,0 }  },	/* KANBUN REV.MARK    */
+	{  { 0x3243 }, { 0,1,0 }  },	/* IDEO. MARK (reach) */
+	{  { 0x32CB }, { 0,1,0 }  },	/* IDEO.TEL.SYM.DEC12 */
+	{  { 0x32FE }, { 0,1,0 }  },	/* MARU KATAKANA wo   */
+	{  { 0x33FE }, { 0,1,0 }  },	/* CJK IDEO.TEL.31th  */
+#else
+	{  { 0x3191 }, { 0,0,0 }  },	/* KANBUN REV.MARK    */
+	{  { 0x3243 }, { 0,0,0 }  },	/* IDEO. MARK (reach) */
+	{  { 0x32CB }, { 0,0,0 }  },	/* IDEO.TEL.SYM.DEC12 */
+	{  { 0x32FE }, { 0,0,0 }  },	/* MARU KATAKANA wo   */
+	{  { 0x33FE }, { 0,0,0 }  },	/* CJK IDEO.TEL.31th  */
+#endif
+	{  { 0x4E00 }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */  /* 20 */
+	{  { 0x4E05 }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x4E06 }, { 0,1,0 }  },	/* CJK UNI.IDEO.NON-J */
+	{  { 0x4E07 }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x4FFF }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x9000 }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x9006 }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x9007 }, { 0,1,0 }  },	/* CJK UNI.IDEO.NON-J */
+	{  { 0x9FA4 }, { 0,1,0 }  },	/* CJK UNI.IDEO.NON-J */
+	{  { 0x9FA5 }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+#ifdef SHOJI_IS_RIGHT
+	{  { 0xFE4F }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */  /* 30 */
+#else
+	{  { 0xFE4F }, { 0,0,0 }  },	/* CJK UNI.IDEO.      */  /* 30 */
+#endif
+	{  { 0xFF0F }, { 0,0,0 }  },	/* FULL SLASH	      */
+	{  { 0xFF19 }, { 0,1,0 }  },	/* FULL 9	      */
+	{  { 0xFF20 }, { 0,0,0 }  },	/* FULL @	      */
+	{  { 0xFF3A }, { 0,1,0 }  },	/* FULL Z	      */
+	{  { 0xFF40 }, { 0,0,0 }  },	/* FULL GRAVE ACC.    */
+	{  { 0xFF5A }, { 0,1,0 }  },	/* FULL z	      */
+	{  { 0xFF5E }, { 0,0,0 }  },	/* FULL ~ (tilde)     */
+	{  { 0xFF61 }, { 0,0,0 }  },	/* HALF IDEO.STOP. .  */
+	{  { 0xFF65 }, { 0,0,0 }  },	/* HALF KATA MID.DOT  */
+	{  { 0xFF66 }, { 0,1,0 }  },	/* HALF KATA WO	      */  /* 40 */
+	{  { 0xFF6F }, { 0,1,0 }  },	/* HALF KATA tu	      */
+	{  { 0xFF70 }, { 0,1,0 }  },	/* HALF KATA PL -     */
+	{  { 0xFF71 }, { 0,1,0 }  },	/* HALF KATA A	      */
+	{  { 0xFF9E }, { 0,1,0 }  },	/* HALF KATA MI	      */
+	{ .is_last = 1 }		/* Last element.  */
+      }
+  },
+  {   TST_ISW_REC (end, punct) }
+};

+ 129 - 0
test/locale-mbwc/dat_iswspace.c

@@ -0,0 +1,129 @@
+/*
+ *  TEST SUITE FOR MB/WC FUNCTIONS IN C LIBRARY
+ *
+ *	 FILE:	dat_iswspace.c
+ *
+ *	 ISW*:	int iswspace (wint_t wc);
+ */
+
+
+#include "dat_isw-funcs.h"
+
+
+TST_ISW_LOC (SPACE, space) = {
+
+  {   TST_ISW_REC (de, space)
+      {
+	{  { 0x0080 }, { 0,1,0 }  },	/* CTRL	    */
+	{  { 0x009F }, { 0,1,0 }  },	/* CTRL	    */
+	{  { 0x00A0 }, { 0,1,0 }  },	/* NB SPACE */
+	{  { 0x00A1 }, { 0,1,0 }  },	/* UD !	    */
+	{  { 0x00B0 }, { 0,1,0 }  },	/* Degree   */
+	{  { 0x00B1 }, { 0,1,0 }  },	/* +- sign  */
+	{  { 0x00B2 }, { 0,1,0 }  },	/* SUP 2    */
+	{  { 0x00B3 }, { 0,1,0 }  },	/* SUP 3    */
+	{  { 0x00B4 }, { 0,1,0 }  },	/* ACUTE    */
+	{  { 0x00B8 }, { 0,1,0 }  },	/* CEDILLA  */
+	{  { 0x00B9 }, { 0,1,0 }  },	/* SUP 1    */
+	{  { 0x00BB }, { 0,1,0 }  },	/* >>	    */
+	{  { 0x00BC }, { 0,1,0 }  },	/* 1/4	    */
+	{  { 0x00BD }, { 0,1,0 }  },	/* 1/2	    */
+	{  { 0x00BE }, { 0,1,0 }  },	/* 3/4	    */
+	{  { 0x00BF }, { 0,1,0 }  },	/* UD ?	    */
+	{  { 0x00C0 }, { 0,1,0 }  },	/* A Grave  */
+	{  { 0x00D6 }, { 0,1,0 }  },	/* O dia    */
+	{  { 0x00D7 }, { 0,1,0 }  },	/* multipl. */
+	{  { 0x00D8 }, { 0,1,0 }  },	/* O stroke */
+	{  { 0x00DF }, { 0,1,0 }  },	/* small Sh */
+	{  { 0x00E0 }, { 0,1,0 }  },	/* a grave  */
+	{  { 0x00F6 }, { 0,1,0 }  },	/* o dia    */
+	{  { 0x00F7 }, { 0,1,0 }  },	/* division */
+	{  { 0x00F8 }, { 0,1,0 }  },	/* o stroke */
+	{  { 0x00FF }, { 0,1,0 }  },	/* y dia    */
+	{ .is_last = 1 }		/* Last element.  */
+      }
+  },
+  {   TST_ISW_REC (enUS, space)
+      {
+	{  { WEOF   }, { 0,1,0 }  },
+	{  { 0x0000 }, { 0,1,0 }  },
+	{  { 0x0008 }, { 0,1,0 }  },
+	{  { 0x0009 }, { 0,0,0 }  },
+	{  { 0x000D }, { 0,0,0 }  },
+	{  { 0x000E }, { 0,1,0 }  },
+	{  { 0x001F }, { 0,1,0 }  },
+	{  { 0x0020 }, { 0,0,0 }  },
+	{  { 0x0021 }, { 0,1,0 }  },
+	{  { 0x002F }, { 0,1,0 }  },
+	{  { 0x0030 }, { 0,1,0 }  },
+	{  { 0x0039 }, { 0,1,0 }  },
+	{  { 0x003A }, { 0,1,0 }  },
+	{  { 0x0040 }, { 0,1,0 }  },
+	{  { 0x0041 }, { 0,1,0 }  },
+	{  { 0x005A }, { 0,1,0 }  },
+	{  { 0x005B }, { 0,1,0 }  },
+	{  { 0x0060 }, { 0,1,0 }  },
+	{  { 0x0061 }, { 0,1,0 }  },
+	{  { 0x007A }, { 0,1,0 }  }, /* 20 */
+	{  { 0x007B }, { 0,1,0 }  },
+	{  { 0x007E }, { 0,1,0 }  },
+	{  { 0x007F }, { 0,1,0 }  },
+	{  { 0x0080 }, { 0,1,0 }  },
+	{ .is_last = 1 }		/* Last element.  */
+      }
+  },
+#if 0
+  {   TST_ISW_REC (eucJP, space)
+#else
+  {   TST_ISW_REC (ja_UTF8, space)
+#endif
+      {
+	{  { 0x3000 }, { 0,0,0 }  },	/* IDEO. SPACE	      */
+	{  { 0x3020 }, { 0,1,0 }  },	/* POSTAL MARK FACE   */
+	{  { 0x3029 }, { 0,1,0 }  },	/* Hangzhou NUM9      */
+	{  { 0x302F }, { 0,1,0 }  },	/* Diacritics(Hangul) */
+	{  { 0x3037 }, { 0,1,0 }  },	/* Separator Symbol   */
+	{  { 0x303F }, { 0,1,0 }  },	/* IDEO. HALF SPACE   */  /* No JIS */
+	{  { 0x3041 }, { 0,1,0 }  },	/* HIRAGANA a	      */
+	{  { 0x3094 }, { 0,1,0 }  },	/* HIRAGANA u"	      */
+	{  { 0x3099 }, { 0,1,0 }  },	/* SOUND MARK	      */
+	{  { 0x309E }, { 0,1,0 }  },	/* ITERATION MARK     */
+	{  { 0x30A1 }, { 0,1,0 }  },	/* KATAKANA a	      */
+	{  { 0x30FA }, { 0,1,0 }  },	/* KATAKANA wo"	      */
+	{  { 0x30FB }, { 0,1,0 }  },	/* KATAKANA MID.DOT   */
+	{  { 0x30FE }, { 0,1,0 }  },	/* KATAKANA ITERATION */
+	{  { 0x3191 }, { 0,1,0 }  },	/* KANBUN REV.MARK    */
+	{  { 0x3243 }, { 0,1,0 }  },	/* IDEO. MARK (reach) */
+	{  { 0x32CB }, { 0,1,0 }  },	/* IDEO.TEL.SYM.DEC12 */
+	{  { 0x32FE }, { 0,1,0 }  },	/* MARU KATAKANA wo   */
+	{  { 0x33FE }, { 0,1,0 }  },	/* CJK IDEO.TEL.31th  */
+	{  { 0x4E00 }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x4E05 }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x4E06 }, { 0,1,0 }  },	/* CJK UNI.IDEO.NON-J */
+	{  { 0x4E07 }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x4FFF }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x9000 }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x9006 }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0x9007 }, { 0,1,0 }  },	/* CJK UNI.IDEO.NON-J */
+	{  { 0x9FA4 }, { 0,1,0 }  },	/* CJK UNI.IDEO.NON-J */
+	{  { 0x9FA5 }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0xFE4F }, { 0,1,0 }  },	/* CJK UNI.IDEO.      */
+	{  { 0xFF0F }, { 0,1,0 }  },	/* FULL SLASH	      */
+	{  { 0xFF19 }, { 0,1,0 }  },	/* FULL 9	      */
+	{  { 0xFF20 }, { 0,1,0 }  },	/* FULL @	      */
+	{  { 0xFF3A }, { 0,1,0 }  },	/* FULL Z	      */
+	{  { 0xFF40 }, { 0,1,0 }  },	/* FULL GRAVE ACC.    */
+	{  { 0xFF5A }, { 0,1,0 }  },	/* FULL z	      */
+	{  { 0xFF5E }, { 0,1,0 }  },	/* FULL ~ (tilde)     */
+	{  { 0xFF61 }, { 0,1,0 }  },	/* HALF IDEO.STOP. .  */
+	{  { 0xFF65 }, { 0,1,0 }  },	/* HALF KATA MID.DOT  */
+	{  { 0xFF66 }, { 0,1,0 }  },	/* HALF KATA WO	      */
+	{  { 0xFF6F }, { 0,1,0 }  },	/* HALF KATA tu	      */
+	{  { 0xFF70 }, { 0,1,0 }  },	/* HALF KATA PL -     */
+	{  { 0xFF71 }, { 0,1,0 }  },	/* HALF KATA A	      */
+	{  { 0xFF9E }, { 0,1,0 }  },	/* HALF KATA MI	      */
+	{ .is_last = 1 }		/* Last element.  */
+      }
+  },
+  {   TST_ISW_REC (end, space) }
+};

+ 94 - 0
test/locale-mbwc/dat_iswupper.c

@@ -0,0 +1,94 @@
+/*
+ *  TEST SUITE FOR MB/WC FUNCTIONS IN C LIBRARY
+ *
+ *	 FILE:	dat_iswupper.c
+ *
+ *	 ISW*:	int iswupper (wint_t wc);
+ */
+
+
+#include "dat_isw-funcs.h"
+
+
+TST_ISW_LOC (UPPER, upper) = {
+
+  {   TST_ISW_REC (de, upper)
+      {
+	{  { 0x0080 }, { 0,1,0 }  },	/* CTRL	    */
+	{  { 0x009F }, { 0,1,0 }  },	/* CTRL	    */
+	{  { 0x00A0 }, { 0,1,0 }  },	/* NB SPACE */
+	{  { 0x00A1 }, { 0,1,0 }  },	/* UD !	    */
+	{  { 0x00B0 }, { 0,1,0 }  },	/* Degree   */
+	{  { 0x00B1 }, { 0,1,0 }  },	/* +- sign  */
+	{  { 0x00B2 }, { 0,1,0 }  },	/* SUP 2    */
+	{  { 0x00B3 }, { 0,1,0 }  },	/* SUP 3    */
+	{  { 0x00B4 }, { 0,1,0 }  },	/* ACUTE    */
+	{  { 0x00B8 }, { 0,1,0 }  },	/* CEDILLA  */
+	{  { 0x00B9 }, { 0,1,0 }  },	/* SUP 1    */
+	{  { 0x00BB }, { 0,1,0 }  },	/* >>	    */
+	{  { 0x00BC }, { 0,1,0 }  },	/* 1/4	    */
+	{  { 0x00BD }, { 0,1,0 }  },	/* 1/2	    */
+	{  { 0x00BE }, { 0,1,0 }  },	/* 3/4	    */
+	{  { 0x00BF }, { 0,1,0 }  },	/* UD ?	    */
+	{  { 0x00C0 }, { 0,0,0 }  },	/* A Grave  */
+	{  { 0x00D6 }, { 0,0,0 }  },	/* O dia    */
+	{  { 0x00D7 }, { 0,1,0 }  },	/* multipl. */
+	{  { 0x00D8 }, { 0,0,0 }  },	/* O stroke */
+	{  { 0x00DF }, { 0,1,0 }  },	/* small Sh */
+	{  { 0x00E0 }, { 0,1,0 }  },	/* a grave  */
+	{  { 0x00F6 }, { 0,1,0 }  },	/* o dia    */
+	{  { 0x00F7 }, { 0,1,0 }  },	/* division */
+	{  { 0x00F8 }, { 0,1,0 }  },	/* o stroke */
+	{  { 0x00FF }, { 0,1,0 }  },	/* y dia    */
+	{ .is_last = 1 }		/* Last entry.	*/
+      }
+  },
+  {   TST_ISW_REC (enUS, upper)
+      {
+	{  { WEOF   }, { 0,1,0 }  },
+	{  { 0x0000 }, { 0,1,0 }  },
+	{  { 0x001F }, { 0,1,0 }  },
+	{  { 0x0020 }, { 0,1,0 }  },
+	{  { 0x0021 }, { 0,1,0 }  },
+	{  { 0x002F }, { 0,1,0 }  },
+	{  { 0x0030 }, { 0,1,0 }  },
+	{  { 0x0039 }, { 0,1,0 }  },
+	{  { 0x003A }, { 0,1,0 }  },
+	{  { 0x0040 }, { 0,1,0 }  },
+	{  { 0x0041 }, { 0,0,0 }  },
+	{  { 0x005A }, { 0,0,0 }  },
+	{  { 0x005B }, { 0,1,0 }  },
+	{  { 0x0060 }, { 0,1,0 }  },
+	{  { 0x0061 }, { 0,1,0 }  },
+	{  { 0x007A }, { 0,1,0 }  },
+	{  { 0x007B }, { 0,1,0 }  },
+	{  { 0x007E }, { 0,1,0 }  },
+	{  { 0x007F }, { 0,1,0 }  },
+	{  { 0x0080 }, { 0,1,0 }  },
+	{ .is_last = 1 }		/* Last entry.  */
+      }
+  },
+#if 0
+  {   TST_ISW_REC (eucJP, upper)
+#else
+  {   TST_ISW_REC (ja_UTF8, upper)
+#endif
+      {
+	{  { 0x3041 }, { 0,1,0 }  },	/* HIRAGANA a	      */
+	{  { 0x3094 }, { 0,1,0 }  },	/* HIRAGANA u"	      */
+	{  { 0x30A1 }, { 0,1,0 }  },	/* KATAKANA a	      */
+	{  { 0x30FA }, { 0,1,0 }  },	/* KATAKANA wo"	      */
+	{  { 0xFF19 }, { 0,1,0 }  },	/* FULL 9	      */
+	{  { 0xFF20 }, { 0,1,0 }  },	/* FULL @	      */
+	{  { 0xFF3A }, { 0,0,0 }  },	/* FULL Z	      */
+	{  { 0xFF40 }, { 0,1,0 }  },	/* FULL GRAVE ACC.    */
+	{  { 0xFF5A }, { 0,1,0 }  },	/* FULL z	      */
+	{  { 0xFF66 }, { 0,1,0 }  },	/* HALF KATA WO	      */
+	{  { 0xFF6F }, { 0,1,0 }  },	/* HALF KATA tu	      */
+	{  { 0xFF71 }, { 0,1,0 }  },	/* HALF KATA A	      */
+	{  { 0xFF9E }, { 0,1,0 }  },	/* HALF KATA MI	      */
+	{ .is_last = 1 }		/* Last entry.	*/
+      }
+  },
+  {   TST_ISW_REC (end, upper) }
+};

Some files were not shown because too many files changed in this diff