summaryrefslogtreecommitdiffstats
path: root/private/oleauto/src
diff options
context:
space:
mode:
authorAdam <you@example.com>2020-05-17 05:51:50 +0200
committerAdam <you@example.com>2020-05-17 05:51:50 +0200
commite611b132f9b8abe35b362e5870b74bce94a1e58e (patch)
treea5781d2ec0e085eeca33cf350cf878f2efea6fe5 /private/oleauto/src
downloadNT4.0-e611b132f9b8abe35b362e5870b74bce94a1e58e.tar
NT4.0-e611b132f9b8abe35b362e5870b74bce94a1e58e.tar.gz
NT4.0-e611b132f9b8abe35b362e5870b74bce94a1e58e.tar.bz2
NT4.0-e611b132f9b8abe35b362e5870b74bce94a1e58e.tar.lz
NT4.0-e611b132f9b8abe35b362e5870b74bce94a1e58e.tar.xz
NT4.0-e611b132f9b8abe35b362e5870b74bce94a1e58e.tar.zst
NT4.0-e611b132f9b8abe35b362e5870b74bce94a1e58e.zip
Diffstat (limited to 'private/oleauto/src')
-rw-r--r--private/oleauto/src/dispatch/asmhelp.c55
-rw-r--r--private/oleauto/src/dispatch/assert.cpp134
-rw-r--r--private/oleauto/src/dispatch/assert.dlg13
-rw-r--r--private/oleauto/src/dispatch/assrtdlg.h29
-rw-r--r--private/oleauto/src/dispatch/bstr.cpp615
-rw-r--r--private/oleauto/src/dispatch/bstrdate.c2802
-rw-r--r--private/oleauto/src/dispatch/cdispti.cpp1360
-rw-r--r--private/oleauto/src/dispatch/cdispti.h111
-rw-r--r--private/oleauto/src/dispatch/clsid.c54
-rw-r--r--private/oleauto/src/dispatch/clsid.h28
-rw-r--r--private/oleauto/src/dispatch/convert.cpp2939
-rw-r--r--private/oleauto/src/dispatch/crtstuff.c214
-rw-r--r--private/oleauto/src/dispatch/crtstuff.h47
-rw-r--r--private/oleauto/src/dispatch/dbcsdate.c87
-rw-r--r--private/oleauto/src/dispatch/dbcsdate.h228
-rw-r--r--private/oleauto/src/dispatch/dispbind.cpp221
-rw-r--r--private/oleauto/src/dispatch/disphelp.cpp229
-rw-r--r--private/oleauto/src/dispatch/dispiid.c59
-rw-r--r--private/oleauto/src/dispatch/dispmrsh.cpp1894
-rw-r--r--private/oleauto/src/dispatch/dispmrsh.h316
-rw-r--r--private/oleauto/src/dispatch/disppch.cpp3
-rw-r--r--private/oleauto/src/dispatch/dispprox.cpp707
-rw-r--r--private/oleauto/src/dispatch/dispps.h267
-rw-r--r--private/oleauto/src/dispatch/dispstrm.cpp375
-rw-r--r--private/oleauto/src/dispatch/dispstrm.h78
-rw-r--r--private/oleauto/src/dispatch/dispstub.cpp803
-rw-r--r--private/oleauto/src/dispatch/errinfo.cpp680
-rw-r--r--private/oleauto/src/dispatch/evprox.cpp402
-rw-r--r--private/oleauto/src/dispatch/evps.h179
-rw-r--r--private/oleauto/src/dispatch/evstub.cpp500
-rw-r--r--private/oleauto/src/dispatch/getobj.cpp202
-rw-r--r--private/oleauto/src/dispatch/idispiid.c58
-rw-r--r--private/oleauto/src/dispatch/invhelp.cpp154
-rw-r--r--private/oleauto/src/dispatch/memory.cpp64
-rw-r--r--private/oleauto/src/dispatch/namemacs.h1305
-rw-r--r--private/oleauto/src/dispatch/nlsapi.c3148
-rw-r--r--private/oleauto/src/dispatch/nlsdbcs.h176
-rw-r--r--private/oleauto/src/dispatch/nlshelp.cpp276
-rw-r--r--private/oleauto/src/dispatch/nlsintrn.h409
-rw-r--r--private/oleauto/src/dispatch/oaglue.c664
-rw-r--r--private/oleauto/src/dispatch/oaglue.v126
-rw-r--r--private/oleauto/src/dispatch/oaimp.h164
-rw-r--r--private/oleauto/src/dispatch/oaimp.mak172
-rw-r--r--private/oleauto/src/dispatch/oavtbl.c156
-rw-r--r--private/oleauto/src/dispatch/oavtbl.h293
-rw-r--r--private/oleauto/src/dispatch/ole2.ini275
-rw-r--r--private/oleauto/src/dispatch/ole2auto.reg79
-rw-r--r--private/oleauto/src/dispatch/oledate.c370
-rw-r--r--private/oleauto/src/dispatch/oledisp.h817
-rw-r--r--private/oleauto/src/dispatch/oleguids.c27
-rw-r--r--private/oleauto/src/dispatch/oleguids.h71
-rw-r--r--private/oleauto/src/dispatch/olenames.h100
-rw-r--r--private/oleauto/src/dispatch/psfactry.cpp434
-rw-r--r--private/oleauto/src/dispatch/psfactry.h52
-rw-r--r--private/oleauto/src/dispatch/sarray.cpp1713
-rw-r--r--private/oleauto/src/dispatch/stddisp.cpp856
-rw-r--r--private/oleauto/src/dispatch/stddisp.h325
-rw-r--r--private/oleauto/src/dispatch/string.c530
-rw-r--r--private/oleauto/src/dispatch/tables.c95
-rw-r--r--private/oleauto/src/dispatch/tcprox.cpp440
-rw-r--r--private/oleauto/src/dispatch/tcps.h196
-rw-r--r--private/oleauto/src/dispatch/tcstub.cpp496
-rw-r--r--private/oleauto/src/dispatch/time-api.cpp173
-rw-r--r--private/oleauto/src/dispatch/tiprox.cpp1627
-rw-r--r--private/oleauto/src/dispatch/tips.h297
-rw-r--r--private/oleauto/src/dispatch/tistub.cpp1034
-rw-r--r--private/oleauto/src/dispatch/tiutil.cpp99
-rw-r--r--private/oleauto/src/dispatch/tlprox.cpp867
-rw-r--r--private/oleauto/src/dispatch/tlps.h226
-rw-r--r--private/oleauto/src/dispatch/tlstub.cpp846
-rw-r--r--private/oleauto/src/dispatch/ups.cpp1719
-rw-r--r--private/oleauto/src/dispatch/ups.h170
-rw-r--r--private/oleauto/src/dispatch/uvft.cpp396
-rw-r--r--private/oleauto/src/dispatch/validate.cpp291
-rw-r--r--private/oleauto/src/dispatch/variant.cpp1168
-rw-r--r--private/oleauto/src/dispatch/win16/0401.c714
-rw-r--r--private/oleauto/src/dispatch/win16/0403.c531
-rw-r--r--private/oleauto/src/dispatch/win16/0404.c1036
-rw-r--r--private/oleauto/src/dispatch/win16/0405.c711
-rw-r--r--private/oleauto/src/dispatch/win16/0406.c705
-rw-r--r--private/oleauto/src/dispatch/win16/0407.c524
-rw-r--r--private/oleauto/src/dispatch/win16/0408.c706
-rw-r--r--private/oleauto/src/dispatch/win16/0409.c714
-rw-r--r--private/oleauto/src/dispatch/win16/040a.c723
-rw-r--r--private/oleauto/src/dispatch/win16/040b.c526
-rw-r--r--private/oleauto/src/dispatch/win16/040c.c521
-rw-r--r--private/oleauto/src/dispatch/win16/040d.c696
-rw-r--r--private/oleauto/src/dispatch/win16/040e.c750
-rw-r--r--private/oleauto/src/dispatch/win16/040f.c704
-rw-r--r--private/oleauto/src/dispatch/win16/0410.c518
-rw-r--r--private/oleauto/src/dispatch/win16/0411.c1679
-rw-r--r--private/oleauto/src/dispatch/win16/0412.c1729
-rw-r--r--private/oleauto/src/dispatch/win16/0413.c526
-rw-r--r--private/oleauto/src/dispatch/win16/0414.c526
-rw-r--r--private/oleauto/src/dispatch/win16/0415.c695
-rw-r--r--private/oleauto/src/dispatch/win16/0416.c532
-rw-r--r--private/oleauto/src/dispatch/win16/0419.c690
-rw-r--r--private/oleauto/src/dispatch/win16/041b.c706
-rw-r--r--private/oleauto/src/dispatch/win16/041d.c701
-rw-r--r--private/oleauto/src/dispatch/win16/041f.c699
-rw-r--r--private/oleauto/src/dispatch/win16/0429.c536
-rw-r--r--private/oleauto/src/dispatch/win16/0801.c536
-rw-r--r--private/oleauto/src/dispatch/win16/0804.c724
-rw-r--r--private/oleauto/src/dispatch/win16/0807.c518
-rw-r--r--private/oleauto/src/dispatch/win16/0809.c525
-rw-r--r--private/oleauto/src/dispatch/win16/080a.c537
-rw-r--r--private/oleauto/src/dispatch/win16/080c.c522
-rw-r--r--private/oleauto/src/dispatch/win16/0810.c518
-rw-r--r--private/oleauto/src/dispatch/win16/0813.c524
-rw-r--r--private/oleauto/src/dispatch/win16/0814.c526
-rw-r--r--private/oleauto/src/dispatch/win16/0816.c532
-rw-r--r--private/oleauto/src/dispatch/win16/0c01.c528
-rw-r--r--private/oleauto/src/dispatch/win16/0c07.c525
-rw-r--r--private/oleauto/src/dispatch/win16/0c09.c528
-rw-r--r--private/oleauto/src/dispatch/win16/0c0a.c708
-rw-r--r--private/oleauto/src/dispatch/win16/0c0c.c522
-rw-r--r--private/oleauto/src/dispatch/win16/1001.c528
-rw-r--r--private/oleauto/src/dispatch/win16/1009.c523
-rw-r--r--private/oleauto/src/dispatch/win16/100c.c517
-rw-r--r--private/oleauto/src/dispatch/win16/1401.c528
-rw-r--r--private/oleauto/src/dispatch/win16/1409.c528
-rw-r--r--private/oleauto/src/dispatch/win16/1801.c521
-rw-r--r--private/oleauto/src/dispatch/win16/1809.c523
-rw-r--r--private/oleauto/src/dispatch/win16/1c01.c520
-rw-r--r--private/oleauto/src/dispatch/win16/2001.c528
-rw-r--r--private/oleauto/src/dispatch/win16/2401.c528
-rw-r--r--private/oleauto/src/dispatch/win16/2801.c536
-rw-r--r--private/oleauto/src/dispatch/win16/2c01.c536
-rw-r--r--private/oleauto/src/dispatch/win16/3001.c536
-rw-r--r--private/oleauto/src/dispatch/win16/3401.c528
-rw-r--r--private/oleauto/src/dispatch/win16/3801.c530
-rw-r--r--private/oleauto/src/dispatch/win16/3c01.c528
-rw-r--r--private/oleauto/src/dispatch/win16/4001.c528
-rw-r--r--private/oleauto/src/dispatch/win16/invoke.asm783
-rw-r--r--private/oleauto/src/dispatch/win16/loc11-3.txt4900
-rw-r--r--private/oleauto/src/dispatch/win16/locale.jap111
-rw-r--r--private/oleauto/src/dispatch/win16/locale.kor110
-rw-r--r--private/oleauto/src/dispatch/win16/locale.prc113
-rw-r--r--private/oleauto/src/dispatch/win16/locale.twn111
-rw-r--r--private/oleauto/src/dispatch/win16/locale.txt4877
-rw-r--r--private/oleauto/src/dispatch/win16/ole2disp.def207
-rw-r--r--private/oleauto/src/dispatch/win16/ole2disp.rc92
-rw-r--r--private/oleauto/src/dispatch/win16/ole2nls.def80
-rw-r--r--private/oleauto/src/dispatch/win16/ole2nls.rc93
-rw-r--r--private/oleauto/src/dispatch/win16/oleconva.asm653
-rw-r--r--private/oleauto/src/dispatch/win16/oledisp.cpp89
-rw-r--r--private/oleauto/src/dispatch/win32/alpha/invoke.s728
-rw-r--r--private/oleauto/src/dispatch/win32/i386/invoke.asm832
-rw-r--r--private/oleauto/src/dispatch/win32/i386/oleconva.asm675
-rw-r--r--private/oleauto/src/dispatch/win32/mips/invoke.s725
-rw-r--r--private/oleauto/src/dispatch/win32/mips/invtest.cpp413
-rw-r--r--private/oleauto/src/dispatch/win32/mips/invtest.h72
-rw-r--r--private/oleauto/src/dispatch/win32/oleconva.cpp549
-rw-r--r--private/oleauto/src/dispatch/win32/oledisp.cpp119
-rw-r--r--private/oleauto/src/dispatch/win32/ppc/invoke.s853
-rw-r--r--private/oleauto/src/inc/dispatch.h1412
-rw-r--r--private/oleauto/src/inc/oautil.h283
-rw-r--r--private/oleauto/src/inc/olenls.h502
-rw-r--r--private/oleauto/src/inc/variant.h277
-rw-r--r--private/oleauto/src/inc/verstamp.h5
-rw-r--r--private/oleauto/src/mktyplib/dimalloc.cxx1787
-rw-r--r--private/oleauto/src/mktyplib/errors.h104
-rw-r--r--private/oleauto/src/mktyplib/fileinfo.h329
-rw-r--r--private/oleauto/src/mktyplib/hout.c1111
-rw-r--r--private/oleauto/src/mktyplib/intlstr.c212
-rw-r--r--private/oleauto/src/mktyplib/intlstr.h35
-rw-r--r--private/oleauto/src/mktyplib/lexer.c890
-rw-r--r--private/oleauto/src/mktyplib/mktyplib.c1302
-rw-r--r--private/oleauto/src/mktyplib/mktyplib.def7
-rw-r--r--private/oleauto/src/mktyplib/mktyplib.h162
-rw-r--r--private/oleauto/src/mktyplib/mktyplib.icobin0 -> 766 bytes
-rw-r--r--private/oleauto/src/mktyplib/mktyplib.r165
-rw-r--r--private/oleauto/src/mktyplib/mktyplib.rc87
-rw-r--r--private/oleauto/src/mktyplib/parser.c3218
-rw-r--r--private/oleauto/src/mktyplib/parser.h93
-rw-r--r--private/oleauto/src/mktyplib/stdole.def15
-rw-r--r--private/oleauto/src/mktyplib/stdole.odl117
-rw-r--r--private/oleauto/src/mktyplib/stdole.rc114
-rw-r--r--private/oleauto/src/mktyplib/stdole32.rc92
-rw-r--r--private/oleauto/src/mktyplib/tlviewer.cpp1473
-rw-r--r--private/oleauto/src/mktyplib/tlviewer.hxx157
-rw-r--r--private/oleauto/src/mktyplib/tmpguid.c23
-rw-r--r--private/oleauto/src/mktyplib/tokens.h132
-rw-r--r--private/oleauto/src/mktyplib/typelib.err85
-rw-r--r--private/oleauto/src/mktyplib/typout.cpp1186
-rw-r--r--private/oleauto/src/typelib/blkdsc32.hxx232
-rw-r--r--private/oleauto/src/typelib/blkmgr.cxx1385
-rw-r--r--private/oleauto/src/typelib/blkmgr.hxx752
-rw-r--r--private/oleauto/src/typelib/bstr.h109
-rw-r--r--private/oleauto/src/typelib/cltypes.hxx687
-rw-r--r--private/oleauto/src/typelib/clutil.cxx3210
-rw-r--r--private/oleauto/src/typelib/clutil.hxx417
-rw-r--r--private/oleauto/src/typelib/convert.cxx356
-rw-r--r--private/oleauto/src/typelib/convert.hxx37
-rw-r--r--private/oleauto/src/typelib/ctseg.hxx84
-rw-r--r--private/oleauto/src/typelib/dassert.c35
-rw-r--r--private/oleauto/src/typelib/dbindtbl.cxx811
-rw-r--r--private/oleauto/src/typelib/dbindtbl.hxx249
-rw-r--r--private/oleauto/src/typelib/dblkmgr.hxx690
-rw-r--r--private/oleauto/src/typelib/debug.h234
-rw-r--r--private/oleauto/src/typelib/debug.hxx175
-rw-r--r--private/oleauto/src/typelib/debug2.cxx164
-rw-r--r--private/oleauto/src/typelib/defn.hxx1640
-rw-r--r--private/oleauto/src/typelib/dfntbind.cxx80
-rw-r--r--private/oleauto/src/typelib/dfntbind.hxx272
-rw-r--r--private/oleauto/src/typelib/dfntcomp.cxx569
-rw-r--r--private/oleauto/src/typelib/dfntcomp.hxx92
-rw-r--r--private/oleauto/src/typelib/dfstream.cxx408
-rw-r--r--private/oleauto/src/typelib/dfstream.hxx77
-rw-r--r--private/oleauto/src/typelib/dstrmgr.cxx1692
-rw-r--r--private/oleauto/src/typelib/dstrmgr.hxx196
-rw-r--r--private/oleauto/src/typelib/dtbind.cxx1210
-rw-r--r--private/oleauto/src/typelib/dtbind.hxx282
-rw-r--r--private/oleauto/src/typelib/dtmbrs.cxx3285
-rw-r--r--private/oleauto/src/typelib/dtmbrs.hxx361
-rw-r--r--private/oleauto/src/typelib/dyntinfo.hxx90
-rw-r--r--private/oleauto/src/typelib/ebvers.h22
-rw-r--r--private/oleauto/src/typelib/entrymgr.cxx1017
-rw-r--r--private/oleauto/src/typelib/entrymgr.hxx506
-rw-r--r--private/oleauto/src/typelib/errmap.cxx161
-rw-r--r--private/oleauto/src/typelib/errmap.hxx31
-rw-r--r--private/oleauto/src/typelib/exbind.hxx167
-rw-r--r--private/oleauto/src/typelib/fstream.cxx364
-rw-r--r--private/oleauto/src/typelib/gbindtbl.cxx1377
-rw-r--r--private/oleauto/src/typelib/gbindtbl.hxx415
-rw-r--r--private/oleauto/src/typelib/gdtinfo.cxx4981
-rw-r--r--private/oleauto/src/typelib/gdtinfo.hxx1323
-rw-r--r--private/oleauto/src/typelib/gdtrt.cxx2576
-rw-r--r--private/oleauto/src/typelib/gptbind.cxx1526
-rw-r--r--private/oleauto/src/typelib/gptbind.hxx254
-rw-r--r--private/oleauto/src/typelib/gtlibole.cxx6619
-rw-r--r--private/oleauto/src/typelib/gtlibole.hxx1220
-rw-r--r--private/oleauto/src/typelib/gtlibstg.cxx1609
-rw-r--r--private/oleauto/src/typelib/gtlibstg.hxx208
-rw-r--r--private/oleauto/src/typelib/impmgr.cxx1502
-rw-r--r--private/oleauto/src/typelib/impmgr.hxx490
-rw-r--r--private/oleauto/src/typelib/machine.hxx222
-rw-r--r--private/oleauto/src/typelib/macros.hxx276
-rw-r--r--private/oleauto/src/typelib/mbstring.cxx667
-rw-r--r--private/oleauto/src/typelib/mbstring.h46
-rw-r--r--private/oleauto/src/typelib/mem.cxx417
-rw-r--r--private/oleauto/src/typelib/mem.hxx174
-rw-r--r--private/oleauto/src/typelib/namemacs.h1305
-rw-r--r--private/oleauto/src/typelib/nammgr.cxx1521
-rw-r--r--private/oleauto/src/typelib/nammgr.hxx621
-rw-r--r--private/oleauto/src/typelib/ncache.hxx287
-rw-r--r--private/oleauto/src/typelib/newexe.h387
-rw-r--r--private/oleauto/src/typelib/ntimage.h968
-rw-r--r--private/oleauto/src/typelib/ntstring.cxx397
-rw-r--r--private/oleauto/src/typelib/ntstring.h153
-rw-r--r--private/oleauto/src/typelib/oautil.cxx522
-rw-r--r--private/oleauto/src/typelib/obguid.c65
-rw-r--r--private/oleauto/src/typelib/obguid.h46
-rw-r--r--private/oleauto/src/typelib/obole2.h224
-rw-r--r--private/oleauto/src/typelib/obwin.hxx93
-rw-r--r--private/oleauto/src/typelib/obwlm.h374
-rw-r--r--private/oleauto/src/typelib/oleaut32.def241
-rw-r--r--private/oleauto/src/typelib/oleaut32.rc96
-rw-r--r--private/oleauto/src/typelib/olenames.h100
-rw-r--r--private/oleauto/src/typelib/oletmgr.cxx468
-rw-r--r--private/oleauto/src/typelib/oletmgr.hxx100
-rw-r--r--private/oleauto/src/typelib/rtarray.h39
-rw-r--r--private/oleauto/src/typelib/rtsheap.cxx473
-rw-r--r--private/oleauto/src/typelib/rtsheap.h128
-rw-r--r--private/oleauto/src/typelib/segnames.h246
-rw-r--r--private/oleauto/src/typelib/segorder.asm99
-rw-r--r--private/oleauto/src/typelib/sheapmgr.cxx1996
-rw-r--r--private/oleauto/src/typelib/sheapmgr.hxx1057
-rw-r--r--private/oleauto/src/typelib/silver.hxx143
-rw-r--r--private/oleauto/src/typelib/stltinfo.cxx500
-rw-r--r--private/oleauto/src/typelib/stltinfo.hxx558
-rw-r--r--private/oleauto/src/typelib/strdcl.c2
-rw-r--r--private/oleauto/src/typelib/stream.hxx188
-rw-r--r--private/oleauto/src/typelib/switches.hxx457
-rw-r--r--private/oleauto/src/typelib/sysutils.h13
-rw-r--r--private/oleauto/src/typelib/tdata.hxx1372
-rw-r--r--private/oleauto/src/typelib/tdata1.cxx2465
-rw-r--r--private/oleauto/src/typelib/tdata2.cxx3651
-rw-r--r--private/oleauto/src/typelib/tdesck.hxx72
-rw-r--r--private/oleauto/src/typelib/tinfo.hxx56
-rw-r--r--private/oleauto/src/typelib/tiperr.h92
-rw-r--r--private/oleauto/src/typelib/tlibfrag.r36
-rw-r--r--private/oleauto/src/typelib/tlibguid.c69
-rw-r--r--private/oleauto/src/typelib/tlibpch.cxx178
-rw-r--r--private/oleauto/src/typelib/tlibutil.cxx7729
-rw-r--r--private/oleauto/src/typelib/tlibutil.hxx40
-rw-r--r--private/oleauto/src/typelib/tls.c340
-rw-r--r--private/oleauto/src/typelib/tls.h175
-rw-r--r--private/oleauto/src/typelib/tmpguid.c104
-rw-r--r--private/oleauto/src/typelib/typelib.def74
-rw-r--r--private/oleauto/src/typelib/typelib.hxx336
-rw-r--r--private/oleauto/src/typelib/typelib.rc131
-rw-r--r--private/oleauto/src/typelib/types.h342
-rw-r--r--private/oleauto/src/typelib/typesx.h190
-rw-r--r--private/oleauto/src/typelib/validate.h71
-rw-r--r--private/oleauto/src/typelib/version.hxx67
-rw-r--r--private/oleauto/src/typelib/wep.c144
-rw-r--r--private/oleauto/src/typelib/xstring.h60
-rw-r--r--private/oleauto/src/typelib/xutil.h196
299 files changed, 187390 insertions, 0 deletions
diff --git a/private/oleauto/src/dispatch/asmhelp.c b/private/oleauto/src/dispatch/asmhelp.c
new file mode 100644
index 000000000..72526a8d0
--- /dev/null
+++ b/private/oleauto/src/dispatch/asmhelp.c
@@ -0,0 +1,55 @@
+/***
+*asmhelp.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Misc asm interfacing stuff.
+*
+*
+*Revision History:
+*
+* [00] 03-Jun-93 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+
+/* Max and min floating point values that can fit in a currency
+ * Used for overflow detection in some of the currency coersion routines.
+ * Numbers are scaled by 10,000
+ */
+
+#if _MAC
+#pragma code_seg("OLECONV")
+double __declspec(allocate("_CODE")) g_dblMaxPosCy = 9.223372036854775807e+18;
+double __declspec(allocate("_CODE")) g_dblMaxNegCy = -9.223372036854775808e+18;
+#pragma code_seg()
+#else
+
+double NEARDATA g_dblMaxPosCy = 9.223372036854775807e+18;
+double NEARDATA g_dblMaxNegCy = -9.223372036854775808e+18;
+#endif
+
+/* These routines is called by some of the assembly helpers to
+ * assist in returning an appropriate HRESULT. We do this here
+ * in C because the Ole2 routines used to report an HRESULT are
+ * different and in a state of flux on our various platforms,
+ * so this helps insulate... a bit.
+ */
+INTERNAL_(HRESULT)
+ReportOverflow()
+{
+ return RESULT(DISP_E_OVERFLOW);
+}
+
+INTERNAL_(HRESULT)
+ReportInvalidarg()
+{
+ return RESULT(E_INVALIDARG);
+}
+
diff --git a/private/oleauto/src/dispatch/assert.cpp b/private/oleauto/src/dispatch/assert.cpp
new file mode 100644
index 000000000..76d7e1585
--- /dev/null
+++ b/private/oleauto/src/dispatch/assert.cpp
@@ -0,0 +1,134 @@
+/***
+*assert.cpp
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Internal assertion support.
+*
+*Revision History:
+*
+* [00] 22-May-93 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+// Disable Unicode expansion for assertions
+#ifdef WIN32
+# undef UNICODE
+#endif
+
+#include "oledisp.h"
+#include "assrtdlg.h"
+
+#if OE_WIN32
+#include "oautil.h"
+#endif // OE_WIN32
+
+#include <stdio.h> // sprintf
+
+
+#ifdef _DEBUG // {
+
+#ifndef _MAC // {
+
+// this is setup in the DLL's LibMain
+extern "C" {
+extern HINSTANCE g_hinstDLL;
+}
+
+LPSTR g_szLoc;
+LPSTR g_szMsg;
+
+BOOL EXPORT FAR PASCAL
+AssertDlgProc(
+ HWND hdlg,
+ WORD message,
+ WORD wParam,
+ LONG lParam)
+{
+ switch (message){
+ case WM_INITDIALOG:
+ SetDlgItemText(hdlg, ASSERT_ID_LOC, g_szLoc);
+ if(g_szMsg)
+ SetDlgItemText(hdlg, ASSERT_ID_MSG, g_szMsg);
+ break;
+
+ case WM_COMMAND:
+ switch(wParam){
+ case ASSERT_ID_BREAK:
+ case ASSERT_ID_EXIT:
+ case ASSERT_ID_IGNORE:
+ EndDialog(hdlg, wParam);
+ return TRUE;
+ }
+ break;
+ }
+ return FALSE;
+}
+
+#endif // }
+
+#endif // }
+
+STDAPI_(void)
+DispAssert(
+ char FAR* szMsg,
+ char FAR* szFileName,
+ int line)
+{
+#ifdef _DEBUG // {
+
+ char rgchBuf[200];
+ char rgchLoc[200];
+
+#ifdef _MAC // {
+
+ SPRINTF(rgchLoc, "File %s, line %d", szFileName, line);
+ rgchBuf[0] = SPRINTF(
+ rgchBuf+1, "Assertion failed: %s %s\n",
+ rgchLoc, szMsg == NULL ? "" : szMsg);
+ --rgchBuf[0]; // kill the cr in string
+ DebugStr((const unsigned char FAR*)rgchBuf);
+
+#else // }{
+
+ int i;
+ FARPROC pfnAssertDlgProc;
+
+ pfnAssertDlgProc = MakeProcInstance((FARPROC)AssertDlgProc, g_hinstDLL);
+ SPRINTF(rgchBuf, "Assertion failed: ");
+ SPRINTF(rgchLoc, "File %s, line %d", szFileName, line);
+
+ OutputDebugString(rgchBuf);
+ OutputDebugString(rgchLoc);
+ if(szMsg){
+ OutputDebugString("\r\n");
+ OutputDebugString(szMsg);
+ }
+ OutputDebugString("\r\n");
+
+ g_szMsg = szMsg;
+ g_szLoc = rgchLoc;
+
+#ifdef WIN32 // required by new Daytona headers
+ i = DialogBox(g_hinstDLL, "AssertFailDlg", NULL, (DLGPROC)pfnAssertDlgProc);
+#else //WIN32
+ i = DialogBox(g_hinstDLL, "AssertFailDlg", NULL, pfnAssertDlgProc);
+#endif //WIN32
+ FreeProcInstance(pfnAssertDlgProc);
+
+ switch(i){
+ case ASSERT_ID_BREAK:
+ DebugBreak();
+ break;
+ case ASSERT_ID_EXIT:
+ FatalAppExit(0, "Assertion failure");
+ break;
+ }
+
+#endif // }
+#endif // }
+}
diff --git a/private/oleauto/src/dispatch/assert.dlg b/private/oleauto/src/dispatch/assert.dlg
new file mode 100644
index 000000000..d520400ee
--- /dev/null
+++ b/private/oleauto/src/dispatch/assert.dlg
@@ -0,0 +1,13 @@
+#include "assrtdlg.h"
+
+ASSERTFAILDLG DIALOG 72, 32, 260, 67
+STYLE DS_MODALFRAME | WS_POPUP | WS_VISIBLE | WS_CAPTION
+CAPTION "Assertion failure!"
+FONT 8, "MS Sans Serif"
+BEGIN
+ CTEXT "", ASSERT_ID_LOC, 11, 15, 240, 8
+ CTEXT "", ASSERT_ID_MSG, 11, 28, 240, 8
+ PUSHBUTTON "&Break", ASSERT_ID_BREAK, 54, 47, 40, 14
+ PUSHBUTTON "E&xit", ASSERT_ID_EXIT, 110, 47, 40, 14
+ PUSHBUTTON "&Ignore", ASSERT_ID_IGNORE, 166, 47, 40, 14
+END
diff --git a/private/oleauto/src/dispatch/assrtdlg.h b/private/oleauto/src/dispatch/assrtdlg.h
new file mode 100644
index 000000000..2d2864efb
--- /dev/null
+++ b/private/oleauto/src/dispatch/assrtdlg.h
@@ -0,0 +1,29 @@
+/***
+*assrtdlg.h
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Constants for the assert dialog.
+*
+*Revision History:
+*
+* [00] 05-Jun-92 bradlo: Added header.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#ifndef _ASSRTDLG_H_
+#define _ASSRTDLG_H_
+
+#define ASSERT_ID_BREAK 5103
+#define ASSERT_ID_EXIT 5104
+#define ASSERT_ID_IGNORE 5105
+#define ASSERT_ID_LOC 5106
+#define ASSERT_ID_EXPR 5107
+#define ASSERT_ID_MSG 5108
+
+#endif
+
diff --git a/private/oleauto/src/dispatch/bstr.cpp b/private/oleauto/src/dispatch/bstr.cpp
new file mode 100644
index 000000000..4f82f7b8c
--- /dev/null
+++ b/private/oleauto/src/dispatch/bstr.cpp
@@ -0,0 +1,615 @@
+/***
+*bstr.cpp
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* The module contains the implementation of the BSTR API.
+*
+*
+*Revision History:
+*
+* [00] 24-Apr-93 bradlo: Created
+* [01] 27-Apr-93 tomteng: Add Unicode support for WIN32
+*
+*Implementation Notes:
+*
+* BSTR is implemented as a NULL terminated string with a unsigned
+* long length field prefix. The length field indicates the number
+* of 'characters' defined in the BSTR, where 'character' is define
+* as bytes for ANSI and word (16-bits) for Unicode BSTR.
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#if OE_WIN32
+#include "oautil.h"
+#endif // OE_WIN32
+
+ASSERTDATA
+
+#if OE_WIN16
+
+// Answer if there is room for the given count of bytes between the
+// given pointer, and the end of its segment.
+//
+// (64k - offset(ptr)) >= cb ?
+//
+#define PTROFFSET(PV) \
+ ((USHORT)*(USHORT FAR*)&(PV))
+
+#define ROOMINSEG(PV, CB) \
+ (((1024UL*64UL) - (DWORD)PTROFFSET(PV)) >= (CB))
+
+#endif
+
+// only turn on BSTR cache for WIN32 builds at the moment
+#define CACHE OE_WIN32
+
+#if CACHE
+#define ROUNDUP 1 // round up string alloc requests to nearest N-byte
+ // boundary, since allocator will round up anyway.
+ // improves cache hits.
+
+#define ALLOC_ALIGN (4 - 1) // UNDONE: optimal for Chicago is 4
+ // UNDONE: optimal for Daytona is 32
+ // UNDONE: 4 didn't help the a$ = a$ + "x" case at all.
+ // UNDONE: 8 did (gave 50% cache hit)
+#define ALIGN_MASK ~ALLOC_ALIGN
+
+#define CB_MAX_CACHE 0x0000ffff // biggest block we'll cache
+#ifdef _DEBUG
+#define PROFILE 0 // TEMPORARY TESTING
+#endif //DEBUG
+#if PROFILE
+DWORD g_cAllocTot = 0;
+DWORD g_cReallocTot = 0;
+DWORD g_cFreeTot = 0;
+DWORD g_cAllocHits = 0;
+DWORD g_cFreeHits = 0;
+#endif //PROFILE
+
+#endif //CACHE
+
+
+// these routines are not needed for network automation
+#if !defined(NETDISP)
+/***
+*BSTR SysAllocString(char*)
+*Purpose:
+* UNDONE
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value = BSTR, NULL if allocation failed
+*
+***********************************************************************/
+STDAPI_(BSTR)
+SysAllocString(const OLECHAR FAR* psz)
+{
+ if(psz == NULL)
+ return NULL;
+
+ return SysAllocStringLen(psz, STRLEN(psz));
+}
+
+
+/***
+*BSTR SysAllocStringLen(char*, unsigned int)
+*Purpose:
+* UNDONE
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value = BSTR, NULL if the allocation failed.
+*
+***********************************************************************/
+STDAPI_(BSTR)
+SysAllocStringLen(const OLECHAR FAR* psz, unsigned int len)
+{
+ BSTR bstr;
+ IMalloc FAR* pmalloc;
+ DWORD cbTotal;
+#if CACHE
+ APP_DATA *pappdata;
+#endif //CACHE
+
+#if OE_WIN32
+#if ROUNDUP
+ cbTotal = ((DWORD)len*2 + sizeof(DWORD) + 2L + ALLOC_ALIGN) & ALIGN_MASK;
+#else //ROUNDUP
+ cbTotal = (DWORD)len*2 + sizeof(DWORD) + 2L;
+#endif //ROUNDUP
+#else
+ cbTotal = (DWORD)len + sizeof(DWORD) + 1L;
+#endif
+
+#if OE_WIN16
+ // BSTRs are limited to 64k on Win16
+ if(cbTotal > 65535)
+ return NULL;
+#endif
+
+#if CACHE
+#if PROFILE
+ g_cAllocTot++;
+#endif //PROFILE
+ if (FAILED(GetAppData(&pappdata)))
+ return NULL;
+ if (pappdata->m_cbFreeBlock >= cbTotal) {
+ // found big enough block in cache
+ bstr = pappdata->m_pbFreeBlock;
+ pappdata->m_cbFreeBlock = 0;
+#if PROFILE
+ g_cAllocHits++;
+#endif //PROFILE
+ goto GotBlock;
+ }
+ pmalloc = pappdata->m_pimalloc;
+
+#else //CACHE
+ if(GetMalloc(&pmalloc) != NOERROR)
+ return NULL;
+#endif //CACHE
+
+ bstr = (BSTR)pmalloc->Alloc(cbTotal);
+
+ if(bstr != NULL){
+#if OE_WIN16
+ // Even if IMalloc was able to allocate the ammount we asked
+ // for, we need to make sure that there is enough room in the
+ // first segment of the allocation for the string, because BSTRs
+ // aren't HUGE pts on Win16.
+ //
+ if(!ROOMINSEG(bstr, cbTotal))
+ {
+ pmalloc->Free(bstr);
+ bstr = NULL;
+ }
+ else
+#endif
+
+#if CACHE
+GotBlock:
+#endif //CACHE
+
+ {
+#if OE_WIN32
+ *(DWORD FAR*)bstr = (DWORD)len*2;
+
+ bstr = (WCHAR*) ((char*) bstr + sizeof(DWORD));
+
+ if(psz != NULL){
+ MEMCPY(bstr, psz, len*2);
+ }
+
+ bstr[len] = L'\0'; // always 0 terminate
+
+#else
+ *(DWORD FAR*)bstr = (DWORD)len;
+
+ bstr += sizeof(DWORD);
+
+ if(psz != NULL){
+ MEMCPY(bstr, psz, len);
+ }
+
+ bstr[len] = '\0'; // always 0 terminate
+#endif
+
+ }
+ }
+
+ return bstr;
+}
+
+
+/***
+*int SysReAllocString(BSTR*, char*)
+*Purpose:
+* UNDONE
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value = int. TRUE = success, FALSE = failure
+*
+***********************************************************************/
+STDAPI_(int)
+SysReAllocString(BSTR FAR* pbstr, const OLECHAR FAR* psz)
+{
+ if(psz == NULL)
+ {
+ SysFreeString(*pbstr);
+ *pbstr = NULL;
+ return TRUE;
+ }
+
+ return SysReAllocStringLen(pbstr, psz, STRLEN(psz));
+}
+
+
+/***
+*int SysReAllocStringLen(BSTR*, char*, unsigned int)
+*Purpose:
+* UNDONE
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value = int. TRUE = success, FALSE = failure
+*
+***********************************************************************/
+STDAPI_(int)
+SysReAllocStringLen(BSTR FAR* pbstr, const OLECHAR FAR* psz, unsigned int len)
+{
+ BSTR bstr;
+ IMalloc FAR* pmalloc;
+ DWORD cbTotal;
+
+#if OE_WIN32
+#if ROUNDUP
+ cbTotal = ((DWORD)len*2 + sizeof(DWORD) + 2L + ALLOC_ALIGN) & ALIGN_MASK;
+#else //ROUNDUP
+ cbTotal = (DWORD)len*2 + sizeof(DWORD) + 2L;
+#endif //ROUNDUP
+#else
+ cbTotal = (DWORD)len + sizeof(DWORD) + 1L;
+#endif
+
+#if OE_WIN16
+ // BSTRs are limited to 64k on Win16
+ if(cbTotal > 65535)
+ return NULL;
+#endif
+
+ if(GetMalloc(&pmalloc) != NOERROR)
+ return NULL;
+
+ bstr = *pbstr;
+ if (bstr != NULL)
+ {
+ if (psz == bstr)
+ psz = NULL; // don't do a copy to self
+ bstr -= sizeof(long) / sizeof(*bstr);
+ }
+
+#if PROFILE
+ g_cReallocTot++;
+#endif //PROFILE
+ bstr = (BSTR)pmalloc->Realloc(bstr, cbTotal);
+ if(bstr == NULL)
+ return FALSE;
+
+#if OE_WIN16
+ // Even if IMalloc was able to allocate the ammount we asked
+ // for, we need to make sure that there is enough room in the
+ // first segment of the allocation for the string, because BSTRs
+ // aren't HUGE pts on Win16.
+ //
+ if(!ROOMINSEG(bstr, cbTotal))
+ {
+ pmalloc->Free(bstr);
+ bstr = NULL;
+ }
+ else
+#endif
+ {
+#if OE_WIN32
+ *(DWORD FAR*)bstr = (DWORD)len*2;
+ bstr = (WCHAR*) ((char*) bstr + sizeof(DWORD));
+
+ if(psz != NULL)
+ MEMCPY(bstr, psz, len*2);
+
+ bstr[len] = L'\0'; // always 0 terminate
+
+#else
+ *(DWORD FAR*)bstr = (DWORD)len;
+ bstr += sizeof(DWORD);
+
+ if(psz != NULL)
+ MEMCPY(bstr, psz, len);
+
+ bstr[len] = '\0'; // always 0 terminate
+#endif
+ }
+
+ *pbstr = bstr;
+ return TRUE;
+}
+
+
+/***
+*void SysFreeString(BSTR)
+*Purpose:
+* Free the given BSTR.
+*
+*Entry:
+* bstr = the BSTR to free
+*
+*Exit:
+* None
+*
+***********************************************************************/
+STDAPI_(void)
+SysFreeString(BSTR bstr)
+{
+ IMalloc FAR* pmalloc;
+
+
+ if(bstr == NULL)
+ return;
+
+#if OE_WIN32
+ bstr = (WCHAR*) ((char *) bstr - sizeof(DWORD));
+#else
+ bstr -= sizeof(DWORD);
+#endif
+
+#if CACHE
+#if ROUNDUP
+ DWORD cbFree = (*((DWORD FAR*)bstr) + sizeof(DWORD) + 2L + ALLOC_ALIGN) & ALIGN_MASK;
+#else //ROUNDUP
+ DWORD cbFree = *((DWORD FAR*)bstr) + sizeof(DWORD) + 2L;
+#endif //ROUNDUP
+#if PROFILE
+ g_cFreeTot++;
+#endif //PROFILE
+ APP_DATA * pappdata = Pappdata();
+ if (pappdata == NULL) {
+ // we MUST be being called after OleUninitialize. This is wierd,
+ // but I don't want to do a GetAppData in this case (init's way too
+ // much stuff to just do a free. So just do it the fat way instead.
+ if (FAILED(CoGetMalloc(MEMCTX_TASK, &pmalloc)))
+ return;
+ pmalloc->Free(bstr);
+ pmalloc->Release();
+ return;
+ }
+ if (cbFree > pappdata->m_cbFreeBlock && cbFree <= CB_MAX_CACHE) {
+ // If this block is better than the one in the cache (if any), and
+ // is less than our threshhold for keeping memory (we don't want to
+ // hold onto too much memory), then cache this block instead of
+ // freeing it.
+ if (pappdata->m_cbFreeBlock) {
+ // free the old one in the cache
+ pmalloc = pappdata->m_pimalloc;
+ ASSERT(pmalloc != NULL);
+ pmalloc->Free(pappdata->m_pbFreeBlock);
+ }
+#if PROFILE
+ else
+ g_cFreeHits++;
+#endif //PROFILE
+ // put this block in the cache
+ pappdata->m_cbFreeBlock = cbFree;
+ pappdata->m_pbFreeBlock = bstr;
+ return;
+ }
+ pmalloc = pappdata->m_pimalloc;
+ ASSERT(pmalloc != NULL);
+
+#else //CACHE
+ if(GetMalloc(&pmalloc) != NOERROR)
+ return; // REVIEW: shouldnt this be an error?
+#endif //CACHE
+
+ pmalloc->Free(bstr);
+}
+
+
+/***
+*unsigned int SysStringLen(BSTR)
+*Purpose:
+* return the length in bytes of the given BSTR.
+*
+*Entry:
+* bstr = the BSTR to return the length of
+*
+*Exit:
+* return value = unsigned int, length in bytes.
+*
+***********************************************************************/
+STDAPI_(unsigned int)
+SysStringLen(BSTR bstr)
+{
+ if(bstr == NULL)
+ return 0;
+#if OE_WIN32
+ return (unsigned int)((((DWORD FAR*)bstr)[-1]) / 2);
+#else
+ return (unsigned int)(((DWORD FAR*)bstr)[-1]);
+#endif
+}
+#endif // !NETDISP
+
+
+/***
+*PRIVATE HRESULT ErrSysAllocString(char*, BSTR*)
+*Purpose:
+* This is an implementation of SysAllocString that check for the
+* NULL return value and return the corresponding error - E_OUTOFMEMORY.
+*
+* This is simply a convenience, and this routine is only used
+* internally by the oledisp component.
+*
+*Entry:
+* psz = the source string
+*
+*Exit:
+* return value = HRESULT
+* S_OK
+* E_OUTOFMEMORY
+*
+* *pbstrOut = the newly allocated BSTR
+*
+***********************************************************************/
+EXTERN_C INTERNAL_(HRESULT)
+ErrSysAllocString(const OLECHAR FAR* psz, BSTR FAR* pbstrOut)
+{
+ BSTR bstrNew;
+
+
+ if(psz == NULL){
+ *pbstrOut = NULL;
+ return NOERROR;
+ }
+
+ if((bstrNew = SysAllocString(psz)) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+
+ *pbstrOut = bstrNew;
+
+ return NOERROR;
+}
+
+
+EXTERN_C INTERNAL_(HRESULT)
+ErrSysAllocStringLen(const OLECHAR FAR* psz, unsigned int len, BSTR FAR* pbstrOut)
+{
+ BSTR bstrNew;
+
+ if((bstrNew = SysAllocStringLen(psz, len)) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+
+ *pbstrOut = bstrNew;
+
+ return NOERROR;
+}
+
+#if OE_WIN32
+// Helper function that will correctly handle odd-length ANSI BSTR's (BSTRA's)
+EXTERN_C INTERNAL_(HRESULT)
+ErrStringCopy(BSTR bstrSrc, BSTR FAR * pbstrOut)
+{
+ BSTR bstrNew;
+
+ if((bstrNew = SysAllocStringByteLen((char FAR *)bstrSrc,
+ SysStringByteLen(bstrSrc))) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+
+ *pbstrOut = bstrNew;
+
+ return NOERROR;
+}
+#endif //OE_WIN32
+
+// these routines are not needed for network automation
+#if !defined(NETDISP)
+#if OE_WIN32
+/************************************************************************/
+/************************ Win32 Unicode Support *************************/
+/************************************************************************/
+
+STDAPI_(unsigned int)
+SysStringByteLen(BSTR bstr)
+{
+ if(bstr == NULL)
+ return 0;
+ return (unsigned int)(((DWORD FAR*)bstr)[-1]);
+}
+
+
+STDAPI_(BSTR)
+SysAllocStringByteLen(const char FAR* psz, unsigned int len)
+{
+ BSTR bstr;
+ IMalloc FAR* pmalloc;
+ DWORD cbTotal;
+#if CACHE
+ APP_DATA *pappdata;
+#endif //CACHE
+
+#if ROUNDUP
+ cbTotal = ((DWORD)len + sizeof(DWORD) + 2L + ALLOC_ALIGN) & ALIGN_MASK;
+#else //ROUNDUP
+ cbTotal = (DWORD)len + sizeof(DWORD) + sizeof(OLECHAR);
+#endif //ROUNDUP
+
+#if CACHE
+#if PROFILE
+ g_cAllocTot++;
+#endif //PROFILE
+ if (FAILED(GetAppData(&pappdata)))
+ return NULL;
+ if (pappdata->m_cbFreeBlock >= cbTotal) {
+ // found big enough block in cache
+ bstr = pappdata->m_pbFreeBlock;
+ pappdata->m_cbFreeBlock = 0;
+#if PROFILE
+ g_cAllocHits++;
+#endif //PROFILE
+ goto GotBlock;
+ }
+ pmalloc = pappdata->m_pimalloc;
+#else //CACHE
+ if(GetMalloc(&pmalloc) != NOERROR)
+ return NULL;
+#endif //CACHE
+
+ bstr = (BSTR)pmalloc->Alloc(cbTotal);
+
+ if(bstr != NULL){
+#if CACHE
+GotBlock:
+#endif //CACHE
+ *(DWORD FAR*)bstr = (DWORD)len;
+
+ bstr = (WCHAR*) ((char*) bstr + sizeof(DWORD));
+
+ if(psz != NULL){
+ MEMCPY(bstr, psz, len);
+ }
+
+ *(WCHAR UNALIGNED*)((char *)bstr + len) = L'\0';
+ // always 0 terminate with a WIDE zero
+ }
+
+ return bstr;
+}
+#endif //OE_WIN32
+#endif // !NETDISP
+
+#if CACHE
+// called right before the appdata structure is being destroyed -- we release
+// any cached free block(s) here.
+STDAPI_(void) ReleaseBstrCache(APP_DATA * pappdata)
+{
+ IMalloc FAR* pmalloc;
+ if (pappdata->m_cbFreeBlock) {
+ // free the old one in the cache
+ pmalloc = pappdata->m_pimalloc;
+ ASSERT(pmalloc != NULL);
+ pmalloc->Free(pappdata->m_pbFreeBlock);
+ pappdata->m_cbFreeBlock = 0;
+#if PROFILE
+ g_cFreeHits--; // make the numbers balance. We counted
+ // this as a free "hit" before, but
+ // we eventually have to free it.
+#endif //PROFILE
+ }
+
+#if PROFILE // dumps statistics about the BSTR cache
+ {
+ char buffer[256];
+
+#if 0
+ sprintf(buffer, "cAllocTot = %ld, cReallocTot = %ld, cFreeTot = %ld, cAllocHits = %ld, cFreeHits = %ld", g_cAllocTot, g_cReallocTot, g_cFreeTot, g_cAllocHits, g_cFreeHits);
+ MessageBox(NULL, buffer, "BSTR cache statistics", MB_OK);
+#else //0
+ sprintf(buffer, "BSTR cache stats: cAllocTot = %ld, cReallocTot = %ld, cFreeTot = %ld, cAllocHits = %ld, cFreeHits = %ld", g_cAllocTot, g_cReallocTot, g_cFreeTot, g_cAllocHits, g_cFreeHits);
+ OutputDebugString(buffer);
+#endif //0
+ }
+#endif //PROFILE
+}
+#endif //CACHE
diff --git a/private/oleauto/src/dispatch/bstrdate.c b/private/oleauto/src/dispatch/bstrdate.c
new file mode 100644
index 000000000..791ab433b
--- /dev/null
+++ b/private/oleauto/src/dispatch/bstrdate.c
@@ -0,0 +1,2802 @@
+/**
+*bstrdate.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file contains the BSTR<->DATE coersion support routines.
+*
+*
+*Revision History:
+*
+* [00] 14-Feb-92 bradlo: Created.
+* [01] 25-Jul-93 bassams: DBCS enable date coersion routines.
+* [02] 15-May-94 makotom: VBA2: Enable ambiguous date format.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#ifdef FE_DBCS
+#include "dbcsdate.h" // DBCS date constant strings
+#endif //FE_DBCS
+
+ASSERTDATA
+
+
+#if 0
+
+INTERNAL_(HRESULT)
+StringOfInt(int, OLECHAR FAR*, int FAR* pcbLen);
+
+#endif
+
+INTERNAL_(HRESULT)
+IntOfString(LCID lcid, OLECHAR FAR*, int FAR*);
+
+#define ISWHITE(L,X) (IsCharType(L,X, C1_SPACE))
+#define ISDIGIT(L,X) (IsCharType(L,X, C1_DIGIT))
+#define ISALPHA(L,X) (IsCharType(L,X, C1_ALPHA))
+#define ISALPHANUM(L,X) (IsCharType(L,X, C1_ALPHA | C1_DIGIT))
+#define EATWHITE(L,X) while(ISWHITE((L),*(X))){++(X);}
+
+int
+IsCharType(LCID lcid, OLECHAR ch, DWORD dwType)
+{
+ WORD wOut[2];
+ OLECHAR str[2];
+ BOOL bRet;
+
+#if !OE_WIN32
+ //REVIEW: OLE GetStringTypeA seems to think ascii 0 is a digit.
+ if (ch == 0)
+ return 0;
+#endif
+
+ str[0] = ch;
+ str[1] = 0;
+
+ bRet = GETSTRINGTYPE(lcid, CT_CTYPE1, str, -1, wOut);
+
+ ASSERT(bRet);
+
+ return (int)(wOut[0]&dwType);
+}
+
+
+//---------------------------------------------------------------------
+// DATE from BSTR
+//---------------------------------------------------------------------
+
+// Date Format Ordering (DFO_*)
+
+// Note! there is code that depends on the values of the following enum
+
+enum {
+ DFO_MDY = 0,
+ DFO_DMY,
+ DFO_YMD,
+ DFO_MAX /* marker */
+};
+
+
+#ifdef FE_DBCS
+
+// Imperial Date Info
+
+#define MAX_ERA_NAMES 3
+#define MAX_EMPERORS 4
+
+typedef struct tagIMPERIALERA {
+ UDS beginDate;
+ OLECHAR FAR* szName[MAX_ERA_NAMES];
+} IMPERIALERA;
+
+
+#define MAX_REPUBLIC_NAMES 2
+#define MAX_REPUBLIC_ERAS 2
+
+typedef struct tagREPUBLICERA {
+ BOOL Before1912;
+ OLECHAR FAR* szName[MAX_REPUBLIC_NAMES];
+} REPUBLICERA;
+
+#define BADERA -1
+
+#endif // FE_DBCS
+
+
+// the following struct holds locale specific info needed
+// to parse (input) and render (output) a date string
+
+// REVIEW: the size of the fields in the following struct - the idea
+// is for them to be large enough to hold locale specific info for
+// any locale we can concieve of supporting.
+
+typedef struct tagDATEINFO {
+ LCID lcid; // LOCALE_USER_DEFAULT
+#if OE_WIN16
+ DWORD dwFlags; // flags used to build this dateinfo
+#endif //OE_WIN16
+ int dfo; // derived from LOCALE_IDATE
+ OLECHAR sz1159[12]; // AM designator
+ OLECHAR sz2359[12]; // PM designator
+ OLECHAR szDatesep[8]; // date separator character(s)
+ OLECHAR szTimesep[8]; // time separator character(s)
+ BOOL fTlzero; // does hour have leading zero?
+ BOOL fAmpm; // does time output use 24hour or Ampm format?
+
+#ifdef FE_DBCS
+ // date information specific to DBCS. Note imperial era is only valid
+ // on certain DBCS locales (Japan for now).
+ union eras {
+ IMPERIALERA impEras[MAX_EMPERORS]; // imperial era information
+ REPUBLICERA repEras[MAX_REPUBLIC_ERAS]; // republic eras for taiwan
+ OLECHAR FAR* dbEraName; // era string for simplified chinese
+ };
+ OLECHAR FAR* dbYearSuff; // year suffix DBCS character
+ OLECHAR FAR* dbMonthSuff; // month suffix DBCS character
+ OLECHAR FAR* dbDaySuff; // day suffix DBCS character
+ OLECHAR FAR* dbHourSuff; // hour suffix DBCS character
+ OLECHAR FAR* dbMinuteSuff; // minute suffix DBCS character
+ OLECHAR FAR* dbSecondSuff; // second suffix DBCS character
+ OLECHAR FAR* db1159; // hard-coded double byte AM (lcid-based)
+ OLECHAR FAR* db2359; // hard-coded double byte PM (lcid-based)
+ OLECHAR hp1159[12]; // half-pitch c.p. am string
+ OLECHAR hp2359[12]; // half-pitch c.p. pm string
+ BOOL fAmPmPrefix; // TRUE if am/pm is at start of time str
+ BOOL IsDBCS; // value of IsDBCS(pdi->lcid)
+#endif // FE_DBCS
+
+} DATEINFO;
+
+#if OE_WIN16
+DATEINFO g_diCache; // cached DATEINFO from last LCID used
+#endif // OE_WIN16
+
+
+// Date Token Types (DTT_*)
+//
+// Following is the set of tokens that can be generated from a date
+// string. Notice that the legal set of trailing separators have been
+// folded in with the date number, and month name tokens. This set
+// of tokens is chosen to reduce the number of date parse states.
+
+enum {
+ DTT_End, // '\0'
+ DTT_NumEnd, // Num[ ]*[\0]
+ DTT_NumAmpm, // Num[ ]+AmPm
+ DTT_NumSpace, // Num[ ]+^[Dsep|Tsep|'0\']
+ DTT_NumDatesep, // Num[ ]*Dsep
+ DTT_NumTimesep, // Num[ ]*Tsep
+ DTT_MonthEnd, // Month[ ]*'\0'
+ DTT_MonthSpace, // Month[ ]+^[Dsep|Tsep|'\0']
+ DTT_MonthDatesep, // Month[ ]*Dsep
+#ifdef FE_DBCS
+ DTT_NumDatesuff, // Month[ ]*DSuff
+ DTT_NumTimesuff, // Month[ ]*TSuff
+#endif // FE_DBCS
+ DTT_Unk, // unknown (not one of the following
+ DTT_Max /* marker */
+};
+
+typedef enum tagAMPM {
+ AMPM_NONE = 0,
+ AMPM_AM,
+ AMPM_PM,
+ AMPM_MAX /* marker */
+} AMPM;
+
+#ifdef FE_DBCS
+// DBCS Suffix formats
+typedef enum tagSuffixes {
+ SUFFIX_NONE,
+ SUFFIX_YEAR,
+ SUFFIX_MONTH,
+ SUFFIX_DAY,
+ SUFFIX_HOUR,
+ SUFFIX_MINUTE,
+ SUFFIX_SECOND,
+ SUFFIX_MAX
+} SUFFIX;
+#endif // FE_DBCS
+
+typedef struct tagDATETOK {
+ int dtt; // token type
+ int num; // DTT_Num*, DTT_Month*
+ AMPM ampm; // DTT_NumAmpm
+#ifdef FE_DBCS
+ SUFFIX suffix;
+#endif // FE_DBCS
+} DATETOK;
+
+
+typedef struct tagDATERAW {
+ AMPM ampm; // ampm designator, if any
+ int num[3]; // parsed numbers, as they appear left to right
+ int FAR* pnum;
+ int month; // index of the month (if any), 1-12
+} DATERAW;
+
+PRIVATE_(BOOL) DayOfNN(DATERAW FAR* praw, DATEINFO FAR* pdi, UDS FAR* puds);
+PRIVATE_(BOOL) DayOfNNN(DATERAW FAR* praw, DATEINFO FAR*pdi, UDS FAR* puds);
+PRIVATE_(BOOL) DayOfMN(DATERAW FAR* praw, DATEINFO FAR* pdi, UDS FAR* puds);
+PRIVATE_(BOOL) DayOfMNN(DATERAW FAR* praw, DATEINFO FAR* pdi, UDS FAR* puds);
+PRIVATE_(void) AdjustTime(UDS FAR* puds, AMPM ampm);
+#ifdef FE_DBCS
+PRIVATE_(BOOL) AdjustUDSTime(DATERAW FAR* praw, DATEINFO FAR* pdi, UDS FAR* puds);
+PRIVATE_(BOOL) AdjustUDSDate(DATERAW FAR* praw, DATEINFO FAR* pdi, UDS FAR* puds);
+PRIVATE_(BOOL) IsImperialEra(OLECHAR FAR* FAR* pszIn, DATEINFO FAR* pdi, int FAR* year);
+PRIVATE_(BOOL) IsRepublicEra(OLECHAR FAR* FAR* pszIn, DATEINFO FAR* pdi, int FAR* year);
+PRIVATE_(int) GetImperialEra(UDS FAR* pdate, DATEINFO FAR* pdi);
+#endif // FE_DBCS
+
+/***
+*PRIVATE int MonthNumOfMonthName(char*, DATEINFO*)
+*Purpose:
+* return the (one-based) number of the month with the given
+* (locale specific) month name.
+*
+*Entry:
+* psz = the name of the month to lookup.
+* pdi = the locale specific dateinfo
+*
+*Exit:
+* return value = int, 0 if the month was not found, 1-12 if it was.
+*
+***********************************************************************/
+PRIVATE_(int)
+MonthNumOfMonthName(OLECHAR FAR* psz, DATEINFO FAR* pdi)
+{
+ int mm, len;
+ OLECHAR rgch[32];
+
+
+ len = STRLEN(psz);
+
+ // any prefix of 3 or more characters will match
+
+ if(len >= 3){
+
+ for(mm = 0; mm < 12; ++mm) {
+
+ // Note: the following assumes that the definitions for
+ // LOCALE_SMONTHNAME1 -> LOCALE_SMONTHNAME12 are consecutive
+ //
+ // This code also assumes that the short month name is a subset
+ // of the long month name (ie, a short month name of length n
+ // will match the first n characters of the long month name).
+
+ // REVIEW: is the following the correct action to take if the
+ // GetLocalInfo call fails?
+
+ // REVIEW: should the following try for NOUSEROVERRIDE if the
+ // call fails (its possible that the user may have modified
+ // the following value to an empty string)
+
+ if(GetLocaleInfo(pdi->lcid, LOCALE_SMONTHNAME1 + mm, rgch, sizeof(rgch)) == 0)
+ continue;
+
+ if(CompareString(pdi->lcid, NORM_IGNORECASE, psz, len, rgch, len) == 2)
+ return mm + 1;
+
+#ifdef FE_DBCS
+ if (pdi->IsDBCS) {
+ // Also check if we have an english month in the date.
+ // REVIEW: Is there a const for US lcid's.
+ if(GetLocaleInfo(0x409, LOCALE_SMONTHNAME1 + mm, rgch, sizeof(rgch)) == 0)
+ continue;
+
+ if(CompareString(0x409, NORM_IGNORECASE, psz, len, rgch, len) == 2)
+ return mm + 1;
+ }
+#endif // FE_DBCS
+ }
+ }
+
+ return 0; // not found
+}
+
+
+// this routine handles overriding the user specified locale info if the
+// user has somehow hammered their win.ini to an invalid (or nonexistant)
+// string.
+
+INTERNAL_(HRESULT)
+SafeGetLocaleInfo(LCID lcid, LCTYPE lctype, OLECHAR FAR* rgch, int size)
+{
+ int len;
+
+ len = GetLocaleInfo(lcid, lctype, rgch, size);
+ if(len < 2)
+ goto LNoUserOverride;
+
+ switch(lctype){
+ case LOCALE_IDATE:
+ if(len != 2 ||
+ (*rgch != OASTR('0') && *rgch != OASTR('1') && *rgch != OASTR('2')))
+ goto LNoUserOverride;
+ break;
+ case LOCALE_ITIME:
+ case LOCALE_ITLZERO:
+ if(len != 2 || (*rgch != OASTR('0') && *rgch != OASTR('1')))
+ goto LNoUserOverride;
+ break;
+ }
+
+ return NOERROR;
+
+LNoUserOverride:;
+
+ // if string is empty or bogus, retry with NOUSEROVERRIDE
+
+ len = GetLocaleInfo(lcid, lctype|LOCALE_NOUSEROVERRIDE, rgch, size);
+ if(len < 2)
+ return RESULT(E_FAIL);
+
+ return NOERROR;
+}
+
+
+/***
+*PRIVATE BOOL GetDateInfo(DATEINFO*)
+*Purpose:
+* Fill in the given DATEINFO structure.
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = BOOL. TRUE if successful, FALSE if not
+*
+* *pdi = the filled DATEINFO struct
+*
+***********************************************************************/
+PRIVATE_(HRESULT)
+GetDateInfo(DATEINFO FAR* pdi, LCID lcid, unsigned long dwFlags)
+{
+ OLECHAR szTmp[2];
+#ifdef FE_DBCS
+ int len;
+#endif
+
+#if OE_WIN16
+ if (g_diCache.lcid == lcid && g_diCache.dwFlags == dwFlags) {
+ memcpy(pdi, &g_diCache, sizeof(DATEINFO));
+ return NOERROR;
+ }
+ // Else cache is marked invalid (lcid==-1), or cache contains info
+ // for another lcid. In either case, must build a new DATEINFO
+#endif //OE_WIN16
+
+ ASSERT(dwFlags == 0 || dwFlags == LOCALE_NOUSEROVERRIDE);
+
+ pdi->lcid = lcid;
+#ifdef FE_DBCS
+ pdi->IsDBCS = IsDBCS(lcid); // cache (it's somewhat slow)
+#endif
+
+ // date format ordering
+ // "0" = MDY, "1" = DMY, "2" = YMD
+ IfFailRet(
+ SafeGetLocaleInfo(lcid, LOCALE_IDATE | dwFlags,
+ szTmp, SIZEOFCH(szTmp)));
+
+ pdi->dfo = szTmp[0] - OASTR('0');
+ ASSERT(pdi->dfo >= 0 && pdi->dfo < DFO_MAX);
+
+ // Note: dont override the Ampm designators. If the current settings
+ // specify 24hour format, then these strings may be empty and if the
+ // user has hammered these to something bizarre - then so be it.
+
+ if(GetLocaleInfo(lcid, LOCALE_S1159 | dwFlags,
+ pdi->sz1159, SIZEOFCH(pdi->sz1159)) == 0){
+ pdi->sz1159[0] = OASTR('\0');
+ }
+
+ if(GetLocaleInfo(lcid, LOCALE_S2359 | dwFlags,
+ pdi->sz2359, SIZEOFCH(pdi->sz2359)) == 0){
+ pdi->sz2359[0] = OASTR('\0');
+ }
+#ifdef FE_DBCS
+ if (pdi->IsDBCS) {
+ len = STRLEN(pdi->sz1159)+1;
+ LCMapString(lcid, LCMAP_HALFWIDTH, pdi->sz1159, len, pdi->hp1159, len);
+ len = STRLEN(pdi->sz2359)+1;
+ LCMapString(lcid, LCMAP_HALFWIDTH, pdi->sz2359, len, pdi->hp2359, len);
+ }
+#endif
+ IfFailRet(
+ SafeGetLocaleInfo(
+ lcid, LOCALE_SDATE | dwFlags,
+ pdi->szDatesep, SIZEOFCH(pdi->szDatesep)));
+
+ IfFailRet(
+ SafeGetLocaleInfo(
+ lcid, LOCALE_STIME | dwFlags,
+ pdi->szTimesep, SIZEOFCH(pdi->szTimesep)));
+
+ // "0" == no leading zero on hour
+ // "1" == output hour with leading zero
+ //
+ IfFailRet(
+ SafeGetLocaleInfo(lcid, LOCALE_ITLZERO | dwFlags,
+ szTmp, SIZEOFCH(szTmp)));
+ ASSERT(szTmp[0] == OASTR('0') || szTmp[0] == OASTR('1'));
+ pdi->fTlzero = szTmp[0] - OASTR('0');
+
+ // "0" == use 12 hour (ampm) format
+ // "1" == use 24 hour format
+ //
+ IfFailRet(
+ SafeGetLocaleInfo(lcid, LOCALE_ITIME | dwFlags,
+ szTmp, SIZEOFCH(szTmp)));
+ ASSERT(szTmp[0] == OASTR('0') || szTmp[0] == OASTR('1'));
+ pdi->fAmpm = (szTmp[0] == OASTR('0'));
+
+#ifdef FE_DBCS
+ if (IsJapan(lcid)) {
+
+ pdi->impEras[0].beginDate.Year = 1868;
+ pdi->impEras[0].beginDate.Month = 10;
+ pdi->impEras[0].beginDate.DayOfMonth = 23;
+ pdi->impEras[0].szName[0] = OLESTR("M");
+ pdi->impEras[0].szName[1] = szJapanimpEras0Name1;
+ pdi->impEras[0].szName[2] = szJapanimpEras0Name2;
+ pdi->impEras[1].beginDate.Year = 1912;
+ pdi->impEras[1].beginDate.Month = 7;
+ pdi->impEras[1].beginDate.DayOfMonth = 30;
+ pdi->impEras[1].szName[0] = OLESTR("T");
+ pdi->impEras[1].szName[1] = szJapanimpEras1Name1;
+ pdi->impEras[1].szName[2] = szJapanimpEras1Name2;
+ pdi->impEras[2].beginDate.Year = 1926;
+ pdi->impEras[2].beginDate.Month = 12;
+ pdi->impEras[2].beginDate.DayOfMonth = 25;
+ pdi->impEras[2].szName[0] = OLESTR("S");
+ pdi->impEras[2].szName[1] = szJapanimpEras2Name1;
+ pdi->impEras[2].szName[2] = szJapanimpEras2Name2;
+ pdi->impEras[3].beginDate.Year = 1989;
+ pdi->impEras[3].beginDate.Month = 1;
+ pdi->impEras[3].beginDate.DayOfMonth = 8;
+ pdi->impEras[3].szName[0] = OLESTR("H");
+ pdi->impEras[3].szName[1] = szJapanimpEras3Name1;
+ pdi->impEras[3].szName[2] = szJapanimpEras3Name2;
+
+ pdi->dbYearSuff = szJapandbYearSuff;
+ pdi->dbMonthSuff = szJapandbMonthSuff;
+ pdi->dbDaySuff = szJapandbDaySuff;
+ pdi->dbHourSuff = szJapandbHourSuff;
+ pdi->dbMinuteSuff = szJapandbMinuteSuff;
+ pdi->dbSecondSuff = szJapandbSecondSuff;
+
+ pdi->db1159 = szJapandb1159;
+ pdi->db2359 = szJapandb2359;
+
+ } else if (IsKorea(pdi->lcid)) {
+ pdi->dbYearSuff = szKoreadbYearSuff;
+ pdi->dbMonthSuff = szKoreadbMonthSuff;
+ pdi->dbDaySuff = szKoreadbDaySuff;
+ pdi->dbHourSuff = szKoreadbHourSuff;
+ pdi->dbMinuteSuff = szKoreadbMinuteSuff;
+ pdi->dbSecondSuff = szKoreadbSecondSuff;
+
+ pdi->db1159 = szKoreadb1159;
+ pdi->db2359 = szKoreadb2359;
+
+ } else if (IsTaiwan(lcid)) {
+ pdi->dbYearSuff = szTaiwandbYearSuff;
+ pdi->dbMonthSuff = szTaiwandbMonthSuff;
+ pdi->dbDaySuff = szTaiwandbDaySuff;
+ pdi->dbHourSuff = szTaiwandbHourSuff;
+ pdi->dbMinuteSuff = szTaiwandbMinuteSuff;
+ pdi->dbSecondSuff = szTaiwandbSecondSuff;
+
+ pdi->db1159 = szTaiwandb1159;
+ pdi->db2359 = szTaiwandb2359;
+
+ pdi->repEras[0].Before1912 = TRUE;
+ pdi->repEras[0].szName[0] = szTaiwanrepEras0Name0;
+ pdi->repEras[0].szName[1] = szTaiwanrepEras0Name1;
+
+ pdi->repEras[1].Before1912 = FALSE;
+ pdi->repEras[1].szName[0] = szTaiwanrepEras1Name0;
+ pdi->repEras[1].szName[1] = szTaiwanrepEras1Name1;
+
+ } else if (IsChina(lcid)) {
+ pdi->dbYearSuff = szChinadbYearSuff;
+ pdi->dbMonthSuff = szChinadbMonthSuff;
+ pdi->dbDaySuff = szChinadbDaySuff;
+ pdi->dbHourSuff = szChinadbHourSuff;
+ pdi->dbMinuteSuff = szChinadbMinuteSuff;
+ pdi->dbSecondSuff = szChinadbSecondSuff;
+
+ pdi->db1159 = szChinadb1159;
+ pdi->db2359 = szChinadb2359;
+
+ pdi->dbEraName = szChinadbEraName;
+ } else {
+ // UNDONE: bassams: What should DBCS chars be initialized to
+ // if none of the above ???
+ }
+
+ if (pdi->IsDBCS) {
+ // UNDONE: bassams: We need to get this value from the NLS api once it
+ // is defined. For now, grab it directly from the INI file if
+ // running under win16 or win32. For all other system, set to false.
+#if OE_WIN
+#ifdef UNICODE
+ pdi->fAmPmPrefix = GetProfileIntW(OASTR("intl"), OASTR("iTimePrefix"), FALSE);
+#else //UNICODE
+ pdi->fAmPmPrefix = GetProfileInt("intl", "iTimePrefix", FALSE);
+#endif //UNICODE
+#else // MAC
+ pdi->fAmPmPrefix = FALSE;
+#endif // OE_WIN16
+ }
+
+#endif // FE_DBCS
+
+#if OE_WIN16
+ pdi->dwFlags = dwFlags; // cache hit requires both LCID and flags
+ // cache the DATEINFO for subsequent calls
+ memcpy(&g_diCache, pdi, sizeof(DATEINFO));
+#endif //OE_WIN16
+ return NOERROR;
+}
+
+// locale specific case insensitive string compare using the Ole NLS dll
+#define STRICMPA(LCID, SZ1, SZ2) \
+ (CompareString((LCID), NORM_IGNORECASE , (SZ1), -1, (SZ2), -1) - 2)
+#define STRNICMPA(LCID, SZ1, SZ2, LEN) \
+ (CompareString((LCID), NORM_IGNORECASE, (SZ1), \
+ MIN(STRLEN(SZ1),LEN), (SZ2), MIN(STRLEN(SZ2),LEN)) - 2)
+
+
+// separator types
+enum {
+ SEP_Unk,
+ SEP_End,
+ SEP_Space,
+ SEP_Am,
+ SEP_Pm,
+ SEP_Date,
+ SEP_Time,
+#ifdef FE_DBCS
+ SEP_YearSuff,
+ SEP_MonthSuff,
+ SEP_DaySuff,
+ SEP_HourSuff,
+ SEP_MinuteSuff,
+ SEP_SecondSuff,
+#endif // FE_DBCS
+ SEP_Max
+};
+
+/***
+*PRIVATE int IsImperialEra
+*Purpose:
+* Given a pointer to a str, determine if the next token is an imperial
+* era of the form: emperor offset [year-suffix]
+*
+*Exit:
+* return value = 0 Not imperial era
+* 1 Imperial era. year contains equivalent gregorian year
+* or BADERA. No suffix specified.
+* 2 Imperial era with a suffix. year contains equivalent
+* gregorian year.
+*
+***********************************************************************/
+#ifdef FE_DBCS
+PRIVATE_(int)
+IsImperialEra(OLECHAR FAR* FAR* pszIn, DATEINFO FAR* pdi, int FAR* year)
+{
+ int emperorIndex, nameIndex, tmpIndex = 0;
+ IMPERIALERA emperor;
+ OLECHAR szTmp[32];
+ OLECHAR *pszTmp = *pszIn;
+
+ // search for emperor name in the emperor structure.
+
+ ASSERT(IsJapan(pdi->lcid));// Lcid must be Japan to call this function
+
+ for (emperorIndex = 0; emperorIndex < MAX_EMPERORS; emperorIndex++) {
+ emperor = pdi->impEras[emperorIndex];
+
+ for (nameIndex = MAX_ERA_NAMES-1; nameIndex >= 0; nameIndex--) {
+
+ //NOTE: code below depends on the emperor names to be sorted based
+ //on the length of the szName string:
+ // strlen(szName[0]) <= strlen(szName[1]) <= strlen(szName[2]) ...
+
+ if (!STRNICMPA(pdi->lcid, pszTmp, emperor.szName[nameIndex],
+ STRLEN(emperor.szName[nameIndex]))) {
+
+ // found emperor; skip over name to the index of emperor era.
+ pszTmp += STRLEN(emperor.szName[nameIndex]);
+ EATWHITE(pdi->lcid, pszTmp);
+ if(STRCHR(pdi->szDatesep, *pszTmp) ||
+ STRCHR(OASTR(",/-"), *pszTmp) ) {
+
+ // skip over date separator
+ pszTmp++;
+ }
+ EATWHITE(pdi->lcid, pszTmp);
+
+ if (!ISDIGIT(pdi->lcid, *pszTmp))
+ return 0;
+
+ // calculate "offset" into imperial era.
+ while (ISDIGIT(pdi->lcid, *pszTmp) && pszTmp != 0) {
+ szTmp[tmpIndex++] = *pszTmp;
+ pszTmp++;
+ }
+ szTmp[tmpIndex] = 0;
+ IntOfString(pdi->lcid, szTmp, year); // REVIEW: check return value?
+
+ if (*year <= 0) {
+ *year = BADERA;
+ return 1;
+ }
+
+ // calcualate gergorian year from "offset" into imperial era.
+ *year += emperor.beginDate.Year -1;
+
+ // validate imperial era.
+ if (emperorIndex < MAX_EMPERORS &&
+ (*year < emperor.beginDate.Year ||
+ (emperorIndex == 3 ? 0 :
+ *year > pdi->impEras[emperorIndex+1].beginDate.Year))) {
+ *year = BADERA;
+ return 1;
+ }
+ // era found: Year now contains either the appropriate
+ // gregorian year or BADERA; Eat up the year
+ // suffix if one exists and return TRUE.
+
+ EATWHITE(pdi->lcid, pszTmp);
+
+ // REVIEW: assuming year suffix is always 1 db char.
+ if( !STRNICMPA(pdi->lcid, pszTmp, pdi->dbYearSuff, 2) ) {
+ *pszIn = pszTmp+2;
+ return 2;
+
+ } else if(STRCHR(pdi->szDatesep, *pszTmp) ||
+ STRCHR(OASTR(",/-"), *pszTmp) ) {
+
+ // skip over date separator
+ pszTmp++;
+ }
+
+
+ *pszIn = pszTmp;
+ return 1;
+ }
+ }
+ }
+ return 0; // No imperial era found. year is undefined.
+}
+
+
+/***
+*PRIVATE int IsRepublicEra
+*Purpose:
+* Given a pointer to a str, determine if the next token is an republic
+* era for simplified and traditional Chinese : era offset year-suffix
+*
+*Exit:
+* return value = 0 Not republic era
+* 1 republic era. year contains equivalent gregorian year
+* or BADERA.
+*
+***********************************************************************/
+PRIVATE_(int)
+IsRepublicEra(OLECHAR FAR* FAR* pszIn, DATEINFO FAR* pdi, int FAR* year)
+{
+ int eraIndex, nameIndex, tmpIndex = 0;
+ REPUBLICERA era;
+ OLECHAR szTmp[32];
+ OLECHAR *pszTmp = *pszIn;
+
+ // search for emperor name in the emperor structure.
+ if (IsChina(pdi->lcid)) {
+ if (!STRNICMPA(pdi->lcid, pszTmp, pdi->dbEraName,
+ STRLEN(pdi->dbEraName))) {
+ *pszIn += STRLEN(pdi->dbEraName);
+ EATWHITE(pdi->lcid, *pszIn);
+ // since the era string in simplified chinese does nothing to the
+ // date, just eat it up and let the normal code path handle the year
+ // and the prefix.
+ }
+ return FALSE;
+
+ }
+
+ ASSERT(IsTaiwan(pdi->lcid));// LCID must be either china or taiwan to call this func
+
+ for (eraIndex = 0; eraIndex < MAX_REPUBLIC_ERAS; eraIndex++) {
+ era = pdi->repEras[eraIndex];
+
+ for (nameIndex = MAX_REPUBLIC_NAMES-1; nameIndex >= 0; nameIndex--) {
+
+ //NOTE: code below depends on the era names to be sorted based
+ //on the length of the szName string:
+ // strlen(szName[0]) <= strlen(szName[1]) <= strlen(szName[2]) ...
+
+ if (!STRNICMPA(pdi->lcid, pszTmp, era.szName[nameIndex],
+ STRLEN(era.szName[nameIndex]))) {
+
+ // found era; skip over name to the index of emperor era.
+ pszTmp += STRLEN(era.szName[nameIndex]);
+ EATWHITE(pdi->lcid, pszTmp);
+ if(STRCHR(pdi->szDatesep, *pszTmp) ||
+ STRCHR(OASTR(",/-"), *pszTmp) ) {
+
+ // skip over date separator
+ pszTmp++;
+ }
+ EATWHITE(pdi->lcid, pszTmp);
+
+ // calculate "offset" into republic era.
+ while (ISDIGIT(pdi->lcid, *pszTmp) && pszTmp != 0) {
+ szTmp[tmpIndex++] = *pszTmp;
+ pszTmp++;
+ }
+ szTmp[tmpIndex] = 0;
+ IntOfString(pdi->lcid, szTmp, year); // REVIEW: check return value?
+
+ if (*year <= 0) {
+ *year = BADERA;
+ return 1;
+ }
+
+ // calcualate gergorian year from republic era year
+ if (era.Before1912)
+ *year = 1912 - *year;
+ else
+ *year = 1911 + *year;
+
+ // era found: Year now contains the appropriate
+ // gregorian year
+ if (*year <= 0) {
+ *year = BADERA;
+ return 1;
+ }
+
+ EATWHITE(pdi->lcid, pszTmp);
+
+ // REVIEW: assuming year suffix is always 1 db char.
+ if(!STRNICMPA(pdi->lcid, pszTmp, pdi->dbYearSuff, 2) ) {
+ // skip past the suffix
+ *pszIn = pszTmp+2;
+ return 2;
+ } else if(STRCHR(pdi->szDatesep, *pszTmp) ||
+ STRCHR(OASTR(",/-"), *pszTmp) ) {
+
+ // skip over date separator
+ pszTmp++;
+ }
+
+ *pszIn = pszTmp;
+ return 1;
+ }
+ }
+ }
+ return 0; // No republic era found. year is undefined.
+}
+
+
+
+PRIVATE_(unsigned int)
+IsDBCSAmPm(DATEINFO *pdi, OLECHAR FAR* pszIn, unsigned int * plen)
+{
+
+ if(pdi->IsDBCS) {
+ if (pdi->hp1159[0] != 0 &&
+ !STRNICMPA(pdi->lcid, pszIn,
+ pdi->hp1159, *plen = STRLEN(pdi->hp1159)) ||
+ !STRNICMPA(pdi->lcid, pszIn,
+ pdi->db1159, *plen = STRLEN(pdi->db1159))) {
+ return AMPM_AM;
+ } else if (!STRNICMPA(pdi->lcid, pszIn, OASTR("am"), 2)) {
+ *plen = 2;
+ return AMPM_AM;
+#if !VBA2
+ } else if (!STRNICMPA(pdi->lcid, pszIn, OASTR("a"), 1)
+ && !ISALPHA(pdi->lcid, *(pszIn+1))) {
+ *plen = 1;
+ return AMPM_AM;
+#endif
+ } else if (pdi->hp2359[0] != 0 &&
+ !STRNICMPA(pdi->lcid, pszIn,
+ pdi->hp2359, *plen = STRLEN(pdi->hp2359)) ||
+ !STRNICMPA(pdi->lcid, pszIn,
+ pdi->db2359, *plen = STRLEN(pdi->db2359))) {
+ return AMPM_PM;
+ } else if (!STRNICMPA(pdi->lcid, pszIn, OASTR("pm"), 2)) {
+ *plen = 2;
+ return AMPM_PM;
+#if !VBA2
+ } else if (!STRNICMPA(pdi->lcid, pszIn, OASTR("p"), 1)
+ && !ISALPHA(pdi->lcid, *(pszIn+1))) {
+ *plen = 1;
+ return AMPM_PM;
+#endif
+ }
+ }
+ return 0;
+}
+
+
+#endif // FE_DBCS
+
+
+PRIVATE_(int)
+ddsep(OLECHAR FAR* FAR* ppsz, DATEINFO FAR* pdi, DATERAW FAR *praw)
+{
+ int sep;
+ OLECHAR rgch[32]; // REVIEW
+ OLECHAR FAR* pszIn, FAR* pszOut, FAR* pszTmp;
+#ifdef FE_DBCS
+ unsigned int len;
+ AMPM ampm;
+#endif
+
+ pszIn = *ppsz;
+ sep = SEP_Unk;
+
+ if(ISWHITE(pdi->lcid, *pszIn)){
+ EATWHITE(pdi->lcid, pszIn);
+ sep = SEP_Space;
+ }
+
+ if(*pszIn == OASTR('\0')){
+
+ sep = SEP_End;
+
+#ifdef FE_DBCS
+ // check for special case DBCS am/pm both hard-code and
+ // from the control panel.
+ } else if (ampm = IsDBCSAmPm(pdi, pszIn, &len)) {
+ pszTmp = pszIn + len;
+ EATWHITE(pdi->lcid, pszTmp);
+ if (praw->ampm || *pszTmp != 0) {
+ sep = SEP_Space;
+ goto LDone;
+ }
+ sep = (ampm == AMPM_AM ? SEP_Am : SEP_Pm);
+ pszIn = pszTmp;
+ goto LDone;
+#endif
+ }else if(ISALPHA(pdi->lcid, *pszIn)){
+
+ // check for special case strings: am/pm...
+
+ pszOut = rgch;
+ pszTmp = pszIn;
+ while(ISALPHANUM(pdi->lcid, *pszTmp)) {
+ if (pszOut >= &rgch[DIM(rgch)-1]) // overrun buffer
+ return SEP_Unk;
+ *pszOut++ = *pszTmp++;
+ }
+ *pszOut = OASTR('\0');
+
+ // make sure we didn't overwrite the buffer
+ //ASSERT(pszOut < &rgch[DIM(rgch)]);
+
+#ifdef FE_DBCS
+ // use sz1159 converted to half-pitch
+ if(pdi->IsDBCS && !STRICMPA(pdi->lcid, rgch, pdi->hp1159)){
+ sep = SEP_Am;
+ }else if(pdi->IsDBCS && !STRICMPA(pdi->lcid, rgch, pdi->hp2359)){
+ sep = SEP_Pm;
+ }else
+#endif
+ if(!STRICMPA(pdi->lcid, rgch, pdi->sz1159)){
+ sep = SEP_Am;
+ }else if(!STRICMPA(pdi->lcid, rgch, pdi->sz2359)){
+ sep = SEP_Pm;
+ }else
+#if !VBA2
+ if(!STRICMPA(pdi->lcid, rgch, OASTR("am")) ||
+ !STRICMPA(pdi->lcid, rgch, OASTR("a"))){
+#else
+ if(!STRICMPA(pdi->lcid, rgch, OASTR("am")) ||
+ (!STRICMPA(pdi->lcid, rgch, OASTR("a")) &&
+ !ISALPHA(pdi->lcid, *(rgch+1))) ){
+#endif
+ sep = SEP_Am;
+ }else
+#if !VBA2
+ if(!STRICMPA(pdi->lcid, rgch, OASTR("pm")) ||
+ !STRICMPA(pdi->lcid, rgch, OASTR("p"))){
+#else
+ if(!STRICMPA(pdi->lcid, rgch, OASTR("pm")) ||
+ !STRICMPA(pdi->lcid, rgch, OASTR("p")) &&
+ !ISALPHA(pdi->lcid, *(rgch+1)) ){
+#endif
+ sep = SEP_Pm;
+ }else
+ goto LDone;
+
+ // it was something we recognized, so accept the token.
+
+#ifdef FE_DBCS
+ if (pdi->IsDBCS) {
+ EATWHITE(pdi->lcid, pszTmp);
+ if (praw->ampm || *pszTmp != 0) {
+ sep = SEP_Space;
+ goto LDone;
+ }
+ }
+#endif
+
+ pszIn = pszTmp;
+
+ }else{
+
+ // Note: the following code assumes that a date/time
+ // separator is a single character.
+
+ if(STRCHR(pdi->szDatesep, *pszIn)){ // locale date sep
+ sep = SEP_Date;
+ ++pszIn;
+ }else if(STRCHR(pdi->szTimesep, *pszIn)){ // locale time sep
+ sep = SEP_Time;
+ ++pszIn;
+ }else if(STRCHR(OASTR(",/-"), *pszIn)){ // default date sep
+ sep = SEP_Date;
+ ++pszIn;
+ }else if(STRCHR(OASTR(".:"), *pszIn)){ // default time sep
+ sep = SEP_Time;
+ ++pszIn;
+
+#ifdef FE_DBCS
+ }else if (pdi->IsDBCS) {
+
+ // REVIEW: bassams: is the suffix always a one dbcs character?
+ if(!STRNICMPA(pdi->lcid, pszIn, pdi->dbYearSuff, 2) ){
+ sep = SEP_YearSuff;
+ pszIn += 2;
+ }else if(!STRNICMPA(pdi->lcid, pszIn, pdi->dbMonthSuff, 2) ){
+ sep = SEP_MonthSuff;
+ pszIn += 2;
+ }else if(!STRNICMPA(pdi->lcid, pszIn, pdi->dbDaySuff, 2) ){
+ sep = SEP_DaySuff;
+ pszIn += 2;
+ }else if(!STRNICMPA(pdi->lcid, pszIn, pdi->dbHourSuff, 2) ){
+ sep = SEP_HourSuff;
+ pszIn += 2;
+ }else if(!STRNICMPA(pdi->lcid, pszIn, pdi->dbMinuteSuff, 2) ){
+ sep = SEP_MinuteSuff;
+ pszIn += 2;
+ }else if(!STRNICMPA(pdi->lcid, pszIn, pdi->dbSecondSuff, 2) ){
+ sep = SEP_SecondSuff;
+ pszIn += 2;
+ }
+ if (sep == SEP_HourSuff || sep == SEP_MinuteSuff || sep == SEP_SecondSuff) {
+ EATWHITE(pdi->lcid, pszIn);
+ if (ampm = IsDBCSAmPm(pdi, pszIn, &len)) {
+ pszTmp = pszIn + len;
+ EATWHITE(pdi->lcid, pszTmp);
+ if (praw->ampm == AMPM_NONE && *pszTmp == 0) {
+ pszIn = pszTmp;
+ praw->ampm= ampm;
+ }
+ }
+ }
+#endif // FE_DBCS
+ }
+ }
+
+LDone:;
+
+ *ppsz = pszIn;
+
+ return sep;
+}
+
+
+/***
+*PRIVATE void ddlex(char**, DATEINFO*, DATETOK*)
+*Purpose:
+* This routine returns the next date token (DATETOK) in the given
+* date string, and the separator following it (if any).
+*
+*Entry:
+* ppsz = the string to lex
+* pdi = locale specific date info required to lex the date string
+*
+*Exit:
+* return value = 0 error
+* 1 successful
+*
+***********************************************************************/
+
+PRIVATE_(int)
+ddlex(OLECHAR FAR* FAR* ppsz, DATEINFO FAR* pdi, DATETOK FAR* pdtok, DATERAW FAR* praw)
+{
+ int nMonth;
+ OLECHAR rgch[32]; // REVIEW
+ OLECHAR FAR* pszIn, FAR* pszOut, FAR* pszTmp;
+#ifdef FE_DBCS
+ int year; // gregorian year from imperial era.
+ unsigned int len;
+ AMPM ampm;
+#endif // FE_DBCS
+
+
+ pszIn = *ppsz;
+ pszOut = rgch;
+ pdtok->dtt = DTT_Unk;
+#ifdef FE_DBCS
+ pdtok->suffix = SUFFIX_NONE;
+#endif // FE_DBCS
+
+ EATWHITE(pdi->lcid, pszIn);
+
+ if(*pszIn == OASTR('\0')){
+ pdtok->dtt = DTT_End;
+ goto LDone;
+ }
+
+#ifdef FE_DBCS
+ if (IsJapan(pdi->lcid)) {
+
+ switch (IsImperialEra(&pszIn, pdi, &year)) {
+ case 1:
+ pdtok->dtt = DTT_NumDatesep;
+ pdtok->num = year;
+ goto LDone;
+
+ case 2:
+ if(year == BADERA)
+ goto LDone;
+
+ pdtok->dtt = DTT_NumDatesuff;
+ pdtok->suffix = SUFFIX_YEAR;
+ pdtok->num = year;
+ goto LDone;
+ }
+ }
+
+ if (IsChina(pdi->lcid) || IsTaiwan(pdi->lcid)) {
+ switch (IsRepublicEra(&pszIn, pdi, &year)) {
+ case 1:
+ pdtok->dtt = DTT_NumDatesep;
+ pdtok->num = year;
+ goto LDone;
+
+ case 2:
+ if(year == BADERA)
+ goto LDone;
+
+ pdtok->dtt = DTT_NumDatesuff;
+ pdtok->suffix = SUFFIX_YEAR;
+ pdtok->num = year;
+ goto LDone;
+ }
+ }
+
+ if (ampm = IsDBCSAmPm(pdi, pszIn, &len)) {
+ pszTmp = pszIn + len;
+ EATWHITE(pdi->lcid, pszTmp);
+ if (praw->ampm == AMPM_NONE && *pszTmp != 0 &&
+ praw->pnum == praw->num) {
+ pszIn = pszTmp;
+ praw->ampm= ampm;
+ }
+ }
+
+#endif // FE_DBCS
+
+ if(ISALPHA(pdi->lcid, *pszIn)){
+
+ while(ISALPHANUM(pdi->lcid, *pszIn)) {
+ if (pszOut >= &rgch[DIM(rgch)-1]) return 0; // overflow buffer
+ *pszOut++ = *pszIn++;
+ }
+ *pszOut = OASTR('\0');
+
+ // Eat "." to be VB3 compatible (oob#3876) (e.g., "dec.")
+ if (*pszIn == OASTR('.'))
+ pszIn++;
+
+ if((nMonth = MonthNumOfMonthName(rgch, pdi)) != 0){
+ pszTmp = pszIn;
+
+ switch(ddsep(&pszTmp, pdi, praw)){
+ case SEP_End:
+ pdtok->dtt = DTT_MonthEnd;
+ break;
+ case SEP_Space:
+ pdtok->dtt = DTT_MonthSpace;
+ break;
+ case SEP_Date:
+ pdtok->dtt = DTT_MonthDatesep;
+ break;
+ default:
+ goto LDone; // we didnt recognize it after all
+ }
+
+ // recognized the month and the trailing separator, so accept
+
+ pszIn = pszTmp;
+ pdtok->num = nMonth;
+ }
+
+
+ }else if(ISDIGIT(pdi->lcid, *pszIn)){
+
+ while(ISDIGIT(pdi->lcid, *pszIn)) {
+ if (pszOut >= &rgch[DIM(rgch)-1]) return 0; // overflow buffer
+ *pszOut++ = *pszIn++;
+ }
+ *pszOut = OASTR('\0');
+
+ // It looks like a DTT_Num*, check the trailing separator
+
+ pszTmp = pszIn;
+ switch(ddsep(&pszTmp, pdi, praw)){
+ case SEP_End:
+ pdtok->dtt = DTT_NumEnd;
+ break;
+ case SEP_Am:
+ pdtok->ampm = AMPM_AM;
+ pdtok->dtt = DTT_NumAmpm;
+ break;
+ case SEP_Pm:
+ pdtok->ampm = AMPM_PM;
+ pdtok->dtt = DTT_NumAmpm;
+ break;
+ case SEP_Space:
+ pdtok->dtt = DTT_NumSpace;
+ break;
+ case SEP_Date:
+ pdtok->dtt = DTT_NumDatesep;
+ break;
+ case SEP_Time:
+ pdtok->dtt = DTT_NumTimesep;
+ break;
+#ifdef FE_DBCS
+ case SEP_YearSuff:
+ pdtok->dtt = DTT_NumDatesuff;
+ pdtok->suffix = SUFFIX_YEAR;
+ break;
+ case SEP_MonthSuff:
+ pdtok->dtt = DTT_NumDatesuff;
+ pdtok->suffix = SUFFIX_MONTH;
+ break;
+ case SEP_DaySuff:
+ pdtok->dtt = DTT_NumDatesuff;
+ pdtok->suffix = SUFFIX_DAY;
+ break;
+ case SEP_HourSuff:
+ pdtok->dtt = DTT_NumTimesuff;
+ pdtok->suffix = SUFFIX_HOUR;
+ break;
+ case SEP_MinuteSuff:
+ pdtok->dtt = DTT_NumTimesuff;
+ pdtok->suffix = SUFFIX_MINUTE;
+ break;
+ case SEP_SecondSuff:
+ pdtok->dtt = DTT_NumTimesuff;
+ pdtok->suffix = SUFFIX_SECOND;
+ break;
+#endif // FE_DBCS
+
+ default:
+ goto LDone; // didnt recognize it after all;
+ }
+
+ // recognized a num with a legal trailing separator, so accept
+
+ pszIn = pszTmp;
+
+ IntOfString(pdi->lcid, rgch, &pdtok->num); // REVIEW: check return value?
+
+ }
+
+LDone:;
+
+ // make sure we didn't overwrite the buffer
+ ASSERT(pszOut < &rgch[DIM(rgch)]);
+
+ if(pdtok->dtt != DTT_Unk)
+ *ppsz = pszIn;
+
+ return 1;
+}
+
+
+// Date parse States (DS_*)
+//
+// DS_* unqualified states
+// DS_D_* day parse states
+// DS_T_* time parse states
+// DS_DX_* day terminal states
+// DS_TX_* time terminal states
+
+enum
+{
+ DS_BEGIN = 0,
+ DS_N, // have one number
+ DS_NN, // have two numbers
+
+ // following are known to be part of a date
+
+ DS_D_Nd, // have number followed by date separator
+ DS_D_NN, // have 2 numbers
+ DS_D_NNd, // have 2 numbers followed by date separator
+ DS_D_M, // have a month
+ DS_D_MN, // have a month and a number
+ DS_D_MNd, // have a month and number followed by date separator
+
+ // following are known to be part of a time
+
+ DS_T_Nt, // have num followed by time separator
+ DS_T_NNt, // have 2 num followed by time separator
+
+#ifdef FE_DBCS
+ DS_D_S, // have number followed by a date suffix.
+ DS_T_S, // have number followed by a time suffix.
+#endif // FE_DBCS
+
+ DS_ERROR,
+
+ // The following are terminal states. These all have an action
+ // associated with them, and transition back to DS_BEGIN.
+
+ DS_DX_NN, // day from two numbers
+ DS_DX_NNN, // day from three numbers
+ DS_DX_MN, // day from month and one number
+ DS_DX_MNN, // day from month and two numbers
+#ifdef FE_DBCS
+ DS_DX_DS, // a set of date suffixed numbers.
+#endif // FE_DBCS
+ DS_TX_N, // time from one number (must have ampm)
+ DS_TX_NN, // time from two numbers
+ DS_TX_NNN, // time from three numbers
+#ifdef FE_DBCS
+ DS_TX_TS, // a set of time suffixed numbers.
+#endif // FE_DBCS
+
+ DS_MAX /* marker: end of enum */
+};
+
+#define DS_ISTERMINAL(X) ((X) >= DS_ERROR)
+
+
+#ifdef FE_DBCS
+
+// DPSDAT() - This macro is used to define the date parse state
+// transition table.
+//
+// the arguments are for each date token (DTT_*), in increasing order
+// (as declared)
+//
+#define DPSDAT(END, NEND, NAMPM, NSPACE, NDSEP, NTSEP, MEND, MSPACE, MDSEP, NDS, NTS) \
+ { DS_ ## END, \
+ DS_ ## NEND, \
+ DS_ ## NAMPM, \
+ DS_ ## NSPACE, \
+ DS_ ## NDSEP, \
+ DS_ ## NTSEP, \
+ DS_ ## MEND, \
+ DS_ ## MSPACE, \
+ DS_ ## MDSEP, \
+ DS_ ## NDS, \
+ DS_ ## NTS }
+
+
+// NOTE: the following table is dependent on the order of the
+// DS_ and DTT_ enumerations.
+
+// For each non terminal state, the following table defines the next state
+// for each given date token type.
+
+// End
+// NumEnd
+// NumAmPm
+// NumSpace
+// NumDaySep
+// NumTimesep
+// MonthEnd
+// MonthSpace
+// MonthDSep
+// NumDateSuff
+// NumTimeSuff
+char g_dpsNext[DS_MAX-1][DTT_Max-1] =
+{
+// DS_BEGIN
+DPSDAT( ERROR, ERROR, TX_N, N, D_Nd, T_Nt, ERROR, D_M, D_M, D_S, T_S),
+
+// DS_N
+DPSDAT( ERROR, DX_NN, ERROR, NN, D_NNd, ERROR, D_MN, D_MN, D_MNd, ERROR, ERROR),
+
+// DS_NN
+DPSDAT( DX_NN, DX_NNN, TX_N, DX_NNN, ERROR, T_Nt, DX_MNN, DX_MNN, ERROR, ERROR, T_S),
+
+// DS_D_Nd
+DPSDAT( ERROR, DX_NN, ERROR, D_NN, D_NNd, ERROR, D_MN, D_MN, D_MNd, ERROR, ERROR),
+
+// DS_D_NN
+DPSDAT( DX_NN, DX_NNN, TX_N, DX_NNN, ERROR, T_Nt, DX_MNN, DX_MNN, ERROR, DX_DS, T_S),
+
+// DS_D_NNd
+DPSDAT( ERROR, DX_NNN, ERROR, DX_NNN, ERROR, ERROR, DX_MNN, DX_MNN, ERROR, DX_DS, ERROR),
+
+// DS_D_M
+DPSDAT( ERROR, D_MN, ERROR, D_MN, D_MNd, ERROR, ERROR, ERROR, ERROR, ERROR, ERROR),
+
+// DS_D_MN
+DPSDAT( DX_MN, DX_MNN, TX_N, DX_MNN, ERROR, T_Nt, ERROR, ERROR, ERROR, DX_DS, T_S),
+
+// DS_D_MNd
+DPSDAT( ERROR, DX_MNN, ERROR, DX_MNN, ERROR, ERROR, ERROR, ERROR, ERROR, ERROR, ERROR),
+
+// DS_T_Nt
+DPSDAT( ERROR, TX_NN, TX_NN, TX_NN, ERROR, T_NNt, ERROR, ERROR, ERROR, ERROR, T_S),
+
+// DS_T_NNt
+DPSDAT( ERROR, TX_NNN, TX_NNN, TX_NNN, ERROR, ERROR, ERROR, ERROR, ERROR, ERROR, T_S),
+
+// DS_D_S
+DPSDAT( DX_DS, ERROR, TX_N, T_Nt, ERROR, T_Nt, ERROR, ERROR, ERROR, D_S, T_S),
+
+// DS_T_S
+#if !VBA2
+DPSDAT( TX_TS, TX_TS, TX_TS, T_Nt, ERROR, ERROR, ERROR, ERROR, ERROR, ERROR, T_S),
+#else
+DPSDAT( TX_TS, TX_TS, TX_TS, T_Nt, D_Nd, ERROR, ERROR, ERROR, ERROR, D_S, T_S),
+#endif
+
+};
+
+
+
+#else // !FE_DBCS
+
+// DPSDAT() - This macro is used to define the date parse state
+// transition table.
+//
+// the arguments are for each date token (DTT_*), in increasing order
+// (as declared)
+//
+#define DPSDAT(END, NEND, NAMPM, NSPACE, NDSEP, NTSEP, MEND, MSPACE, MDSEP) \
+ { DS_ ## END, \
+ DS_ ## NEND, \
+ DS_ ## NAMPM, \
+ DS_ ## NSPACE, \
+ DS_ ## NDSEP, \
+ DS_ ## NTSEP, \
+ DS_ ## MEND, \
+ DS_ ## MSPACE, \
+ DS_ ## MDSEP }
+
+
+// NOTE: the following table is dependent on the order of the
+// DS_ and DTT_ enumerations.
+
+// For each non terminal state, the following table defines the next state
+// for each given date token type.
+
+// End
+// NumEnd
+// NumAmPm
+// NumSpace
+// NumDaySep
+// NumTimesep
+// MonthEnd
+// MonthSpace
+// MonthDSep
+char g_dpsNext[DS_MAX-1][DTT_Max-1] =
+{
+// DS_BEGIN
+DPSDAT( ERROR, ERROR, TX_N, N, D_Nd, T_Nt, ERROR, D_M, D_M),
+
+// DS_N
+DPSDAT( ERROR, DX_NN, ERROR, NN, D_NNd, ERROR, D_MN, D_MN, D_MNd),
+
+// DS_NN
+DPSDAT( DX_NN, DX_NNN, TX_N, DX_NNN, ERROR, T_Nt, DX_MNN, DX_MNN, ERROR),
+
+// DS_D_Nd
+DPSDAT( ERROR, DX_NN, ERROR, D_NN, D_NNd, ERROR, D_MN, D_MN, D_MNd),
+
+// DS_D_NN
+DPSDAT( DX_NN, DX_NNN, TX_N, DX_NNN, ERROR, T_Nt, DX_MNN, DX_MNN, ERROR),
+
+// DS_D_NNd
+DPSDAT( ERROR, DX_NNN, ERROR, DX_NNN, ERROR, ERROR, DX_MNN, DX_MNN, ERROR),
+
+// DS_D_M
+DPSDAT( ERROR, D_MN, ERROR, D_MN, D_MNd, ERROR, ERROR, ERROR, ERROR),
+
+// DS_D_MN
+DPSDAT( DX_MN, DX_MNN, TX_N, DX_MNN, ERROR, T_Nt, ERROR, ERROR, ERROR),
+
+// DS_D_MNd
+DPSDAT( ERROR, DX_MNN, ERROR, DX_MNN, ERROR, ERROR, ERROR, ERROR, ERROR),
+
+// DS_T_Nt
+DPSDAT( ERROR, TX_NN, TX_NN, TX_NN, ERROR, T_NNt, ERROR, ERROR, ERROR),
+
+// DS_T_NNt
+DPSDAT( ERROR, TX_NNN, TX_NNN, TX_NNN, ERROR, ERROR, ERROR, ERROR, ERROR)
+};
+
+#endif // FE_DBCS
+
+STDAPI
+
+VarDateFromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, DATE FAR* pdateOut)
+{
+ int dps; // date parse state
+ UDS uds;
+ DATERAW raw;
+ DATEINFO di;
+ DATETOK dtok;
+ OLECHAR FAR* pch;
+ BOOL fDay, fTime;
+ HRESULT hr = RESULT(DISP_E_TYPEMISMATCH);
+
+#ifdef FE_DBCS
+#if !VBA2
+ BOOL fTimeElement = FALSE;
+#endif
+#endif
+ OLECHAR FAR* lpStr;
+
+#if HC_MPW
+ PRIVATECALLTYPE BOOL (*pfnUdsOfRaw)(DATERAW FAR*, DATEINFO FAR*, UDS FAR*);
+#else
+ BOOL (PRIVATECALLTYPE *pfnUdsOfRaw)(DATERAW FAR*, DATEINFO FAR*, UDS FAR*);
+#endif
+
+ ASSERT(!(dwFlags & ~(LOCALE_NOUSEROVERRIDE |
+ VAR_TIMEVALUEONLY |
+ VAR_DATEVALUEONLY)));
+
+
+ // aquire the locale info required to parse a date string
+
+
+ IfFailRet(GetDateInfo(&di, lcid, dwFlags & LOCALE_NOUSEROVERRIDE));
+
+#ifdef FE_DBCS
+ if(di.IsDBCS) {
+ IfFailRet(MapHalfWidth(lcid, strIn, &lpStr));
+ pch = lpStr;
+ } else
+ pch = lpStr = strIn;
+#else
+ pch = lpStr = strIn;
+#endif
+
+ dps = DS_BEGIN;
+ fDay = FALSE;
+ fTime = FALSE;
+ uds.Year = uds.Month = uds.DayOfMonth = uds.Hour = uds.Minute = uds.Second = -1;
+ raw.month = 0;
+#if VBA2
+ raw.ampm = AMPM_NONE;
+#endif
+
+ while(1){
+
+ // reset the rawdate struct, if appropriate
+
+ if(dps == DS_BEGIN){
+ raw.pnum = raw.num;
+#if !VBA2
+ raw.ampm = AMPM_NONE;
+#endif
+ }
+
+ // if not at a terminal state, then grab the next token
+ // from the input string.
+
+ if(!DS_ISTERMINAL(dps)){
+
+ if (ddlex(&pch, &di, &dtok, &raw) == 0)
+ goto LNotDate;
+
+ // default actions
+
+ switch(dtok.dtt){
+#ifdef FE_DBCS
+ // Note for suffixed DBCS numbers, we'll modifiy the uds directly
+ // (no need to use the raw struct). The functions AdjustUDSDate
+ // and AdjustUDSTime will post-process the struct for validity.
+ // The reason it is done this way is because having one state for
+ // each suffix type will require a huge state table.
+ case DTT_NumDatesuff:
+ case DTT_NumTimesuff:
+ switch (dtok.suffix) {
+ case SUFFIX_YEAR:
+#if !VBA2
+ if (fTimeElement || fTime || fDay || uds.Year != -1)
+#else
+ if (fDay || uds.Year != -1)
+#endif
+ goto LNotDate;
+ uds.Year = dtok.num;
+ break;
+ case SUFFIX_MONTH:
+#if !VBA2
+ if (fTimeElement || fTime || fDay || uds.Month != -1)
+#else
+ if (fDay || uds.Month != -1)
+#endif
+ goto LNotDate;
+ uds.Month = dtok.num;
+ break;
+ case SUFFIX_DAY:
+#if !VBA2
+ if (fTimeElement || fTime || fDay || uds.DayOfMonth != -1)
+#else
+ if (fDay || uds.DayOfMonth != -1)
+#endif
+ goto LNotDate;
+ uds.DayOfMonth = dtok.num;
+ break;
+ case SUFFIX_HOUR:
+#if !VBA2
+ if (fTime || uds.Hour != -1)
+ goto LNotDate;
+ fTimeElement = TRUE;
+#else
+ if (uds.Hour != -1)
+ goto LNotDate;
+#endif
+ uds.Hour = dtok.num;
+ break;
+ case SUFFIX_MINUTE:
+#if !VBA2
+ if (fTime || uds.Minute != -1)
+ goto LNotDate;
+ fTimeElement = TRUE;
+#else
+ if (uds.Minute != -1)
+ goto LNotDate;
+#endif
+ uds.Minute = dtok.num;
+ break;
+ case SUFFIX_SECOND:
+#if !VBA2
+ if (fTime || uds.Second != -1)
+ goto LNotDate;
+ fTimeElement = TRUE;
+#else
+ if (uds.Second != -1)
+ goto LNotDate;
+#endif
+ uds.Second = dtok.num;
+ break;
+ default:
+ ASSERT(UNREACHED);
+ break;
+
+ }
+ break;
+#endif // FE_DBCS
+ case DTT_NumAmpm:
+ // Note: if this was not a legal place for an ampm designator,
+ // then the error will be caught below in our state transition.
+ raw.ampm = dtok.ampm;
+
+ /* FALLTHROUGH */
+ case DTT_NumDatesep:
+ case DTT_NumTimesep:
+ case DTT_NumEnd:
+ case DTT_NumSpace:
+ ASSERT(raw.pnum < &raw.num[DIM(raw.num)]);
+ *raw.pnum++ = dtok.num;
+ break;
+
+ case DTT_MonthEnd:
+ case DTT_MonthSpace:
+ case DTT_MonthDatesep:
+ raw.month = dtok.num;
+ break;
+ }
+ }
+
+ // process the current state - handling special case transitional
+ // states, or executing terminal state actions.
+
+ switch(dps){
+ case DS_BEGIN:
+ if(dtok.dtt == DTT_End)
+ goto LDone;
+ break;
+
+
+ case DS_NN:
+ case DS_D_NN:
+ switch(dtok.dtt){
+ case DTT_NumAmpm:
+ case DTT_NumTimesep:
+
+ // special case: we have 3 numbers, the last of which is
+ // followed by either a timesep or an ampm marker. So we
+ // assume the first 2 were the date, and the third is the
+ // time. For example,
+ //
+ // "1 93 1 pm" would be "january 1, 1993 23:00:00"
+ //
+
+ pfnUdsOfRaw = DayOfNN;
+ goto LSpecial;
+ }
+ break;
+
+ case DS_D_MN:
+ switch(dtok.dtt){
+ case DTT_NumAmpm:
+ case DTT_NumTimesep:
+
+ // special case: we have month and two numbers, where the last
+ // number is followed by a timesep or an ampm designator. So
+ // we assume that the first month and number were the date, and
+ // the last number is the time. For example,
+ //
+ // "jan 93 1:00" would be "january 1, 1993 01:00:00"
+
+ pfnUdsOfRaw = DayOfMN;
+
+LSpecial:;
+ // compose the day
+ if(fDay || !pfnUdsOfRaw(&raw, &di, &uds))
+ goto LNotDate;
+ fDay = TRUE;
+
+ // start the time
+ raw.ampm = dtok.ampm;
+ raw.pnum = raw.num;
+ *raw.pnum++ = dtok.num;
+ break;
+ }
+ break;
+
+ // The following are terminal states that compute a UDS from a rawdate
+
+ case DS_DX_NN:
+ pfnUdsOfRaw = DayOfNN;
+ goto LDay;
+
+ case DS_DX_NNN:
+ pfnUdsOfRaw = DayOfNNN;
+ goto LDay;
+
+ case DS_DX_MN:
+ pfnUdsOfRaw = DayOfMN;
+ goto LDay;
+
+ case DS_DX_MNN:
+ pfnUdsOfRaw = DayOfMNN;
+LDay:;
+ if(fDay || !pfnUdsOfRaw(&raw, &di, &uds))
+ goto LNotDate;
+ fDay = TRUE;
+ break;
+
+ case DS_TX_N:
+ // if there is only a single time number, then we require
+ // an ampm designator
+ if(raw.ampm == AMPM_NONE)
+ goto LNotDate;
+ uds.Hour = raw.num[0];
+ uds.Minute = 0;
+ uds.Second = 0;
+ goto LTime;
+
+ case DS_TX_NN:
+ uds.Hour = raw.num[0];
+ uds.Minute = raw.num[1];
+ uds.Second = 0;
+ goto LTime;
+
+ case DS_TX_NNN:
+ uds.Hour = raw.num[0];
+ uds.Minute = raw.num[1];
+ uds.Second = raw.num[2];
+LTime:;
+ if(fTime)
+ goto LNotDate;
+#ifdef FE_DBCS
+LTime2:;
+#endif
+ AdjustTime(&uds, raw.ampm);
+ fTime = TRUE;
+#if VBA2
+ raw.ampm = AMPM_NONE;
+#endif
+ break;
+
+#ifdef FE_DBCS
+ case DS_TX_TS: // Done with time. Adjust UDS
+ if (!AdjustUDSTime(&raw, &di, &uds))
+ goto LNotDate;
+ goto LTime2; // fTime will already be set to true, so skip check
+ break;
+
+ case DS_DX_DS: // Done with date. Adjust.
+LDateSep:;
+ if (!AdjustUDSDate(&raw, &di, &uds))
+ goto LNotDate;
+ fDay = TRUE;
+ break;
+#endif // FE_DBCS
+
+ // the following are transitional states, with no special cases
+ // actions. (Note: these are split out into separate cases to
+ // make tracing the state transitions easier when debugging).
+
+ case DS_N:
+ break;
+
+ case DS_D_Nd:
+ break;
+
+ case DS_D_NNd:
+ break;
+
+ case DS_D_M:
+ break;
+
+ case DS_D_MNd:
+ break;
+
+ case DS_T_Nt:
+ break;
+
+ case DS_T_NNt:
+ break;
+
+#ifdef FE_DBCS
+ case DS_D_S: // date suffix.
+ // this case is handled differently. If the next token is not a
+ // date-suffixed number, it means we are done with the date and we
+ // need to adjust the UDS and set fDay to true. Otherwise, this is
+ // just another state transition.
+ if (dtok.dtt != DTT_NumDatesuff)
+ goto LDateSep;
+ break;
+
+ case DS_T_S: // time suffix.
+#if VBA2
+ fTime = TRUE;
+#endif
+ break;
+#endif // FE_DBCS
+
+
+ case DS_ERROR:
+ goto LNotDate;
+
+ default:
+ ASSERT(UNREACHED);
+ goto LNotDate;
+ }
+
+ // advance to the next state, and continue
+ dps = (dps < DS_ERROR) ? g_dpsNext[dps][dtok.dtt] : DS_BEGIN;
+
+ ASSERT(dps >= 0 && dps < DS_MAX);
+ }
+
+LDone:;
+
+ if(fDay || fTime){
+ VARIANT var;
+
+ if(!fDay){
+ // default the day
+ uds.Month = 12;
+ uds.DayOfMonth = 30;
+ uds.Year = 1899;
+ }
+
+ if(!fTime){
+ // default the time
+ uds.Hour = 0;
+ uds.Minute = 0;
+ uds.Second = 0;
+ }
+#if VBA2
+ else {
+ AdjustTime(&uds, raw.ampm);
+ }
+#endif
+
+ if(ErrPackDate(&uds, &var, TRUE, dwFlags) == NOERROR){
+ *pdateOut = V_DATE(&var);
+ hr = NOERROR; // success!
+ }
+ }
+
+LNotDate:;
+
+#ifdef FE_DBCS
+ if(di.IsDBCS) {
+ DispFree(lpStr);
+ }
+#endif
+
+ return hr;
+}
+
+
+/* following are the utilites for constructing a proper UDS from
+ * a raw set of numbers (or month and numbers).
+ *
+ * These utilities encapsulate the knowledge of how to interpret
+ * the set of numbers based on locale info, and what our defaulting
+ * rules (poorly defined though they are) when given an incomplete
+ * date.
+ *
+ */
+#if !VBA2
+#define LEGAL_DAY(DAY) ((DAY)>0 && (DAY)<=31)
+#define LEGAL_MONTH(MON) ((MON)>0 && (MON)<=12)
+#else //VBA2
+#define LEGAL_MONTH(MON) ((MON)>0 && (MON)<=12)
+int g_fDay31th[] = { 0,/*0*/ 1,/*Jan*/ 0,/*Feb*/ 1,0,1,0,1,1,0,1,0,1 };
+PRIVATE_(BOOL)
+LEGAL_DAY(int Year, int Month, int Day)
+{
+ if (Day <= 0) return FALSE;
+ if (Day > 31) return FALSE;
+ if ((Day == 31) && (LEGAL_MONTH(Month))) {
+ if (! g_fDay31th[Month]) return FALSE;
+ }
+ if (Month == 2) {
+ if (Day == 30) return FALSE;
+ if (Day == 29) { //for leap year
+ if (! (((Year & 3) == 0) && ((Year % 100) != 0 || (Year % 400) == 0)))
+ return FALSE;
+ }
+ }
+ return TRUE;
+}
+#endif //VBA2
+
+#if !VBA2
+// Fillin the day and year of the given uds, using the given
+// tentative day - default either the year or the day appropriately.
+
+PRIVATE_(BOOL)
+DefaultDayOrYear(UDS FAR* puds, int day)
+{
+ if(!LEGAL_DAY(day)){
+
+ // If the day is not valid then assume it was really a year,
+ // and default the day to 1.
+
+ // Note: the check for <31 should really be a check
+ // for <max_days(puds->Month), but this is the way EB did it.
+
+ puds->Year = day;
+ puds->DayOfMonth = 1;
+
+ }else{
+
+ puds->DayOfMonth = day;
+
+ // fillin the year with the current year
+ puds->Year = GetCurrentYear();
+ }
+
+ return TRUE;
+}
+#endif //!VBA2
+
+#if VBA2
+// fillin the uds day given params
+//PRIVATE_(VOID)
+void SetUDSfromYMD(UDS FAR* puds, int Y, int M, int D)
+{
+ puds->Year = Y;
+ puds->Month = M;
+ puds->DayOfMonth = D;
+}
+#endif //VBA2
+
+// fillin the uds day given two numbers
+
+PRIVATE_(BOOL)
+DayOfNN(DATERAW FAR* praw, DATEINFO FAR* pdi, UDS FAR* puds)
+{
+#if !VBA2
+ int n1, n2;
+
+ switch(pdi->dfo){
+ case DFO_MDY:
+ puds->Month = praw->num[0];
+ return DefaultDayOrYear(puds, praw->num[1]);
+
+ case DFO_DMY:
+ puds->Month = praw->num[1];
+ return DefaultDayOrYear(puds, praw->num[0]);
+
+ // This case is somewhat strange - we assume that the two
+ // given numbers are a day and a month, and we default the
+ // year.
+ case DFO_YMD:
+ n1 = praw->num[0], n2 = praw->num[1];
+ if(LEGAL_MONTH(n1) && LEGAL_DAY(n2)){
+ puds->Month = n1, puds->DayOfMonth = n2;
+ }else
+ if(LEGAL_MONTH(n2) && LEGAL_DAY(n1)){
+ puds->Month = n2, puds->DayOfMonth = n1;
+ }else
+ return FALSE;
+ puds->Year = GetCurrentYear();
+ return TRUE;
+ }
+ ASSERT(UNREACHED);
+ return FALSE;
+#else //VBA2
+ int n1 = praw->num[0];
+ int n2 = praw->num[1];
+ int nCurrentYear = GetCurrentYear();
+
+ switch (pdi->dfo) {
+ case DFO_YMD:
+ if (LEGAL_MONTH(n1) && LEGAL_DAY(nCurrentYear, n1, n2)) //M and D
+ SetUDSfromYMD(puds, nCurrentYear, n1, n2);
+ else if (LEGAL_MONTH(n2) && LEGAL_DAY(nCurrentYear, n2, n1)) //D and M
+ SetUDSfromYMD(puds, nCurrentYear, n2, n1);
+ else if (LEGAL_MONTH(n2)) //Y and M
+ SetUDSfromYMD(puds, n1, n2, 1);
+ else if (LEGAL_MONTH(n1)) //M and Y
+ SetUDSfromYMD(puds, n2, n1, 1);
+ else
+ return FALSE;
+ return TRUE;
+
+ case DFO_MDY:
+ if (LEGAL_MONTH(n1) && LEGAL_DAY(nCurrentYear, n1, n2)) //M and D
+ SetUDSfromYMD(puds, nCurrentYear, n1, n2);
+ else if (LEGAL_MONTH(n2) && LEGAL_DAY(nCurrentYear, n2, n1)) //D and M
+ SetUDSfromYMD(puds, nCurrentYear, n2, n1);
+ else if (LEGAL_MONTH(n1)) //M and Y
+ SetUDSfromYMD(puds, n2, n1, 1);
+ else if (LEGAL_MONTH(n2)) //Y and M
+ SetUDSfromYMD(puds, n1, n2, 1);
+ else
+ return FALSE;
+ return TRUE;
+
+ case DFO_DMY:
+ if (LEGAL_MONTH(n2) && LEGAL_DAY(nCurrentYear, n2, n1)) //D and M
+ SetUDSfromYMD(puds, nCurrentYear, n2, n1);
+ else if (LEGAL_MONTH(n1) && LEGAL_DAY(nCurrentYear, n1, n2)) //M and D
+ SetUDSfromYMD(puds, nCurrentYear, n1, n2);
+ else if (LEGAL_MONTH(n1)) //M and Y
+ SetUDSfromYMD(puds, n2, n1, 1);
+ else if (LEGAL_MONTH(n2)) //Y and M
+ SetUDSfromYMD(puds, n1, n2, 1);
+ else
+ return FALSE;
+ return TRUE;
+ }
+ ASSERT(UNREACHED);
+ return FALSE;
+#endif //VBA2
+}
+
+
+/***
+*PRIVATE BOOL DayOfNNN
+*Purpose:
+* Build a UDS date given three raw integers, in the textual order
+* that they appeared.
+*
+* There a 6 possible ways for the 3 raw numbers to be interpreted
+* as a m-d-y sequence. Choose the best fit, first based on the NLS
+* date-format ordering, and second on the legality of the actual
+* values.
+*
+*Entry:
+* praw = the raw values to process
+* pdi = the dateinfo (nls info)
+*
+*Exit:
+* return value = BOOL
+*
+* puds = the
+*
+***********************************************************************/
+PRIVATE_(BOOL)
+DayOfNNN(DATERAW FAR* praw, DATEINFO FAR* pdi, UDS FAR* puds)
+{
+#if !VBA2
+ int m, d, y, n0, n1, n2, a, b;
+
+ n0 = praw->num[0];
+ n1 = praw->num[1];
+ n2 = praw->num[2];
+
+ // Note: if none of the values for month or day are legally in
+ // range, then we default to the textual order (according to the
+ // nls date-info), and let the chips fall...
+
+ // remember when looking at the following code that
+ // *any* number is a legal year (ie, there are no checks
+ // for LEGAL_YEAR()
+
+ switch(pdi->dfo){
+ case DFO_MDY:
+ // 1. try to match the locale's date format ordering
+ if(LEGAL_MONTH(n0) && LEGAL_DAY(n1)){
+ m = n0, d = n1, y = n2;
+ break;
+ }
+ // 2. try universal date format: YMD
+ if(LEGAL_MONTH(n1) && LEGAL_DAY(n2)){
+ y = n0, m = n1, d = n2;
+ break;
+ }
+ // 3. try to find a some other reasonable fit for the numbers
+ if(LEGAL_MONTH(n0)){
+ goto Lmdy0;
+ }else if(LEGAL_MONTH(n1)){
+ m = n1; a = n0; b = n2;
+ }else if(LEGAL_MONTH(n2)){
+ m = n2; a = n0; b = n1;
+ }else{
+Lmdy0:; m = n0; a = n1; b = n2;
+ }
+ if(LEGAL_DAY(a)){
+ goto Lmdy1;
+ }else if(LEGAL_DAY(b)){
+ d = b; y = a;
+ }else{
+Lmdy1:; d = a; y = b;
+ }
+ break;
+
+ case DFO_DMY:
+ // 1. try to match the locale's date format ordering
+ if(LEGAL_DAY(n0) && LEGAL_MONTH(n1)){
+ d = n0, m = n1, y = n2;
+ break;
+ }
+ // 2. try universal date format: YMD
+ if(LEGAL_MONTH(n1) && LEGAL_DAY(n2)){
+ y = n0, m = n1, d = n2;
+ break;
+ }
+ // 3. try to find some other reasonable fit
+ if(LEGAL_DAY(n0)){
+ goto Ldmy0;
+ }else if(LEGAL_DAY(n1)){
+ d = n1; a = n0; b = n2;
+ }else if(LEGAL_DAY(n2)){
+ d = n2; a = n0; b = n1;
+ }else{
+Ldmy0:; d = n0; a = n1; b = n2;
+ }
+ if(LEGAL_MONTH(a)){
+ goto Ldmy1;
+ }else if(LEGAL_MONTH(b)){
+ m = b; y = a;
+ }else{
+Ldmy1:; m = a; y = b;
+ }
+ break;
+
+ case DFO_YMD:
+ y = n0; a = n1; b = n2;
+ if(LEGAL_MONTH(a)){
+ goto Lymd;
+ }else if(LEGAL_MONTH(b)){
+ m = b; d = a;
+ }else{
+Lymd:; m = a; d = b;
+ }
+ break;
+
+ default:
+ ASSERT(UNREACHED);
+ }
+
+ puds->Month = m;
+ puds->DayOfMonth = d;
+ puds->Year = y;
+
+ return TRUE;
+
+#else //VBA2
+ int n1 = praw->num[0];
+ int n2 = praw->num[1];
+ int n3 = praw->num[2];
+ int nCurrentYear = GetCurrentYear();
+
+ switch (pdi->dfo) {
+ case DFO_YMD:
+ if (LEGAL_MONTH(n2) && LEGAL_DAY(n1, n2, n3)) //Y&M&D
+ SetUDSfromYMD(puds, n1, n2, n3);
+ else if (LEGAL_MONTH(n1) && LEGAL_DAY(n3, n1, n2)) //M&D&Y
+ SetUDSfromYMD(puds, n3, n1, n2);
+ else if (LEGAL_MONTH(n2) && LEGAL_DAY(n3, n2, n1)) //D&M&Y
+ SetUDSfromYMD(puds, n3, n2, n1);
+ else
+ return FALSE;
+ return TRUE;
+
+ case DFO_MDY:
+ if (LEGAL_MONTH(n1) && LEGAL_DAY(n3, n1, n2)) //M&D&Y
+ SetUDSfromYMD(puds, n3, n1, n2);
+ else if (LEGAL_MONTH(n2) && LEGAL_DAY(n1, n2, n3)) //Y&M&D
+ SetUDSfromYMD(puds, n1, n2, n3);
+ else if (LEGAL_MONTH(n2) && LEGAL_DAY(n3, n2, n1)) //D&M&Y
+ SetUDSfromYMD(puds, n3, n2, n1);
+ else
+ return FALSE;
+ return TRUE;
+
+ case DFO_DMY:
+ if (LEGAL_MONTH(n2) && LEGAL_DAY(n3, n2, n1)) //D&M&Y
+ SetUDSfromYMD(puds, n3, n2, n1);
+ else if (LEGAL_MONTH(n2) && LEGAL_DAY(n1, n2, n3)) //Y&M&D
+ SetUDSfromYMD(puds, n1, n2, n3);
+ else if (LEGAL_MONTH(n1) && LEGAL_DAY(n3, n1, n2)) //M&D&Y
+ SetUDSfromYMD(puds, n3, n1, n2);
+ else
+ return FALSE;
+ return TRUE;
+ }
+ return TRUE;
+#endif //VBA2
+}
+
+
+// fillin the uds day given one number and a month
+
+PRIVATE_(BOOL)
+DayOfMN(DATERAW FAR* praw, DATEINFO FAR* pdi, UDS FAR* puds)
+{
+#if !VBA2
+ puds->Month = praw->month;
+
+ switch(pdi->dfo){
+ case DFO_MDY:
+ case DFO_DMY:
+ return DefaultDayOrYear(puds, praw->num[0]);
+
+ case DFO_YMD:
+ puds->DayOfMonth = 1;
+ puds->Year = praw->num[0];
+ return TRUE;
+ }
+
+ ASSERT(UNREACHED);
+ return FALSE;
+
+#else //VBA2
+ int nCurrentYear = GetCurrentYear();
+
+ if (LEGAL_DAY(nCurrentYear, praw->month, praw->num[0]))
+ SetUDSfromYMD(puds, nCurrentYear, praw->month, praw->num[0]);
+ else
+ SetUDSfromYMD(puds, praw->num[0], praw->month, 1);
+ return TRUE;
+#endif //VBA2
+}
+
+
+// fillin the uds day given a month and two numbers
+
+PRIVATE_(BOOL)
+DayOfMNN(DATERAW FAR* praw, DATEINFO FAR* pdi, UDS FAR* puds)
+{
+#if !VBA2
+ puds->Month = praw->month;
+
+ switch(pdi->dfo){
+ case DFO_MDY:
+ case DFO_DMY:
+ puds->DayOfMonth = praw->num[0];
+ puds->Year = praw->num[1];
+ break;
+
+ case DFO_YMD:
+ puds->DayOfMonth = praw->num[1];
+ puds->Year = praw->num[0];
+ break;
+ }
+
+ return TRUE;
+
+#else //VBA2
+ int n1 = praw->num[0];
+ int n2 = praw->num[1];
+
+ switch (pdi->dfo) {
+ case DFO_YMD: //YD, DY
+ if (LEGAL_DAY(n1, praw->month, n2))
+ SetUDSfromYMD(puds, n1, praw->month, n2);
+ else
+ SetUDSfromYMD(puds, n2, praw->month, n1);
+ break;
+ case DFO_MDY: //DY, YD
+ if (LEGAL_DAY(n2, praw->month, n1))
+ SetUDSfromYMD(puds, n2, praw->month, n1);
+ else
+ SetUDSfromYMD(puds, n1, praw->month, n2);
+ break;
+ case DFO_DMY: //DY, YD
+ if (LEGAL_DAY(n2, praw->month, n1))
+ SetUDSfromYMD(puds, n2, praw->month, n1);
+ else
+ SetUDSfromYMD(puds, n1, praw->month, n2);
+ break;
+ }
+ return TRUE;
+#endif //VBA2
+}
+
+
+// adjust the given time according to the given ampm designator
+
+PRIVATE_(void)
+AdjustTime(UDS FAR* puds, AMPM ampm)
+{
+ // REVIEW: check for invalid time here?
+
+ switch(ampm){
+ case AMPM_PM:
+ if(puds->Hour != 12)
+ puds->Hour += 12;
+ break;
+ case AMPM_AM:
+ if(puds->Hour == 12)
+ puds->Hour = 0;
+ break;
+ }
+}
+
+
+#ifdef FE_DBCS
+PRIVATE_(BOOL)
+AdjustUDSTime(DATERAW FAR* praw, DATEINFO FAR* pdi, UDS FAR* puds)
+{
+ // UDS already contains all the suffixed time information.
+ // just fill in remaining defaults. Make sure there are no numbers
+ // without suffixes..
+
+ if (praw->pnum != praw->num)
+ return FALSE;
+
+ if (puds->Hour == -1) puds->Hour = 0;
+ if (puds->Minute == -1) puds->Minute = 0;
+ if (puds->Second == -1) puds->Second = 0;
+
+ return TRUE;
+
+}
+
+
+PRIVATE_(BOOL)
+AdjustUDSDate(DATERAW FAR* praw, DATEINFO FAR* pdi, UDS FAR* puds)
+{
+ // UDS already contains all the suffixed date information.
+ // Just fill in remaining defaults. Verify enough information
+ // is provided.
+
+ if (praw->pnum > praw->num+1)
+ return FALSE;
+
+ if (puds->Year == -1 && puds->Month != -1 && puds->DayOfMonth != -1)
+ puds->Year = GetCurrentYear();
+ if (puds->DayOfMonth == -1 && puds->Year != -1 && puds->Month != -1)
+ puds->DayOfMonth = 1;
+
+ if (puds->Year == -1 || puds->Month == -1 || puds->DayOfMonth == -1)
+ return FALSE;
+
+ return TRUE;
+
+}
+#endif // FE_DBCS
+
+//---------------------------------------------------------------------
+// BSTR from DATE
+//---------------------------------------------------------------------
+
+#ifdef FE_DBCS
+
+// Given a UDS date, return an index into the impEras table for the
+// appropriate imperail era. If date falls before first imperial range,
+// return -1.
+
+PRIVATE_(int)
+GetImperialEra(UDS FAR* pdate, DATEINFO FAR* pdi)
+{
+ int i;
+ VARIANT find;
+ VARIANT first;
+ VARIANT next;
+
+ if (ErrPackDate(pdate, &find, TRUE, 0) != NOERROR)
+ return -1;
+
+ if (ErrPackDate(&pdi->impEras[0].beginDate, &first, TRUE, 0) != NOERROR)
+ return -1;
+
+ if (V_DATE(&find) < V_DATE(&first)) {
+ return -1;
+
+ } else for (i = 0; i < MAX_EMPERORS-1; i++) {
+ if (ErrPackDate(&pdi->impEras[i+1].beginDate, &next, TRUE, 0) != NOERROR)
+ return -1;
+
+ if (V_DATE(&find) >= V_DATE(&first) && V_DATE(&find) < V_DATE(&next))
+ return i;
+
+ V_DATE(&first) = V_DATE(&next);
+ }
+
+ return MAX_EMPERORS -1;
+}
+
+#endif // FE_DBCS
+
+
+
+/***
+*PRIVATE HRESULT RenderDate
+*Purpose:
+* Render the given date as a string. The string is formatted
+* based on the short date format for the current locale. The
+* possible (legal) date formatting characters that may appear
+* in a short date format string are,
+*
+* m month, 1-12
+* mm month with leading zero, 01-12
+*
+* M same as 'm'
+* MM same as 'mm'
+*
+* d day, 1-31
+* dd day with leading zero, 01-31
+*
+* yy year as two digit number, 00-99 (if current century)
+* yyyy year as four digit number, 100-9999
+*
+*
+*Entry:
+* puds = pointer to the unpacked date
+* pdi = pointer to the locale specific date info
+* pszFmt = the short date format string
+* *pszOut = the buffer to format the string into
+*
+*Exit:
+* return value = HRESULT
+*
+* *pszOut = pointer to the end of the formatted string
+*
+***********************************************************************/
+
+PRIVATE_(HRESULT)
+RenderDate(
+ UDS FAR* puds,
+ DATEINFO FAR* pdi,
+ OLECHAR FAR* pszFmt,
+ OLECHAR FAR* FAR* pszOut)
+{
+ int len, num;
+ OLECHAR ch, FAR* psz;
+
+ UNUSED(pdi);
+
+ psz = *pszOut;
+
+ while(*pszFmt != OASTR('\0')){
+ switch(*pszFmt){
+#if 0
+// I dont remember why I thought we should treat a backslash as an
+// escape character. There are no cases in our locale info that it
+// is used this way, and treating it this way breaks its (obscure)
+// use as a date separator. -BHL
+ case OASTR('\\'):
+ // copy out escaped character
+ ++pszFmt;
+ if(*pszFmt != OASTR('\0'))
+ *psz++ = *pszFmt++;
+ break;
+#endif
+
+ case OASTR('\''):
+ // copy out the quoted string
+ ++pszFmt;
+ while(*pszFmt != OASTR('\0')){
+ if((ch = *pszFmt++) == OASTR('\''))
+ break;
+ *psz++ = ch;
+ }
+ break;
+
+ case OASTR('d'): // handle 'd' and 'dd'
+ num = puds->DayOfMonth;
+ goto LDayOrMonth;
+
+ case OASTR('m'): // handle 'm' and 'mm'
+ case OASTR('M'): // handle 'M' and 'MM'
+ num = puds->Month;
+LDayOrMonth:;
+ if(pszFmt[0] == pszFmt[1]){
+ pszFmt += 2;
+ if(num < 10)
+ *psz++ = OASTR('0'); // leading zero if appropriate
+ }else{
+ pszFmt += 1;
+ }
+ ASSERT(num >= 0);
+ disp_itoa(num, psz, 10);
+ len = STRLEN(psz);
+ ASSERT(len <= 2);
+ psz += len;
+ break;
+
+ case 'y': // handle 'yy' or 'yyyy'
+ if(pszFmt[1] == OASTR('y')){
+ num = puds->Year;
+ ASSERT(num >= 0 && num <= 9999);
+ if(pszFmt[2] == OASTR('y') && pszFmt[3] == OASTR('y')){
+ // date as a four digit number
+ pszFmt += 4;
+ }else{
+ // date as a two digit number
+ pszFmt += 2;
+ if((num / 100) == 19)
+ num %= 100;
+ if(num < 10)
+ *psz++ = OASTR('0'); // leading zero if appropriate
+ }
+ ASSERT(num >= 0);
+ disp_itoa(num, psz, 10);
+ len = STRLEN(psz);
+ ASSERT(len <= 4);
+ psz += len;
+ break;
+ }
+#ifdef FE_DBCS
+ case OASTR('e'):
+ case OASTR('E'):
+ pszFmt++;
+
+ if (IsJapan(pdi->lcid)) {
+ int era;
+ short fLeadZero = 0;
+
+ if (pszFmt[0] == OASTR('e') || pszFmt[0] == OASTR('E')) {
+ fLeadZero = 1;
+ pszFmt++;
+ }
+
+ // find imperial era
+ if ( (era = GetImperialEra(puds, pdi)) >= 0 ) {
+ int year = puds->Year - pdi->impEras[era].beginDate.Year + 1;
+ if (year < 10 && fLeadZero)
+ *psz++ = OASTR('0');
+ disp_itoa(year, psz, 10);
+ psz += STRLEN(psz);
+ }
+
+ } else {
+ // UNDONE: bassams: What should we do here. 'ee' on a non-japanese machine.
+ }
+ break;
+
+ case OASTR('g'):
+ case OASTR('G'): // Japanese imperial eras.
+ pszFmt++;
+ if (IsJapan(pdi->lcid)) {
+ int era;
+ short sFmt = 0;
+
+ if (pszFmt[0] == OASTR('g') || pszFmt[0] == OASTR('G')) {
+ if (pszFmt[1] == OASTR('g') || pszFmt[0] == OASTR('G')) {
+ // three 'g's
+ sFmt = 2;
+ } else {
+ // two 'g's
+ sFmt = 1;
+ }
+ }
+
+ pszFmt += sFmt;
+ // find imperial era
+ if ( (era = GetImperialEra(puds, pdi)) < 0 ) {
+ // Use gregorian year.
+ disp_itoa(puds->Year, psz, 10);
+ len = STRLEN(psz);
+ ASSERT(len <= 4);
+ psz += len;
+
+ } else {
+ STRCPY(psz, pdi->impEras[era].szName[sFmt]);
+ psz += STRLEN(psz);
+ }
+
+ } else {
+ // UNDONE: bassams: What should we do here. 'ggg' on non-Japanese.
+ }
+ break;
+#endif // FE_DBCS
+
+ /* else FALLTHROUGH */
+
+ default:
+ *psz++ = *pszFmt++;
+ break;
+ }
+ }
+
+ *psz = OASTR('\0');
+
+ *pszOut = psz;
+
+ return NOERROR;
+}
+
+
+// tack on the Ampm designator -
+//
+PRIVATE_(void)
+AppendAmPm(
+ DATEINFO FAR *pdi,
+ OLECHAR FAR* FAR* psz,
+ UDS FAR* puds,
+ BOOL fAmPmPrefix)
+{
+ OLECHAR FAR* pszAmpm;
+
+ // Note: If were using a 24hour format, then we still tack on the
+ // s2359 string. Although this will typically be empty, the user may
+ // enter something in their intl settings, and this is what basic does.
+ // (oleprog#186)
+ pszAmpm = (!pdi->fAmpm)
+ ? pdi->sz2359
+ : (puds->Hour < 12) ? pdi->sz1159 : pdi->sz2359;
+
+ if(*pszAmpm != OASTR('\0')){
+ if(!fAmPmPrefix)
+ *(*psz)++ = OASTR(' ');
+
+ while(*pszAmpm != OASTR('\0'))
+ *(*psz)++ = *pszAmpm++;
+
+ if(fAmPmPrefix)
+ *(*psz)++ = OASTR(' ');
+ }
+}
+
+/***
+*PRIVATE HRESULT RenderTime
+*Purpose:
+* Render the given time as a string. All times are formatted
+* as Hour:Minute:Second, with the following options,
+*
+* - locale specific time separator
+* - optional leading zero on time
+* - 12hour format with locale specific am/pm designator, or 24hour fmt.
+*
+*Entry:
+* puds = the unpacked time to render
+* pdi = pointer to the DATEINFO struct with the appropriate locale info
+* *pszOut = the buffer to format into
+*
+*Exit:
+* return value = HRESULT
+*
+* *pszOut = pointer to the end of the formatted string.
+*
+***********************************************************************/
+PRIVATE_(HRESULT)
+RenderTime(UDS FAR* puds, DATEINFO FAR* pdi, OLECHAR FAR* FAR* pszOut)
+{
+ OLECHAR FAR* psz;
+ int i, len, hms[3];
+
+ psz = *pszOut;
+
+#ifdef FE_DBCS
+ if (pdi->IsDBCS && pdi->fAmPmPrefix)
+ AppendAmPm(pdi, &psz, puds, TRUE);
+#endif // FE_DBCS
+
+ hms[0] = puds->Hour;
+ if(pdi->fAmpm){
+ if(hms[0] > 12)
+ hms[0] -= 12;
+ else if(hms[0] == 0)
+ hms[0] = 12;
+ }
+ hms[1] = puds->Minute;
+ hms[2] = puds->Second;
+
+ for(i = 0; i < 3; ++i){
+ if(hms[i] < 10 && (i > 0 || pdi->fTlzero))
+ *psz++ = OASTR('0');
+ disp_itoa(hms[i], psz, 10);
+ len = STRLEN(psz);
+ ASSERT(len <= 2);
+ psz += len;
+ if (i < 2)
+ *psz++ = pdi->szTimesep[0];
+ }
+
+#ifdef FE_DBCS
+ if (pdi->IsDBCS) {
+ if (!pdi->fAmPmPrefix)
+ AppendAmPm(pdi, &psz, puds, FALSE);
+ } else
+#endif
+ AppendAmPm(pdi, &psz, puds, FALSE);
+
+ *psz = OASTR('\0');
+ *pszOut = psz;
+ return NOERROR;
+}
+
+
+/***
+*PUBLIC HRESULT VarBstrFromDate(DATE, LCID, unsigned long, BSTR FAR*);
+*Purpose:
+*
+*Entry:
+* date = the date to coerce
+*
+*Exit:
+* return value = HRESULT
+*
+* *pszOut = the resulting string
+*
+***********************************************************************/
+
+STDAPI
+VarBstrFromDate(
+ DATE dateIn,
+ LCID lcid,
+ unsigned long dwFlags,
+ BSTR FAR* pbstrOut)
+{
+ UDS uds;
+ VARIANT var;
+ DATEINFO di;
+ BOOL fNoDate;
+ OLECHAR FAR* psz;
+ OLECHAR rgchFmt[64]; // REVIEW
+ OLECHAR rgchBuf[128]; // REVIEW
+
+ ASSERT(dwFlags == 0 || dwFlags == LOCALE_NOUSEROVERRIDE);
+
+ IfFailRet(GetDateInfo(&di, lcid, dwFlags));
+
+ // get the short date format string
+
+ IfFailRet(
+ SafeGetLocaleInfo(
+ di.lcid, LOCALE_SSHORTDATE | dwFlags, rgchFmt, sizeof(rgchFmt)));
+
+ // unpack the serial date
+
+ V_VT(&var) = VT_DATE;
+ V_DATE(&var) = dateIn;
+ IfFailRet(ErrUnpackDate(&uds, &var));
+
+ psz = rgchBuf;
+
+ // dont render the date if the serialized date is 0,
+ // which corresponds to an unpacked date of 12/30/1899
+
+ fNoDate = (uds.Month == 12 && uds.DayOfMonth == 30 && uds.Year == 1899);
+ if(!fNoDate){
+ IfFailRet(RenderDate(&uds, &di, rgchFmt, &psz));
+ }
+
+ // append the time to the string if its != 0:0:0, or we didnt render
+ // the date.
+
+ if(fNoDate || uds.Hour != 0 || uds.Minute != 0 || uds.Second != 0){
+ if(!fNoDate)
+ *psz++ = OASTR( ' ');
+ IfFailRet(RenderTime(&uds, &di, &psz));
+ }
+
+ ASSERT(psz < &rgchBuf[DIM(rgchBuf)]);
+
+ return ErrSysAllocString(rgchBuf, pbstrOut);
+}
+
+INTERNAL_(HRESULT)
+IntOfString(LCID lcid, OLECHAR FAR* psz, int FAR* pval)
+{
+ int val;
+ OLECHAR chSign;
+
+ EATWHITE(lcid, psz);
+
+ chSign = *psz;
+ if(*psz == OASTR('-') || *psz == OASTR('+'))
+ ++psz;
+
+ for(val = 0; *psz >= OASTR('0') && *psz <= OASTR('9') ; ++psz){
+ val = (val*10) + (*psz - OASTR('0'));
+ }
+
+ EATWHITE(lcid, psz);
+
+ if(*psz != OASTR('\0'))
+ return RESULT(E_INVALIDARG);;
+
+ *pval = (chSign == OASTR('-')) ? -val : val;
+
+ return NOERROR;
+}
+
+#if 0
+
+INTERNAL_(HRESULT)
+StringOfInt(int val, OLECHAR FAR* pszOut, int FAR* pcbLen)
+{
+ int v, r;
+ OLECHAR FAR* psz;
+
+ if(val == 0){
+ pszOut[0] = OASTR('0');
+ pszOut[1] = OASTR('\0');
+ *pcbLen = 1;
+ return NOERROR;
+ }
+
+ psz = pszOut;
+ for(v = val; v != 0;){
+ r = v % 10;
+ v = v / 10;
+ *psz++ = r + OASTR('0');
+ }
+ if(val < 0)
+ *psz++ = OASTR('-');
+ *psz = OASTR('\0');
+
+ STRREV(pszOut);
+
+ *pcbLen = psz - pszOut;
+ ASSERT(*pcbLen >= 1);
+ return NOERROR;
+}
+
+#endif
+
+#if OE_WIN16
+/***
+*PUBLIC void NLSInfoChangedHandler(void)
+*Purpose:
+* When WIN.INI changes, the DATEINFO cache must be invalidated. This
+* routine is called by ole2nls.dll when WIN.INI changes, and once when
+* ole2nls.dll creates its hidden window.
+*
+*Entry:
+* None
+*
+*Exit:
+* None
+*
+***********************************************************************/
+#pragma code_seg("_TEXT") // called during ole2disp startup
+EXTERN_C void EXPORT CALLBACK NLSInfoChangedHandler(void)
+{
+ // flag the cache as invalid
+ g_diCache.lcid = 0xffffffff;
+}
+#pragma code_seg()
+#endif
diff --git a/private/oleauto/src/dispatch/cdispti.cpp b/private/oleauto/src/dispatch/cdispti.cpp
new file mode 100644
index 000000000..29b2d2e9c
--- /dev/null
+++ b/private/oleauto/src/dispatch/cdispti.cpp
@@ -0,0 +1,1360 @@
+/***
+*cdispti.cpp
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This module implements CDispTypeInfo, which is an INTERFACEDATA
+* driven implementation of the TypeInfo interface.
+*
+*
+*Revision History:
+*
+* [00] 19-Nov-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+ASSERTDATA
+
+
+// the following structure is used to assemble the arguments for
+// use by the low level invocation helper - DoInvokeMethod()
+
+typedef struct tagINVOKEARGS{
+ unsigned int cArgs;
+ VARTYPE FAR* rgvt;
+ VARIANTARG FAR* FAR* rgpvarg;
+ VARIANTARG FAR* rgvarg;
+} INVOKEARGS;
+
+
+// REVIEW: this should support aggregation
+
+class CDispTypeInfo : public ITypeInfo {
+public:
+ static HRESULT Create(
+ TYPEKIND tkind,
+ INTERFACEDATA FAR* pidata,
+ LCID lcid,
+ ITypeInfo FAR* FAR* pptinfo);
+
+
+ // IUnknown methods
+ //
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+
+ // ITypeInfo methods
+ //
+ STDMETHOD(GetTypeAttr)(TYPEATTR FAR* FAR* pptattr);
+
+ STDMETHOD(GetTypeComp)(ITypeComp FAR* FAR* pptcomp);
+
+ STDMETHOD(GetFuncDesc)(unsigned int index, FUNCDESC FAR* FAR* ppfuncdesc);
+
+ STDMETHOD(GetVarDesc)(unsigned int index, VARDESC FAR* FAR* ppvardesc);
+
+ STDMETHOD(GetNames)(
+ MEMBERID memid,
+ BSTR FAR* rgbstrNames,
+ unsigned int cMaxNames,
+ unsigned int FAR* pcNames);
+
+ STDMETHOD(GetRefTypeOfImplType)(
+ unsigned int index,
+ HREFTYPE FAR* phreftype);
+
+ STDMETHOD(GetImplTypeFlags)(
+ unsigned int index,
+ int FAR* pimpltypeflags);
+
+ STDMETHOD(GetIDsOfNames)(
+ OLECHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ MEMBERID FAR* rgmemid);
+
+ STDMETHOD(Invoke)(
+ void FAR* pvInstance,
+ MEMBERID memid,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pdispparams,
+ VARIANT FAR* pvarResult,
+ EXCEPINFO FAR* pexcepinfo,
+ unsigned int FAR* puArgErr);
+
+ STDMETHOD(GetDocumentation)(
+ MEMBERID memid,
+ BSTR FAR* pbstrName,
+ BSTR FAR* pbstrDocString,
+ unsigned long FAR* pdwHelpContext,
+ BSTR FAR* pbstrHelpFile);
+
+ STDMETHOD(GetDllEntry)(
+ MEMBERID memid,
+ INVOKEKIND invkind,
+ BSTR FAR* pbstrDllName,
+ BSTR FAR* pbstrName,
+ unsigned short FAR* pwOrdinal);
+
+ STDMETHOD(GetRefTypeInfo)(
+ HREFTYPE hreftype, ITypeInfo FAR* FAR* pptinfo);
+
+ STDMETHOD(AddressOfMember)(
+ MEMBERID memid, INVOKEKIND invkind, void FAR* FAR* ppv);
+
+ STDMETHOD(CreateInstance)(IUnknown FAR* punkOuter,
+ REFIID riid,
+ void FAR* FAR* ppv);
+
+ STDMETHOD(GetMops)(MEMBERID memid, BSTR FAR* pbstrMops);
+
+ STDMETHOD(GetContainingTypeLib)(
+ ITypeLib FAR* FAR* pptlib, unsigned int FAR* pindex);
+
+ STDMETHOD_(void, ReleaseTypeAttr)(TYPEATTR FAR* ptattr);
+ STDMETHOD_(void, ReleaseFuncDesc)(FUNCDESC FAR* pfuncdesc);
+ STDMETHOD_(void, ReleaseVarDesc)(VARDESC FAR* pvardesc);
+
+ inline int StrICmp(OLECHAR FAR* sz1, int len1, OLECHAR FAR* sz2, int len2)
+ {
+ LCTYPE type = NORM_IGNORECASE; // all versions are case insensitive
+
+#ifdef FE_DBCS
+ if (IsDBCS(m_lcid)) {
+ type |= NORM_IGNOREWIDTH; // DBCS is width insensitive
+
+ if (IsJapan(m_lcid))
+ type |= NORM_IGNOREKANATYPE; // Japan is Kanatype insensitive
+
+ } else
+#endif
+ type |= NORM_IGNORENONSPACE; // US-Euro only
+
+ return CompareString(m_lcid, type, sz1, len1, sz2, len2) - 2;
+ }
+
+ CDispTypeInfo();
+
+private:
+
+ HRESULT PmdataOfDispid(
+ MEMBERID memid, unsigned short wFlags, METHODDATA FAR* FAR* ppmdata);
+
+ inline HRESULT PmdataOfPropGet(
+ MEMBERID memid, METHODDATA FAR* FAR* ppmdata)
+ {
+ return PmdataOfDispid(memid, DISPATCH_PROPERTYGET, ppmdata);
+ }
+
+ HRESULT AllocInvokeArgs(
+ unsigned int cArgs,
+ INVOKEARGS FAR* FAR* ppinvargs);
+
+ HRESULT GetInvokeArgs(
+ METHODDATA FAR* pmdata,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pdispparams,
+ INVOKEARGS FAR* FAR* pinvargsOut,
+ unsigned int FAR* puArgErr);
+
+ void ReleaseInvokeArgs(INVOKEARGS FAR* pinvargs);
+
+ inline BOOL IsPropGet(unsigned short wFlags) const {
+ return ((wFlags & DISPATCH_PROPERTYGET) != 0);
+ }
+
+ inline BOOL IsPropPut(unsigned short wFlags) const {
+ return ((wFlags & (DISPATCH_PROPERTYPUT | DISPATCH_PROPERTYPUTREF)) != 0);
+ }
+
+ inline BOOL IsLegalInvokeFlags(unsigned short wFlags) const {
+ return ((wFlags & ~(DISPATCH_METHOD | DISPATCH_PROPERTYGET | DISPATCH_PROPERTYPUT | DISPATCH_PROPERTYPUTREF)) == 0);
+ }
+
+ unsigned long m_refs;
+ LCID m_lcid;
+ TYPEKIND m_tkind;
+ INTERFACEDATA FAR* m_pidata;
+};
+
+
+#if 0
+LOCAL HRESULT
+PmdataOfImeth(INTERFACEDATA FAR*, unsigned int, METHODDATA FAR* FAR*);
+#endif
+
+
+// REVIEW: we really should have a separate error to indicate not-supported
+#define E_NOTSUPPORTED E_NOTIMPL
+
+
+/***
+*HRESULT CDispTypeInfo::Create
+*Purpose:
+* Create an instance of CDispTypeInfo
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = CDispTypeInfo*. NULL if create failed.
+*
+***********************************************************************/
+HRESULT
+CDispTypeInfo::Create(
+ TYPEKIND tkind,
+ INTERFACEDATA FAR* pidata,
+ LCID lcid,
+ ITypeInfo FAR* FAR* pptinfo)
+{
+ CDispTypeInfo FAR* ptinfo;
+
+ if((ptinfo = new FAR CDispTypeInfo()) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+ ptinfo->AddRef();
+
+ ptinfo->m_lcid = lcid;
+ ptinfo->m_tkind = tkind;
+ ptinfo->m_pidata = pidata;
+
+ *pptinfo = ptinfo;
+
+ return NOERROR;
+}
+
+
+/***
+*HRESULT CreateDispTypeInfo(INTERFACEDATA*, CDispTypeInfo**)
+*Purpose:
+* Create a CDispTypeInfo and initialize it from the given
+* INTERFACEDATA
+*
+*Entry:
+* pidata = pointer to an INTERFACEDATA
+*
+*Exit:
+* return value = HRESULT
+* S_OK
+* E_OUTOFMEMORY
+*
+* *pptinfo = pointer to the created CDispTypeInfo
+*
+*Note:
+* UNDONE: This function currently returns an CDispTypeInfo*, it
+* should return an ITypeInfo*, but the currently implementation is
+* not complete... this will change.
+*
+***********************************************************************/
+STDAPI
+CreateDispTypeInfo(
+ INTERFACEDATA FAR* pidata,
+ LCID lcid,
+ ITypeInfo FAR* FAR* pptinfo)
+{
+ ITypeInfo FAR* ptinfo;
+
+ IfFailRet(CDispTypeInfo::Create(TKIND_COCLASS, pidata, lcid, &ptinfo));
+
+ *pptinfo = ptinfo;
+
+ return NOERROR;
+}
+
+CDispTypeInfo::CDispTypeInfo()
+{
+ m_refs = 0;
+ m_pidata = NULL;
+}
+
+
+//---------------------------------------------------------------------
+// IUnknown methods
+//---------------------------------------------------------------------
+
+
+STDMETHODIMP
+CDispTypeInfo::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ if(IsEqualIID(riid, IID_IUnknown)){
+ *ppv = this;
+ AddRef();
+ }else if(IsEqualIID(riid, IID_ITypeInfo)){
+ *ppv = this;
+ AddRef();
+ }else{
+ *ppv = NULL;
+ return RESULT(E_NOINTERFACE);
+ }
+ return NOERROR;
+}
+
+
+STDMETHODIMP_(unsigned long)
+CDispTypeInfo::AddRef()
+{
+ return ++m_refs;
+}
+
+
+STDMETHODIMP_(unsigned long)
+CDispTypeInfo::Release()
+{
+ if(--m_refs == 0){
+ delete this;
+ return 0;
+ }
+ return m_refs;
+}
+
+
+//---------------------------------------------------------------------
+// ITypeInfo methods
+//---------------------------------------------------------------------
+
+
+/***
+*PUBLIC CDispTypeInfo::GetTypeAttr(TYPEATTR**)
+*Purpose:
+* Return a TYPEATTR that contains info about the described type.
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+* S_OK
+* E_OUTOFMEMORY
+*
+* *pptattr = filled in TYPEATTR structure
+*
+***********************************************************************/
+STDMETHODIMP
+CDispTypeInfo::GetTypeAttr(TYPEATTR FAR* FAR* pptattr)
+{
+ TYPEATTR FAR* ptattr;
+
+ if((ptattr = new FAR TYPEATTR) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+
+ ptattr->typekind = m_tkind;
+ ptattr->lcid = m_lcid;
+
+ ptattr->wMajorVerNum = 0;
+ ptattr->wMinorVerNum = 0;
+
+ ptattr->cVars = 0;
+
+ switch(m_tkind){
+ case TKIND_COCLASS:
+ ptattr->cFuncs = 0;
+ ptattr->cImplTypes = 1;
+ break;
+ case TKIND_INTERFACE:
+ ptattr->cFuncs = m_pidata->cMembers;
+ ptattr->cImplTypes = 0;
+ break;
+ default:;
+ ASSERT(UNREACHED);
+ break;
+ }
+
+ ptattr->guid = GUID_NULL;
+ ptattr->wTypeFlags = 0;
+
+ ptattr->cbSizeVft = (unsigned short)-1; // REVIEW: UNKNOWN?
+ ptattr->cbSizeInstance = (unsigned short)-1;// REVIEW: UNKNOWN?
+
+ // REVIEW: the following is Win16 specific
+ ptattr->cbAlignment = 2; // WORD align;
+
+ ptattr->idldescType.wIDLFlags = IDLFLAG_NONE;
+#if defined(WIN16)
+ ptattr->idldescType.bstrIDLInfo = NULL;
+#else
+ ptattr->idldescType.dwReserved = 0;
+#endif
+ ptattr->memidDestructor = DISPID_UNKNOWN;
+ ptattr->memidConstructor = DISPID_UNKNOWN;
+
+ *pptattr = ptattr;
+
+ return NOERROR;
+}
+
+
+STDMETHODIMP
+CDispTypeInfo::GetTypeComp(ITypeComp FAR* FAR* pptcomp)
+{
+ UNUSED(pptcomp);
+
+ return RESULT(E_NOTSUPPORTED);
+}
+
+
+PRIVATE_(HRESULT)
+InvkindOfDispkind(unsigned short wFlags, INVOKEKIND FAR* pinvkind)
+{
+ switch(wFlags){
+ case DISPATCH_METHOD:
+ *pinvkind = INVOKE_FUNC;
+ break;
+ case DISPATCH_PROPERTYGET:
+ *pinvkind = INVOKE_PROPERTYGET;
+ break;
+ case DISPATCH_PROPERTYPUT:
+ *pinvkind = INVOKE_PROPERTYPUT;
+ break;
+ case DISPATCH_PROPERTYPUTREF:
+ *pinvkind = INVOKE_PROPERTYPUTREF;
+ break;
+ default:
+ return RESULT(E_FAIL); // bad dispkind
+ }
+ return NOERROR;
+}
+
+STDMETHODIMP
+CDispTypeInfo::GetFuncDesc(
+ unsigned int index,
+ FUNCDESC FAR* FAR* ppfuncdesc)
+{
+ unsigned int u;
+ HRESULT hresult;
+ FUNCDESC FAR* pfuncdesc;
+ METHODDATA FAR* pmdata;
+ ELEMDESC FAR* rgelemdesc;
+
+ // can only return a funcdesc on an interface
+ if(m_tkind != TKIND_INTERFACE)
+ return RESULT(E_FAIL);
+
+#if 0
+ // lookup the METHODDATA that corresponds to the given index.
+ IfFailGo(PmdataOfImeth(m_pidata, index, &pmdata), LError0);
+#else
+ if(index >= m_pidata->cMembers)
+ return RESULT(DISP_E_MEMBERNOTFOUND);
+ pmdata = &m_pidata->pmethdata[index];
+#endif
+
+ if((pfuncdesc = new FAR FUNCDESC) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LError0;
+ }
+
+ if((rgelemdesc = new FAR ELEMDESC [pmdata->cArgs]) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LError1;
+ }
+
+ pfuncdesc->memid = pmdata->dispid;
+ pfuncdesc->funckind = FUNC_VIRTUAL;
+ IfFailGo(InvkindOfDispkind(pmdata->wFlags, &pfuncdesc->invkind), LError2);
+ pfuncdesc->callconv = pmdata->cc;
+ pfuncdesc->cParams = pmdata->cArgs;
+ pfuncdesc->cParamsOpt = 0;
+ pfuncdesc->oVft = pmdata->iMeth * sizeof(void FAR*);
+ pfuncdesc->wFuncFlags = 0;
+
+ pfuncdesc->elemdescFunc.tdesc.vt = pmdata->vtReturn;
+ pfuncdesc->elemdescFunc.idldesc.wIDLFlags = IDLFLAG_NONE;
+
+#if defined(WIN16)
+ pfuncdesc->elemdescFunc.idldesc.bstrIDLInfo = NULL;
+#else
+ pfuncdesc->elemdescFunc.idldesc.dwReserved = 0;
+#endif
+
+ for(u = 0; u < pmdata->cArgs; ++u){
+ rgelemdesc[u].tdesc.vt = pmdata->ppdata[u].vt;
+ rgelemdesc[u].idldesc.wIDLFlags = IDLFLAG_NONE;
+#if defined(WIN16)
+ rgelemdesc[u].idldesc.bstrIDLInfo = NULL;
+#else
+ rgelemdesc[u].idldesc.dwReserved = 0;
+#endif
+ }
+ pfuncdesc->lprgelemdescParam = rgelemdesc;
+
+ *ppfuncdesc = pfuncdesc;
+
+ return NOERROR;
+
+LError2:
+ delete rgelemdesc;
+
+LError1:
+ delete pfuncdesc;
+
+LError0:
+ return hresult;
+}
+
+
+STDMETHODIMP
+CDispTypeInfo::GetVarDesc(
+ unsigned int index,
+ VARDESC FAR* FAR* ppvardesc)
+{
+ UNUSED(index);
+ UNUSED(ppvardesc);
+
+ // there are no variables described an an INTERFACEDATA
+ //
+ return RESULT(DISP_E_MEMBERNOTFOUND);
+}
+
+
+STDMETHODIMP
+CDispTypeInfo::GetNames(
+ MEMBERID memid,
+ BSTR FAR* rgbstrNames,
+ unsigned int cMaxNames,
+ unsigned int FAR* pcNames)
+{
+ unsigned short wFlags;
+ unsigned int u, cNames;
+ HRESULT hresult;
+ METHODDATA FAR* pmdata;
+
+
+ if(m_tkind != TKIND_INTERFACE || cMaxNames == 0){
+ *pcNames = 0;
+ return NOERROR;
+ }
+
+ wFlags = DISPATCH_METHOD|DISPATCH_PROPERTYPUT|DISPATCH_PROPERTYPUTREF|DISPATCH_PROPERTYGET;
+ // lookup the METHODDATA with the corresponding DISPID.
+ IfFailGo(PmdataOfDispid(memid, wFlags, &pmdata), LError0);
+
+ cNames = MIN(pmdata->cArgs+1, cMaxNames);
+
+ MEMSET(rgbstrNames, 0, cNames);
+
+ IfFailGo(ErrSysAllocString(pmdata->szName, &rgbstrNames[0]), LError1);
+
+ for(u = 1; u < cNames; ++u){
+ IfFailGo(
+ ErrSysAllocString(pmdata->ppdata[u-1].szName, &rgbstrNames[u]),
+ LError1);
+ }
+
+ *pcNames = cNames;
+
+ return NOERROR;
+
+LError1:;
+ // unwind BSTR allocations
+ for(u = 0; u <= pmdata->cArgs; ++u){
+ if(rgbstrNames[u] == NULL)
+ break;
+ SysFreeString(rgbstrNames[0]);
+ rgbstrNames[u] = NULL;
+ }
+
+LError0:;
+ return hresult;
+}
+
+
+STDMETHODIMP
+CDispTypeInfo::GetRefTypeOfImplType(
+ unsigned int index,
+ HREFTYPE FAR* phreftype)
+{
+ UNUSED(index);
+
+ if(m_tkind != TKIND_COCLASS)
+ return RESULT(E_UNEXPECTED); // REVIEW
+
+ *phreftype = 0;
+ return NOERROR;
+}
+
+STDMETHODIMP
+CDispTypeInfo::GetImplTypeFlags(
+ unsigned int index,
+ int FAR* pimpltypeflags)
+{
+ UNUSED(index);
+ UNUSED(pimpltypeflags);
+
+ return RESULT(E_NOTSUPPORTED);
+}
+
+/***
+*HRESULT CDispTypeInfo::GetIDsOfNames
+*Purpose:
+* Translate the given array of names (method and optional params)
+* into a corresponding array of DISPIDs.
+*
+*Entry:
+* rgszNames = the array of names to translate
+* cNames = count of names
+*
+*Exit:
+* return value = HRESULT
+* S_OK
+* E_INVALIDARG
+* DISP_E_UNKNOWNNAME
+*
+* rgmemid[] = array of DISPIDs corresponding to the given array of names
+*
+*Note:
+*
+* This routine depends on the PARAMDATA structure being declared in
+* the correct positional order - because the DISPID of a param name
+* is its one based positional index (textually). Unfortunately there
+* is no way to verify that this structure was declared properly by
+* the caller.
+*
+***********************************************************************/
+STDMETHODIMP
+CDispTypeInfo::GetIDsOfNames(
+ OLECHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ MEMBERID FAR* rgmemid)
+{
+ int cbName;
+ HRESULT hresult;
+ METHODDATA FAR* pmdata;
+ unsigned int iName, nName, cMembers, cArgs;
+
+ // REVIEW: do we really want to error on the following?
+ if(cNames == 0)
+ return RESULT(E_INVALIDARG);
+
+#ifdef _DEBUG
+ if(IsBadReadPtr(rgszNames, cNames * sizeof(OLECHAR FAR*)))
+ return RESULT(E_INVALIDARG);
+ for(iName = 0; iName < cNames; ++iName){
+ if(FIsBadStringPtr(rgszNames[iName], (unsigned int)-1))
+ return RESULT(E_INVALIDARG);
+ }
+ if(IsBadWritePtr(rgmemid, cNames * sizeof(DISPID)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ // Lookup the member name
+ cbName = STRLEN(rgszNames[0]);
+ cMembers = m_pidata->cMembers;
+ for(iName = 0;; ++iName){
+ if(iName == cMembers)
+ goto LMemberNotFound;
+ pmdata = &m_pidata->pmethdata[iName];
+ if(StrICmp(rgszNames[0], cbName, pmdata->szName, -1) == 0){
+ rgmemid[0] = pmdata->dispid;
+ break;
+ }
+ }
+
+ hresult = NOERROR;
+
+ if(cNames > 1){
+ // Lookup the named parameters.
+ cArgs = pmdata->cArgs;
+ for(iName = 1; iName < cNames; ++iName){
+
+ cbName = STRLEN(rgszNames[iName]);
+
+ for(nName = 0;; nName++) {
+
+ if(nName == cArgs) {
+ hresult = RESULT(DISP_E_UNKNOWNNAME);
+ rgmemid[iName] = -1;
+ break;
+ }
+
+ if(StrICmp(rgszNames[iName], cbName,
+ pmdata->ppdata[nName].szName, -1) == 0) {
+ // the named param ID is defined to be its zero based
+ // positional index.
+ //
+ // Note: this requires that the paramdata array be declared
+ // in positional order.
+ //
+ rgmemid[iName] = (DISPID) nName;
+ break;
+ }
+ }
+ }
+ }
+
+ return hresult;
+
+LMemberNotFound:;
+ // If we can't find the member name, then we can find the named
+ // params either, so everything is unknown.
+ MEMSET(rgmemid, 0xFF, cNames * sizeof(DISPID));
+
+ return RESULT(DISP_E_UNKNOWNNAME);
+}
+
+
+EXTERN_C INTERNAL_(HRESULT)
+IndexOfParam(
+ DISPPARAMS FAR* pdispparams,
+ unsigned int uPosition,
+ unsigned int FAR* puArgIndex);
+
+
+/***
+*PUBLIC HRESULT CDispTypeInfo::Invoke(...)
+*Purpose:
+* Implementation of ITypeInfo::Invoke
+*
+*Entry:
+* UNDONE
+* ...
+*
+*Exit:
+* return value = HRESULT
+* S_OK
+* E_INVALIDARG
+* E_OUTOFMEMORY
+* DISP_E_TYPEMISMATCH - could not coerce arg to expected type
+* DISP_E_PARAMNOTFOUND - could not locate the param in the DISPPARAMS
+*
+* *pvarResult = UNDONE
+* *pexcepinfo = UNDONE
+* *puArgErr = UNDONE
+*
+***********************************************************************/
+STDMETHODIMP
+CDispTypeInfo::Invoke(
+ void FAR* pvInstance,
+ MEMBERID memid,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pdispparams,
+ VARIANT FAR* pvarResult,
+ EXCEPINFO FAR* pexcepinfo,
+ unsigned int FAR* puArgErr)
+{
+ unsigned int uArgErr;
+ HRESULT hresult;
+ VARIANT varResultTmp;
+ METHODDATA FAR* pmdata;
+ INVOKEARGS FAR* pinvargs;
+
+ // the caller may be ignoring these... this simplifies the following code
+ //
+ V_VT(&varResultTmp) = VT_EMPTY;
+ if(pvarResult == NULL)
+ pvarResult = &varResultTmp;
+ if(puArgErr == NULL)
+ puArgErr = &uArgErr;
+
+#ifdef _DEBUG
+ if(IsBadReadPtr(pvInstance, sizeof(void FAR*)))
+ return RESULT(E_INVALIDARG);
+ if(IsBadDispParams(pdispparams))
+ return RESULT(E_INVALIDARG);
+ if(IsBadWritePtr(pvarResult, sizeof(*pvarResult)))
+ return RESULT(E_INVALIDARG);
+ if(IsBadWritePtr(puArgErr, sizeof(*puArgErr)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ if(!IsLegalInvokeFlags(wFlags))
+ return RESULT(E_INVALIDARG);
+
+ if(PmdataOfDispid(memid, wFlags, &pmdata) == NOERROR){
+
+ if(pdispparams->cArgs == pmdata->cArgs){
+
+ goto LInvokeStandard;
+
+ }else if(pdispparams->cArgs > pmdata->cArgs){
+
+ // handle possible indexed collection property access
+
+ if(IsPropGet(wFlags)){
+
+ if(IsPropGet(pmdata->wFlags) && pmdata->cArgs == 0)
+ goto LCollectionProperty;
+
+ }else if(IsPropPut(wFlags)){
+
+ if(IsPropPut(pmdata->wFlags) && pmdata->cArgs == 1){
+ if(PmdataOfPropGet(memid, &pmdata) == NOERROR && pmdata->cArgs == 0)
+ goto LCollectionProperty;
+ }
+ }
+
+ }else{ // pdispparams->cArgs < pmdata->cArgs
+
+ // handle possible optional arguments
+
+ // Note: DispTypeInfo doesnt support optional parameters
+
+ }
+
+ return RESULT(DISP_E_BADPARAMCOUNT);
+ }
+
+ // Member not found - but there is one more special case to check for.
+ //
+ // This may be an indexed collection PropertyPut where the collection
+ // property itself has only a get method.
+
+ if(IsPropPut(wFlags) &&
+ (GetScode(PmdataOfDispid(memid,
+ (wFlags == DISPATCH_PROPERTYPUT) ?
+ DISPATCH_PROPERTYPUTREF :
+ DISPATCH_PROPERTYPUT,
+ &pmdata)) == DISP_E_MEMBERNOTFOUND))
+ {
+ if(PmdataOfPropGet(memid, &pmdata) == NOERROR && pmdata->cArgs == 0)
+ goto LCollectionProperty;
+ }
+
+ return RESULT(DISP_E_MEMBERNOTFOUND);
+
+// standard method or property invocation
+//
+LInvokeStandard:;
+
+ IfFailGo(
+ GetInvokeArgs(pmdata, wFlags, pdispparams, &pinvargs, puArgErr),
+ LError0);
+
+ hresult = DoInvokeMethod(
+ pvInstance,
+ pmdata->iMeth * sizeof(void FAR*),
+ pmdata->cc,
+ pmdata->vtReturn,
+ pinvargs->cArgs,
+ pinvargs->rgvt,
+ pinvargs->rgpvarg,
+ pvarResult);
+
+ ReleaseInvokeArgs(pinvargs);
+
+ if(V_VT(&varResultTmp) != VT_EMPTY)
+ VariantClear(&varResultTmp);
+
+ return hresult;
+
+
+LCollectionProperty:;
+
+ VARIANT varTmp;
+
+ ASSERT(pmdata->cArgs == 0 && IsPropGet(pmdata->wFlags));
+
+ IfFailGo(
+ DoInvokeMethod(
+ pvInstance,
+ pmdata->iMeth * sizeof(void FAR*),
+ pmdata->cc,
+ pmdata->vtReturn,
+ 0, NULL, NULL, &varTmp),
+ LError0);
+
+ if ((V_VT(&varTmp) != VT_DISPATCH))
+ hresult = RESULT(DISP_E_NOTACOLLECTION);
+ else {
+ IDispatch FAR* pdisp;
+
+ pdisp = V_DISPATCH(&varTmp);
+ hresult = pdisp ?
+ pdisp->Invoke(DISPID_VALUE, IID_NULL,
+ m_lcid, wFlags, pdispparams,
+ pvarResult, pexcepinfo, puArgErr) :
+ RESULT(DISP_E_MEMBERNOTFOUND);
+ }
+
+ VariantClear(&varTmp);
+
+ if(V_VT(&varResultTmp) != VT_EMPTY)
+ VariantClear(&varResultTmp);
+
+ return hresult;
+
+
+LError0:;
+ return hresult;
+}
+
+
+/***
+*PRIVATE HRESULT CDispTypeInfo::AllocInvokeArgs
+*Purpose:
+* Allocate and initialize an INVOKEARGS structure
+*
+*Entry:
+* cArgs = the count of args to be held by the invokeargs struct
+*
+*Exit:
+* return value = HRESULT
+*
+* *ppinvargs = ptr to a newly allocated INVOKEARGS struct
+*
+* REVIEW: the following could be optimized by allocating a single block
+* for the whole deal - and then fixeing up the ptrs accordingly...
+*
+***********************************************************************/
+HRESULT
+CDispTypeInfo::AllocInvokeArgs(unsigned int cArgs, INVOKEARGS FAR* FAR* ppinvargs)
+{
+ INVOKEARGS FAR* pinvargs;
+
+ if((pinvargs = new FAR INVOKEARGS) == NULL)
+ goto LError0;
+ pinvargs->cArgs = cArgs;
+ if(cArgs == 0){
+ pinvargs->rgvarg = NULL;
+ pinvargs->rgpvarg = NULL;
+ pinvargs->rgvt = NULL;
+ }else{
+ if((pinvargs->rgvarg = new FAR VARIANTARG[cArgs]) == NULL)
+ goto LError1;
+ if((pinvargs->rgpvarg = new FAR VARIANTARG FAR*[cArgs]) == NULL)
+ goto LError2;
+ if((pinvargs->rgvt = new FAR VARTYPE[cArgs]) == NULL)
+ goto LError3;
+
+ for(unsigned int u = 0; u < cArgs; ++u)
+ V_VT(&pinvargs->rgvarg[u]) = VT_EMPTY;
+ }
+ *ppinvargs = pinvargs;
+ return NOERROR;
+
+LError3:;
+ delete pinvargs->rgpvarg;
+LError2:;
+ delete pinvargs->rgvarg;
+LError1:;
+ delete pinvargs;
+LError0:;
+ return RESULT(E_OUTOFMEMORY);
+}
+
+
+/***
+*PRIVATE HRESULT CDispTypeInfo::GetInvokeArgs
+*Purpose:
+* Gather all arguments (looking up by position or name), coerce
+* to the expected type (if possible) and build a linearized
+* positional array of pointers to those arguments.
+*
+* Note: this is a helper for ITypeInfo::Invoke implementations
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value = HRESULT
+*
+* *ppinvargs =
+* *puArgErr = if there was an error coercing an argument, this is the
+* index in the pdispparams->rgvarg array of the problem arg.
+*
+***********************************************************************/
+HRESULT
+CDispTypeInfo::GetInvokeArgs(
+ METHODDATA FAR* pmdata,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pdispparams,
+ INVOKEARGS FAR* FAR* ppinvargs,
+ unsigned int FAR* puArgErr)
+{
+ VARTYPE vt;
+ HRESULT hresult;
+ PARAMDATA FAR* ppdata;
+ unsigned int u, uArgIndex, cArgs;
+ INVOKEARGS FAR* pinvargs;
+ VARIANTARG FAR* pvarg, FAR* pvargSrc;
+
+ // DispTypeInfo doesnt support optional arguments of any kind...
+ ASSERT(pmdata->cArgs == pdispparams->cArgs);
+
+ IfFailRet(AllocInvokeArgs(pdispparams->cArgs, &pinvargs));
+
+ if((cArgs = pinvargs->cArgs) == 0)
+ goto LDone;
+
+ ppdata = pmdata->ppdata;
+
+ // Gather actuals based on expected argument type. Note that
+ // the interpretation of VARTYPE as an argument type is a bit
+ // different that its interpretation as a VARIANT type tag
+ // (see VT_VARIANT below).
+ //
+ for(u = 0; u < cArgs; ++u){
+
+ // locate the index of the param identified by position 'u'
+ // in the dispparams rgvarg array
+
+ // special case the handling of the rhs of a property put
+
+ if(u == (cArgs-1) && IsPropPut(wFlags)){
+
+ if (pdispparams->cNamedArgs == 0
+ || pdispparams->rgdispidNamedArgs[0] != DISPID_PROPERTYPUT)
+ {
+ hresult = RESULT(DISP_E_PARAMNOTOPTIONAL); // REVIEW: correct error?
+ goto LError0;
+ }
+
+ uArgIndex = 0;
+
+ }else{
+
+ IfFailGo(IndexOfParam(pdispparams, u, &uArgIndex), LError0);
+ }
+
+ pvargSrc = &pdispparams->rgvarg[uArgIndex];
+
+ // attempt to coerce the actual to the expected type
+
+ vt = pinvargs->rgvt[u] = ppdata[u].vt;
+
+ switch(vt){
+#if VBA2
+ case VT_UI1:
+#endif //VBA2
+ case VT_I2:
+ case VT_I4:
+ case VT_R4:
+ case VT_R8:
+ case VT_CY:
+ case VT_DATE:
+ case VT_BSTR:
+ case VT_ERROR:
+ case VT_BOOL:
+ case VT_UNKNOWN:
+ case VT_DISPATCH:
+ pvarg = &pinvargs->rgvarg[u];
+ hresult = VariantChangeType(pvarg, pvargSrc, 0, vt);
+ if(hresult != NOERROR){
+ *puArgErr = uArgIndex;
+ // If VariantChangeType returned a TypeMismatch, and the
+ // TypeMismatch was do to an attempt to pass an unsupplied
+ // optional param to a non variant argument, then translate
+ // the error to the more appropriate DISP_E_PARAMNOTOPTIONAL
+ //
+ // Remember: unsupplied optional params are passed by the
+ // client as VT_ERROR(DISP_E_PARAMNOTFOUND)
+ //
+ if(GetScode(hresult) == DISP_E_TYPEMISMATCH){
+ if (V_VT(pvargSrc) == VT_ERROR
+ && V_ERROR(pvargSrc) == DISP_E_PARAMNOTFOUND)
+ {
+ hresult = RESULT(DISP_E_PARAMNOTOPTIONAL);
+ }
+ }
+ goto LError0;
+ }
+ pinvargs->rgpvarg[u] = pvarg;
+ break;
+
+ // Note that VT_VARIANT is not a legal VARIANT type tag, but
+ // as an argument type, it means to simply pass the entire
+ // VARIANTARG to the member as-is.
+ //
+ case VT_VARIANT:
+ pinvargs->rgpvarg[u] = pvargSrc;
+ break;
+
+ default:
+ if(vt & (VT_BYREF | VT_ARRAY)){
+ // If the target argument is ByRef (or Array), then we
+ // require an exact match in type between formal and actual
+ // because we want the original copy to get updated, and
+ // we cant of course coerce the original in place (and we
+ // dont have rules for the coersion of an Array).
+ //
+ if(V_VT(pvargSrc) != vt){
+ hresult = RESULT(DISP_E_TYPEMISMATCH);
+ goto LError0;
+ }
+ pinvargs->rgpvarg[u] = pvargSrc;
+ break;
+ }
+
+ // Otherwise: unrecognized or unsupported member argument type.
+ // this means there is a problem with the given method description.
+ //
+ // REVIEW: probably need better error code
+ //
+ hresult = RESULT(E_INVALIDARG);
+ goto LError0;
+ }
+ }
+
+LDone:;
+ *ppinvargs = pinvargs;
+ return NOERROR;
+
+LError0:;
+ ReleaseInvokeArgs(pinvargs);
+ *ppinvargs = NULL;
+ return hresult;
+}
+
+
+void
+CDispTypeInfo::ReleaseInvokeArgs(INVOKEARGS FAR* pinvargs)
+{
+ if(pinvargs != NULL){
+ if(pinvargs->rgvarg != NULL){
+ for(unsigned int u = 0; u < pinvargs->cArgs; ++u)
+ VariantClear(&pinvargs->rgvarg[u]);
+ delete pinvargs->rgvarg;
+ }
+ if(pinvargs->rgpvarg != NULL)
+ delete pinvargs->rgpvarg;
+ if(pinvargs->rgvt != NULL)
+ delete pinvargs->rgvt;
+ delete pinvargs;
+ }
+}
+
+
+STDMETHODIMP
+CDispTypeInfo::GetDocumentation(
+ MEMBERID memid,
+ BSTR FAR* pbstrName,
+ BSTR FAR* pbstrDocString,
+ unsigned long FAR* pdwHelpContext,
+ BSTR FAR* pbstrHelpFile)
+{
+ HRESULT hresult;
+ unsigned short wFlags;
+ METHODDATA FAR* pmdata;
+
+#if 0
+ // REVIEW: add this if we decide to add an szName field to the
+ // INTERFACEDATA struct.
+
+ // get documentation of the TypeInfo itself
+ //
+ if(memid == DISPID_NONE){
+ if(pbstrName != NULL)
+ return ErrSysAllocString(m_pidata->szName, pbstrName);
+ }
+#endif
+
+ wFlags = DISPATCH_METHOD|DISPATCH_PROPERTYPUT|DISPATCH_PROPERTYPUTREF|DISPATCH_PROPERTYGET;
+ IfFailGo(PmdataOfDispid(memid, wFlags, &pmdata), LError0);
+
+ if(pbstrName != NULL){
+ IfFailGo(ErrSysAllocString(pmdata->szName, pbstrName), LError0);
+ }
+
+ // INTERFACEDATA does not supply the following info
+ //
+ *pbstrDocString = NULL;
+ *pdwHelpContext = 0L;
+ *pbstrHelpFile = NULL;
+
+ return NOERROR;
+
+LError0:;
+ return hresult;
+}
+
+
+STDMETHODIMP
+CDispTypeInfo::GetDllEntry(
+ MEMBERID memid,
+ INVOKEKIND invkind,
+ BSTR FAR* pbstrDllName,
+ BSTR FAR* pbstrName,
+ unsigned short FAR* pwOrdinal)
+{
+ UNUSED(memid);
+ UNUSED(invkind);
+ UNUSED(pbstrDllName);
+ UNUSED(pbstrName);
+ UNUSED(pwOrdinal);
+
+ return RESULT(E_NOTSUPPORTED);
+}
+
+
+STDMETHODIMP
+CDispTypeInfo::GetRefTypeInfo(
+ HREFTYPE hreftype,
+ ITypeInfo FAR* FAR* pptinfo)
+{
+ ITypeInfo FAR* ptinfo;
+
+ if(m_tkind != TKIND_COCLASS)
+ return RESULT(E_FAIL);
+
+ // INTERFACEDATA only describes a CoClass with a single reftype
+ if(hreftype != 0)
+ return RESULT(E_FAIL);
+
+ IfFailRet(
+ CDispTypeInfo::Create(TKIND_INTERFACE, m_pidata, m_lcid, &ptinfo));
+
+ *pptinfo = ptinfo;
+
+ return NOERROR;
+}
+
+STDMETHODIMP
+CDispTypeInfo::AddressOfMember(
+ MEMBERID memid,
+ INVOKEKIND invkind,
+ void FAR* FAR* ppv)
+{
+ UNUSED(memid);
+ UNUSED(invkind);
+ UNUSED(ppv);
+
+ return RESULT(E_NOTSUPPORTED);
+}
+
+STDMETHODIMP
+CDispTypeInfo::CreateInstance(
+ IUnknown FAR* punkOuter,
+ REFIID riid,
+ void FAR* FAR* ppv)
+{
+ UNUSED(ppv);
+
+ return RESULT(E_NOTSUPPORTED);
+}
+
+STDMETHODIMP
+CDispTypeInfo::GetMops(
+ MEMBERID memid,
+ BSTR FAR* pbstrMops)
+{
+ UNUSED(memid);
+ UNUSED(pbstrMops);
+
+ return RESULT(E_NOTSUPPORTED);
+}
+
+STDMETHODIMP
+CDispTypeInfo::GetContainingTypeLib(
+ ITypeLib FAR* FAR* pptlib,
+ unsigned int FAR* pindex)
+{
+ UNUSED(pptlib);
+ UNUSED(pindex);
+
+ return RESULT(E_NOTSUPPORTED);
+}
+
+STDMETHODIMP_(void)
+CDispTypeInfo::ReleaseTypeAttr(TYPEATTR FAR* ptattr)
+{
+ delete ptattr;
+}
+
+STDMETHODIMP_(void)
+CDispTypeInfo::ReleaseFuncDesc(FUNCDESC FAR* pfuncdesc)
+{
+ delete pfuncdesc->lprgelemdescParam;
+ delete pfuncdesc;
+}
+
+STDMETHODIMP_(void)
+CDispTypeInfo::ReleaseVarDesc(VARDESC FAR* pvardesc)
+{
+ UNUSED(pvardesc);
+
+#ifdef _DEBUG
+ // an INTERFACEDATA driven typeinfo never returns a
+ // VARDESC (because it cannot describe variables), so
+ // we should never try to free one.
+ //
+ ASSERT(UNREACHED);
+#endif
+}
+
+
+//---------------------------------------------------------------------
+// utilities
+//---------------------------------------------------------------------
+
+
+#if 0
+/***
+*PRIVATE HRESULT PmdataOfImeth(INTERFACEDATA*, unsigned int, METHODDATA**)
+*Purpose:
+* Return the METHODDATA that corresponds to the method with the
+* given method index (iMeth).
+*
+*Entry:
+* pidata = the INTERFACEDATA to do the lookup on
+* iMeth = the method index
+*
+*Exit:
+* return value = HRESULT
+* S_OK
+* DISP_E_MEMBERNOTFOUND
+*
+* *ppmdata = the method data of the given index
+*
+***********************************************************************/
+HRESULT
+PmdataOfImeth(
+ INTERFACEDATA FAR* pidata,
+ unsigned int iMeth,
+ METHODDATA FAR* FAR* ppmdata)
+{
+ METHODDATA FAR* pmdata, FAR* pmdataEnd;
+
+
+ pmdata = pidata->pmethdata;
+ pmdataEnd = &pmdata[pidata->cMembers];
+ for(; pmdata < pmdataEnd; ++pmdata){
+ if(pmdata->iMeth == iMeth){
+ *ppmdata = pmdata;
+ return NOERROR;
+ }
+ }
+ return RESULT(DISP_E_MEMBERNOTFOUND);
+}
+
+#endif
+
+/***
+*PRIVATE HRESULT CDispTypeInfo::PmdataOfDispid
+*Purpose:
+* Return the METHODDATA that corresponds to the given memberid
+* and invoke flags.
+*
+*Entry:
+* memid = the method id
+*
+*Exit:
+* return value = HRESULT
+* S_OK
+* DISP_E_MEMBERNOTFOUND
+*
+* *ppmdata = the method data of the given member id
+*
+***********************************************************************/
+HRESULT
+CDispTypeInfo::PmdataOfDispid(
+ MEMBERID memid,
+ unsigned short wFlags,
+ METHODDATA FAR* FAR* ppmdata)
+{
+ METHODDATA FAR* pmdata, FAR* pmdataEnd;
+
+ pmdata = m_pidata->pmethdata;
+ pmdataEnd = &pmdata[m_pidata->cMembers];
+ for(; pmdata < pmdataEnd; ++pmdata){
+ if(pmdata->dispid == (DISPID)memid && (pmdata->wFlags & wFlags) != 0){
+ *ppmdata = pmdata;
+ return NOERROR;
+ }
+ }
+ return RESULT(DISP_E_MEMBERNOTFOUND);
+}
diff --git a/private/oleauto/src/dispatch/cdispti.h b/private/oleauto/src/dispatch/cdispti.h
new file mode 100644
index 000000000..e0903a731
--- /dev/null
+++ b/private/oleauto/src/dispatch/cdispti.h
@@ -0,0 +1,111 @@
+/***
+*cdispti.h
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Definition of CDispTypeInfo.
+*
+*
+*Revision History:
+*
+* [00] 19-Nov-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+class CDispTypeInfo : public ITypeInfo {
+public:
+ static HRESULT Create(CDispTypeInfo FAR* FAR* pptinfo);
+
+
+ // IUnknown methods
+ //
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+
+ // ITypeInfo methods
+ //
+ STDMETHOD(GetTypeAttr)(TYPEATTR FAR* FAR* pptattr);
+
+ STDMETHOD(GetTypeComp)(ITypeComp FAR* FAR* pptcomp);
+
+ STDMETHOD(GetFuncDesc)(unsigned int index, FUNCDESC FAR* FAR* ppfuncdesc);
+
+ STDMETHOD(GetVarDesc)(unsigned int index, VARDESC FAR* FAR* ppvardesc);
+
+ STDMETHOD(GetNames)(
+ MEMBERID memid,
+ BSTR FAR* rgbstrNames,
+ unsigned int cMaxNames,
+ unsigned int FAR* pcNames);
+
+ STDMETHOD(GetRefTypeOfImplType)(
+ unsigned int index,
+ HREFTYPE FAR* phreftype);
+
+ STDMETHOD(GetImplTypeFlags)(
+ unsigned int index,
+ int FAR* pimpltypeflags);
+
+ STDMETHOD(GetIDsOfNames)(
+ OLECHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ MEMBERID FAR* rgmemid);
+
+ STDMETHOD(Invoke)(
+ void FAR* pvInstance,
+ MEMBERID memid,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pdispparams,
+ VARIANT FAR* pvarResult,
+ EXCEPINFO FAR* pexcepinfo,
+ unsigned int FAR* puArgErr);
+
+ STDMETHOD(GetDocumentation)(
+ MEMBERID memid,
+ BSTR FAR* pbstrName,
+ BSTR FAR* pbstrDocString,
+ unsigned long FAR* pdwHelpContext,
+ BSTR FAR* pbstrHelpFile);
+
+ STDMETHOD(GetDllEntry)(
+ MEMBERID memid,
+ INVOKEKIND invkind,
+ BSTR FAR* pbstrDllName,
+ BSTR FAR* pbstrName,
+ unsigned short FAR* pwOrdinal);
+
+ STDMETHOD(GetRefTypeInfo)(
+ HREFTYPE hreftype, ITypeInfo FAR* FAR* pptinfo);
+
+ STDMETHOD(AddressOfMember)(
+ MEMBERID memid, INVOKEKIND invkind, void FAR* FAR* ppv);
+
+ STDMETHOD(CreateInstance)(IUnknown FAR* punkOuter,
+ REFIID riid,
+ void FAR* FAR* ppv);
+
+ STDMETHOD(GetMops)(MEMBERID memid, BSTR FAR* pbstrMops);
+
+ STDMETHOD(GetContainingTypeLib)(
+ ITypeLib FAR* FAR* pptlib, unsigned int FAR* pindex);
+
+ STDMETHOD_(void, ReleaseTypeAttr)(TYPEATTR FAR* ptattr);
+ STDMETHOD_(void, ReleaseFuncDesc)(FUNCDESC FAR* pfuncdesc);
+ STDMETHOD_(void, ReleaseVarDesc)(VARDESC FAR* pvardesc);
+
+ CDispTypeInfo();
+
+ LCID m_lcid;
+
+ INTERFACEDATA FAR* m_pidata;
+
+private:
+
+ unsigned long m_refs;
+};
diff --git a/private/oleauto/src/dispatch/clsid.c b/private/oleauto/src/dispatch/clsid.c
new file mode 100644
index 000000000..7d2fea73d
--- /dev/null
+++ b/private/oleauto/src/dispatch/clsid.c
@@ -0,0 +1,54 @@
+/***
+*clsid.c
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file allocates and initializes the CLSIDs.
+*
+*****************************************************************************/
+
+#ifdef _MAC
+# ifdef _MSC_VER
+# include <macos/types.h>
+# include <macos/packages.h>
+# include <macos/resource.h>
+# include <macos/menus.h>
+# include <macos/windows.h>
+# include <macos/osutils.h>
+# include <macos/appleeve.h>
+# define far
+# define FAR far
+# define near
+# define NEAR near
+# ifndef _PPCMAC
+# define pascal _pascal
+# endif
+# define PASCAL pascal
+# define cdecl _cdecl
+# define CDECL cdecl
+# else
+# include <types.h>
+# include <packages.h>
+# include <resources.h>
+# include <menus.h>
+# include <windows.h>
+# include <appleevents.h>
+# include <osutils.h>
+# include <AppleEvents.h>
+# endif
+#else
+# include <windows.h>
+#endif
+#include <ole2.h>
+
+// this redefines the Ole DEFINE_GUID() macro to do allocation.
+//
+#include <initguid.h>
+
+// due to the previous header, including this causes the DEFINE_GUID
+// definitions in the following header(s) to actually allocate data.
+//
+#include "clsid.h"
+
diff --git a/private/oleauto/src/dispatch/clsid.h b/private/oleauto/src/dispatch/clsid.h
new file mode 100644
index 000000000..2cd71d998
--- /dev/null
+++ b/private/oleauto/src/dispatch/clsid.h
@@ -0,0 +1,28 @@
+/***
+*clsid.h
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file defines the CLSIDs
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#if defined(WIN32) && 0
+DEFINE_OLEGUID(CLSID_PSDispatch, 0x00020400, 0, 0);
+DEFINE_OLEGUID(CLSID_PSEnumVARIANT, 0x00020404, 0, 0);
+DEFINE_OLEGUID(CLSID_PSTypeInfo, 0x00020401, 0, 0);
+DEFINE_OLEGUID(CLSID_PSTypeLib, 0x00020402, 0, 0);
+#else
+DEFINE_OLEGUID(CLSID_PSDispatch, 0x00020420, 0, 0);
+DEFINE_OLEGUID(CLSID_PSEnumVARIANT, 0x00020421, 0, 0);
+DEFINE_OLEGUID(CLSID_PSTypeInfo, 0x00020422, 0, 0);
+DEFINE_OLEGUID(CLSID_PSTypeLib, 0x00020423, 0, 0);
+#endif
+
+DEFINE_OLEGUID(CLSID_PSAutomation, 0x00020424, 0, 0);
+DEFINE_OLEGUID(CLSID_PSTypeComp, 0x00020425, 0, 0);
+
diff --git a/private/oleauto/src/dispatch/convert.cpp b/private/oleauto/src/dispatch/convert.cpp
new file mode 100644
index 000000000..df899762a
--- /dev/null
+++ b/private/oleauto/src/dispatch/convert.cpp
@@ -0,0 +1,2939 @@
+/***
+*convert.cpp
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This module contains the low level VARTYPE coersion API.
+*
+*
+*Revision History:
+*
+* [00] 17-May-93 tomteng: from VBA oleconv.c
+* [01] 27-Jun-93 bassams: Enable LCID-based to/from string conversions.
+* recognize currency and various negative formats
+* in VarCyFromStr.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#if OE_WIN32
+#include "oautil.h"
+#endif // OE_WIN32
+
+#include <stdio.h>
+#include <math.h>
+#include <float.h>
+#include <ctype.h>
+#if !OE_MAC || HC_MPW
+// something in the wings errno.h is conflicting with stdlib.h
+#include <errno.h>
+#endif
+#include <stdlib.h>
+
+ASSERTDATA
+
+#ifndef EZERO
+# define EZERO 0
+#endif
+
+
+#if _X86_ || OE_WIN16
+
+typedef struct {
+ BYTE lo:4;
+ BYTE hi:4;
+} DIGARY[10];
+
+typedef struct {
+ ULONG mantLo;
+ ULONG mantHi:19;
+ ULONG mantMSB:1;
+ ULONG exp:11;
+ ULONG sign:1;
+} DBLSTRUCT;
+
+OLECHAR pstrInf[] = OASTR("INF");
+OLECHAR pstrInd[] = OASTR("IND");
+OLECHAR pstrNan[] = OASTR("NAN");
+
+#endif // _X86_ || OE_WIN16
+
+
+// The following are supplied by $(TARG)\oleconva.$(A)
+
+extern "C" {
+
+// Note: the floating point IN params on the following utilities are
+// passed byref, because mpw and wings pass floating point values
+// differently byval, and we need to interface these asm routines
+// with both compilers.
+
+INTERNAL_(HRESULT) ErrCyFromI2(short sIn, CY FAR* pcyOut);
+INTERNAL_(HRESULT) ErrCyFromI4(long lIn, CY FAR* pcyOut);
+INTERNAL_(HRESULT) ErrCyFromR4(float FAR* pfltIn, CY FAR* pcyOut);
+INTERNAL_(HRESULT) ErrCyFromR8(double FAR* pdlbIn, CY FAR* pcyOut);
+INTERNAL_(HRESULT) ErrI2FromCy(CY cyIn, short FAR* psOut);
+INTERNAL_(HRESULT) ErrI4FromCy(CY cyIn, long FAR* plOut);
+INTERNAL_(HRESULT) ErrR4FromCy(CY cyIn, float FAR* pfltOut);
+INTERNAL_(HRESULT) ErrR8FromCy(CY cyIn, double FAR* pdblOut);
+INTERNAL_(HRESULT) ErrMultCyI4(CY cyIn, long lIn, CY FAR* pcyOut);
+
+#if OE_WIN16 || _X86_
+int PASCAL ConvFloatToAscii(double dblIn, DIGARY NEAR *pdigOut);
+
+// WARNING: Do not call this on Win16 if there is no math coprocessor
+// WARNING: present - the win87em.dll emulator does not implement
+// WARNING: fbstp. The FP stack will remain unchanged and the destination
+// WARNING: address is not written to. VBA #3514 (Win32 emulator is OK)
+void NEAR PASCAL DoFbstp(CY NEAR *pcyIn, DIGARY NEAR *pdigOut);
+#endif
+
+}
+
+OLECHAR CurrencyFromLcid(LCID lcid, unsigned long dwFlags);
+OLECHAR DecimalFromLcid(LCID lcid, unsigned long dwFlags);
+OLECHAR ThousandFromLcid(LCID lcid, unsigned long dwFlags);
+INTERNAL_(HRESULT) StripThousandSeparator(OLECHAR FAR* strIn,
+ OLECHAR FAR* strOut, LCID lcid, long dwFlags);
+
+PRIVATE_(long)
+ConvI4FromR8(double FAR* pdblVal);
+
+PRIVATE_(HRESULT)
+StrToCy(OLECHAR FAR*, OLECHAR FAR* FAR*, int, CY FAR*, LCID, unsigned long dwFlags);
+
+PRIVATE_(long)
+StrToLong(OLECHAR FAR* pchInput, OLECHAR FAR* FAR* ppchAfter);
+
+PRIVATE_(unsigned long)
+StrToOct(OLECHAR FAR* pchIn, OLECHAR FAR* FAR* ppchAfter);
+
+PRIVATE_(unsigned long)
+StrToHex(OLECHAR FAR* pchIn, OLECHAR FAR* FAR* ppchAfter);
+
+PRIVATE_(long)
+HexOctStrToLong(OLECHAR FAR* pchInput, OLECHAR FAR* FAR* ppchAfter);
+
+PRIVATE_(void)
+EditStrFromReal(OLECHAR FAR* pchBuffer, int cDigits, LCID lcid, unsigned long dwFlags);
+
+PRIVATE_(int)
+FMakePosCy(CY FAR* pcyValue);
+
+PRIVATE_(void)
+NegCyNoOflo(CY FAR* pcyInput);
+
+PRIVATE_(int)
+FixNegativeCyStr(OLECHAR FAR* pInput, OLECHAR cDecimal, int FAR* fReturnNegative);
+
+PRIVATE_(int)
+fStripCurrency (OLECHAR FAR* FAR* ppch, OLECHAR FAR* FAR* ppchLast, OLECHAR FAR* cySymbol);
+
+PRIVATE_(int)
+fParseEnd (OLECHAR FAR* FAR* ppchLast, OLECHAR FAR* sz, OLECHAR FAR* lpchFirst);
+
+PRIVATE_(int)
+fParseBegin (OLECHAR FAR* FAR* ppch, OLECHAR FAR* sz, OLECHAR FAR* lpchLast);
+
+PRIVATE_(HRESULT)
+GetDispProperty(
+ IDispatch FAR* pdisp,
+ LCID lcid,
+ VARTYPE vt,
+ VARIANT FAR* pvarResult);
+
+extern "C" {
+
+INTERNAL_(HRESULT)
+DispAlloc(size_t cb, void FAR* FAR* ppv)
+{
+ void FAR* pv;
+ HRESULT hresult;
+ IMalloc FAR* pmalloc;
+
+ IfFailRet(GetMalloc(&pmalloc));
+
+ hresult = NOERROR;
+ if((pv = (void FAR*)pmalloc->Alloc(cb)) == NULL)
+ hresult = ResultFromScode(E_OUTOFMEMORY);
+
+ *ppv = pv;
+
+ return hresult;
+}
+
+INTERNAL_(void)
+DispFree(void FAR* pv)
+{
+ IMalloc FAR* pmalloc;
+
+ if(pv == NULL)
+ return;
+
+ if(GetMalloc(&pmalloc) == NOERROR) {
+ pmalloc->Free(pv);
+ }
+}
+
+};
+
+
+#if VBA2
+STDAPI
+VarBoolFromUI1(unsigned char bIn, VARIANT_BOOL FAR* pboolOut)
+{
+ *pboolOut = (bIn != 0) ? -1 : 0;
+ return NOERROR;
+}
+#endif //VBA2
+
+STDAPI
+VarBoolFromI2(short sIn, VARIANT_BOOL FAR* pboolOut)
+{
+ *pboolOut = (sIn != 0) ? -1 : 0;
+ return NOERROR;
+}
+
+STDAPI
+VarBoolFromI4(long lIn, VARIANT_BOOL FAR* pboolOut)
+{
+ *pboolOut = (lIn != 0L) ? -1 : 0;
+ return NOERROR;
+}
+
+STDAPI
+VarBoolFromR4(
+ float fltIn,
+ VARIANT_BOOL FAR* pboolOut)
+{
+ *pboolOut = (fltIn != 0.0) ? -1 : 0;
+ return NOERROR;
+}
+
+STDAPI
+VarBoolFromR8(double dblIn, VARIANT_BOOL FAR* pboolOut)
+{
+ *pboolOut = (dblIn != 0.0) ? -1 : 0;
+ return NOERROR;
+}
+
+STDAPI
+VarBoolFromDate(DATE dateIn, VARIANT_BOOL FAR* pboolOut)
+{
+ return VarBoolFromR8(dateIn, pboolOut);
+}
+
+STDAPI
+VarBoolFromCy(CY cyIn, VARIANT_BOOL FAR* pboolOut)
+{
+ *pboolOut = ((cyIn.Hi | cyIn.Lo) != 0) ? -1 : 0;
+ return NOERROR;
+}
+
+STDAPI
+VarBoolFromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, VARIANT_BOOL FAR* pboolOut)
+{
+ unsigned int cbLength;
+ double dblVal;
+ HRESULT hresult;
+ OLECHAR FAR* lpStr = strIn;
+
+ ASSERT(dwFlags == 0 || dwFlags == LOCALE_NOUSEROVERRIDE);
+
+ hresult = NOERROR;
+
+ cbLength = STRLEN(strIn);
+
+ if(cbLength == 0)
+ return RESULT(DISP_E_TYPEMISMATCH);
+
+#ifdef FE_DBCS
+ if(IsDBCS(lcid)) {
+ IfFailRet(MapHalfWidth(lcid, strIn, &lpStr));
+ }
+#endif
+
+ if((STRCMP(lpStr, OASTR("#FALSE#")) == 0 &&
+ cbLength == SIZEOFSTRING(OASTR("#FALSE#"))) ||
+ (STRICMP(lpStr, OASTR("FALSE")) == 0 &&
+ cbLength == SIZEOFSTRING(OASTR("FALSE"))))
+ *pboolOut = 0;
+ else if((STRCMP(lpStr, OASTR("#TRUE#")) == 0 &&
+ cbLength == SIZEOFSTRING(OASTR("#TRUE#"))) ||
+ (STRICMP(lpStr, OASTR("TRUE")) == 0 &&
+ cbLength == SIZEOFSTRING(OASTR("TRUE"))))
+ *pboolOut = -1;
+
+ else if((hresult = VarR8FromStr(lpStr, lcid, dwFlags, &dblVal)) == NOERROR)
+ *pboolOut = (short)(dblVal != 0.0) ? -1 : 0;
+
+#ifdef FE_DBCS
+ if(IsDBCS(lcid)) {
+ DispFree(lpStr);
+ }
+#endif
+
+ return hresult;
+}
+
+STDAPI
+VarBoolFromDisp(IDispatch FAR* pdispIn, LCID lcid, VARIANT_BOOL FAR* pboolOut)
+{
+ VARIANT varTmp;
+ HRESULT hresult;
+
+ hresult = GetDispProperty(pdispIn, lcid, VT_BOOL, &varTmp);
+ if (hresult == NOERROR)
+ *pboolOut = V_BOOL(&varTmp);
+ return hresult;
+}
+
+
+#if VBA2
+STDAPI
+VarUI1FromI2(short sIn, unsigned char FAR* pbOut)
+{
+ if((unsigned short)sIn <= 255L){
+ *pbOut = (unsigned char)sIn;
+ return NOERROR;
+ }
+ return RESULT(DISP_E_OVERFLOW);
+}
+
+STDAPI
+VarUI1FromI4(long lIn, unsigned char FAR* pbOut)
+{
+ if((unsigned long)lIn <= 255L){
+ *pbOut = (unsigned char)lIn;
+ return NOERROR;
+ }
+ return RESULT(DISP_E_OVERFLOW);
+}
+
+STDAPI
+VarUI1FromR4(
+ float fltIn,
+ unsigned char FAR* pbOut)
+{
+ double dblIn = (double) fltIn;
+ return VarUI1FromR8(dblIn, pbOut);
+}
+
+
+STDAPI
+VarUI1FromR8(double dblIn, unsigned char FAR* pbOut)
+{
+ if(dblIn >= -0.5 && dblIn < 255.5){
+ *pbOut = (unsigned char)ConvI4FromR8(&dblIn);
+ return NOERROR;
+ }
+ return RESULT(DISP_E_OVERFLOW);
+}
+
+STDAPI
+VarUI1FromCy(CY cyIn, unsigned char FAR* pbOut)
+{
+ short sVal;
+ HRESULT hresult;
+
+ hresult = ErrI2FromCy(cyIn, &sVal);
+ if (hresult == NOERROR) {
+ hresult = VarUI1FromI2(sVal, pbOut);
+ }
+ return hresult;
+}
+
+STDAPI
+VarUI1FromDate(DATE dateIn, unsigned char FAR* pbOut)
+{
+ return VarUI1FromR8(dateIn, pbOut);
+}
+
+STDAPI
+VarUI1FromBool(VARIANT_BOOL boolIn, unsigned char FAR* pbOut)
+{
+ *pbOut = (unsigned char)boolIn; // UNDONE: correct???
+ return NOERROR;
+}
+
+STDAPI
+VarUI1FromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, unsigned char FAR* pbOut)
+{
+ short sVal;
+ HRESULT hresult;
+
+ hresult = VarI2FromStr(strIn, lcid, dwFlags, &sVal);
+ if (hresult == NOERROR) {
+ hresult = VarUI1FromI2(sVal, pbOut);
+ }
+ return hresult;
+}
+
+STDAPI
+VarUI1FromDisp(IDispatch FAR* pdispIn, LCID lcid, unsigned char FAR* pbOut)
+{
+ VARIANT varTmp;
+ HRESULT hresult;
+
+ hresult = GetDispProperty(pdispIn, lcid, VT_UI1, &varTmp);
+ if (hresult == NOERROR)
+ *pbOut = V_UI1(&varTmp);
+ return hresult;
+}
+#endif //VBA2
+
+#if VBA2
+STDAPI
+VarI2FromUI1(unsigned char bIn, short FAR* psOut)
+{
+ *psOut = (short)(unsigned short)bIn;
+ return NOERROR;
+}
+#endif //VBA2
+
+STDAPI
+VarI2FromI4(long lIn, short FAR* psOut)
+{
+ if(lIn >= -32768L && lIn <= 32767L){
+ *psOut = (short)lIn;
+ return NOERROR;
+ }
+ return RESULT(DISP_E_OVERFLOW);
+}
+
+STDAPI
+VarI2FromR4(
+ float fltIn,
+ short FAR* psOut)
+{
+ double dblIn = (double) fltIn;
+ return VarI2FromR8(dblIn, psOut);
+}
+
+
+STDAPI
+VarI2FromR8(double dblIn, short FAR* psOut)
+{
+ if(dblIn >= -32768.5 && dblIn < 32767.5){
+ *psOut = (short)ConvI4FromR8(&dblIn);
+ return NOERROR;
+ }
+ return RESULT(DISP_E_OVERFLOW);
+}
+
+STDAPI
+VarI2FromCy(CY cyIn, short FAR* psOut)
+{
+ return ErrI2FromCy(cyIn, psOut);
+}
+
+STDAPI
+VarI2FromDate(DATE dateIn, short FAR* psOut)
+{
+ return VarI2FromR8(dateIn, psOut);
+}
+
+STDAPI
+VarI2FromBool(VARIANT_BOOL boolIn, short FAR* psOut)
+{
+ *psOut = boolIn;
+ return NOERROR;
+}
+
+STDAPI
+VarI2FromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, short FAR* psOut)
+{
+ long lVal;
+ HRESULT hresult;
+ OLECHAR FAR* pchStart;
+ OLECHAR FAR* lpStr;
+
+ ASSERT(dwFlags == 0 || dwFlags == LOCALE_NOUSEROVERRIDE);
+
+ if(strIn == NULL)
+ return RESULT(DISP_E_TYPEMISMATCH);
+
+#ifdef FE_DBCS
+ if(IsDBCS(lcid)) {
+ IfFailRet(MapHalfWidth(lcid, strIn, &lpStr));
+ pchStart = lpStr;
+ } else
+ pchStart = lpStr = strIn;
+#else
+ pchStart = lpStr = strIn;
+#endif
+
+ // if not null, point pchStart to the first nonblank character
+ while(isspace(*pchStart))
+ pchStart++;
+
+ if((hresult = VarI4FromStr(strIn, lcid, dwFlags, &lVal)) == NOERROR){
+
+ // do special sign-extending for octal/hex value
+ if(*pchStart == OASTR('&') && lVal >= 0x8000L && lVal <= 0xffffL)
+ lVal |= 0xffff0000L;
+
+ hresult = VarI2FromI4(lVal, psOut);
+ }
+
+#ifdef FE_DBCS
+ if(IsDBCS(lcid)) {
+ DispFree(lpStr);
+ }
+#endif
+
+ return hresult;
+}
+
+STDAPI
+VarI2FromDisp(IDispatch FAR* pdispIn, LCID lcid, short FAR* psOut)
+{
+ VARIANT varTmp;
+ HRESULT hresult;
+
+ hresult = GetDispProperty(pdispIn, lcid, VT_I2, &varTmp);
+ if (hresult == NOERROR)
+ *psOut = V_I2(&varTmp);
+ return hresult;
+}
+
+#if VBA2
+STDAPI
+VarI4FromUI1(unsigned char bIn, long FAR* plOut)
+{
+ *plOut = (long)(unsigned long)bIn;
+ return NOERROR;
+}
+#endif //VBA2
+
+STDAPI
+VarI4FromI2(short sIn, long FAR* plOut)
+{
+ *plOut = (long)sIn;
+ return NOERROR;
+}
+
+STDAPI
+VarI4FromBool(VARIANT_BOOL boolIn, long FAR* plOut)
+{
+ return VarI4FromI2(boolIn, plOut);
+}
+
+STDAPI
+VarI4FromR4(
+ float fltIn,
+ long FAR* plOut)
+{
+ return VarI4FromR8((double)fltIn, plOut);
+}
+
+STDAPI
+VarI4FromR8(double dblIn, long FAR* plOut)
+{
+ if(dblIn >= -2147483648.5 && dblIn < 2147483647.5){
+ *plOut = ConvI4FromR8(&dblIn);
+ return NOERROR;
+ }
+ return RESULT(DISP_E_OVERFLOW);
+}
+
+STDAPI
+VarI4FromCy(CY cyIn, long FAR* plOut)
+{
+ return ErrI4FromCy(cyIn, plOut);
+}
+
+STDAPI
+VarI4FromDate(DATE dateIn, long FAR* plOut)
+{
+ return VarI4FromR8(dateIn, plOut);
+}
+
+STDAPI
+VarI4FromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, long FAR* plOut)
+{
+ long lVal;
+ unsigned int cbLen;
+ double dblVal;
+ HRESULT hresult;
+ OLECHAR FAR* pchStart;
+ OLECHAR FAR* pchAfter;
+ OLECHAR FAR* lpStr;
+
+ ASSERT(dwFlags == 0 || dwFlags == LOCALE_NOUSEROVERRIDE);
+
+ if (strIn == NULL)
+ return RESULT(DISP_E_TYPEMISMATCH);
+
+#ifdef FE_DBCS
+ if(IsDBCS(lcid)) {
+ IfFailRet(MapHalfWidth(lcid, strIn, &lpStr));
+ pchStart = lpStr;
+ } else
+ pchStart = lpStr = strIn;
+#else
+ pchStart = lpStr = strIn;
+#endif
+
+ while (isspace(*pchStart))
+ pchStart++;
+
+ if (*pchStart == OASTR('\0')) {
+ hresult = RESULT(DISP_E_TYPEMISMATCH);
+ goto LError0;
+ }
+
+ errno = EZERO;
+
+ if (*pchStart == OASTR('&'))
+ lVal = HexOctStrToLong(pchStart, &pchAfter);
+ else
+ lVal = StrToLong(pchStart, &pchAfter);
+
+ while (isspace(*pchAfter))
+ pchAfter++;
+
+ cbLen = STRLEN(lpStr);
+
+ if (pchAfter == (lpStr + cbLen) && errno == EZERO)
+ hresult = NOERROR;
+
+ else if ((hresult = VarR8FromStr(strIn, lcid, dwFlags, &dblVal)) == NOERROR)
+ hresult = VarI4FromR8(dblVal, &lVal);
+
+ // assign the return value if the coersion was successful
+ if(hresult == NOERROR)
+ *plOut = lVal;
+
+
+LError0:
+
+#ifdef FE_DBCS
+ if(IsDBCS(lcid)) {
+ DispFree(lpStr);
+ }
+#endif
+
+ return hresult;
+}
+
+STDAPI
+VarI4FromDisp(IDispatch FAR* pdispIn, LCID lcid, long FAR* plOut)
+{
+ VARIANT varTmp;
+ HRESULT hresult;
+
+ hresult = GetDispProperty(pdispIn, lcid, VT_I4, &varTmp);
+ if (hresult == NOERROR)
+ *plOut = V_I4(&varTmp);
+ return hresult;
+}
+
+PRIVATE_(long)
+ConvI4FromR8(double FAR* pdblVal)
+{
+ long lResult;
+ double dblInt, dblFrac;
+
+ // split double value into integer and fractional parts
+
+ dblFrac = modf(*pdblVal, &dblInt);
+
+
+ // convert the integer part to a long value
+ //[barrybo] WARNING: the caller must ensure that the R8 to I4 conversion
+ // will not overflow the I4. If it does, the Win16
+ // compiler doesn't call FWAIT after the _aFftol call
+ // so the exception won't be raised until the next
+ // FWAIT, which may not be for a very long time.
+ // Ole2Disp isn't supposed to raise exceptions, so
+ // it is a bug if a subsequent FWAIT causes an exception.
+ lResult = (long)dblInt;
+
+ // round to the nearer integer, if at midpoint,
+ // towards the integer with the LSB zero
+
+ if (dblFrac > 0.5 || (dblFrac == 0.5 && (lResult & 1)))
+ lResult++;
+
+ else if (dblFrac < -0.5 || (dblFrac == -0.5 && (lResult & 1)))
+ lResult--;
+
+ return lResult;
+}
+
+#if VBA2
+STDAPI
+VarR4FromUI1(unsigned char bIn, float FAR* pfltOut)
+{
+ *pfltOut = (float)bIn;
+ return NOERROR;
+}
+#endif //VBA2
+
+STDAPI
+VarR4FromI2(short sIn, float FAR* pfltOut)
+{
+ *pfltOut = (float)sIn;
+ return NOERROR;
+}
+
+STDAPI
+VarR4FromBool(VARIANT_BOOL boolIn, float FAR* pfltOut)
+{
+ return VarR4FromI2(boolIn, pfltOut);
+}
+
+STDAPI
+VarR4FromI4(long lIn, float FAR* pfltOut)
+{
+ *pfltOut = (float)lIn;
+ return NOERROR;
+}
+
+STDAPI
+VarR4FromR8(double dblIn, float FAR* pfltOut)
+{
+ if(dblIn > -3.402823466e+38 && dblIn < 3.402823466e+38){
+ *pfltOut = (float)dblIn;
+ return NOERROR;
+ }
+ return RESULT(DISP_E_OVERFLOW);
+}
+
+STDAPI
+VarR4FromCy(CY cyIn, float FAR* pfltOut)
+{
+ return ErrR4FromCy(cyIn, pfltOut);
+}
+
+STDAPI
+VarR4FromDate(DATE dateIn, float FAR* pfltOut)
+{
+ return VarR4FromR8(dateIn, pfltOut);
+}
+
+STDAPI
+VarR4FromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, float FAR* pfltOut)
+{
+ double dblVal;
+ HRESULT hresult;
+
+ ASSERT(dwFlags == 0 || dwFlags == LOCALE_NOUSEROVERRIDE);
+
+ if((hresult = VarR8FromStr(strIn, lcid, dwFlags, &dblVal)) == NOERROR)
+ hresult = VarR4FromR8(dblVal, pfltOut);
+ return hresult;
+}
+
+STDAPI
+VarR4FromDisp(IDispatch FAR* pdispIn, LCID lcid, float FAR* pfltOut)
+{
+ VARIANT varTmp;
+ HRESULT hresult;
+
+ hresult = GetDispProperty(pdispIn, lcid, VT_R4, &varTmp);
+ if (hresult == NOERROR)
+ *pfltOut = V_R4(&varTmp);
+ return hresult;
+}
+
+
+#if VBA2
+STDAPI
+VarR8FromUI1(unsigned char bIn, double FAR* pdblOut)
+{
+ *pdblOut = (double)bIn;
+ return NOERROR;
+}
+
+#endif //VBA2
+
+STDAPI
+VarR8FromI2(short sIn, double FAR* pdblOut)
+{
+ *pdblOut = (double)sIn;
+ return NOERROR;
+}
+
+STDAPI
+VarR8FromBool(VARIANT_BOOL boolIn, double FAR* pdblOut)
+{
+ return VarR8FromI2(boolIn, pdblOut);
+}
+
+STDAPI
+VarR8FromI4(long lIn, double FAR* pdblOut)
+{
+ *pdblOut = (double)lIn;
+ return NOERROR;
+}
+
+STDAPI
+VarR8FromR4(
+ float fltIn,
+ double FAR* pdblOut)
+{
+ *pdblOut = (double)fltIn;
+ return NOERROR;
+}
+
+STDAPI
+VarR8FromCy(CY cyIn, double FAR* pdblOut)
+{
+ return ErrR8FromCy(cyIn, pdblOut);
+}
+
+STDAPI
+VarR8FromDate(DATE dateIn, double FAR* pdblOut)
+{
+ *pdblOut = dateIn;
+ return NOERROR;
+}
+
+STDAPI
+VarR8FromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, double FAR* pdblOut)
+{
+ int count;
+ unsigned int cbLen;
+ double dblVal;
+ OLECHAR FAR* pchStart;
+ OLECHAR FAR* pchAfter;
+ OLECHAR FAR* pchTemp;
+ OLECHAR FAR* pchSave = NULL;
+ OLECHAR chSave;
+ OLECHAR chDecimal;
+ OLECHAR FAR* buf;
+ OLECHAR FAR* lpStr;
+ HRESULT hresult;
+
+ ASSERT(dwFlags == 0 || dwFlags == LOCALE_NOUSEROVERRIDE);
+
+ count = 0;
+
+ if (strIn == NULL)
+ return RESULT(DISP_E_TYPEMISMATCH);
+
+#ifdef FE_DBCS
+ if(IsDBCS(lcid)) {
+ IfFailRet(MapHalfWidth(lcid, strIn, &lpStr));
+ pchStart = lpStr;
+ } else
+ pchStart = lpStr = strIn;
+#else
+ pchStart = lpStr = strIn;
+#endif
+
+ while (isspace(*pchStart))
+ pchStart++;
+
+ if (*pchStart == OASTR('\0')) {
+ hresult = RESULT(DISP_E_TYPEMISMATCH);
+ goto LError0;
+ }
+
+ errno = EZERO;
+
+ IfFailRet(DispAlloc(BYTELEN(pchStart), (void FAR* FAR*)&buf));
+
+ if(*pchStart == OASTR('&')){
+
+ dblVal = (double)HexOctStrToLong(pchStart, &pchAfter);
+
+ }else{
+
+ // strip off all currency (thousand) separator
+ // before being process by strtod
+ IfFailGo(StripThousandSeparator(pchStart, buf, lcid, dwFlags), LError);
+
+ // unfortunetly, the C-runtime is not locale-aware, so we
+ // have to replace the locale decimal with a '.'.
+ // If the locale decimal is not a period and the string does
+ // contain a period '.', then replace the '.' in the buffer
+ // by the locale decimal so it does not get recognized by strtod.
+ // Save the original char and the location and restore after
+ // doing the conversion.
+
+ pchTemp = pchStart = buf;
+ chDecimal = DecimalFromLcid(lcid, dwFlags);
+ while(*pchTemp) {
+ if (*pchTemp == OASTR('.') && chDecimal != OASTR('.')) {
+ pchSave = pchTemp;
+ chSave = *pchTemp;
+ *pchTemp = chDecimal;
+ break;
+ } else if (*pchTemp == chDecimal) {
+ pchSave = pchTemp;
+ chSave = *pchTemp;
+ *pchTemp = OASTR('.');
+ break;
+ }
+ pchTemp++;
+ }
+
+ dblVal = disp_strtod(pchStart, &pchAfter);
+
+ // Restore the decimal point
+ if (pchSave)
+ *pchSave = chSave;
+
+ // ignore underflow error
+ if (errno == ERANGE && dblVal == 0.0)
+ errno = EZERO;
+ }
+
+ while(isspace(*pchAfter))
+ pchAfter++;
+
+ cbLen = STRLEN(pchStart);
+
+ if(pchAfter == (pchStart + cbLen) && errno == EZERO){
+ *pdblOut = dblVal;
+ hresult = NOERROR;
+ }
+ else
+ hresult = RESULT(DISP_E_TYPEMISMATCH);
+
+LError:
+ DispFree(buf);
+
+LError0:
+
+#ifdef FE_DBCS
+ if(IsDBCS(lcid)) {
+ DispFree(lpStr);
+ }
+#endif
+
+ return hresult;
+}
+
+STDAPI
+VarR8FromDisp(IDispatch FAR* pdispIn, LCID lcid, double FAR* pdblOut)
+{
+ VARIANT varTmp;
+ HRESULT hresult;
+
+ hresult = GetDispProperty(pdispIn, lcid, VT_R8, &varTmp);
+ if (hresult == NOERROR)
+ *pdblOut = V_R8(&varTmp);
+ return hresult;
+}
+
+#if VBA2
+STDAPI
+VarDateFromUI1(unsigned char bIn, DATE FAR* pdateOut)
+{
+ return VarDateFromI2((short)(unsigned short)bIn, pdateOut);
+}
+#endif //VBA2
+
+STDAPI
+VarDateFromI2(short sIn, DATE FAR* pdateOut)
+{
+ HRESULT hresult;
+
+ hresult = IsValidDate((DATE) sIn);
+ if (hresult == NOERROR)
+ *pdateOut = (DATE) sIn;
+ return hresult;
+}
+
+STDAPI
+VarDateFromBool(VARIANT_BOOL boolIn, DATE FAR* pdateOut)
+{
+ return VarDateFromI2(boolIn, pdateOut);
+}
+
+STDAPI
+VarDateFromI4(long lIn, DATE FAR* pdateOut)
+{
+ HRESULT hresult;
+
+ hresult = IsValidDate((DATE) lIn);
+ if (hresult == NOERROR)
+ *pdateOut = (DATE) lIn;
+ return hresult;
+}
+
+STDAPI
+VarDateFromR4(
+ float fltIn,
+ DATE FAR* pdateOut)
+{
+
+ HRESULT hresult;
+
+ hresult = IsValidDate((DATE) fltIn);
+ if (hresult == NOERROR)
+ *pdateOut = (DATE) fltIn;
+ return hresult;
+}
+
+STDAPI
+VarDateFromR8(double dblIn, DATE FAR* pdateOut)
+{
+ HRESULT hresult;
+
+ hresult = IsValidDate((DATE) dblIn);
+ if (hresult == NOERROR)
+ *pdateOut = (DATE) dblIn;
+ return hresult;
+}
+
+STDAPI
+VarDateFromCy(CY cyIn, DATE FAR* pdateOut)
+{
+ double r8;
+ HRESULT hresult;
+
+ VarR8FromCy(cyIn, &r8);
+ hresult = IsValidDate((DATE) r8);
+ if (hresult == NOERROR)
+ *pdateOut = (DATE) r8;
+ return hresult;
+}
+
+INTERNAL_(HRESULT)
+IsValidDate(DATE date)
+{
+ UDS uds;
+ VARIANT var;
+
+ V_VT(&var) = VT_DATE;
+ V_DATE(&var) = date;
+ return ErrUnpackDate(&uds, &var);
+}
+
+STDAPI
+VarDateFromDisp(IDispatch FAR* pdispIn, LCID lcid, DATE FAR* pdateOut)
+{
+ VARIANT varTmp;
+ HRESULT hresult;
+
+ hresult = GetDispProperty(pdispIn, lcid, VT_DATE, &varTmp);
+ if (hresult == NOERROR)
+ *pdateOut = V_DATE(&varTmp);
+ return hresult;
+}
+
+#if VBA2
+STDAPI
+VarCyFromUI1(unsigned char bIn, CY FAR* pcyOut)
+{
+ return ErrCyFromI2((short)(unsigned short)bIn, pcyOut);
+}
+#endif //VBA2
+
+STDAPI
+VarCyFromI2(short sIn, CY FAR* pcyOut)
+{
+ return ErrCyFromI2(sIn, pcyOut);
+}
+
+STDAPI
+VarCyFromI4(long lIn, CY FAR* pcyOut)
+{
+ return ErrCyFromI4(lIn, pcyOut);
+}
+
+STDAPI
+VarCyFromR4(
+ float fltIn,
+ CY FAR* pcyOut)
+{
+ return ErrCyFromR4(&fltIn, pcyOut);
+}
+
+STDAPI
+VarCyFromR8(double dlbIn, CY FAR* pcyOut)
+{
+ return ErrCyFromR8(&dlbIn, pcyOut);
+}
+
+STDAPI
+VarCyFromDate(DATE dateIn, CY FAR* pcyOut)
+{
+ return VarCyFromR8(dateIn, pcyOut);
+}
+
+STDAPI
+VarCyFromBool(VARIANT_BOOL boolIn, CY FAR* pcyOut)
+{
+ return VarCyFromI2(boolIn, pcyOut);
+}
+
+
+STDAPI
+VarCyFromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, CY FAR* pcyOut)
+{
+ CY cyTemp;
+ BSTR bstr;
+ long lTemp;
+ HRESULT hresult;
+ unsigned int cbLen;
+ OLECHAR FAR* pch;
+ OLECHAR FAR* pchAfter;
+ OLECHAR rgchCySym[10];
+ int fNegative;
+ OLECHAR FAR *buf;
+
+ ASSERT(dwFlags == 0 || dwFlags == LOCALE_NOUSEROVERRIDE);
+
+
+#ifdef FE_DBCS
+ if(IsDBCS(lcid)) {
+ IfFailRet(MapHalfWidth(lcid, strIn, &buf));
+ } else {
+ IfFailRet(DispAlloc(BYTELEN(strIn), (void FAR* FAR*)&buf));
+ STRCPY(buf, strIn);
+ }
+#else
+ IfFailRet(DispAlloc(BYTELEN(strIn), (void FAR* FAR*)&buf));
+ STRCPY(buf, strIn);
+#endif
+
+ IfFailGo(StripThousandSeparator(buf, buf, lcid, dwFlags), LError0);
+
+ IfFailGo(ErrSysAllocString(buf, &bstr), LError0);
+
+ pch = (OLECHAR FAR*)bstr;
+
+ // first, determine if this is a negative number (of all formats)
+ // and if so, strip negative indicator ('-', or '()')
+
+ if(!FixNegativeCyStr(pch, DecimalFromLcid(lcid, dwFlags), &fNegative)){
+ hresult = RESULT(DISP_E_TYPEMISMATCH); // bad format.
+ goto LRet;
+ }
+
+ // read past leading spaces
+
+ while(*pch == OASTR(' '))
+ pch++;
+
+ // remove currency symbol
+
+ pchAfter = pch + STRLEN(pch) - 1;
+
+ while (*pchAfter == OASTR(' '))
+ pchAfter--;
+
+ if(GetLocaleInfo(lcid, LOCALE_SCURRENCY | dwFlags, rgchCySym, SIZEOFCH(rgchCySym)) <= 0){
+ rgchCySym[0] = OASTR('$');
+ rgchCySym[1] = OASTR('\0');
+ }
+
+ // convert both the initial string and the currency to lower case
+ // so that the comparison for currency is not case sensitive.
+ // do a locale-aware case mapping in place.
+
+ { int len = STRLEN(pch);
+ LCMapString(lcid, LCMAP_LOWERCASE, pch, len, pch, len);
+ }
+
+ { int len = STRLEN(rgchCySym);
+ LCMapString(lcid, LCMAP_LOWERCASE, rgchCySym, len, rgchCySym, len);
+ }
+
+ if(fStripCurrency(&pch, &pchAfter, rgchCySym)) {
+ *(pchAfter + 1) = OASTR('\0'); // terminate new string.
+ }
+
+ // read past any remaining spaces
+ while(*pch == OASTR(' '))
+ pch++;
+
+#if 0
+ STRCPY(bstr, pch);
+ pch = bstr;
+#endif
+
+ // test for hex or octal constant
+
+ if(*pch == OASTR('&')) {
+ hresult = VarI4FromStr(pch, lcid, dwFlags, &lTemp);
+ if (hresult == NOERROR)
+ hresult = VarCyFromI4(lTemp, pcyOut);
+ goto LRet;
+ }
+
+ // convert string to currency value
+
+ errno = EZERO;
+
+ hresult = StrToCy(pch, &pchAfter, FALSE, &cyTemp, lcid, dwFlags);
+ if(hresult != NOERROR)
+ goto LRet;
+
+ if(errno == ERANGE){
+ hresult = RESULT(DISP_E_OVERFLOW);
+ goto LRet;
+ }
+
+ // skip over any trailing spaces and test for end of BSTR
+
+ while (*pchAfter++ == OASTR(' '));
+
+ cbLen = STRLEN(pch);
+ if (pchAfter != (OLECHAR FAR*)pch + cbLen + 1){
+ hresult = RESULT(DISP_E_TYPEMISMATCH);
+ goto LRet;
+ }
+
+ // assign value and return
+
+ pcyOut->Hi = cyTemp.Hi;
+ pcyOut->Lo = cyTemp.Lo;
+
+ if(fNegative)
+ NegCyNoOflo(pcyOut);
+
+ hresult = NOERROR;
+
+LRet:;
+ DispFree(buf);
+ SysFreeString(bstr);
+ return hresult;
+
+LError0:;
+ DispFree(buf);
+ return hresult;
+
+}
+
+STDAPI
+VarCyFromDisp(IDispatch FAR* pdispIn, LCID lcid, CY FAR* pcyOut)
+{
+ VARIANT varTmp;
+ HRESULT hresult;
+
+ hresult = GetDispProperty(pdispIn, lcid, VT_CY, &varTmp);
+ if (hresult == NOERROR)
+ *pcyOut = V_CY(&varTmp);
+ return hresult;
+}
+
+OLECHAR
+CurrencyFromLcid(LCID lcid, unsigned long dwFlags)
+{
+ OLECHAR szBuff[2];
+
+ if (GetLocaleInfo(lcid,
+ LOCALE_SCURRENCY | dwFlags,
+ szBuff,
+ SIZEOFCH(szBuff)) <= 0)
+ return OASTR('$');
+ else
+ return szBuff[0];
+}
+
+OLECHAR
+DecimalFromLcid(LCID lcid, unsigned long dwFlags)
+{
+ OLECHAR szBuff[2];
+
+ if (GetLocaleInfo(lcid, LOCALE_SDECIMAL | dwFlags, szBuff, SIZEOFCH(szBuff)) <= 0)
+ return OASTR('.');
+ else
+ return szBuff[0];
+}
+
+#ifdef FE_DBCS
+EXTERN_C
+INTERNAL_(HRESULT)
+MapHalfWidth(LCID lcid, OLECHAR FAR* strIn, OLECHAR FAR* FAR* ppv)
+{
+ size_t cb;
+
+ *ppv = NULL;
+ cb = BYTELEN(strIn);
+
+ IfFailRet(DispAlloc(cb, (void FAR* FAR*) ppv));
+
+ // Map any full-pitch chars to half-pitch
+ if (LCMapString(lcid, LCMAP_HALFWIDTH,
+ strIn, -1,
+ *ppv, cb) == 0) {
+ DispFree(*ppv);
+ return RESULT(DISP_E_TYPEMISMATCH);
+ }
+ return NOERROR;
+}
+#endif
+
+
+
+OLECHAR
+ThousandFromLcid(LCID lcid, unsigned long dwFlags)
+{
+ OLECHAR szBuff[2];
+
+ if (GetLocaleInfo(lcid, LOCALE_STHOUSAND | dwFlags,
+ szBuff, SIZEOFCH(szBuff)) <= 0)
+ return OASTR(',');
+ else
+ return szBuff[0];
+}
+
+
+
+INTERNAL_(HRESULT)
+StripThousandSeparator(OLECHAR FAR* strIn, OLECHAR FAR* strOut, LCID lcid, long dwFlags)
+{
+ int loc;
+ OLECHAR chThousand;
+ int fNBSpace = 0;
+
+// UNDONE: On the MAC, the following 2 locales have a different
+// non-breaking space code:
+// Arabic 0x81
+// Thai 0xA0
+
+#if OE_MAC
+ static unsigned char chNBSpace = (unsigned char) 0xCA;
+#else /* !OE_MAC */
+ static unsigned char chNBSpace = (unsigned char) 0xA0;
+#endif /* OE_MAC */
+
+ loc = 0;
+ chThousand = ThousandFromLcid(lcid, dwFlags);
+ if (chThousand == OASTR(' ') || chThousand == chNBSpace)
+ fNBSpace = 1;
+
+ // strip off all currency (thousand) separator
+ while (*strIn) {
+ if (fNBSpace && *strIn != chThousand && *strIn != chNBSpace)
+ strOut[loc++] = *strIn;
+ else if (*strIn != chThousand)
+ strOut[loc++] = *strIn;
+ strIn++;
+ }
+ strOut[loc] = NULL;
+
+ if (strOut[0] == 0)
+ // error: string only contained thousands sep.
+ return RESULT(DISP_E_TYPEMISMATCH);
+
+ return NOERROR;
+}
+
+
+// Mpw errors (!) on inline routines containing 'vector' temps
+#ifndef HC_MPW
+inline
+#endif
+int
+LeadingZeroForDecimalFromLcid(LCID lcid, unsigned long dwFlags)
+{
+ char szBuff[2];
+
+ GetLocaleInfoA(lcid, LOCALE_ILZERO | dwFlags, szBuff, SIZEOFCH(szBuff));
+ return (szBuff[0] == OASTR('0')) ? 0 : 1;
+}
+
+
+/***
+* FMakePosCy - make a positive currency value and return sign
+* Purpose:
+* Return the positive value of the input currency value and a
+* flag with the sign of the original value.
+*
+* Entry:
+* pcyValue - pointer to currency input value
+*
+* Exit:
+* pcyValue - pointer to positive currency value
+* returns: FALSE if positive, TRUE if negative
+*
+* Exceptions:
+*
+* Note:
+* A maximum negative value input is returned unchanged, but
+* treated as an unsigned value by the calling routines.
+*
+***********************************************************************/
+
+PRIVATE_(int)
+FMakePosCy(CY FAR* pcy)
+{
+ int fNegative;
+
+ fNegative = FALSE;
+ if(pcy->Hi < 0){
+ pcy->Hi = ~pcy->Hi;
+ if((pcy->Lo = (unsigned long)(-(long)pcy->Lo)) == 0)
+ pcy->Hi++;
+ fNegative = TRUE;
+ }
+ return fNegative;
+}
+
+/***
+* UnpackCy - separate currency value into four two-byte integers
+* Purpose:
+* Unpack the currency value input into the lower half of the
+* specified pointer to an array of unsigned longs. The array
+* goes from least- to most-significant values.
+*
+* Entry:
+* pcy - pointer to currency input value
+*
+* Exit:
+* plValues - pointer to start of unsigned long array
+*
+* Exceptions:
+*
+***********************************************************************/
+
+PRIVATE_(void)
+UnpackCy(CY FAR* pcy, unsigned long FAR* plValues)
+{
+ *plValues++ = pcy->Lo & 0xffff;
+ *plValues++ = pcy->Lo >> 16;
+ *plValues++ = (unsigned long)pcy->Hi & 0xffff;
+ *plValues = (unsigned long)pcy->Hi >> 16;
+}
+
+// pcyInput = -pcyInput
+//
+PRIVATE_(void)
+NegCyNoOflo(CY FAR* pcyInput)
+{
+ CY cyResult;
+
+ cyResult.Hi = ~pcyInput->Hi;
+ cyResult.Lo = (unsigned long)(-(long)pcyInput->Lo);
+
+ if (cyResult.Lo == 0)
+ cyResult.Hi++;
+
+ *pcyInput = cyResult;
+}
+
+// pcyInput1 += pcyInput2
+//
+PRIVATE_(void)
+AddCyNoOflo(CY FAR* pcyInput1, CY FAR* pcyInput2)
+{
+ CY cySum;
+
+ // add high and low parts separately
+
+ cySum.Hi = pcyInput1->Hi + pcyInput2->Hi;
+ cySum.Lo = pcyInput1->Lo + pcyInput2->Lo;
+
+ // test for carry out of the low part and propagate to
+ // the high part
+
+ if(cySum.Lo < pcyInput2->Lo)
+ cySum.Hi++;
+
+ pcyInput1->Lo = cySum.Lo;
+ pcyInput1->Hi = cySum.Hi;
+}
+
+#if VBA2
+STDAPI
+VarBstrFromUI1(unsigned char bVal, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut)
+{
+ return VarBstrFromI2((short)(unsigned short)bVal, lcid, dwFlags, pbstrOut);
+}
+#endif //VBA2
+
+STDAPI
+VarBstrFromI2(short iVal, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut)
+{
+ OLECHAR buffer[40];
+ OLECHAR FAR* pchBuffer;
+
+ // integers have no decimals, and thus they are locale-unaware.
+ // lcid remains unused
+
+ UNUSED(lcid);
+ UNUSED(dwFlags);
+
+ pchBuffer = buffer;
+
+ disp_itoa((int)iVal, pchBuffer, 10);
+
+ return ErrSysAllocString(buffer, pbstrOut);
+}
+
+STDAPI
+VarBstrFromBool(VARIANT_BOOL boolIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut)
+{
+ OLECHAR buffer[40];
+
+ UNUSED(lcid);
+ UNUSED(dwFlags);
+
+ STRCPY(buffer, boolIn ? OASTR("True") : OASTR("False"));
+ return ErrSysAllocString(buffer, pbstrOut);
+}
+
+STDAPI
+VarBstrFromI4(long lIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut)
+{
+ OLECHAR buffer[40];
+ OLECHAR FAR* pchBuffer = buffer;
+
+ UNUSED(lcid);
+ UNUSED(dwFlags);
+
+ // longs have no decimals, and thus they are locale-unaware.
+ // lcid remains unused
+
+ disp_ltoa(lIn, pchBuffer, 10);
+
+ return ErrSysAllocString(buffer, pbstrOut);
+}
+
+
+// if on Win32, or real Win16 (not WOW), include this code
+#if (OE_WIN16 && !defined(WOW)) || _X86_
+
+HRESULT BstrFromFloat(double dblIn, LCID lcid, DWORD dwFlags,
+ BSTR FAR* pbstrOut, int cDigits)
+{
+ OLECHAR buffer[40];
+ DIGARY digits;
+ int i;
+ int power;
+ int iCur;
+ BOOL fZero;
+ OLECHAR *pstr;
+
+ ASSERT(dwFlags == 0 || dwFlags == LOCALE_NOUSEROVERRIDE);
+
+ if ( ((DBLSTRUCT *)&dblIn)->exp == 0x7FF ) // Is exponent max value?
+ {
+ // Have infinity or NAN
+ //
+ buffer[1] = '1';
+ buffer[2] = DecimalFromLcid(lcid, dwFlags);
+ buffer[3] = '#';
+ iCur = 4;
+
+ if ( ((DBLSTRUCT *)&dblIn)->mantLo == 0 && ((DBLSTRUCT *)&dblIn)->mantHi == 0 )
+ {
+ if ( ((DBLSTRUCT *)&dblIn)->mantMSB == 0 ) // Infinity?
+ {
+ pstr = pstrInf;
+ goto CopyName;
+ }
+ else if ( ((DBLSTRUCT *)&dblIn)->sign == 1 ) // Indefinite?
+ {
+ pstr = pstrInd;
+ goto CopyName;
+ }
+ }
+ // Have a NAN.
+ //
+ buffer[4] = ((DBLSTRUCT *)&dblIn)->mantMSB ? 'Q' : 'S';
+ iCur = 5;
+ pstr = pstrNan;
+
+CopyName:
+ buffer[iCur++] = *pstr++;
+ buffer[iCur++] = *pstr++;
+ buffer[iCur] = *pstr;
+ }
+ else
+ {
+ if (dblIn == 0.0)
+ return ErrSysAllocStringLen(OASTR("0"), 1, pbstrOut);
+
+#if OE_WIN16
+ ASSERT(g_fbstpImplemented);
+#endif //OE_WIN16
+ power = ConvFloatToAscii(dblIn, (DIGARY NEAR *)&digits) + 17;
+
+ iCur = 1; // leave room for sign
+
+ // Check for leading zero. Never more than one.
+ //
+ if (digits[8].hi == 0)
+ {
+ power--;
+ iCur--; // leading zero will be overwritten by sign
+ ASSERT(digits[8].lo != 0)
+ }
+
+ for (i = 8; i >= 0; i--)
+ {
+ // Extract each pair of digits.
+ //
+ buffer[iCur++] = '0' + digits[i].hi;
+ buffer[iCur++] = '0' + digits[i].lo;
+
+ } //for
+
+ // Round to the number of digits requested and strip trailing zeros.
+ //
+ iCur = cDigits + 1;
+
+ if ( buffer[iCur--] >= '5' ) // need to round up?
+ {
+ while (buffer[iCur] == '9')
+ iCur--; // it's now a trailing zero, just strip it off
+ buffer[iCur]++;
+ if (iCur == 0) // we had all 9's
+ {
+ buffer[1] = '1';
+ iCur = 1;
+ power++;
+ }
+ }
+ else
+ {
+ while (buffer[iCur] == '0')
+ iCur--; // strip off trailing zeros
+ }
+
+ // Now we know where we stand:
+ // power = power of 10 of leading digit (power to use if E notation).
+ // iCur = index of last digit = no. of digits
+ //
+ // Check for scientific notation.
+ //
+ if (power >= cDigits || iCur - power > cDigits + 1)
+ {
+ // Format scientific notation
+ //
+ if (iCur > 1) // Need to make room for decimal point
+ {
+ for (i = iCur; i >= 2; i--)
+ buffer[i+1] = buffer[i];
+ buffer[2] = DecimalFromLcid(lcid, dwFlags);
+ iCur++; // include decimal in count
+ }
+
+ buffer[++iCur] = 'E';
+ if (power < 0)
+ {
+ buffer[++iCur] = '-';
+ power = -power;
+ }
+ else
+ buffer[++iCur] = '+';
+
+ if (power >= 100)
+ {
+ buffer[++iCur] = power / 100 + '0';
+ power = power % 100;
+ }
+
+ buffer[++iCur] = power / 10 + '0';
+ buffer[++iCur] = power % 10 + '0';
+ }
+ else
+ {
+ // Fixed-point notation
+ //
+ while (iCur <= power) // Need trailing zeros
+ buffer[++iCur] = '0';
+
+ if (iCur > power + 1) // Need decimal point
+ {
+ if (power <= -1)
+ {
+ // Make room for leading zero, decimal point, and zeros following it
+ //
+ if ( fZero = LeadingZeroForDecimalFromLcid(lcid, dwFlags) )
+ power--;
+
+ for (i = iCur; i >= 1; i--)
+ buffer[i-power] = buffer[i];
+
+ iCur -= power;
+ i = 1;
+ if (fZero)
+ {
+ buffer[1] = '0';
+ i = 2;
+ }
+ buffer[i++] = DecimalFromLcid(lcid, dwFlags);
+ for ( ; i < 1-power; i++)
+ buffer[i] = '0';
+ }
+ else
+ {
+ for (i = iCur; i > power+1; i--)
+ buffer[i+1] = buffer[i];
+ buffer[power+2] = DecimalFromLcid(lcid, dwFlags);
+ iCur++; // include decimal in count
+ }
+ }
+ }
+ } // else exponent == max value
+
+ // Check sign
+ //
+ buffer[0] = '-'; // just in case
+ i = 1; // return index if positive
+ if ( ((DBLSTRUCT *)&dblIn)->sign == 1 ) // negative?
+ {
+ iCur++; // one more char
+ i = 0; // include '-' sign
+ }
+
+ return ErrSysAllocStringLen( &buffer[i], iCur, pbstrOut );
+
+}
+#endif // OE_WIN16 || _X86_
+
+
+STDAPI
+VarBstrFromR4(
+ float fltIn,
+ LCID lcid,
+ unsigned long dwFlags,
+ BSTR FAR* pbstrOut)
+{
+#if _X86_
+
+ return BstrFromFloat((double)fltIn, lcid, dwFlags, pbstrOut, 7);
+
+#else
+#if OE_WIN16 && !defined(WOW)
+ if (g_fbstpImplemented)
+ return BstrFromFloat((double)fltIn, lcid, dwFlags, pbstrOut, 7);
+#endif //OE_WIN16
+
+ OLECHAR buffer[40];
+
+ ASSERT(dwFlags == 0 || dwFlags == LOCALE_NOUSEROVERRIDE);
+
+ disp_gcvt((double)fltIn, 7, buffer, 40);
+
+ // process the string to the BASIC format
+ EditStrFromReal(buffer, 7, lcid, dwFlags);
+
+ return ErrSysAllocString(buffer, pbstrOut);
+
+#endif
+}
+
+STDAPI
+VarBstrFromR8(double dblIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut)
+{
+#if _X86_
+
+ return BstrFromFloat(dblIn, lcid, dwFlags, pbstrOut, 15);
+
+#else
+#if OE_WIN16 && !defined(WOW)
+ if (g_fbstpImplemented)
+ return BstrFromFloat(dblIn, lcid, dwFlags, pbstrOut, 15);
+#endif //OE_WIN16
+
+ OLECHAR buffer[40];
+
+ ASSERT(dwFlags == 0 || dwFlags == LOCALE_NOUSEROVERRIDE);
+
+ disp_gcvt(dblIn, 15, buffer, 40);
+
+ // process the string to the BASIC format
+ EditStrFromReal(buffer, 15, lcid, dwFlags);
+
+ return ErrSysAllocString(buffer, pbstrOut);
+
+#endif
+}
+
+
+STDAPI
+VarBstrFromCy(CY cyIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut)
+{
+ OLECHAR buffer[40];
+
+#if _X86_ || (OE_WIN16 && !defined(WOW))
+
+#if OE_WIN16
+ if (g_fbstpImplemented) {
+#endif //OE_WIN16
+
+ OLECHAR hi,lo;
+ int i;
+ int iCur;
+ DIGARY digits;
+
+ if ((cyIn.Hi | cyIn.Lo) == 0)
+ return ErrSysAllocStringLen(OASTR("0"), 1, pbstrOut);
+
+ // Execute the x87 FBSTP instruction. This assembly-language
+ // routine actually extends the instruction to handle a 19th
+ // digit.
+ //
+ DoFbstp( (CY NEAR *)&cyIn, (DIGARY NEAR *)&digits );
+
+ iCur = 1;
+ lo = digits[9].lo;
+ if (lo != 0)
+ {
+ buffer[1] = '0' + lo;
+ iCur = 2;
+ }
+
+ for (i = 8; i >= 2; i--)
+ {
+ // Extract each pair of digits. Strip off leading zeros.
+ //
+ hi = digits[i].hi;
+ lo = digits[i].lo;
+
+ if (iCur == 1) // still scanning leading zeros?
+ if (hi == 0)
+ {
+ if (lo != 0)
+ goto LoDigit;
+ continue;
+ }
+ buffer[iCur++] = '0' + hi;
+LoDigit:
+ buffer[iCur++] = '0' + lo;
+
+ } //for
+
+ // Last 4 digits remain.
+ //
+ if ( *((WORD *)digits) != 0 ) // Low 4 digits non-zero?
+ {
+ // See if we need leading zero before decimal point
+ //
+ if (iCur == 1 && LeadingZeroForDecimalFromLcid(lcid, dwFlags) )
+ {
+ buffer[1] = '0';
+ iCur = 2;
+ }
+
+ buffer[iCur++] = DecimalFromLcid(lcid, dwFlags);
+ buffer[iCur++] = '0' + digits[1].hi;
+
+ if ( (*(WORD *)digits & 0xFFF) != 0 ) // Low 3 digits non-zero?
+ {
+ buffer[iCur++] = '0' + digits[1].lo;
+
+ if ( *(BYTE *)digits != 0 ) // Low 2 digits non-zero?
+ {
+ buffer[iCur++] = '0' + digits[0].hi;
+
+ if ( digits[0].lo != 0 ) // Low digit non-zero?
+ buffer[iCur++] = '0' + digits[0].lo;
+ }
+ }
+ }
+
+ // Check sign
+ //
+ buffer[0] = '-'; // just in case
+ i = 1; // return index if positive
+ if (digits[9].hi & 8) // negative?
+ {
+ iCur++; // one more char
+ i = 0; // include '-' sign
+ }
+
+ return ErrSysAllocStringLen( &buffer[i], iCur-1, pbstrOut );
+
+#if OE_WIN16
+ } // if g_fbstpImplemented
+#endif //OE_WIN16
+
+
+#endif // _X86_ || (OE_WIN16 && !defined(WOW))
+
+
+#if !_X86_
+
+ OLECHAR * pchBuffer = buffer;
+
+#define CYSTRMAX 32
+
+ int index;
+ int grpValue;
+ int indResult;
+ int fNegative;
+ int fNzQuotient;
+ OLECHAR chResult[CYSTRMAX];
+ unsigned long input[4];
+
+ ASSERT(dwFlags == 0 || dwFlags == LOCALE_NOUSEROVERRIDE);
+
+ // if value is negative, set flag and negate
+ // (max. negative value 0x80...0 works since it inverts to itself)
+
+ fNegative = FMakePosCy(&cyIn);
+
+ // split number into four short values
+
+ UnpackCy(&cyIn, input);
+
+ // string will be built from right to left
+ // index to the end of the string (null-to-be)
+
+ indResult = CYSTRMAX - 1;
+
+ // outer loop to divide input array by 10000 repeatedly
+
+ do {
+ // flag is set if any quotient is nonzero to stop dividing
+
+ fNzQuotient = FALSE;
+
+ // divide the value in input by 10000, with the remainder
+ // in grpValue
+
+ for (index = 3; index > 0; index--) {
+
+ input[index - 1] |= (input[index] % 10000) << 16;
+ if ((input[index] /= 10000) != 0)
+ fNzQuotient = TRUE;
+ }
+
+ grpValue = (int)(input[index] % 10000);
+ if ((input[0] /= 10000) != 0)
+ fNzQuotient = TRUE;
+
+ // inner loop divides grpValue by 10 repeatedly to get digits
+
+ for (index = 0; index < 4; index++) {
+ chResult[--indResult] = (OLECHAR)(grpValue % 10 + OASTR('0'));
+ grpValue /= 10;
+ }
+
+ // for first grouping, put in decimal point
+
+ if (indResult == CYSTRMAX - 5)
+ chResult[--indResult] = DecimalFromLcid(lcid, dwFlags);
+
+ }while (fNzQuotient);
+
+ // trim any leading zeroes from the string
+
+ while (chResult[indResult] == OASTR('0'))
+ indResult++;
+
+ // remove a leading zero to a decimal point depending on Locale setting
+
+ if (LeadingZeroForDecimalFromLcid(lcid, dwFlags) &&
+ chResult[indResult] == DecimalFromLcid(lcid, dwFlags))
+ chResult[--indResult] = OASTR('0');
+
+ // trim any trailing zeroes from the string
+
+ index = CYSTRMAX - 2;
+ while (chResult[index] == OASTR('0'))
+ index--;
+
+ // process trailing decimal point
+
+ if (chResult[index] == DecimalFromLcid(lcid, dwFlags)) {
+
+ // if just decimal point, put in a zero before it depending on locale
+
+ if (index == indResult)
+ chResult[--indResult] = OASTR('0');
+
+ // move before the decimal point
+
+ index--;
+ }
+
+ // fix the end of the string
+
+ chResult[++index] = OASTR('\0');
+
+ // if negative, put sign in buffer
+ if(fNegative)
+ *pchBuffer++ = OASTR('-');
+
+ STRCPY(pchBuffer, &chResult[indResult]);
+
+ return ErrSysAllocString(buffer, pbstrOut);
+
+#endif // !_X86_
+}
+
+
+STDAPI
+VarBstrFromDisp(IDispatch FAR* pdispIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut)
+{
+ VARIANT varTmp;
+ HRESULT hresult;
+
+ UNUSED(dwFlags);
+ hresult = GetDispProperty(pdispIn, lcid, VT_BSTR, &varTmp);
+ if (hresult == NOERROR)
+ *pbstrOut = V_BSTR(&varTmp);
+ return hresult;
+}
+
+// Return TRUE if this is a legal Cy number. Return FALSE otherwise.
+// On exit, fNegative will be TRUE if this is a negative number
+//
+PRIVATE_(int)
+FixNegativeCyStr(OLECHAR FAR* pInput, OLECHAR cDecimal, int FAR* fReturnNegative)
+{
+ int fSignFound = FALSE;
+ int fOpenParenFound = FALSE;
+ int fNegative = FALSE;
+ int fNumberFound = FALSE;
+
+ *fReturnNegative = FALSE;
+
+ while (*pInput) {
+ switch(*pInput) {
+ case OASTR('+'):
+ case OASTR('-'):
+ if (fSignFound || fOpenParenFound)
+ return FALSE;
+ fNegative = (*pInput == OASTR('-'));
+ *pInput++ = OASTR(' ');
+ fSignFound = TRUE;
+ break;
+
+ case OASTR('('):
+ if (fSignFound || fNumberFound)
+ return FALSE;
+ *pInput++ = OASTR(' ');
+ fOpenParenFound = TRUE;
+ break;
+
+ case OASTR(')'):
+ if (!fOpenParenFound || fSignFound || !fNumberFound)
+ return FALSE;
+ *pInput++ = OASTR(' ');
+ fSignFound = TRUE;
+ fNegative = TRUE;
+ break;
+
+ default:
+ // start of a possible number; zip through it.
+ if((*pInput >= OASTR('0') && *pInput <= OASTR('9'))
+ || *pInput == OASTR('&')
+ || *pInput == cDecimal)
+ {
+ fNumberFound = TRUE;
+ while((*pInput != OASTR(' '))
+ && (*pInput != OASTR('\0'))
+ && (*pInput != OASTR('+'))
+ && (*pInput != OASTR('-'))
+ && (*pInput != OASTR(')')))
+ {
+ pInput++;
+ }
+ }else{
+ pInput++;
+ }
+
+ break;
+ }
+ }
+
+ if (fOpenParenFound && !fNegative)
+ return FALSE; // not balanced.
+
+ if (fNegative)
+ *fReturnNegative = TRUE;
+
+ return TRUE;
+}
+
+// FParseBegin - check if next token matches given string.
+// If it matches sz, point after it and any spaces and
+// return true. If not, stay put and return FALSE.
+//
+PRIVATE_(int)
+fParseBegin (OLECHAR FAR* FAR* ppch, OLECHAR FAR* sz, OLECHAR FAR* lpchLast)
+{
+ OLECHAR FAR* lpch;
+
+ lpch = *ppch;
+
+ for (; *sz != 0; lpch++, sz++)
+ if (lpch > lpchLast || *lpch != *sz)
+ return FALSE;
+
+ while (lpch <= lpchLast && *lpch == OASTR(' '))
+ lpch++;
+
+ *ppch = lpch;
+ return TRUE;
+}
+
+// FParseEnd - check if last token matches given string.
+// If it matches sz, strip it and trailing blanks and
+// return true. If not, stay put and return FALSE.
+
+PRIVATE_(int)
+fParseEnd (OLECHAR FAR* FAR* ppchLast, OLECHAR FAR* sz, OLECHAR FAR* lpchFirst)
+{
+ OLECHAR FAR* lpch;
+ int cch = STRLEN(sz);
+
+ if (cch > *ppchLast - lpchFirst + 1)
+ return FALSE;
+
+ lpch = *ppchLast - cch + 1;
+
+ for (; *sz != 0; lpch++, sz++)
+ if (*lpch != *sz)
+ return FALSE;
+
+ for (lpch = *ppchLast - cch;
+ lpch >= lpchFirst && *lpch == OASTR(' ');
+ lpch--)
+ {}
+
+ *ppchLast = lpch;
+ return TRUE;
+}
+
+// fStripCurrency -
+// strip currency from beginning or end of string;
+// return true iff currency found.
+//
+PRIVATE_(int)
+fStripCurrency(OLECHAR FAR* FAR* ppch, OLECHAR FAR* FAR* ppchLast, OLECHAR FAR* cySymbol)
+{
+ return(fParseBegin(ppch, cySymbol, *ppchLast)
+ || fParseEnd(ppchLast, cySymbol, *ppch));
+}
+
+PRIVATE_(HRESULT)
+StrToCy(
+ OLECHAR FAR* pchIn,
+ OLECHAR FAR* FAR* ppchAfter,
+ int fRoundAllowed,
+ CY FAR* pcyOut,
+ LCID lcid,
+ unsigned long dwFlags)
+{
+ HRESULT err;
+
+ OLECHAR ch;
+ OLECHAR chSign;
+ OLECHAR chNumber[10];
+ OLECHAR chAfterFifth;
+
+ OLECHAR FAR* pchInt;
+ OLECHAR FAR* pchFrac;
+
+ CY cyOut;
+ CY cyUpper;
+ CY cyLower;
+ CY cyMiddle;
+
+ int cntInt = 0;
+ int cntFrac = 0;
+ int cmpIntMax;
+ int fRounding = FALSE;
+
+ unsigned long upperVal = 0L;
+ unsigned long middleVal = 0L;
+ unsigned long lowerVal = 0L;
+
+ chSign = OASTR('+');
+ chAfterFifth = OASTR('0');
+ fRounding = FALSE;
+
+ if(ppchAfter)
+ *ppchAfter = pchIn;
+
+ cyOut.Lo = 0L;
+ cyOut.Hi = 0L;
+
+ cyUpper.Lo = 0L;
+ cyUpper.Hi = 0L;
+
+ cyMiddle.Lo = 0L;
+ cyMiddle.Hi = 0L;
+
+ cyLower.Lo = 0L;
+ cyLower.Hi = 0L;
+
+ ch = *pchIn++;
+
+ // process any sign
+
+ if(ch == OASTR('+') || ch == OASTR('-')){
+ chSign = ch;
+ ch = *pchIn++;
+ }
+
+ // skip over any leading zeroes
+
+ while (ch == OASTR('0'))
+ ch = *pchIn++;
+
+ // scan to determine count of integer digits and
+ // point to just past the terminating byte
+
+ while (ch >= OASTR('0') && ch <= OASTR('9')) {
+ cntInt++;
+ ch = *pchIn++;
+ }
+
+ pchInt = pchIn;
+
+ // if too many integer digits, or integer value
+ // too large, return overflow
+
+ cmpIntMax = ( (cntInt == 15) ? STRNCMP(pchInt - 16,
+ OASTR("922337203685477"), 15) :
+ -1);
+ if(cntInt > 15 ||
+ (cntInt == 15 &&
+ (cmpIntMax > 0)))
+ {
+ errno = ERANGE;
+ *pcyOut = cyOut;
+ return RESULT(DISP_E_OVERFLOW);
+ }
+
+ // if terminator was decimal separator, scan for number
+ // of decimal digits (up to 4) and point to terminating byte
+
+ if(ch == DecimalFromLcid(lcid, dwFlags)){
+
+ ch = *pchIn++;
+
+ while (ch >= OASTR('0') && ch <= OASTR('9') && cntFrac < 4) {
+ cntFrac++;
+ ch = *pchIn++;
+ }
+
+ pchFrac = pchIn;
+
+ // determine if extra digits at end of fraction for rounding
+
+ if (ch >= OASTR('0') && ch <= OASTR('9')) {
+
+ // if no rounding, then give type-mismatch error by
+ // returning with ppchAfter pointing to string start
+
+ if (!fRoundAllowed) {
+ *pcyOut = cyOut;
+ return RESULT(NOERROR);
+ }
+
+ // note the largest value after the fifth decimal digit
+
+ ch = *pchIn++;
+
+ while (ch >= OASTR('0') && ch <= OASTR('9')) {
+ if (ch > chAfterFifth)
+ ch = chAfterFifth;
+ ch = *pchIn++;
+ }
+
+ // Rounding occurs if:
+ // - the fifth decimal digit is greater than 5, or
+ // - the fifth decimal digit is equal to 5, and
+ // a nonzero decimal digit follows, or
+ // the fourth decimal digit is odd
+ //
+ fRounding = *(pchFrac - 1) > OASTR('5')
+ || (*(pchFrac - 1) == OASTR('5')
+ && (chAfterFifth > OASTR('0')
+ || (*(pchFrac - 2) & 1)));
+ }
+ }
+
+ // if maximum integer value, test fraction for overflow
+
+ if (cmpIntMax == 0) {
+
+ // set maximum fraction for positive value
+
+ STRCPY(chNumber, OASTR("5807"));
+
+ // if negative, increase value by one
+
+ chNumber[3] += (chSign == OASTR('-'));
+
+ // if rounding is set, decrease value by one
+
+ chNumber[3] -= fRounding;
+
+ // compare fraction digits with adjusted maximum
+ // fraction - overflow if greater
+
+ if (STRNCMP(pchFrac - cntFrac - 1, chNumber, cntFrac) > 0){
+
+ errno = ERANGE;
+
+ *pcyOut = cyOut;
+
+ return RESULT(DISP_E_OVERFLOW);
+ }
+ }
+
+ // if start of exponent is next, return type-mismatch
+
+ ch = (OLECHAR) TOLOWER(ch);
+
+ if (ch == OASTR('d') || ch == OASTR('e')) {
+ *pcyOut = cyOut;
+ return NOERROR;
+ }
+
+ // point to terminating byte
+
+ if(ppchAfter)
+ *ppchAfter = pchIn - 1;
+
+ //-------------------------------------------------------------
+ //
+ // scan is finished - compose upperVal, middleVal, lowerVal
+ //
+ //-------------------------------------------------------------
+
+ // process upper value
+
+ if (cntInt == 15) {
+ chNumber[0] = *(pchInt - 16);
+ chNumber[1] = OASTR('\0');
+ cyUpper.Lo = (unsigned long)StrToLong(chNumber, NULL);
+ cntInt--;
+ }
+
+ // process middle value
+
+ if(cntInt > 5){
+ MEMCPY(chNumber, pchInt - cntInt - 1, (cntInt - 5) * sizeof(OLECHAR));
+ chNumber[cntInt - 5] = OASTR('\0');
+ cyMiddle.Lo = (unsigned long)StrToLong(chNumber, NULL);
+ cntInt = 5;
+ }
+
+ // copy integer part of lower value
+
+ if (cntInt > 0)
+ MEMCPY(chNumber, pchInt - cntInt - 1, cntInt * sizeof(OLECHAR));
+
+ // copy fractional part of lower value
+
+ if (cntFrac > 0)
+ MEMCPY(&chNumber[cntInt], pchFrac - cntFrac - 1, cntFrac * sizeof(OLECHAR));
+
+ // add any trailing zeroes as needed
+
+ if (cntFrac < 4)
+#if OE_WIN32
+ // UNDONE: is there an equivelent of 'wmemset'?
+ wcsncpy(&chNumber[cntInt + cntFrac], OLESTR("0000"), 4 - cntFrac);
+#else
+ MEMSET(&chNumber[cntInt + cntFrac], OASTR('0'), 4 - cntFrac);
+#endif
+ // add ending null past last fractional digit
+
+ chNumber[cntInt + 4] = OASTR('\0');
+
+ // convert the lower component and add rounding if needed
+
+ cyLower.Lo = (unsigned long)StrToLong(chNumber, NULL) + (unsigned long)fRounding;
+
+ //--------------------------------------------------------
+ // cyUpper, cyMiddle, and cyLower contain
+ // the component values of the input.
+ //
+ // overflow has already been checked.
+ //
+ // rounding has been added if needed.
+ //--------------------------------------------------------
+
+ // if cyUpper is nonzero, set result to it multiplied by 10**9.
+
+ if(cyUpper.Lo != 0L){
+ err = ErrMultCyI4(cyUpper, 1000000000L, &cyOut);
+ if(err != NOERROR)
+ return err;
+ }
+
+ // if either upperVal or middleVal is nonzero, add
+ // cyMiddle to the result and multiply by 10**9.
+
+ if(cyUpper.Lo != 0L || cyMiddle.Lo != 0L){
+ AddCyNoOflo(&cyOut, &cyMiddle);
+ if((err = ErrMultCyI4(cyOut, 1000000000L, &cyOut)) != NOERROR)
+ return err;
+ }
+
+ // add cyLower to result
+
+ AddCyNoOflo(&cyOut, &cyLower);
+
+ // if sign was '-', negate the value
+
+ if(chSign == OASTR('-'))
+ NegCyNoOflo(&cyOut);
+
+ *pcyOut = cyOut;
+ return NOERROR;
+}
+
+PRIVATE_(long)
+StrToLong(OLECHAR FAR* pchInput, OLECHAR FAR* FAR* ppchAfter)
+{
+ OLECHAR chSign, chInput;
+ unsigned long ulResult, ulMaxValue;
+
+ chSign = OASTR('+');
+ ulResult = 0;
+ chInput = *pchInput++;
+
+ // process any leading sign
+
+ if (chInput == OASTR('+') || chInput == OASTR('-')) {
+ chSign = chInput;
+ chInput = *pchInput++;
+ }
+
+ // compute maximum value for sign
+
+ ulMaxValue = 0x7fffffffL + (unsigned long)(chSign == OASTR('-'));
+
+ // process any decimal digits until overflow
+
+ while (chInput >= OASTR('0') && chInput <= OASTR('9')) {
+ // test for overflow - if the conversion does not cause
+ // overflow, go ahead and perform it; otherwise, return. [01]
+
+ if (ulResult < (0xffffffffL -
+ (unsigned long)(chInput - OASTR('0')))/10) {
+
+ ulResult = ulResult * 10 + (unsigned long)(chInput - OASTR('0'));
+
+ } else {
+
+ if (ppchAfter)
+ *ppchAfter = pchInput - 1;
+ errno = ERANGE;
+ return (long)ulMaxValue;
+ }
+
+ chInput = *pchInput++;
+ }
+
+ // test for range of result
+
+ if (ulResult > ulMaxValue) {
+ if (ppchAfter)
+ *ppchAfter = pchInput - 1;
+ errno = ERANGE;
+ return (long)ulMaxValue;
+ }
+
+ // set sign, pointer, and return
+
+ if (chSign == OASTR('-'))
+ ulResult = (unsigned long)-(long)ulResult;
+
+ if (ppchAfter)
+ *ppchAfter = pchInput - 1;
+
+ return (long)ulResult;
+}
+
+PRIVATE_(long)
+HexOctStrToLong(OLECHAR FAR* pchInput, OLECHAR FAR* FAR* ppchAfter)
+{
+ OLECHAR chInput;
+ unsigned long ulResult;
+
+ ulResult = 0;
+ chInput = *pchInput++;
+
+ // first character must be a '&'
+
+ if (chInput == OASTR('&')) {
+
+ chInput = *pchInput++;
+ chInput = (OLECHAR) TOLOWER(chInput);
+
+ // process as hex if prefix is 'h'
+
+ if(chInput == OASTR('h')){
+ ulResult = StrToHex(pchInput, ppchAfter);
+
+ // process as octal otherwise
+
+ }else{
+
+ // Have string of the form:
+ // &o<octal digits>
+ // &o<not octal digits>
+ // &<digits>
+ // &<not octal digits>
+
+ if (chInput != OASTR('o')) {
+ // if no octal prefix, back up over char, so we point to the first
+ // digit (if it exists).
+ pchInput--;
+ if (chInput < OLECHAR('0') || chInput > OLECHAR('7'))
+ goto NotHexOctNum; // if no digit, then error
+ }
+
+ ulResult = StrToOct(pchInput, ppchAfter);
+ }
+ }
+
+ // if no legal prefix, set pointer to start of string
+
+ else {
+NotHexOctNum:
+ if (ppchAfter)
+ *ppchAfter = pchInput - 1;
+ }
+
+ return (long)ulResult;
+}
+
+PRIVATE_(unsigned long)
+StrToHex(OLECHAR FAR* pchIn, OLECHAR FAR* FAR* ppchAfter)
+{
+ OLECHAR ch;
+ unsigned long ulResult;
+
+ ulResult = 0L;
+
+ ch = *pchIn;
+ ch = (OLECHAR) TOLOWER(ch);
+
+ if (ch != 0)
+ pchIn++;
+
+ while ((ch >= OASTR('0') && ch <= OASTR('9')) ||
+ (ch >= OASTR('a') && ch <= OASTR('f'))) {
+
+ // first test for overflow by a high-order
+ // nonzero hex digit in the result
+
+ if (ulResult & 0xf0000000L) {
+ if(ppchAfter)
+ *ppchAfter = pchIn - 1;
+ errno = ERANGE;
+ return ulResult;
+ }
+
+ // adjust the hex letter value 'a'-'f' to '9'+1 to '9'+6
+ if (ch >= OASTR('a'))
+ ch -= OASTR('a') - OASTR('9') - 1;
+
+ // shift result one hex digit and add digit relative to '0'
+
+ ulResult = (ulResult << 4) + (unsigned long)(ch - OASTR('0'));
+
+ ch = *pchIn++;
+ ch = (OLECHAR) TOLOWER(ch);
+ }
+
+ // point past last character used
+
+ if (ppchAfter)
+ *ppchAfter = pchIn - 1;
+
+ return ulResult;
+}
+
+PRIVATE_(unsigned long)
+StrToOct (OLECHAR FAR* pchIn, OLECHAR FAR* FAR* ppchAfter)
+{
+ OLECHAR ch;
+ unsigned long ulResult;
+
+ ulResult = 0L;
+
+ ch = *pchIn;
+ ch = (OLECHAR) TOLOWER(ch);
+
+ if (ch != 0)
+ pchIn++;
+
+ while (ch >= OASTR('0') && ch <= OASTR('7')) {
+
+ // first test for overflow by a high-order
+ // nonzero octal digit in the result
+
+ if(ulResult & 0xe0000000L){
+ if(ppchAfter)
+ *ppchAfter = pchIn - 1;
+ errno = ERANGE;
+ return ulResult;
+ }
+
+ // shift result one octal digit and add digit relative to '0'
+
+ ulResult = (ulResult << 3) + (unsigned long)(ch - OASTR('0'));
+
+ ch = *pchIn++;
+ ch = (OLECHAR) TOLOWER(ch);
+ }
+
+ // point past last character used
+
+ if(ppchAfter)
+ *ppchAfter = pchIn - 1;
+
+ return ulResult;
+}
+
+/***
+* EditStrFromReal - edit real string to BASIC format
+*
+* Purpose:
+*
+* Convert the given string in place to the BASIC format.RR
+*
+* Fractions less than .1 are output in C in exponent format;
+* e.g., BASIC: .00777 --> C: 7.77e-003
+* Exponents in C use 'e' while BASIC uses 'E'.
+* Exponents in C use three-digit exponents always, BASIC uses
+* two if three are not needed.
+* e.g., BASIC: 3.456E+4 --> C: 3.456e+004
+* Trailing decimals used in C, not in BASIC
+* e.g., BASIC: 1234 --> C: 1234.
+* Fractions less than 1.0 are output with a leading zero depending
+* the locale setting LOCALE_ILZERO
+* e.g., .1234 or 0.1234
+* Maximum length integers are output in C as exponential, but
+* as integers in BASIC
+* e.g., BASIC: 1234567 --> 1.234567e+006
+*
+* Entry:
+* pchBuffer - pointer to string to be processed
+* cDigits - number of signficant digits, or maximum decimal
+*
+* Exit:
+* pchBuffer - converted string of the real value
+*
+* Exceptions:
+***********************************************************************/
+
+PRIVATE_(void)
+EditStrFromReal(OLECHAR FAR* pchBuffer, int cDigits, LCID lcid, unsigned long dwFlags)
+{
+ OLECHAR FAR* pchTemp;
+ OLECHAR FAR* pchEnd;
+ int length, lenFrac, valExp;
+
+ // first, replace the '.' returned by the C-rutime gcvt function with
+ // the locale-specific decimal.
+
+ pchTemp = pchBuffer;
+ while(*pchTemp) {
+ if (*pchTemp == OASTR('.')) {
+ *pchTemp = DecimalFromLcid(lcid, dwFlags);
+ break;
+ }
+ pchTemp++;
+ }
+
+
+ // skip over a leading minus sign
+
+ if(*pchBuffer == OASTR('-'))
+ pchBuffer++;
+
+ // get length and point to 'e' if exponental value
+ length = STRLEN(pchBuffer);
+ pchTemp = pchBuffer + length - 5;
+
+ // test if exponential value
+ if (length > 6 && *pchTemp == OASTR('e')) {
+
+ // test if negative exponent
+ if (*(pchTemp + 1) == OASTR('-')) {
+
+ // point to first exponent digit
+ pchTemp += 2;
+
+ // calcuate length of fraction
+ // "d.mm--mme-nnn" - two before, five after
+
+ lenFrac = length - 7;
+
+ // evaluate exponent value
+
+ valExp = *pchTemp++ - OASTR('0');
+ valExp = valExp * 10 + *pchTemp++ - OASTR('0');
+ valExp = valExp * 10 + *pchTemp - OASTR('0');
+
+ // determine if number can be a fraction...
+ // length is:
+ // valExp - 1 leading zeroes
+ // lenFrac + 1 digits (frac plus first digit)
+ //
+ if (valExp + lenFrac <= cDigits) {
+ // point past new end of fraction and
+ // to end of fraction in exponent
+
+ pchEnd = pchBuffer + valExp + lenFrac + 1;
+ pchTemp = pchBuffer + lenFrac + 1;
+
+ // write null for new fraction
+
+ *pchEnd-- = OASTR('\0');
+
+ // copy exponent fraction to new fraction
+ while(lenFrac--)
+ *pchEnd-- = *pchTemp--;
+
+ // copy leading digit
+ *pchEnd-- = *pchBuffer;
+
+ // set the leading zeroes, if any
+ while (pchEnd > pchBuffer)
+ *pchEnd-- = OASTR('0');
+
+ // set the decimal point of new fraction
+ *pchEnd-- = DecimalFromLcid(lcid, dwFlags);
+
+ // add a leading zero to a decimal point depending on Locale setting
+ // this is OK so long as the input buffer is really greater than
+ // cDigit, which is the case on all call here (buf[40])
+ if (LeadingZeroForDecimalFromLcid(lcid, dwFlags)) {
+ MEMMOVE(pchBuffer+1, pchBuffer, BYTELEN(pchBuffer));
+ *pchBuffer = OASTR('0');
+ }
+
+ }
+ else // if no conversion, point back to 'e' in value
+ pchTemp = pchBuffer + length - 5;
+ }
+ // test if positive exponent
+ else if (*(pchTemp + 1) == OASTR('+')) {
+
+ // point to first exponent digit
+
+ pchTemp += 2;
+
+ // calcuate length of fraction
+ // "d.mm--mme-nnn" - two before, five after
+
+ lenFrac = length - 7;
+
+ // evaluate exponent value
+
+ valExp = *pchTemp++ - OASTR('0');
+ valExp = valExp * 10 + *pchTemp++ - OASTR('0');
+ valExp = valExp * 10 + *pchTemp - OASTR('0');
+
+ // the only conversion done is when the exponent
+ // is one less than the number of digits to make
+ // an integer of length cDigits
+
+ if (valExp == cDigits - 1) {
+
+ // point to first fraction digit
+
+ pchTemp = pchBuffer + 2;
+
+ // copy fraction digits one location to the left
+
+ while (*pchTemp >= OASTR('0') && *pchTemp <= OASTR('9')) {
+ *(pchTemp - 1) = *pchTemp;
+ pchTemp++;
+ valExp--;
+ }
+
+ // zero-fill any remaining digits and terminate
+ // pchTemp is left on null, so exponent is not
+ // processed
+
+ pchTemp--;
+
+ while (valExp--)
+ *pchTemp++ = OASTR('0');
+ *pchTemp = OASTR('\0');
+
+ }
+ else
+ // if no conversion, point back to 'e' in value
+ pchTemp = pchBuffer + length - 5;
+ }
+
+ // if pchTemp points to an 'e', process the exponential
+
+ if (*pchTemp == OASTR('e')) {
+
+ // convert 'e' to upper case
+ *pchTemp = OASTR('E');
+
+ // if first exponent digit is a zero, remove it
+ if (*(pchTemp + 2) == OASTR('0'))
+ MEMMOVE(pchTemp+2, pchTemp+3, BYTELEN(pchTemp));
+
+ // if exponent is preceded by a decimal point, remove it
+ if (*(pchTemp - 1) == DecimalFromLcid(lcid, dwFlags))
+ MEMMOVE(pchTemp -1, pchTemp, BYTELEN(pchTemp));
+ }
+
+ }
+
+ // if not an exponent, do some processing
+
+ else {
+
+ // remove any trailing decimal point
+
+ pchTemp = pchBuffer + length - 1;
+
+ if(*pchTemp == DecimalFromLcid(lcid, dwFlags))
+ *pchTemp = OASTR('\0');
+
+ // remove a leading zero to a decimal point depending on Locale setting
+
+ if (!LeadingZeroForDecimalFromLcid(lcid, dwFlags) &&
+ (*pchBuffer == OASTR('0')) &&
+ (*(pchBuffer + 1) == DecimalFromLcid(lcid, dwFlags)))
+ MEMMOVE(pchBuffer, pchBuffer + 1, BYTELEN(pchBuffer));
+ }
+}
+
+
+PRIVATE_(HRESULT)
+GetDispProperty(
+ IDispatch FAR* pdisp,
+ LCID lcid,
+ VARTYPE vt,
+ VARIANT FAR* pvarResult)
+{
+ DISPPARAMS dispparams;
+ HRESULT hresult;
+
+ if (pdisp == NULL)
+ return RESULT(DISP_E_TYPEMISMATCH);
+
+ pdisp->AddRef();
+
+ V_VT(pvarResult) = VT_EMPTY;
+
+ dispparams.cArgs = 0;
+ dispparams.rgvarg = NULL;
+ dispparams.cNamedArgs = 0;
+ dispparams.rgdispidNamedArgs = NULL;
+
+ hresult = pdisp->Invoke(
+ DISPID_VALUE,
+ IID_NULL,
+ lcid,
+ DISPATCH_PROPERTYGET,
+ &dispparams, pvarResult, NULL, NULL);
+
+ pdisp->Release();
+
+ // if there was an error extracting the value property, then
+ // we simply report a type-mismatch.
+ //
+ if (hresult != NOERROR)
+ return RESULT(DISP_E_TYPEMISMATCH);
+
+ // else coerse the variant to the desire variant type
+ return VariantChangeTypeInternal(pvarResult, lcid, vt);
+}
+
+
+#ifdef FE_DBCS
+
+// FE specific functions used within convert.cpp & bstrdate.c
+
+#define LCID_CHINA_T 0x404 // traditional
+#define LCID_CHINA_S 0x804 // simplified
+#define LCID_JAPAN 0x411
+#define LCID_KOREA 0x412
+
+EXTERN_C INTERNAL_(int)
+IsDBCS(LCID lcid)
+{
+ if (lcid == LOCALE_USER_DEFAULT || lcid == 0)
+ lcid = GetUserDefaultLCID();
+ return ( (lcid == LCID_JAPAN) ||
+ (lcid == LCID_KOREA) ||
+ (lcid == LCID_CHINA_S) || (lcid == LCID_CHINA_T) );
+}
+
+
+EXTERN_C INTERNAL_(int)
+IsJapan(LCID lcid)
+{
+ if (lcid == LOCALE_USER_DEFAULT || lcid == 0)
+ lcid = GetUserDefaultLCID();
+ return (lcid == LCID_JAPAN);
+}
+
+EXTERN_C INTERNAL_(int)
+IsKorea(LCID lcid)
+{
+ if (lcid == LOCALE_USER_DEFAULT || lcid == 0)
+ lcid = GetUserDefaultLCID();
+ return (lcid == LCID_KOREA);
+}
+
+EXTERN_C INTERNAL_(int)
+IsTaiwan(LCID lcid)
+{
+ if (lcid == LOCALE_USER_DEFAULT || lcid == 0)
+ lcid = GetUserDefaultLCID();
+ return (lcid == LCID_CHINA_T);
+}
+
+EXTERN_C INTERNAL_(int)
+IsChina(LCID lcid)
+{
+ if (lcid == LOCALE_USER_DEFAULT || lcid == 0)
+ lcid = GetUserDefaultLCID();
+ return (lcid == LCID_CHINA_S);
+}
+
+
+#endif // FE_DBCS
+
+
+#if OE_MAC /* { */
+
+/* Mac Note: On the Mac, the coersion functions support the
+ * Symantec C++ calling convention for float/double. To support
+ * float/double arguments compiled with the MPW C compiler,
+ * use the following APIs to move MPW float/double values into
+ * a VARIANT.
+ */
+
+
+STDAPI MPWVarFromR4(float FAR* pfltIn, VARIANT FAR* pvarOut)
+{
+
+ V_R4(pvarOut) = *pfltIn;
+ return NOERROR;
+}
+
+
+STDAPI MPWVarFromR8(double FAR* pdblIn, VARIANT FAR* pvarOut)
+{
+ V_R8(pvarOut) = *pdblIn;
+ return NOERROR;
+}
+
+
+STDAPI MPWR4FromVar(VARIANT FAR* pvarIn, float FAR* pfltOut)
+{
+ *pfltOut = V_R4(pvarIn);
+ return NOERROR;
+}
+
+
+STDAPI MPWR8FromVar(VARIANT FAR* pvarIn, double FAR* pdblOut)
+{
+ *pdblOut = V_R8(pvarIn);
+ return NOERROR;
+}
+
+#endif /* } */
diff --git a/private/oleauto/src/dispatch/crtstuff.c b/private/oleauto/src/dispatch/crtstuff.c
new file mode 100644
index 000000000..8b9d1d193
--- /dev/null
+++ b/private/oleauto/src/dispatch/crtstuff.c
@@ -0,0 +1,214 @@
+/***
+*crtstuff.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Misc C Runtime style helper functions.
+*
+* disp_itoa
+* disp_ltoa
+* disp_floor
+*
+*Revision History:
+*
+* [00] 09-Jun-93 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#include <stdlib.h>
+#include <limits.h>
+#include <math.h> // floor()
+
+/* helper routine that does the main job. */
+
+INTERNAL_(void)
+xtoa(unsigned long val, OLECHAR FAR* buf, unsigned radix, int is_neg)
+{
+ OLECHAR FAR* p; /* pointer to traverse string */
+ OLECHAR FAR* firstdig; /* pointer to first digit */
+ OLECHAR temp; /* temp char */
+ unsigned digval; /* value of digit */
+
+ p = buf;
+
+ if (is_neg) {
+ /* negative, so output '-' and negate */
+ *p++ = OASTR('-');
+ val = (unsigned long)-(long)val;
+ }
+
+ firstdig = p; /* save pointer to first digit */
+
+ do {
+ digval = (unsigned) (val % radix);
+ val /= radix; /* get next digit */
+
+ /* convert to ascii and store */
+ if (digval > 9)
+ *p++ = (OLECHAR) (digval - 10 + OASTR('a')); /* a letter */
+ else
+ *p++ = (OLECHAR) (digval + OASTR('0')); /* a digit */
+ } while (val > 0);
+
+ /* We now have the digit of the number in the buffer, but in reverse
+ order. Thus we reverse them now. */
+
+ *p-- = OASTR('\0'); /* terminate string; p points to last digit */
+
+ do {
+ temp = *p;
+ *p = *firstdig;
+ *firstdig = temp; /* swap *p and *firstdig */
+ --p;
+ ++firstdig; /* advance to next two digits */
+ } while (firstdig < p); /* repeat until halfway */
+}
+
+
+/* Actual functions just call conversion helper with neg flag set correctly,
+ and return pointer to buffer. */
+
+INTERNAL_(OLECHAR FAR*)
+disp_itoa(int val, OLECHAR FAR* buf, int radix)
+{
+ if (radix == 10 && val < 0)
+ xtoa((unsigned long)val, buf, radix, 1);
+ else
+ xtoa((unsigned long)(unsigned int)val, buf, radix, 0);
+ return buf;
+}
+
+INTERNAL_(OLECHAR FAR*)
+disp_ltoa(long val, OLECHAR FAR* buf, int radix)
+{
+ xtoa((unsigned long)val, buf, radix, (radix == 10 && val < 0));
+ return buf;
+}
+
+#if 0 /* currently unused */
+
+INTERNAL_(OLECHAR FAR*)
+disp_ultoa(unsigned long val, OLECHAR FAR* buf, int radix)
+{
+ xtoa(val, buf, radix, 0);
+ return buf;
+}
+
+#endif
+
+
+INTERNAL_(double)
+disp_floor(double dbl)
+{
+#if HC_MPW
+
+ GlobalWorld gworld;
+
+ gworld = OpenGlobalWorld();
+
+ dbl = (double)floor((extended)dbl);
+
+ CloseGlobalWorld(gworld);
+
+ return dbl;
+
+#else
+
+ return floor(dbl); // just use the c runtime
+
+#endif
+}
+
+
+#if HC_MPW
+
+INTERNAL_(int)
+disp_stricmp(char *first, char *last)
+{
+ unsigned short f, l;
+
+ do{
+ f = tolower(*first++);
+ l = tolower(*last++);
+ }while(f && f == l);
+
+ return f - l;
+}
+
+#endif
+
+
+INTERNAL_(void)
+disp_gcvt(double dblIn, int ndigits, OLECHAR FAR* pchOut, int bufSize)
+{
+#if HC_MPW
+
+ char *pch;
+ char *pchTmp;
+ extended extIn;
+ int decpt, sign;
+ GlobalWorld gworld;
+
+ pch = pchOut;
+
+ gworld = OpenGlobalWorld();
+
+ extIn = (extended)dblIn;
+ pchTmp = fcvt(extIn, ndigits, &decpt, &sign);
+
+ if(sign < 0)
+ *pch++ = '-';
+
+ if(decpt < 0){
+ *pch++ = '.';
+ while(decpt++ < 0)
+ *pch++ = '0';
+ }else{
+ while(decpt-- > 0)
+ *pch++ = *pchTmp++;
+ *pch++ = '.';
+ }
+ while(*pchTmp != '\0')
+ *pch++ = *pchTmp++;
+ *pch = '\0';
+
+ CloseGlobalWorld(gworld);
+
+#else
+# if OE_WIN32
+ char buf[40];
+
+ _gcvt(dblIn, ndigits, buf);
+ MultiByteToWideChar(CP_ACP, MB_PRECOMPOSED, buf, -1, pchOut, bufSize);
+# else
+ UNUSED(bufSize);
+ _gcvt(dblIn, ndigits, pchOut);
+# endif
+#endif
+}
+
+INTERNAL_(double)
+disp_strtod(OLECHAR FAR* strIn, OLECHAR FAR* FAR* ppchEnd)
+{
+#if HC_MPW
+ double dbl;
+ GlobalWorld gworld;
+
+ gworld = OpenGlobalWorld();
+ dbl = strtod(strIn, ppchEnd);
+ CloseGlobalWorld(gworld);
+
+ return dbl;
+
+#else
+
+ return STRTOD(strIn, ppchEnd);
+
+#endif
+}
diff --git a/private/oleauto/src/dispatch/crtstuff.h b/private/oleauto/src/dispatch/crtstuff.h
new file mode 100644
index 000000000..877bde889
--- /dev/null
+++ b/private/oleauto/src/dispatch/crtstuff.h
@@ -0,0 +1,47 @@
+
+/***
+*crtstuff.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Misc C Runtime style helper functions.
+*
+*Revision History:
+*
+* [00] 09-Jun-93 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+INTERNAL_(HRESULT) DispAlloc(size_t cb, void FAR* FAR* ppv);
+
+INTERNAL_(void) DispFree(void FAR* pv);
+
+INTERNAL_(char FAR*) disp_itoa(int val, char FAR* buf, int radix);
+
+INTERNAL_(char FAR*) disp_ltoa(long val, char FAR* buf, int radix);
+
+INTERNAL_(double) disp_floor(double dbl);
+
+INTERNAL_(void) disp_gcvt(double dblIn, int ndigits, char FAR* pchOut);
+
+INTERNAL_(double) disp_strtod(char FAR* strIn, char FAR* FAR* pchEnd);
+
+#if HC_MPW
+
+INTERNAL_(int) disp_stricmp(char*, char*);
+
+#endif
+
+#ifdef __cplusplus
+}
+#endif
+
diff --git a/private/oleauto/src/dispatch/dbcsdate.c b/private/oleauto/src/dispatch/dbcsdate.c
new file mode 100644
index 000000000..c8dc6a10a
--- /dev/null
+++ b/private/oleauto/src/dispatch/dbcsdate.c
@@ -0,0 +1,87 @@
+// code fragment I used to generate the contents of DBCSDATE.H
+// Needs to be updated & re-run when changing this info. You must have
+// all 4 code pages installed on a DaytonaJ machine in ordedr
+
+void DoIt(int codepage, char * szName, char * szDataA) {
+WCHAR szDataW[20];
+char szBuffer[80];
+char *pch;
+char *pchOut;
+int cb;
+
+ printf("#if OE_WIN32\n");
+ szDataW[0] = 0;
+ MultiByteToWideChar(codepage, MB_PRECOMPOSED, szDataA, strlen(szDataA)+1,
+ szDataW, sizeof(szDataW));
+
+ szBuffer[0] = 0;
+ cb = wcslen(szDataW) * sizeof(WCHAR);
+ for (pchOut = szBuffer, pch = (char *)szDataW; cb > 0; pch++, cb--) {
+ pchOut += sprintf(pchOut, "\\x%x", (unsigned char)*pch);
+ }
+ printf("#define %s (WCHAR *)\"%s\"\n", szName, szBuffer);
+
+ printf("#else \\\\OE_WIN32\n");
+
+ szBuffer[0] = 0;
+ cb = strlen(szDataA);
+ for (pchOut = szBuffer, pch = (char *)szDataA; cb > 0; pch++, cb--) {
+ pchOut += sprintf(pchOut, "\\x%x", (unsigned char)*pch);
+ }
+ printf("#define %s \"%s\"\n", szName, szBuffer);
+
+ printf("#endif \\\\OE_WIN32\n");
+}
+
+int TempDump() {
+ DoIt(932, "szJapanimpEras0Name1", "\x96\xbe");
+ DoIt(932, "szJapanimpEras0Name2", "\x96\xbe\x8e\xa1");
+ DoIt(932, "szJapanimpEras1Name1", "\x91\xe5");
+ DoIt(932, "szJapanimpEras1Name2", "\x91\xe5\x90\xb3");
+ DoIt(932, "szJapanimpEras2Name1", "\x8f\xba");
+ DoIt(932, "szJapanimpEras2Name2", "\x8f\xba\x98\x61");
+ DoIt(932, "szJapanimpEras3Name1", "\x95\xbd");
+ DoIt(932, "szJapanimpEras3Name2", "\x95\xbd\x90\xac");
+ DoIt(932, "szJapandbYearSuff", "\x94\x4e");
+ DoIt(932, "szJapandbMonthSuff", "\x8c\x8e");
+ DoIt(932, "szJapandbDaySuff", "\x93\xfa");
+ DoIt(932, "szJapandbHourSuff", "\x8e\x9e");
+ DoIt(932, "szJapandbMinuteSuff", "\x95\xaa");
+ DoIt(932, "szJapandbSecondSuff", "\x95\x62");
+ DoIt(932, "szJapandb1159", "\x8c\xdf\x91\x4f");
+ DoIt(932, "szJapandb2359", "\x8c\xdf\x8c\xe3");
+
+ DoIt(949, "szKoreadbYearSuff", "\xb3\xe2");
+ DoIt(949, "szKoreadbMonthSuff", "\xbf\xf9");
+ DoIt(949, "szKoreadbDaySuff", "\xc0\xcf");
+ DoIt(949, "szKoreadbHourSuff", "\xbd\xc3");
+ DoIt(949, "szKoreadbMinuteSuff", "\xba\xd0");
+ DoIt(949, "szKoreadbSecondSuff", "\xc3\xca");
+ DoIt(949, "szKoreadb1159", "\xbf\xc0\xc0\xfc");
+ DoIt(949, "szKoreadb2359", "\xbf\xc0\xc8\xc4");
+
+ DoIt(950, "szTaiwandbYearSuff", "\xa6\x7e");
+ DoIt(950, "szTaiwandbMonthSuff", "\xa4\xeb");
+ DoIt(950, "szTaiwandbDaySuff", "\xa4\xe9");
+ DoIt(950, "szTaiwandbHourSuff", "\xae\xc9");
+ DoIt(950, "szTaiwandbMinuteSuff", "\xa4\xc0");
+ DoIt(950, "szTaiwandbSecondSuff", "\xac\xed");
+ DoIt(950, "szTaiwandb1159", "\xa4\x57\xa4\xc8");
+ DoIt(950, "szTaiwandb2359", "\xa4\x55\xa4\xc8");
+ DoIt(950, "szTaiwanrepEras0Name0", "\xa5\xc1\xb0\xea\xab\x65");
+ DoIt(950, "szTaiwanrepEras0Name1", "\xa4\xa4\xb5\xd8\xa5\xc1\xb0\xea\xab\x65");
+ DoIt(950, "szTaiwanrepEras1Name0", "\xa5\xc1\xb0\xea");
+ DoIt(950, "szTaiwanrepEras1Name1", "\xa4\xa4\xb5\xd8\xa5\xc1\xb0\xea");
+
+ DoIt(936, "szChinadbYearSuff", "\xc4\xea");
+ DoIt(936, "szChinadbMonthSuff", "\xd4\xc2");
+ DoIt(936, "szChinadbDaySuff", "\xc8\xd5");
+ DoIt(936, "szChinadbHourSuff", "\xca\xb1");
+ DoIt(936, "szChinadbMinuteSuff", "\xb7\xd6");
+ DoIt(936, "szChinadbSecondSuff", "\xc3\xeb");
+ DoIt(936, "szChinadb1159", "\xc9\xcf\xce\xe7");
+ DoIt(936, "szChinadb2359", "\xcf\xc2\xce\xe7");
+ DoIt(936, "szChinadbEraName", "\xb9\xab\xd4\xaa");
+
+ return 1;
+}
diff --git a/private/oleauto/src/dispatch/dbcsdate.h b/private/oleauto/src/dispatch/dbcsdate.h
new file mode 100644
index 000000000..547bcb278
--- /dev/null
+++ b/private/oleauto/src/dispatch/dbcsdate.h
@@ -0,0 +1,228 @@
+// machine-generated mapping of Ansi DBCS strings to UNICODE strings.
+// See dbcsdate.c for code used to generate this.
+
+#if OE_WIN32
+#define szJapanimpEras0Name1 (WCHAR *)"\xe\x66"
+#else //OE_WIN32
+#define szJapanimpEras0Name1 "\x96\xbe"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szJapanimpEras0Name2 (WCHAR *)"\xe\x66\xbb\x6c"
+#else //OE_WIN32
+#define szJapanimpEras0Name2 "\x96\xbe\x8e\xa1"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szJapanimpEras1Name1 (WCHAR *)"\x27\x59"
+#else //OE_WIN32
+#define szJapanimpEras1Name1 "\x91\xe5"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szJapanimpEras1Name2 (WCHAR *)"\x27\x59\x63\x6b"
+#else //OE_WIN32
+#define szJapanimpEras1Name2 "\x91\xe5\x90\xb3"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szJapanimpEras2Name1 (WCHAR *)"\x2d\x66"
+#else //OE_WIN32
+#define szJapanimpEras2Name1 "\x8f\xba"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szJapanimpEras2Name2 (WCHAR *)"\x2d\x66\x8c\x54"
+#else //OE_WIN32
+#define szJapanimpEras2Name2 "\x8f\xba\x98\x61"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szJapanimpEras3Name1 (WCHAR *)"\x73\x5e"
+#else //OE_WIN32
+#define szJapanimpEras3Name1 "\x95\xbd"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szJapanimpEras3Name2 (WCHAR *)"\x73\x5e\x10\x62"
+#else //OE_WIN32
+#define szJapanimpEras3Name2 "\x95\xbd\x90\xac"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szJapandbYearSuff (WCHAR *)"\x74\x5e"
+#else //OE_WIN32
+#define szJapandbYearSuff "\x94\x4e"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szJapandbMonthSuff (WCHAR *)"\x8\x67"
+#else //OE_WIN32
+#define szJapandbMonthSuff "\x8c\x8e"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szJapandbDaySuff (WCHAR *)"\xe5\x65"
+#else //OE_WIN32
+#define szJapandbDaySuff "\x93\xfa"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szJapandbHourSuff (WCHAR *)"\x42\x66"
+#else //OE_WIN32
+#define szJapandbHourSuff "\x8e\x9e"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szJapandbMinuteSuff (WCHAR *)"\x6\x52"
+#else //OE_WIN32
+#define szJapandbMinuteSuff "\x95\xaa"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szJapandbSecondSuff (WCHAR *)"\xd2\x79"
+#else //OE_WIN32
+#define szJapandbSecondSuff "\x95\x62"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szJapandb1159 (WCHAR *)"\x48\x53\x4d\x52"
+#else //OE_WIN32
+#define szJapandb1159 "\x8c\xdf\x91\x4f"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szJapandb2359 (WCHAR *)"\x48\x53\x8c\x5f"
+#else //OE_WIN32
+#define szJapandb2359 "\x8c\xdf\x8c\xe3"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szKoreadbYearSuff (WCHAR *)"\x5b\x35"
+#else //OE_WIN32
+#define szKoreadbYearSuff "\xb3\xe2"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szKoreadbMonthSuff (WCHAR *)"\xda\x39"
+#else //OE_WIN32
+#define szKoreadbMonthSuff "\xbf\xf9"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szKoreadbDaySuff (WCHAR *)"\xe\x3a"
+#else //OE_WIN32
+#define szKoreadbDaySuff "\xc0\xcf"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szKoreadbHourSuff (WCHAR *)"\xe8\x38"
+#else //OE_WIN32
+#define szKoreadbHourSuff "\xbd\xc3"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szKoreadbMinuteSuff (WCHAR *)"\xdb\x37"
+#else //OE_WIN32
+#define szKoreadbMinuteSuff "\xba\xd0"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szKoreadbSecondSuff (WCHAR *)"\x23\x3b"
+#else //OE_WIN32
+#define szKoreadbSecondSuff "\xc3\xca"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szKoreadb1159 (WCHAR *)"\xa1\x39\x3b\x3a"
+#else //OE_WIN32
+#define szKoreadb1159 "\xbf\xc0\xc0\xfc"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szKoreadb2359 (WCHAR *)"\xa1\x39\xf3\x3c"
+#else //OE_WIN32
+#define szKoreadb2359 "\xbf\xc0\xc8\xc4"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szTaiwandbYearSuff (WCHAR *)"\x74\x5e"
+#else //OE_WIN32
+#define szTaiwandbYearSuff "\xa6\x7e"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szTaiwandbMonthSuff (WCHAR *)"\x8\x67"
+#else //OE_WIN32
+#define szTaiwandbMonthSuff "\xa4\xeb"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szTaiwandbDaySuff (WCHAR *)"\xe5\x65"
+#else //OE_WIN32
+#define szTaiwandbDaySuff "\xa4\xe9"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szTaiwandbHourSuff (WCHAR *)"\x42\x66"
+#else //OE_WIN32
+#define szTaiwandbHourSuff "\xae\xc9"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szTaiwandbMinuteSuff (WCHAR *)"\x6\x52"
+#else //OE_WIN32
+#define szTaiwandbMinuteSuff "\xa4\xc0"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szTaiwandbSecondSuff (WCHAR *)"\xd2\x79"
+#else //OE_WIN32
+#define szTaiwandbSecondSuff "\xac\xed"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szTaiwandb1159 (WCHAR *)"\xa\x4e\x48\x53"
+#else //OE_WIN32
+#define szTaiwandb1159 "\xa4\x57\xa4\xc8"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szTaiwandb2359 (WCHAR *)"\xb\x4e\x48\x53"
+#else //OE_WIN32
+#define szTaiwandb2359 "\xa4\x55\xa4\xc8"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szTaiwanrepEras0Name0 (WCHAR *)"\x11\x6c\xb\x57\x4d\x52"
+#else //OE_WIN32
+#define szTaiwanrepEras0Name0 "\xa5\xc1\xb0\xea\xab\x65"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szTaiwanrepEras0Name1 (WCHAR *)"\x2d\x4e\xef\x83\x11\x6c\xb\x57\x4d\x52"
+#else //OE_WIN32
+#define szTaiwanrepEras0Name1 "\xa4\xa4\xb5\xd8\xa5\xc1\xb0\xea\xab\x65"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szTaiwanrepEras1Name0 (WCHAR *)"\x11\x6c\xb\x57"
+#else //OE_WIN32
+#define szTaiwanrepEras1Name0 "\xa5\xc1\xb0\xea"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szTaiwanrepEras1Name1 (WCHAR *)"\x2d\x4e\xef\x83\x11\x6c\xb\x57"
+#else //OE_WIN32
+#define szTaiwanrepEras1Name1 "\xa4\xa4\xb5\xd8\xa5\xc1\xb0\xea"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szChinadbYearSuff (WCHAR *)"\x74\x5e"
+#else //OE_WIN32
+#define szChinadbYearSuff "\xc4\xea"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szChinadbMonthSuff (WCHAR *)"\x8\x67"
+#else //OE_WIN32
+#define szChinadbMonthSuff "\xd4\xc2"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szChinadbDaySuff (WCHAR *)"\xe5\x65"
+#else //OE_WIN32
+#define szChinadbDaySuff "\xc8\xd5"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szChinadbHourSuff (WCHAR *)"\xf6\x65"
+#else //OE_WIN32
+#define szChinadbHourSuff "\xca\xb1"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szChinadbMinuteSuff (WCHAR *)"\x6\x52"
+#else //OE_WIN32
+#define szChinadbMinuteSuff "\xb7\xd6"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szChinadbSecondSuff (WCHAR *)"\xd2\x79"
+#else //OE_WIN32
+#define szChinadbSecondSuff "\xc3\xeb"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szChinadb1159 (WCHAR *)"\xa\x4e\x48\x53"
+#else //OE_WIN32
+#define szChinadb1159 "\xc9\xcf\xce\xe7"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szChinadb2359 (WCHAR *)"\xb\x4e\x48\x53"
+#else //OE_WIN32
+#define szChinadb2359 "\xcf\xc2\xce\xe7"
+#endif //OE_WIN32
+#if OE_WIN32
+#define szChinadbEraName (WCHAR *)"\x6c\x51\x43\x51"
+#else //OE_WIN32
+#define szChinadbEraName "\xb9\xab\xd4\xaa"
+#endif //OE_WIN32
diff --git a/private/oleauto/src/dispatch/dispbind.cpp b/private/oleauto/src/dispatch/dispbind.cpp
new file mode 100644
index 000000000..2fe0130d2
--- /dev/null
+++ b/private/oleauto/src/dispatch/dispbind.cpp
@@ -0,0 +1,221 @@
+/***
+*dispbind.cpp - Remote object binding support.
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file contains helpers for creating and connecting to an
+* instance of a remote object.
+*
+* The information for binding to an object by name is stored in
+* the windows registry in the following format,
+*
+#if 0
+* \{xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx} = fullname
+* \AuxUserType\1 = fullname
+* \AuxUserType\2 = shortname
+* \AuxUserType\3 = progname
+#else
+*
+* // registry have changed (again), now progname is registered as follows,
+*
+* \CLSID\{xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx} = fullname
+* \CLSID\{xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx}\ProgID = progname
+*
+#endif
+*
+* Where the name we bind to is the progname associated with the subkey
+* \AuxUserType\3.
+#
+*
+*Revision History:
+*
+* [00] 18-Sep-92 bradlo: Created.
+* 18-Jan-92 bradlo: updated to Ole2 beta2 registry format
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#ifdef _MAC
+# include <macos/types.h>
+# include <macos/menus.h>
+# include <macos/windows.h>
+# include "machack.h"
+#else
+# include <windows.h>
+#endif
+
+#include <ole2.h>
+#include <dispatch.h>
+
+#ifndef _MAC
+extern "C"
+{
+#include <shellapi.h>
+}
+#endif
+
+
+#if 0
+
+// the following has been replaced with the Ole2 supplied
+// API, CLSIDFromProgID()
+
+/***
+*PRIVATE HRESULT ClsidOfClassName(char*, CLSID*)
+*Purpose:
+* Lookup the given class name in the registry, and return the
+* associated CLSID.
+*
+* If there are multiple CLSIDs with the same name, then we
+* simply return the first one we come across.
+*
+* Class names matches are case insensitive.
+*
+*Entry:
+* szProgName = the textual name of the class to lookup
+*
+*Exit:
+* return value = HRESULT
+* S_OK - got it!
+* S_FALSE - name not found
+*
+* *pclsid = the CLSID of the given name
+*
+*Note:
+* This is a very nieve implementation, I haven't bothered to
+* optimize this function at all. The registry search is largely
+* stolen from an SDK example, and there may well be more
+* efficient ways to do this.
+*
+***********************************************************************/
+HRESULT
+ClsidOfClassName(char FAR* szProgName, CLSID FAR* pclsid)
+{
+ LONG cb;
+ HRESULT hresult;
+ HKEY hkRoot, hkAux;
+ unsigned long dwIndex;
+ char szKey[256], szValue[256]; // REVIEW: how big can a key/value be?
+
+
+#ifdef _DEBUG // param validation
+ // REVIEW: should validate szProgName as well
+
+ if(IsBadWritePtr(pclsid, sizeof(*pclsid)))
+ return ResultFromScode(E_INVALIDARG);
+#endif
+
+ if(RegOpenKey(HKEY_CLASSES_ROOT, NULL, &hkRoot) != ERROR_SUCCESS){
+ hresult = ResultFromScode(OLE_E_REGDB_KEY);
+ goto LExit;
+ }
+
+ // Scan all top level keys in the registry. If the key begins with
+ // a '{', then assume its a CLSID and look a bit further
+ //
+ for(dwIndex = 0;; ++dwIndex)
+ {
+ if(RegEnumKey(hkRoot, dwIndex, szKey, sizeof(szKey)) != ERROR_SUCCESS){
+ hresult = ResultFromScode(OLE_E_REGDB_KEY);
+ goto LClose0;
+ }
+
+ // if the key's prefix looks like it might be a CLSID, then
+ // examine this entry a bit closer.
+ //
+ if(*szKey == '{')
+ {
+ // if we can convert it successfully, then we assume it
+ // *was* a valid CLSID.
+ //
+ if(CLSIDFromString(szKey, pclsid) == NOERROR)
+ {
+ if(RegOpenKey(hkRoot, szKey, &hkAux) == ERROR_SUCCESS)
+ {
+ cb = sizeof(szValue);
+ if(RegQueryValue(
+ hkAux, "AuxUserType\\3", szValue, &cb) == ERROR_SUCCESS)
+ {
+ // if the name matches, then we have found it
+ //
+ if(!_fstricmp(szValue, szProgName)){
+ hresult = NOERROR;
+ goto LClose1;
+ }
+ }
+
+ RegCloseKey(hkAux);
+ }
+ }
+ }
+ }
+ RegCloseKey(hkRoot);
+
+ // unknown CLSID
+ return ResultFromScode(OLE_E_CLSID);
+
+LClose1:;
+ RegCloseKey(hkAux);
+
+LClose0:;
+ RegCloseKey(hkRoot);
+
+LExit:;
+ return hresult;
+}
+
+#endif
+
+
+/***
+*HRESULT dispbind(char*, IDispatch **)
+*
+*Purpose:
+* Connect to the IDispatch interface on a *new* instance of a class
+* with the given class ID.
+*
+*Entry:
+* szProgName = the name of the class.
+*
+*Exit:
+* return value = HRESULT
+* NOERROR
+* E_FAIL - couldn't bind (REVIEW: need a better error for this?)
+*
+* *ppdisp = pointer to an IDispatch* if the connect was successful.
+*
+***********************************************************************/
+STDAPI
+CreateObject(char FAR* szProgName, IDispatch FAR* FAR* ppdisp)
+{
+ CLSID clsid;
+ HRESULT hresult;
+ IUnknown FAR* punk;
+
+
+ // map the given class name to a CLSID
+ //
+ hresult = CLSIDFromProgID(szProgName, &clsid);
+ if(hresult != NOERROR)
+ goto LError0;
+
+
+ // Create an instance of a class with the given CLSID
+ //
+ hresult = CoCreateInstance(
+ clsid, NULL, CLSCTX_LOCAL_SERVER, IID_IUnknown, (void FAR* FAR*)&punk);
+ if(hresult != NOERROR)
+ goto LError0;
+
+ // Create the proxies
+ //
+ hresult = punk->QueryInterface(IID_IDispatch, (void FAR* FAR*)ppdisp);
+
+ punk->Release();
+
+LError0:;
+ return hresult;
+}
diff --git a/private/oleauto/src/dispatch/disphelp.cpp b/private/oleauto/src/dispatch/disphelp.cpp
new file mode 100644
index 000000000..15add75b4
--- /dev/null
+++ b/private/oleauto/src/dispatch/disphelp.cpp
@@ -0,0 +1,229 @@
+/***
+*disphelp.cpp - App hosted IDispatch implementation helpers
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+*
+*Revision History:
+*
+* [00] 23-Sep-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#include <stdarg.h>
+
+#include "cdispti.h"
+
+ASSERTDATA
+
+
+EXTERN_C INTERNAL_(HRESULT)
+IndexOfParam(DISPPARAMS FAR* pdispparams, unsigned int uPosition, unsigned int FAR* puIndex)
+{
+ int i;
+
+ // try for named parameter first (if there are any)
+ //
+ for(i = 0; i < (int)pdispparams->cNamedArgs; ++i)
+ // sign extend uPosition so any special values will be properly
+ // expanded to 32 bits on win16.
+ //
+ if(pdispparams->rgdispidNamedArgs[i] == (DISPID)((int)uPosition))
+ goto LGotIt;
+
+ i = pdispparams->cArgs - (int)uPosition - 1;
+
+ if(i < (int)pdispparams->cNamedArgs)
+ return RESULT(DISP_E_PARAMNOTFOUND);
+
+ ASSERT(i >= (int)pdispparams->cNamedArgs
+ && i < (int)pdispparams->cArgs);
+
+LGotIt:;
+ *puIndex = (unsigned int)i;
+
+ return NOERROR;
+}
+
+
+/***
+*PUBLIC HRESULT DispGetParam(DISPPARAMS*, unsigned int, VARTYPE, VARIANTARG*, unsigned int*)
+*Purpose:
+* Utility for extracting a parameter from the IDispatch variant array.
+*
+*Entry:
+* pdispparams = pointer to DISPPARAMS struct
+* dispidName = name of the desired param.
+* uPosition = position of the desired parameters.
+* pvarResult = return parameter. This is passed in with the VARTYPE
+* set to the desired result.
+*
+*Exit:
+* return value = HRESULT
+* S_OK
+* E_INVALIDARG
+* E_OUTOFMEMORY
+* DISP_E_OVERFLOW
+* DISP_E_BADVARTYPE
+* DISP_E_TYPEMISMATCH
+* DISP_E_PARAMNOTFOUND
+*
+* pvarResult = pointer to the properly coerced parameter.
+* puArgErr = if the coersion failed, this will be the index of the
+* source param in the dispparams.rgvarg array.
+*
+***********************************************************************/
+STDAPI
+DispGetParam(
+ DISPPARAMS FAR* pdispparams,
+ unsigned int uPosition,
+ VARTYPE vtTarg,
+ VARIANT FAR* pvarResult,
+ unsigned int FAR* puArgErr)
+{
+ unsigned int uIndex;
+ HRESULT hresult;
+
+ IfFailRet(IndexOfParam(pdispparams, uPosition, &uIndex));
+
+ hresult = VariantChangeType(
+ pvarResult, &pdispparams->rgvarg[uIndex], 0, vtTarg);
+
+ if(hresult != NOERROR && puArgErr != NULL)
+ *puArgErr = uIndex;
+
+ return hresult;
+}
+
+#if OE_WIN32 && 0
+STDAPI
+DispGetParamW(
+ DISPPARAMS FAR* pdispparams,
+ unsigned int uPosition,
+ VARTYPE vtTarg,
+ VARIANT FAR* pvarResult,
+ unsigned int FAR* puArgErr)
+{
+ return DispGetParam(pdispparams, uPosition, vtTarg, pvarResult, puArgErr);
+}
+#endif
+
+/***
+*PUBLIC HRESULT DispGetIDsOfNames(ITypeInfo*, char**, unsigned int, DISPID*)
+*Purpose:
+* Default table driven implementation of IDispatch::GetIDsOfNames().
+*
+*Entry:
+* ptinfo = the typeinfo to use to map the names
+* rgszNames = the array of names to translate
+* cNames = count of names
+*
+*Exit:
+* return value = HRESULT
+* S_OK
+* E_INVALIDARG
+* DISP_E_UNKNOWNNAME
+*
+* rgdispid[] = array of DISPIDs corresponding to given array of names
+*
+*Note:
+* this routine that the PARAMDATA structure was declared in the proper
+* order - unfortunately there is no way to verify this. The proper
+* order to declare is in the same textual order that the parameters
+* appear on the argument list.
+*
+***********************************************************************/
+STDAPI
+DispGetIDsOfNames(
+ ITypeInfo FAR* ptinfo,
+ OLECHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ DISPID FAR* rgdispid)
+{
+ return ptinfo->GetIDsOfNames(rgszNames, cNames, rgdispid);
+}
+
+#if OE_WIN32 && 0
+STDAPI
+DispGetIDsOfNamesW(
+ ITypeInfoW FAR* ptinfo,
+ WCHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ DISPID FAR* rgdispid)
+{
+ return ptinfo->GetIDsOfNames(rgszNames, cNames, rgdispid);
+}
+#endif
+
+
+
+/***
+*PUBLIC HRESULT DispInvoke(...)
+*Purpose:
+* Default table driven implementation of IDispatch::Invoke()
+*
+*Entry:
+* _this = UNDONE
+* pmethdata = pointer to the METHODDATA struct describing the method
+* we are going to invoke.
+* pdispparams = pointer to the DISPPARAMS structure for this method.
+* pvarResult = pointer to a VARIANT for the return value.
+* ...
+*
+*Exit:
+* return value = HRESULT
+* S_OK
+* E_INVALIDARG
+* E_OUTOFMEMORY
+* DISP_E_TYPEMISMATCH - could not coerce arg to expected type
+* DISP_E_PARAMNOTFOUND - could not locate the param in the DISPPARAMS
+*
+* *pvarResult = UNDONE
+* *pexcepinfo = UNDONE
+* *puArgErr = UNDONE
+*
+***********************************************************************/
+
+STDAPI
+DispInvoke(
+ void FAR* _this,
+ ITypeInfo FAR* ptinfo,
+ DISPID dispidMember,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pdispparams,
+ VARIANT FAR* pvarResult,
+ EXCEPINFO FAR* pexcepinfo,
+ unsigned int FAR* puArgErr)
+{
+ return
+ ptinfo->Invoke(
+ _this,
+ dispidMember, wFlags, pdispparams,
+ pvarResult, pexcepinfo, puArgErr);
+}
+
+#if OE_WIN32 && 0
+STDAPI
+DispInvokeW(
+ void FAR* _this,
+ ITypeInfoW FAR* ptinfo,
+ DISPID dispidMember,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pdispparams,
+ VARIANT FAR* pvarResult,
+ WEXCEPINFO FAR* pexcepinfo,
+ unsigned int FAR* puArgErr)
+{
+ return
+ ptinfo->Invoke(
+ _this,
+ dispidMember, wFlags, pdispparams,
+ pvarResult, pexcepinfo, puArgErr);
+}
+#endif
diff --git a/private/oleauto/src/dispatch/dispiid.c b/private/oleauto/src/dispatch/dispiid.c
new file mode 100644
index 000000000..bf4bee904
--- /dev/null
+++ b/private/oleauto/src/dispatch/dispiid.c
@@ -0,0 +1,59 @@
+/***
+*dispiid.c
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file allocates (via Ole macro mania) the IDispatch related IIDs.
+*
+*Revision History:
+*
+* [00] 05-Oct-92 bradlo: Created.
+*
+*****************************************************************************/
+
+#ifdef _MAC
+# ifdef _MSC_VER
+# include <macos/types.h>
+# include <macos/packages.h>
+# include <macos/resource.h>
+# include <macos/menus.h>
+# include <macos/windows.h>
+# include <macos/osutils.h>
+# include <macos/appleeve.h>
+# define far
+# define FAR far
+# define near
+# define NEAR near
+# ifndef _PPCMAC
+# define pascal _pascal
+# endif
+# define PASCAL pascal
+# define cdecl _cdecl
+# define CDECL cdecl
+# else
+# include <types.h>
+# include <packages.h>
+# include <resources.h>
+# include <menus.h>
+# include <windows.h>
+# include <appleevents.h>
+# include <osutils.h>
+# include <AppleEvents.h>
+# endif
+#else
+# include <windows.h>
+#endif
+#include <ole2.h>
+
+// this redefines the Ole DEFINE_GUID() macro to do allocation.
+//
+#include <initguid.h>
+
+// due to the previous header, including this causes our DEFINE_GUID
+// definitions in the following headers to actually allocate data.
+
+// instantiate the dispatch related guids
+#include "dispatch.h"
+
diff --git a/private/oleauto/src/dispatch/dispmrsh.cpp b/private/oleauto/src/dispatch/dispmrsh.cpp
new file mode 100644
index 000000000..6c8786593
--- /dev/null
+++ b/private/oleauto/src/dispatch/dispmrsh.cpp
@@ -0,0 +1,1894 @@
+/***
+*dispmrsh.cpp
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Low level IDispatch marshaling support.
+*
+*Revision History:
+*
+* [00] 08-Nov-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+* There are assumptions in this marshaling code that the endianness
+* of the caller and callee are the same.
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#ifndef WIN32
+#include <cobjps.h>
+#endif //!WIN32
+
+#include "dispmrsh.h"
+
+ASSERTDATA
+
+#define SAFEARRAYOVERFLOW 0xffffffff
+
+#if OE_WIN32
+# define BSTRBYTELEN(x) (SysStringByteLen(x))
+#else
+# define BSTRBYTELEN(x) (SysStringLen(x))
+#endif
+
+PRIVATE_(HRESULT)
+SafeArrayReadExisting(
+ IStream FAR*,
+ unsigned char,
+ SAFEARRAY FAR* FAR*,
+ SYSKIND);
+
+
+//---------------------------------------------------------------------
+// VARIANT Marshaling Support
+//---------------------------------------------------------------------
+
+// NOTE: the following table is order dependent on VARENUM
+
+// 0 indicates N/A
+
+unsigned char g_cbVtSizes[] = {
+ 0 // VT_EMPTY
+ , 0 // VT_NULL,
+ , 2 // VT_I2,
+ , 4 // VT_I4,
+ , 4 // VT_R4,
+ , 8 // VT_R8,
+ , 8 // VT_CY,
+ , 8 // VT_DATE,
+ , 0 // VT_BSTR,
+ , 0 // VT_DISPATCH,
+ , 4 // VT_ERROR,
+ , 2 // VT_BOOL,
+ , 0 // VT_VARIANT,
+ , 0 // VT_UNKNOWN,
+ , 0 // unused
+ , 0 // unused
+ , 1 // VT_I1
+ , 1 // VT_UI1
+};
+
+
+/***
+*PRIVATE HRESULT BstrWrite(IStream*, BSTR)
+*Purpose:
+* Write the given BSTR to the given stream
+*
+*Entry:
+* pstm = pointer to the IStream to write the BSTR into
+* bstr = the BSTR to write
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT BstrWrite(IStream FAR* pstm, BSTR bstr, SYSKIND syskind)
+{
+ unsigned int cbSize;
+ unsigned char fIsNull;
+ unsigned long _cbSize;
+
+ cbSize = BSTRBYTELEN(bstr);
+ _cbSize = (unsigned long) cbSize;
+
+ // A Bstr of length 0 may be either a Null, or an empty string ("").
+ // we want to remember which of these it was, so we can reconstitute
+ // it in exactly the same way.
+ if(cbSize == 0){
+ IfFailRet(PUT(pstm, _cbSize));
+ fIsNull = (bstr == NULL) ? TRUE : FALSE;
+ return PUT(pstm, fIsNull);
+ }
+
+#if OE_WIN32 /* enable 16/32 interoperablity support */
+ if (syskind == SYS_WIN16) {
+ char *pBuf;
+ HRESULT hresult;
+
+ cbSize = SysStringLen(bstr);
+ _cbSize = (unsigned long) cbSize;
+ IfFailRet(PUT(pstm, _cbSize));
+
+ // convert UNICODE string to ANSI and stream it
+ if ((pBuf = new FAR char [cbSize]) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+ WideCharToMultiByte(CP_ACP, NULL, (WCHAR *) bstr, cbSize,
+ pBuf, cbSize, NULL, NULL);
+ hresult = pstm->Write(pBuf, cbSize, NULL);
+ delete pBuf;
+ return hresult;
+ } else
+#endif
+ {
+ IfFailRet(PUT(pstm, _cbSize));
+ return pstm->Write(bstr, cbSize, NULL);
+ }
+}
+
+/***
+*PRIVATE HRESULT BstrRead(IStream*, BSTR*, SYSKIND)
+*Purpose:
+* Read a BSTR from the given stream.
+*
+*Entry:
+* pstm = the IStream to read the BSTR from.
+*
+*Exit:
+* *pbstr = the reconstituted BSTR
+*
+***********************************************************************/
+HRESULT BstrRead(IStream FAR* pstm, BSTR FAR* pbstr, SYSKIND syskind)
+{
+ BSTR bstr;
+ HRESULT hresult;
+ unsigned int cbSize;
+ unsigned char fIsNull;
+ unsigned long _cbSize;
+
+ IfFailRet(GET(pstm, _cbSize));
+ cbSize = (unsigned int) _cbSize;
+
+ if(cbSize == 0){
+
+ // reconstitute the zero length bstr as either a Null, or an empty
+ // string (""), depending on how it was originally written into
+ // the stream.
+
+ IfFailRet(GET(pstm, fIsNull));
+ if(fIsNull){
+ *pbstr = NULL;
+ return NOERROR;
+ }
+ return ErrSysAllocStringLen(NULL, 0, pbstr);
+ }
+
+ // Note: SysAllocStringLen allways allocates an extra byte (thats
+ // not counted in the bstr length) and puts a '\0' at the end of the
+ // allocated block (ie, block[cbSize] = '\0')
+
+#if OE_WIN32 /* enable 16/32 interoperablity support */
+ if (syskind == SYS_WIN16) {
+ char *pBuf;
+
+ // Get ANSI string from stream
+ if ((pBuf = new FAR char [cbSize]) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+ IfFailGo(pstm->Read((void FAR*) pBuf, cbSize, NULL), LError0);
+
+ // convert it to UNICODE bstr
+ IfFailRet(ErrSysAllocStringLen(NULL, cbSize, &bstr));
+ MultiByteToWideChar(CP_ACP, MB_PRECOMPOSED,
+ pBuf, cbSize,
+ bstr, cbSize);
+ delete pBuf;
+ } else
+#endif
+ {
+ IfFailRet(ErrSysAllocStringLen(NULL, CHLEN(cbSize), &bstr));
+
+ IfFailGo(pstm->Read(bstr, cbSize, NULL), LError0);
+ }
+
+ *pbstr = bstr;
+
+ return NOERROR;
+
+LError0:
+ SysFreeString(bstr);
+
+ return hresult;
+}
+
+
+#if OE_WIN32 // 16/32 interop support
+/***
+*INTERNAL DispMarshalHresult
+*Purpose:
+* Map hresults that have changed between 16-bit and 32-bit to their 16-bit
+* values.
+*
+*Entry:
+* pstm = the stream to marshal into
+* hresult = the hresult to marshal
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+INTERNAL_(HRESULT)
+DispMarshalHresult(
+ IStream FAR* pstm,
+ HRESULT hresult)
+{
+ // map 32-bit values that have changed to the 16-bit values
+ switch (hresult) {
+ case E_NOTIMPL:
+ hresult = 0x80000001;
+ break;
+ case E_OUTOFMEMORY:
+ hresult = 0x80000002;
+ break;
+ case E_INVALIDARG:
+ hresult = 0x80000003;
+ break;
+ case E_NOINTERFACE:
+ hresult = 0x80000004;
+ break;
+ case E_POINTER:
+ hresult = 0x80000005;
+ break;
+ case E_HANDLE:
+ hresult = 0x80000006;
+ break;
+ case E_ABORT:
+ hresult = 0x80000007;
+ break;
+ case E_FAIL:
+ hresult = 0x80000008;
+ break;
+ case E_ACCESSDENIED:
+ hresult = 0x80000009;
+ break;
+ default:
+ break;
+ }
+ return CoMarshalHresult(pstm, hresult);
+}
+
+
+/***
+*INTERNAL HRESULT DispUnmarshalHresult
+*Purpose:
+* Unmarshal hresults that has changed between 16-bit and 32-bit to their
+* 32-bit values.
+*
+*Entry:
+* pstm = the stream to unmarshal from
+*
+*Exit:
+* return value = HRESULT
+*
+* *phresult = the unmarshaled hresult.
+*
+***********************************************************************/
+INTERNAL_(HRESULT)
+DispUnmarshalHresult(
+ IStream FAR* pstm,
+ HRESULT FAR* phresult)
+{
+ IfFailRet(CoUnmarshalHresult(pstm, phresult));
+
+ // map 16-bit values that have changed to the 32-bit values
+ switch ((DWORD)*phresult) {
+ case 0x80000001L:
+ *phresult = E_NOTIMPL;
+ break;
+ case 0x80000002L:
+ *phresult = E_OUTOFMEMORY;
+ break;
+ case 0x80000003L:
+ *phresult = E_INVALIDARG;
+ break;
+ case 0x80000004L:
+ *phresult = E_NOINTERFACE;
+ break;
+ case 0x80000005L:
+ *phresult = E_POINTER;
+ break;
+ case 0x80000006L:
+ *phresult = E_HANDLE;
+ break;
+ case 0x80000007L:
+ *phresult = E_ABORT;
+ break;
+ case 0x80000008L:
+ *phresult = E_FAIL;
+ break;
+ case 0x80000009L:
+ *phresult = E_ACCESSDENIED;
+ break;
+ default:
+ break;
+ }
+ return NOERROR;
+}
+#endif //OE_WIN32
+
+
+/***
+*PRIVATE HRESULT VariantWrite(IStream*, VARIANTARG*)
+*Purpose:
+* Write the given VARIANTARG to the given stream.
+*
+*Entry:
+* pvarg = the VARIANTARG to write
+* pstm = the stream to write it into
+*
+*Exit:
+* return value = HRESULT
+* S_OK
+* E_INVALIDARG
+*
+**************************************************************************/
+HRESULT
+VariantWrite(IStream FAR* pstm, VARIANTARG FAR* pvarg, SYSKIND syskind)
+{
+ VARTYPE vt;
+ unsigned int cbSize;
+ void FAR* pv;
+
+#ifdef _DEBUG
+ if(pstm == NULL)
+ return RESULT(E_INVALIDARG);
+ if(IsBadReadPtr(pvarg, sizeof(*pvarg)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ IfFailRet(PUT(pstm, V_VT(pvarg)));
+
+ switch(V_VT(pvarg)){
+#if VBA2
+ case VT_UI1 | VT_BYREF:
+#endif //VBA2
+ case VT_I2 | VT_BYREF:
+ case VT_I4 | VT_BYREF:
+ case VT_R4 | VT_BYREF:
+ case VT_R8 | VT_BYREF:
+ case VT_CY | VT_BYREF:
+ case VT_BOOL | VT_BYREF:
+ case VT_DATE | VT_BYREF:
+#if !OE_WIN32
+ case VT_ERROR | VT_BYREF:
+#endif //OE_WIN32
+ pv = V_BYREF(pvarg);
+ goto LWriteVal;
+
+#if VBA2
+ case VT_UI1:
+#endif //VBA2
+ case VT_I2:
+ case VT_I4:
+ case VT_R4:
+ case VT_R8:
+ case VT_CY:
+ case VT_BOOL:
+ case VT_DATE:
+#if !OE_WIN32
+ case VT_ERROR:
+#endif //OE_WIN32
+ pv = &V_NONE(pvarg);
+
+LWriteVal:;
+ vt = V_VT(pvarg) & ~(VT_BYREF|VT_ARRAY);
+ ASSERT(vt < DIM(g_cbVtSizes));
+
+ cbSize = g_cbVtSizes[vt];
+ ASSERT(cbSize != 0);
+
+#ifdef _DEBUG
+ if(IsBadReadPtr(pv, cbSize))
+ return RESULT(E_INVALIDARG);
+#endif
+ return pstm->Write(pv, cbSize, NULL);
+
+ case VT_BSTR:
+ return BstrWrite(pstm, V_BSTR(pvarg), syskind);
+
+ case VT_BSTR | VT_BYREF:
+ return BstrWrite(pstm, *V_BSTRREF(pvarg), syskind);
+
+#if OE_WIN32
+ case VT_ERROR:
+ return DispMarshalHresult(pstm, V_ERROR(pvarg));
+
+ case VT_ERROR | VT_BYREF:
+ return DispMarshalHresult(pstm, *V_ERRORREF(pvarg));
+#endif //OE_WIN32
+
+ case VT_UNKNOWN:
+ return DispMarshalInterface(pstm, IID_IUnknown, V_UNKNOWN(pvarg));
+
+ case VT_UNKNOWN | VT_BYREF:
+ return DispMarshalInterface(pstm, IID_IUnknown, *V_UNKNOWNREF(pvarg));
+
+ case VT_DISPATCH:
+ return DispMarshalInterface(pstm, IID_IDispatch, V_DISPATCH(pvarg));
+
+ case VT_DISPATCH | VT_BYREF:
+ return DispMarshalInterface(pstm, IID_IDispatch, *V_DISPATCHREF(pvarg));
+
+ case VT_VARIANT | VT_BYREF:
+ return VariantWrite(pstm, V_VARIANTREF(pvarg), syskind);
+
+ case VT_NULL:
+ case VT_EMPTY: // nothing to write for these guys.
+ return NOERROR;
+
+ // VT_INTERFACE is an internal type that is used for Marshaling
+ // custom interfaces. This should never be seen by the outside world.
+ //
+ case VT_INTERFACE:
+ { REFIID riid = *((VARIANTX FAR*)pvarg)->piid;
+ IfFailRet(pstm->Write((const void FAR*)&riid, sizeof(IID), NULL));
+ return DispMarshalInterface(pstm, riid, V_UNKNOWN(pvarg));
+ }
+
+ case VT_INTERFACE | VT_BYREF:
+ { REFIID riid = *((VARIANTX FAR*)pvarg)->piid;
+ IfFailRet(pstm->Write((const void FAR*)&riid, sizeof(IID), NULL));
+ return DispMarshalInterface(pstm, riid, *V_UNKNOWNREF(pvarg));
+ }
+
+ default:
+ if(V_VT(pvarg) & VT_ARRAY){
+ // Dont currently support arrays of custom interfaces
+ ASSERT((V_VT(pvarg) & ~(VT_BYREF|VT_ARRAY)) != VT_INTERFACE);
+ return SafeArrayWrite(pstm,
+ V_ISBYREF(pvarg)
+ ? *V_ARRAYREF(pvarg)
+ : V_ARRAY(pvarg),
+ syskind);
+ }
+ return RESULT(E_INVALIDARG);
+ }
+
+ ASSERT(UNREACHED);
+ return RESULT(E_FAIL);
+}
+
+
+/***
+*PRIVATE HRESULT VariantRead(IStream*, VARIANTARG*, VARIANT*)
+*Purpose:
+* Read a VARIANTARG from the given stream.
+*
+*Entry:
+* pstm = pointer to the IStream interface we are to read from
+* pvarg = the VARIANTARG to read into
+* pv = pointer to memory to use for ByRef values. If pv is NULL, then
+* the caller is not expecting a ByRef value, and we return an error.
+*
+*Exit:
+* return value = HRESULT
+* [UNDONE: enumerate results]
+*
+* *pvarg = the unmarshalled VARIANTARG.
+*
+**************************************************************************/
+HRESULT
+VariantRead(IStream FAR* pstm,
+ VARIANTARG FAR* pvarg,
+ VARIANT FAR* pvarRef,
+ SYSKIND syskind)
+{
+ VARTYPE vt;
+ unsigned int cbSize;
+ void FAR* pv;
+
+#ifdef _DEBUG
+ if(pstm == NULL)
+ return RESULT(E_INVALIDARG);
+ if(IsBadWritePtr(pvarg, sizeof(*pvarg)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ IfFailRet(GET(pstm, V_VT(pvarg)));
+
+ if(V_ISBYREF(pvarg)){
+ if(pvarRef == NULL)
+ return RESULT(E_INVALIDARG);
+#ifdef _DEBUG
+ if(IsBadWritePtr(pvarRef, sizeof(*pvarRef)))
+ return RESULT(E_INVALIDARG);
+#endif
+ V_BYREF(pvarg) = &V_NONE(pvarRef);
+ V_VT(pvarRef) = (V_VT(pvarg) & ~VT_BYREF);
+ }
+
+ switch(V_VT(pvarg)){
+#if VBA2
+ case VT_BYREF | VT_UI1:
+#endif //VBA2
+ case VT_BYREF | VT_I2:
+ case VT_BYREF | VT_I4:
+ case VT_BYREF | VT_R4:
+ case VT_BYREF | VT_R8:
+ case VT_BYREF | VT_CY:
+ case VT_BYREF | VT_BOOL:
+ case VT_BYREF | VT_DATE:
+#if !OE_WIN32
+ case VT_ERROR | VT_BYREF:
+#endif //!OE_WIN32
+ pv = (void FAR*)V_BYREF(pvarg);
+ goto LReadVal;
+
+#if VBA2
+ case VT_UI1:
+#endif //VBA2
+ case VT_I2:
+ case VT_I4:
+ case VT_R4:
+ case VT_R8:
+ case VT_CY:
+ case VT_BOOL:
+ case VT_DATE:
+#if !OE_WIN32
+ case VT_ERROR:
+#endif //!OE_WIN32
+ pv = (void FAR*)&V_NONE(pvarg);
+
+LReadVal:;
+ vt = V_VT(pvarg) & ~(VT_BYREF|VT_ARRAY);
+ ASSERT(vt < DIM(g_cbVtSizes));
+
+ cbSize = g_cbVtSizes[vt];
+ ASSERT(cbSize != 0);
+
+ return pstm->Read(pv, cbSize, NULL);
+
+ case VT_BSTR:
+ return BstrRead(pstm, &V_BSTR(pvarg), syskind);
+
+ case VT_BSTR | VT_BYREF:
+ return BstrRead(pstm, V_BSTRREF(pvarg), syskind);
+
+#if OE_WIN32
+ case VT_ERROR:
+ return DispUnmarshalHresult(pstm, &V_ERROR(pvarg));
+
+ case VT_ERROR | VT_BYREF:
+ return DispUnmarshalHresult(pstm, V_ERRORREF(pvarg));
+#endif //OE_WIN32
+
+ case VT_UNKNOWN:
+ return DispUnmarshalInterface(
+ pstm, IID_IUnknown, (void FAR* FAR*)&V_UNKNOWN(pvarg));
+
+ case VT_BYREF | VT_UNKNOWN:
+ return DispUnmarshalInterface(
+ pstm, IID_IUnknown, (void FAR* FAR*)V_UNKNOWNREF(pvarg));
+
+ case VT_DISPATCH:
+ return DispUnmarshalInterface(
+ pstm, IID_IDispatch, (void FAR* FAR*)&V_DISPATCH(pvarg));
+
+ case VT_BYREF | VT_DISPATCH:
+ return DispUnmarshalInterface(
+ pstm, IID_IDispatch, (void FAR* FAR*)V_DISPATCHREF(pvarg));
+
+ case VT_VARIANT | VT_BYREF:
+ V_VARIANTREF(pvarg) = pvarRef;
+ return VariantRead(pstm, pvarRef, NULL, syskind);
+
+ // VT_INTERFACE is an internal type that is used for Marshaling
+ // custom interfaces. This should never be seen by the outside world.
+ //
+ case VT_INTERFACE:
+ pv = &V_UNKNOWN(pvarg);
+ goto VtInterface;
+ case VT_INTERFACE | VT_BYREF:
+ pv = V_UNKNOWN(pvarg);
+ // FALLTHROUGH
+VtInterface:;
+ { VARIANTX FAR* pvarx = (VARIANTX FAR*)pvarg;
+ REFIID riid = *(pvarx->piid);
+ if((pvarx->piid = new IID) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+ IfFailRet(pstm->Read(pvarx->piid, sizeof(IID), NULL));
+ return DispUnmarshalInterface(pstm, riid, (void FAR* FAR*)pv);
+ }
+
+ case VT_NULL:
+ V_I4(pvarg) = 0L;
+ case VT_EMPTY:
+ return NOERROR;
+
+ default:
+ if(V_VT(pvarg) & VT_ARRAY){
+ return SafeArrayRead(
+ pstm,
+ (V_ISBYREF(pvarg)) ? V_ARRAYREF(pvarg) : &V_ARRAY(pvarg),
+ syskind);
+ }
+ return RESULT(E_INVALIDARG);
+ }
+
+ ASSERT(UNREACHED);
+ return RESULT(E_FAIL);
+}
+
+
+/***
+*HRESULT VariantReadType(IStream*, VARIANTARG*)
+*Purpose:
+* Read a VARIANTARG of the type indicated by the given 'pvarg',
+* *and* read it into the given 'pvarg'. This will require releasing
+* the current contents of 'pvarg'.
+*
+*Entry:
+* pstm = pointer to the IStream interface we are to read from
+* pvarg = pointer to a valid VARIANTARG whose contents we are to
+* release and overwrite with date of the same type.
+*
+*Exit:
+* return value = HRESULT
+*
+* *pvarg = the reconstituted VARIANTARG
+*
+**************************************************************************/
+HRESULT
+VariantReadType(IStream FAR* pstm, VARIANTARG FAR* pvarg, SYSKIND syskind)
+{
+ VARTYPE vt;
+ GUID guid;
+ void FAR* pv;
+ unsigned int cbSize;
+ IUnknown FAR* punk;
+ IDispatch FAR* pdisp;
+
+#ifdef _DEBUG
+ if(pstm == NULL)
+ return RESULT(E_INVALIDARG);
+ if(IsBadWritePtr(pvarg, sizeof(*pvarg)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ IfFailRet(GET(pstm, vt));
+
+ if(vt != V_VT(pvarg))
+ return RESULT(E_INVALIDARG); // REVIEW: is this the proper error for this?
+
+ switch(vt){
+#if VBA2
+ case VT_UI1 | VT_BYREF:
+#endif //VBA2
+ case VT_I2 | VT_BYREF:
+ case VT_I4 | VT_BYREF:
+ case VT_R4 | VT_BYREF:
+ case VT_R8 | VT_BYREF:
+ case VT_CY | VT_BYREF:
+ case VT_BOOL | VT_BYREF:
+ case VT_DATE | VT_BYREF:
+#if !OE_WIN32
+ case VT_ERROR | VT_BYREF:
+#endif //!OE_WIN32
+ pv = V_BYREF(pvarg);
+ goto LReadVal;
+
+#if VBA2
+ case VT_UI1:
+#endif //VBA2
+ case VT_I2:
+ case VT_I4:
+ case VT_R4:
+ case VT_R8:
+ case VT_CY:
+ case VT_BOOL:
+ case VT_DATE:
+#if !OE_WIN32
+ case VT_ERROR:
+#endif //!OE_WIN32
+ pv = &V_NONE(pvarg);
+LReadVal:;
+ vt &= ~(VT_BYREF|VT_ARRAY);
+ ASSERT(vt < DIM(g_cbVtSizes));
+ cbSize = g_cbVtSizes[vt];
+ ASSERT(cbSize != 0);
+ return pstm->Read(pv, cbSize, NULL);
+
+ case VT_BSTR:
+ SysFreeString(V_BSTR(pvarg));
+ return BstrRead(pstm, &V_BSTR(pvarg), syskind);
+
+ case VT_BSTR | VT_BYREF:
+ SysFreeString(*V_BSTRREF(pvarg));
+ return BstrRead(pstm, V_BSTRREF(pvarg), syskind);
+
+#if OE_WIN32
+ case VT_ERROR:
+ return DispUnmarshalHresult(pstm, &V_ERROR(pvarg));
+
+ case VT_ERROR | VT_BYREF:
+ return DispUnmarshalHresult(pstm, V_ERRORREF(pvarg));
+#endif //OE_WIN32
+
+ case VT_UNKNOWN:
+ IfFailRet(DispUnmarshalInterface(
+ pstm, IID_IUnknown, (void FAR* FAR*)&punk));
+ if(V_UNKNOWN(pvarg) != NULL)
+ V_UNKNOWN(pvarg)->Release();
+ V_UNKNOWN(pvarg) = punk;
+ return NOERROR;
+
+ case VT_BYREF | VT_UNKNOWN:
+ IfFailRet(DispUnmarshalInterface(
+ pstm, IID_IUnknown, (void FAR* FAR*)&punk));
+ if((*V_UNKNOWNREF(pvarg)) != NULL)
+ (*V_UNKNOWNREF(pvarg))->Release();
+ *V_UNKNOWNREF(pvarg) = punk;
+ return NOERROR;
+
+ case VT_DISPATCH:
+ IfFailRet(DispUnmarshalInterface(
+ pstm, IID_IDispatch, (void FAR* FAR*)&pdisp));
+ if(V_DISPATCH(pvarg) != NULL)
+ V_DISPATCH(pvarg)->Release();
+ V_DISPATCH(pvarg) = pdisp;
+ return NOERROR;
+
+ case VT_BYREF | VT_DISPATCH:
+ IfFailRet(DispUnmarshalInterface(
+ pstm, IID_IDispatch, (void FAR* FAR*)&pdisp));
+ if((*V_DISPATCHREF(pvarg)) != NULL)
+ (*V_DISPATCHREF(pvarg))->Release();
+ *V_DISPATCHREF(pvarg) = pdisp;
+ return NOERROR;
+
+ // VT_INTERFACE is an internal type that is used for Marshaling
+ // custom interfaces. This should never be seen by the outside world.
+ //
+ case VT_INTERFACE:
+ case VT_INTERFACE | VT_BYREF:
+ { VARIANTX FAR* pvarx = (VARIANTX FAR*)pvarg;
+ IfFailRet(GET(pstm, guid));
+ IfFailRet(DispUnmarshalInterface(pstm, guid, (void FAR* FAR*)&punk));
+ ASSERT(pvarx->piid != NULL && *pvarx->piid == guid);
+ if(vt & VT_BYREF){
+ if(*(pvarx->ppunk) != NULL)
+ (*(pvarx->ppunk))->Release();
+ *(pvarx->ppunk) = punk;
+ }else{
+ if(pvarx->punk != NULL)
+ pvarx->punk->Release();
+ pvarx->punk = punk;
+ }
+ }
+ return NOERROR;
+
+ case VT_VARIANT | VT_BYREF:
+
+ VARIANT var;
+ HRESULT hr;
+
+ MEMCPY(&var, V_VARIANTREF(pvarg), sizeof(VARIANT));
+ if ((hr = VariantRead(pstm, V_VARIANTREF(pvarg), NULL, syskind)) == NOERROR)
+ VariantClear(&var);
+ else
+ MEMCPY(V_VARIANTREF(pvarg), &var, sizeof(VARIANT));
+ return hr;
+
+ case VT_NULL:
+ V_I4(pvarg) = 0L;
+ case VT_EMPTY:
+ return NOERROR;
+
+ default:
+ if(vt & VT_ARRAY){
+ if(V_ISBYREF(pvarg)){
+ return SafeArrayReadExisting(pstm, TRUE, V_ARRAYREF(pvarg), syskind);
+ }else{
+ return SafeArrayReadExisting(pstm, FALSE, &V_ARRAY(pvarg), syskind);
+ }
+ }
+
+ return RESULT(E_INVALIDARG);
+ }
+
+ ASSERT(UNREACHED);
+ return RESULT(E_FAIL);
+}
+
+
+//---------------------------------------------------------------------
+// EXCEPINFO Marshaling Support
+//---------------------------------------------------------------------
+
+
+/***
+*HRESULT ExcepinfoRead(IStream*, EXCEPINFO*)
+*Purpose:
+* Read an EXCEPINFO from the given stream.
+*
+* Out: <EXCEPINFO>
+* <BSTR bstrSource>
+* <BSTR bstrDescription>
+* <BSTR bstrHelpFile>
+*
+* Note: this routines sets pfnDeferredFillIn to NULL because it
+* must have already been called when the EXCEPINFO was serialized.
+*
+*Entry:
+* pstm = the IStream to read from
+*
+*Exit:
+* return value = HRESULT
+*
+* *pexcepinfo = the EXCEPINFO read from the stream
+*
+***********************************************************************/
+HRESULT
+ExcepinfoRead(IStream FAR* pstm, EXCEPINFO FAR* pexcepinfo, SYSKIND syskind)
+{
+#ifdef _DEBUG
+ if(IsBadWritePtr(pexcepinfo, sizeof(*pexcepinfo)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ IfFailRet(pstm->Read(pexcepinfo, sizeof(*pexcepinfo), NULL));
+
+ IfFailRet(BstrRead(pstm, &(pexcepinfo->bstrSource), syskind));
+
+ IfFailRet(BstrRead(pstm, &(pexcepinfo->bstrDescription), syskind));
+
+ IfFailRet(BstrRead(pstm, &(pexcepinfo->bstrHelpFile), syskind));
+
+ pexcepinfo->pfnDeferredFillIn = NULL;
+
+ return NOERROR;
+}
+
+
+/***
+*HRESULT ExcepinfoWrite(IStream*, EXCEPINFO*)
+*Purpose:
+* Write the given EXCEPINFO into the given stream.
+*
+* Note: must invoke the pfnDeferredFillIn function (if there is one)
+* because there is no way to serialize the function.
+*
+*Entry:
+* pstm = the IStream to write into
+* pexcepinfo = the EXCEPINFO to write
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+ExcepinfoWrite(IStream FAR* pstm, EXCEPINFO FAR* pexcepinfo, SYSKIND syskind)
+{
+#ifdef _DEBUG
+ if(IsBadReadPtr(pexcepinfo, sizeof(*pexcepinfo)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ if(pexcepinfo->pfnDeferredFillIn != NULL)
+ IfFailRet(pexcepinfo->pfnDeferredFillIn(pexcepinfo));
+
+ IfFailRet(pstm->Write(pexcepinfo, sizeof(*pexcepinfo), NULL));
+
+ IfFailRet(BstrWrite(pstm, pexcepinfo->bstrSource, syskind));
+
+ IfFailRet(BstrWrite(pstm, pexcepinfo->bstrDescription, syskind));
+
+ IfFailRet(BstrWrite(pstm, pexcepinfo->bstrHelpFile, syskind));
+
+ return NOERROR;
+}
+
+
+//---------------------------------------------------------------------
+// Rich Error marshaling support
+//---------------------------------------------------------------------
+
+#if VBA2
+/***
+*PRIVATE HRESULT MarshalErrorInfo
+*Purpose:
+* Marshal the current Rich Error state into the given stream.
+*
+*Entry:
+* pstm = the stream to marshal into
+*
+* Format:
+* long fHasInfo
+* if(fHasInfo){
+* DWORD dwHelpContext
+* GUID guid
+* BSTR bstrSource
+* BSTR bstrDescription
+* BSTR bstrHelpFile
+* }
+*
+*Exit:
+* return value = HRESULT
+*
+*NOTE:
+* This routine has the side effect of removing the current threads
+* rich error state. In effect, it has moved from its physical thread
+* storage, into the given stream.
+*
+***********************************************************************/
+HRESULT
+MarshalErrorInfo(IStream FAR* pstm, SYSKIND syskind)
+{
+ GUID guid;
+ long fHasInfo;
+ HRESULT hresult;
+ DWORD dwHelpContext;
+ IErrorInfo FAR* perrinfo;
+ BSTR bstrSource, bstrDescription, bstrHelpFile;
+
+ perrinfo = NULL;
+
+ guid = GUID_NULL;
+ bstrSource = NULL;
+ bstrDescription = NULL;
+ bstrHelpFile = NULL;
+ dwHelpContext = 0L;
+
+ if(GetErrorInfo(0L, &perrinfo) != NOERROR){
+ fHasInfo = FALSE;
+ IfFailGo(PUT(pstm, fHasInfo), Error);
+ }else{
+ perrinfo->GetGUID(&guid);
+ perrinfo->GetSource(&bstrSource);
+ perrinfo->GetDescription(&bstrDescription);
+ perrinfo->GetHelpFile(&bstrHelpFile);
+ perrinfo->GetHelpContext(&dwHelpContext);
+
+ fHasInfo = TRUE;
+ IfFailGo(PUT(pstm, fHasInfo), Error);
+ IfFailGo(PUT(pstm, dwHelpContext), Error);
+ IfFailGo(PUT(pstm, guid), Error);
+ IfFailGo(BstrWrite(pstm, bstrSource, syskind), Error);
+ IfFailGo(BstrWrite(pstm, bstrDescription, syskind), Error);
+ IfFailGo(BstrWrite(pstm, bstrHelpFile, syskind), Error);
+ }
+
+ hresult = NOERROR;
+
+Error:;
+ SysFreeString(bstrSource);
+ SysFreeString(bstrDescription);
+ SysFreeString(bstrHelpFile);
+ if(perrinfo != NULL)
+ perrinfo->Release();
+ return hresult;
+}
+
+HRESULT
+UnmarshalErrorInfo(IStream FAR* pstm, SYSKIND syskind)
+{
+ GUID guid;
+ long fHasInfo;
+ HRESULT hresult;
+ DWORD dwHelpContext;
+ IErrorInfo FAR* perrinfo;
+ ICreateErrorInfo FAR* pcerrinfo;
+ BSTR bstrSource, bstrDescription, bstrHelpFile;
+
+ perrinfo = NULL;
+ pcerrinfo = NULL;
+
+ guid = GUID_NULL;
+ bstrSource = NULL;
+ bstrDescription = NULL;
+ bstrHelpFile = NULL;
+ dwHelpContext = 0L;
+
+ IfFailGo(GET(pstm, fHasInfo), Error);
+
+ if(!fHasInfo){
+ SetErrorInfo(0L, NULL);
+ return NOERROR;
+ }
+
+ IfFailGo(GET(pstm, dwHelpContext), Error);
+ IfFailGo(GET(pstm, guid), Error);
+ IfFailGo(BstrRead(pstm, &bstrSource, syskind), Error);
+ IfFailGo(BstrRead(pstm, &bstrDescription, syskind), Error);
+ IfFailGo(BstrRead(pstm, &bstrHelpFile, syskind), Error);
+
+ if(CreateErrorInfo(&pcerrinfo) == NOERROR){
+ pcerrinfo->SetGUID(guid);
+ pcerrinfo->SetSource(bstrSource);
+ pcerrinfo->SetDescription(bstrDescription);
+ pcerrinfo->SetHelpFile(bstrHelpFile);
+ pcerrinfo->SetHelpContext(dwHelpContext);
+ if(pcerrinfo->QueryInterface(IID_IErrorInfo, (void FAR* FAR*)&perrinfo) == NOERROR)
+ SetErrorInfo(0L, perrinfo);
+ }
+
+ hresult = NOERROR;
+
+Error:
+ SysFreeString(bstrSource);
+ SysFreeString(bstrDescription);
+ SysFreeString(bstrHelpFile);
+ if(pcerrinfo != NULL)
+ pcerrinfo->Release();
+ if(perrinfo != NULL)
+ perrinfo->Release();
+ return hresult;
+}
+#endif //VBA2
+
+//---------------------------------------------------------------------
+// SafeArray Marshaling Support
+//---------------------------------------------------------------------
+
+/***
+*PRIVATE HRESULT SafeArrayWrite(IStream*, SAFEARRAY)
+*Purpose:
+* Write the given SafeArray into the given stream.
+*
+* Out:
+* unsigned char fIsNull - was the SAFEARRAY ptr Null?
+* unsigned short cDims
+* unsigned short fFeatures
+* unsigned short cbElements
+* SAFEARRAYBOUND rgsabound
+* BYTEs pvData
+*
+*Entry:
+* pstm = the stream to write the SafeArray into
+* psa = pointer to the SafeArray
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+LOCAL HRESULT
+SafeArrayWrite(IStream FAR* pstm, SAFEARRAY FAR* psa, SYSKIND syskind)
+{
+ unsigned char fIsNull;
+ unsigned long i, size, cElements;
+ unsigned long _cbElements;
+
+ if(psa == NULL){
+ fIsNull = TRUE;
+ IfFailRet(PUT(pstm, fIsNull));
+ return NOERROR;
+ }
+
+#ifdef _DEBUG
+ if(IsBadReadPtr(psa, sizeof(*psa)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ fIsNull = FALSE;
+ IfFailRet(PUT(pstm, fIsNull));
+ IfFailRet(PUT(pstm, psa->cDims));
+ //[bb] C9.00 parser bug: (psa->fFeatures & ~FADF_FEATURES) gets the "&"
+ //[bb] operator wrong and tries to take the address of FADF_FEATURES!
+ //[bb] Copy psa->fFeatures into a local and use "&=" to get things to work.
+ unsigned short usFeatures = psa->fFeatures;
+ usFeatures &= ~FADF_FORCEFREE;
+ IfFailRet(PUT(pstm, usFeatures));
+ _cbElements = (unsigned long) psa->cbElements;
+ IfFailRet(PUT(pstm, _cbElements));
+ IfFailRet(
+ pstm->Write(psa->rgsabound, psa->cDims * sizeof(SAFEARRAYBOUND), NULL));
+
+ size = SafeArraySize(psa);
+ ASSERT(size != SAFEARRAYOVERFLOW); // existing array, no overflow possible
+ cElements = size / psa->cbElements;
+
+ SafeArrayLock(psa);
+
+ if(psa->fFeatures & FADF_BSTR){
+
+ BSTR HUGEP *pbstr = (BSTR HUGEP*)psa->pvData;
+ for(i = 0; i < cElements; ++i, ++pbstr)
+ IfFailRet(BstrWrite(pstm, *pbstr, syskind));
+
+ }else if(psa->fFeatures & FADF_VARIANT){
+
+ VARIANT HUGEP* pvar = (VARIANT HUGEP*)psa->pvData;
+ for(i = 0; i < cElements; ++i, ++pvar)
+ IfFailRet(VariantWrite(pstm, pvar, syskind));
+
+ }else if(psa->fFeatures & FADF_UNKNOWN){
+
+ IUnknown FAR* HUGEP* ppunk = (IUnknown FAR* HUGEP*)psa->pvData;
+ for(i = 0; i < cElements; ++i, ++ppunk){
+ IfFailRet(DispMarshalInterface(pstm, IID_IUnknown, *ppunk));
+ }
+
+ }else if(psa->fFeatures & FADF_DISPATCH){
+
+ IDispatch FAR* HUGEP* ppdisp = (IDispatch FAR* HUGEP*)psa->pvData;
+ for(i = 0; i < cElements; ++i, ++ppdisp){
+ IfFailRet(DispMarshalInterface(pstm, IID_IDispatch, *ppdisp));
+ }
+
+ }else{
+
+ IfFailRet(pstm->Write(psa->pvData, size, NULL));
+
+ }
+
+ SafeArrayUnlock(psa);
+
+ return NOERROR;
+}
+
+
+/***
+*PRIVATE HRESULT SafeArrayReadData(IStream*, SAFEARRAY*, SYSKIND)
+*Purpose:
+* Read the data for the given SafeArray from the given stream into
+* the given safe array. This routine releases any existing array
+* contents as it goes.
+*
+*Entry:
+* pstm = the IStream to read from
+* psa = the SafeArray to read the data into
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+LOCAL HRESULT
+SafeArrayReadData(IStream FAR* pstm, SAFEARRAY FAR* psa, SYSKIND syskind)
+{
+ HRESULT hresult;
+ unsigned long i, size, cElements;
+
+
+ size = SafeArraySize(psa);
+ ASSERT(size != SAFEARRAYOVERFLOW); // existing array, no overflow possible
+ cElements = size / psa->cbElements;
+
+ SafeArrayLock(psa);
+
+ if(psa->fFeatures & FADF_BSTR){
+
+ BSTR HUGEP *pbstr = (BSTR HUGEP*)psa->pvData;
+ for(i = 0; i < cElements; ++i, ++pbstr){
+ if(*pbstr != NULL)
+ SysFreeString(*pbstr);
+ IfFailGo(BstrRead(pstm, pbstr, syskind), LError0);
+ }
+
+ }else if(psa->fFeatures & FADF_VARIANT){
+
+ VARIANT HUGEP* pvar = (VARIANT HUGEP*)psa->pvData;
+ for(i = 0; i < cElements; ++i, ++pvar){
+ IfFailGo(VariantClear(pvar), LError0);
+ IfFailGo(VariantRead(pstm, pvar, NULL, syskind), LError0);
+ }
+
+ }else if(psa->fFeatures & FADF_UNKNOWN){
+
+ IUnknown FAR* HUGEP* ppunk = (IUnknown FAR* HUGEP*)psa->pvData;
+ for(i = 0; i < cElements; ++i, ++ppunk){
+ if(*ppunk != NULL)
+ (*ppunk)->Release();
+ IfFailGo(
+ DispUnmarshalInterface(pstm,
+ IID_IUnknown, (void FAR* FAR*)ppunk),
+ LError0);
+ }
+
+ }else if(psa->fFeatures & FADF_DISPATCH){
+
+ IDispatch FAR* HUGEP* ppdisp = (IDispatch FAR* HUGEP*)psa->pvData;
+ for(i = 0; i < cElements; ++i, ++ppdisp){
+ if(*ppdisp != NULL)
+ (*ppdisp)->Release();
+ IfFailGo(
+ DispUnmarshalInterface(pstm,
+ IID_IDispatch, (void FAR* FAR*)ppdisp),
+ LError0);
+ }
+
+ }else{
+
+ IfFailGo(pstm->Read(psa->pvData, size, NULL), LError0);
+
+ }
+
+ hresult = NOERROR;
+
+LError0:;
+ SafeArrayUnlock(psa);
+ return hresult;
+}
+
+
+/***
+*PRIVATE HRESULT SafeArrayRead(IStream*, SAFEARRAY**, SYSKIND)
+*Purpose:
+* Read a SafeArray from the given stream
+*
+* In:
+* unsigned short cDims
+* unsigned short fFeatures
+* unsigned short cbElements
+* SAFEARRAYBOUND rgbound
+* BYTEs pvData
+*
+*Entry:
+* pstm = stream to read the SafeArray from
+*
+*Exit:
+* return value = HRESULT
+* S_OK
+* E_OUTOFMEMORY
+*
+* *ppsa = pointer to the reconstituted SafeArray.
+*
+***********************************************************************/
+LOCAL HRESULT
+SafeArrayRead(IStream FAR* pstm, SAFEARRAY FAR* FAR* ppsa, SYSKIND syskind)
+{
+ HRESULT hresult;
+ SAFEARRAY FAR* psa;
+ unsigned short cDims;
+ unsigned char fIsNull;
+ unsigned long _cbElements;
+
+#ifdef _DEBUG
+ if(pstm == NULL)
+ return RESULT(E_INVALIDARG);
+ if(IsBadWritePtr(ppsa, sizeof(*ppsa)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ IfFailGo(GET(pstm, fIsNull), LError0);
+
+ if(fIsNull){
+ *ppsa = NULL;
+ return NOERROR;
+ }
+
+ IfFailGo(GET(pstm, cDims), LError0);
+
+ // allocate the safe array descriptor
+ IfFailRet(SafeArrayAllocDescriptor(cDims, &psa));
+
+ psa->cDims = cDims;
+ IfFailGo(GET(pstm, psa->fFeatures), LError1);
+ // Even if the array's features indicate that it was not dynamically
+ // allocated, the proxy-side really did dynamically allocate the array,
+ // so set FADF_FORCEFREE to force SafeArrayFree() to ignore FADF_STATIC,
+ // etc. and really free the array. We can't simply clear the FADF_STATIC
+ // because the fFeatures gets marshalled upon function exit to be passed
+ // back the the stub.
+ ASSERT((psa->fFeatures & FADF_FORCEFREE) == 0);
+ if (psa->fFeatures & (FADF_AUTO|FADF_STATIC|FADF_EMBEDDED))
+ psa->fFeatures |= FADF_FORCEFREE;
+ IfFailGo(GET(pstm, _cbElements), LError1);
+ psa->cbElements = (unsigned int)_cbElements;
+ IfFailGo(
+ pstm->Read(psa->rgsabound, cDims * sizeof(SAFEARRAYBOUND), NULL),
+ LError1);
+
+ // allocate memory for the array data.
+ IfFailGo(SafeArrayAllocData(psa), LError1);
+
+ IfFailGo(SafeArrayReadData(pstm, psa, syskind), LError1);
+
+ *ppsa = psa;
+
+ return NOERROR;
+
+LError1:;
+ SafeArrayDestroy(psa);
+
+LError0:;
+ return hresult;
+}
+
+/***
+*PRIVATE HRESULT SafeArrayReadExisting(IStream*, SAFEARRAY**, SYSKIND)
+*Purpose:
+* Read a SafeArray from the given stream into an *existing* array.
+*
+* In:
+* unsigned char fIsNull
+* unsigned short cDims
+* unsigned short fFeatures
+* unsigned short cbElements
+* SAFEARRAYBOUND rgbound
+* BYTEs pvData
+*
+*Entry:
+* pstm = stream to read the SafeArray from
+* psa = SafeArray to unmarshal the array into.
+*
+*Exit:
+* return value = HRESULT
+* S_OK
+* E_OUTOFMEMORY
+*
+***********************************************************************/
+PRIVATE_(HRESULT)
+SafeArrayReadExisting(
+ IStream FAR* pstm,
+ unsigned char fByRef,
+ SAFEARRAY FAR* FAR* ppsa,
+ SYSKIND syskind)
+{
+ HRESULT hresult;
+ unsigned char fIsNull;
+ unsigned char fReAlloc;
+ unsigned short cDims;
+ unsigned long cbBounds;
+ SAFEARRAY FAR* psaNew, FAR* psa;
+ unsigned long _cbElements;
+
+#ifdef _DEBUG
+ if(IsBadReadPtr(ppsa, sizeof(*ppsa)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ psa = *ppsa;
+
+#ifdef _DEBUG
+ if(psa != NULL && IsBadWritePtr(psa, sizeof(*psa)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ psaNew = NULL;
+ fReAlloc = FALSE;
+
+ // handle case of callee returning a null array
+ IfFailGo(GET(pstm, fIsNull), LError0);
+ if(fIsNull){
+ if(psa == NULL)
+ return NOERROR;
+ if(fByRef){
+ IfFailGo(SafeArrayDestroy(psa), LError0);
+ *ppsa = NULL;
+ return NOERROR;
+ }
+ // callee tried to Erase an array that was not ByRef
+ return RESULT(DISP_E_BADCALLEE);
+ }
+
+ IfFailGo(GET(pstm, cDims), LError0);
+
+ // the callee isnt allowed to change the number of dimensions
+ // (unless the array wasn't allocated, ie psa==NULL).
+ if(psa != NULL && cDims != psa->cDims){
+ hresult = RESULT(DISP_E_BADCALLEE);
+ goto LError0;
+ }
+
+ IfFailGo(SafeArrayAllocDescriptor(cDims, &psaNew), LError0);
+
+ IfFailGo(GET(pstm, psaNew->fFeatures), LError0);
+ ASSERT((psaNew->fFeatures & FADF_FORCEFREE) == 0);
+ IfFailGo(GET(pstm, _cbElements), LError0);
+ psaNew->cbElements = (unsigned int)_cbElements;
+
+ cbBounds = psaNew->cDims * sizeof(SAFEARRAYBOUND);
+ IfFailGo(pstm->Read(psaNew->rgsabound, cbBounds, NULL), LError0);
+
+ if(psa == NULL){
+
+ fReAlloc = TRUE;
+
+ // If the callee allocated the array, it must be dynamic
+ if(psaNew->fFeatures & (FADF_AUTO | FADF_STATIC)){
+ hresult = RESULT(DISP_E_BADCALLEE);
+ goto LError0;
+ }
+
+ }else{
+
+ if(psa->fFeatures != psaNew->fFeatures){
+ // the callee isn't allowed to change the allocation features.
+ //
+ // CONSIDER: should probably check everything *except* the
+ // element type features (bstr|var|disp).
+ //
+ if((psaNew->fFeatures ^ psa->fFeatures) & (FADF_AUTO | FADF_STATIC)){
+ hresult = RESULT(DISP_E_BADCALLEE);
+ goto LError0;
+ }
+ fReAlloc = TRUE;
+ }
+
+ if(psa->cbElements != psaNew->cbElements)
+ fReAlloc = TRUE;
+
+ if(MEMCMP(&psa->rgsabound, &psaNew->rgsabound, (size_t)cbBounds))
+ fReAlloc = TRUE;
+ }
+
+ // If the size of the array has changed, then re-allocate the
+ // memory for the array data.
+ //
+ if(fReAlloc){
+
+ if(!fByRef){
+ hresult = RESULT(DISP_E_BADCALLEE);
+ goto LError0;
+ }
+
+ if(psa == NULL){
+ *ppsa = psa = psaNew;
+ psaNew = NULL;
+ }else{
+ IfFailGo(SafeArrayDestroyData(psa), LError0);
+ psa->fFeatures = psaNew->fFeatures;
+ psa->cbElements = psaNew->cbElements;
+ MEMCPY(&psa->rgsabound, &psaNew->rgsabound, (size_t)cbBounds);
+ }
+ IfFailGo(SafeArrayAllocData(psa), LError0);
+ }
+
+ IfFailGo(SafeArrayReadData(pstm, psa, syskind), LError0);
+
+ hresult = NOERROR;
+
+LError0:;
+ if(psaNew != NULL) {
+ // force the array to be freed, even if it is marked as FADF_STATIC:
+ // it is really a dynamically allocated array read from the stream.
+ psaNew->fFeatures |= FADF_FORCEFREE;
+ SafeArrayDestroy(psaNew);
+ }
+
+ return hresult;
+}
+
+
+//---------------------------------------------------------------------
+// table driven structure marshalers
+//---------------------------------------------------------------------
+
+
+// NOTE: the following table is order dependent on FIELD_TYPE
+
+// The numbers that are hard-coded in the following table are assumed,
+// to be machine independent. If we ever deal with a target where this
+// assumption does not hold, then the following code must be reviewed.
+
+// 0 indicates N/A
+
+unsigned char g_cbFtype[] = {
+ 0 // FT_NONE
+ , 1 // FT_CHAR
+ , 1 // FT_UCHAR
+ , 2 // FT_SHORT
+ , 2 // FT_USHORT
+ , 4 // FT_LONG
+ , 4 // FT_ULONG
+ , sizeof(int) // FT_INT (MD)
+ , sizeof(unsigned int) // FT_UINT (MD)
+ , sizeof(int) // FT_ENUM (MD)
+
+ /* sizes of other field types are N/A */
+};
+
+
+/***
+*HRESULT StructWrite
+*Purpose:
+* Write the given structure to the given stream based on the
+* given field descriptor array.
+*
+*Entry:
+* pstm = the stream to marshal into
+* prgfdesc = pointer to the field descriptor array
+* pvStruct = void* to the struct to write
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+StructWrite(
+ IStream FAR* pstm,
+ FIELDDESC FAR* prgfdesc,
+ void FAR* pvStruct,
+ SYSKIND syskind)
+{
+ long l;
+ unsigned long ul;
+ unsigned long cb;
+ void FAR* pvField;
+ FIELDDESC FAR* pfdesc;
+
+ for(pfdesc = prgfdesc; FD_FTYPE(pfdesc) != FT_NONE; ++pfdesc){
+
+ pvField = (char FAR*)pvStruct + FD_OFIELD(pfdesc);
+
+ switch(FD_FTYPE(pfdesc)){
+ case FT_CHAR:
+ case FT_UCHAR:
+ case FT_SHORT:
+ case FT_USHORT:
+ case FT_LONG:
+ case FT_ULONG:
+ ASSERT(FD_FTYPE(pfdesc) < DIM(g_cbFtype));
+ cb = g_cbFtype[FD_FTYPE(pfdesc)];
+ ASSERT(cb != 0);
+ IfFailRet(pstm->Write(pvField, cb, NULL));
+ break;
+
+ case FT_MBYTE:
+ IfFailRet(pstm->Write(pvField, FD_CBFIELD(pfdesc), NULL));
+ break;
+
+ case FT_STRUCT:
+ IfFailRet(StructWrite(pstm, FD_PRGFDESC(pfdesc), pvField, syskind));
+ break;
+
+ case FT_BSTR:
+ IfFailRet(BstrWrite(pstm, *(BSTR FAR*)pvField, syskind));
+ break;
+
+ case FT_SPECIAL:
+ IfFailRet(FD_PFNSPECIAL(pfdesc)(pstm, FALSE, pvField));
+ break;
+
+ // The following are machine-int size dependent. They are written
+ // in a fixed size to facilitate 16/32 interoperability.
+
+ case FT_INT:
+ case FT_ENUM:
+ l = (long)*(int FAR*)pvField;
+ IfFailRet(PUT(pstm, l));
+ break;
+
+ case FT_UINT:
+ ul = (unsigned long)*(unsigned int FAR*)pvField;
+ IfFailRet(PUT(pstm, ul));
+ break;
+
+ default:
+ ASSERT(UNREACHED);
+ return RESULT(E_UNEXPECTED);
+ }
+ }
+
+ return NOERROR;
+}
+
+
+/***
+*HRESULT StructRead
+*Purpose:
+* Read a struct from the given stream into the caller provided
+* structure based on the given array of structure field descriptors.
+*
+*Entry:
+* pstm = the stream to unmarshal from
+* prgfdesc = pointer to the array of field descriptors
+*
+*Exit:
+* return value = HRESULT
+*
+* *pvStruct = structure containing unmarshaled values
+*
+***********************************************************************/
+HRESULT
+StructRead(
+ IStream FAR* pstm,
+ FIELDDESC FAR* prgfdesc,
+ void FAR* pvStruct,
+ SYSKIND syskind)
+{
+ long l;
+ unsigned long ul;
+ unsigned long cb;
+ void FAR* pvField;
+ FIELDDESC FAR* pfdesc;
+
+ for(pfdesc = prgfdesc; FD_FTYPE(pfdesc) != FT_NONE; ++pfdesc){
+
+ pvField = (char FAR*)pvStruct + FD_OFIELD(pfdesc);
+
+ switch(FD_FTYPE(pfdesc)){
+ case FT_CHAR:
+ case FT_UCHAR:
+ case FT_SHORT:
+ case FT_USHORT:
+ case FT_LONG:
+ case FT_ULONG:
+ ASSERT(FD_FTYPE(pfdesc) < DIM(g_cbFtype));
+ cb = g_cbFtype[FD_FTYPE(pfdesc)];
+ ASSERT(cb != 0);
+ IfFailRet(pstm->Read(pvField, cb, NULL));
+ break;
+
+ case FT_MBYTE:
+ IfFailRet(pstm->Read(pvField, FD_CBFIELD(pfdesc), NULL));
+ break;
+
+ case FT_STRUCT:
+ IfFailRet(StructRead(pstm, FD_PRGFDESC(pfdesc), pvField, syskind));
+ break;
+
+ case FT_BSTR:
+ IfFailRet(BstrRead(pstm, (BSTR FAR*)pvField, syskind));
+ break;
+
+ case FT_SPECIAL:
+ IfFailRet(FD_PFNSPECIAL(pfdesc)(pstm, TRUE, pvField));
+ break;
+
+ // The following are machine-int size dependent. They are written
+ // in a fixed size to facilitate 16/32 interoperability.
+
+ case FT_INT:
+ case FT_ENUM:
+ IfFailRet(GET(pstm, l));
+ *(int FAR*)pvField = (int)l;
+ break;
+
+ case FT_UINT:
+ IfFailRet(GET(pstm, ul));
+ *(unsigned int FAR*)pvField = (unsigned int)ul;
+ break;
+
+ default:
+ ASSERT(UNREACHED);
+ return RESULT(E_UNEXPECTED);
+ }
+ }
+
+ return NOERROR;
+}
+
+
+// network automation provides different implementations of these (netmrsh.cpp)
+#if !defined(NETDISP)
+//---------------------------------------------------------------------
+// Interface marshaling helpers
+//---------------------------------------------------------------------
+
+/*
+ * IMPORTANT NOTE ON INTERFACE MARSHALING:
+ *
+ * On Win16, when marshaling an interface on a proxy, OLE does
+ * not add a reference to the original server. As a result, if
+ * the proxy is the only reference to the server, once we have
+ * marshaled the proxy and released it the server will go away
+ * and we will be unable to extract the interface on the other
+ * side.
+ *
+ * In order to work around this problem, whenever we marshal an
+ * interface, we create a small holder object that holds an extra
+ * reference to the proxy, and marshal it along with the interface.
+ * Once the original interface has been successfully extracted on
+ * the other side, then we release this holder object which triggers
+ * the release on the proxy in the source process.
+ *
+ * This problem doesn't exist on Win32, or in the 16 bit WOW Dlls
+ * which thunk to the 32bit Dlls. We only use this technique on Win16 and
+ * when running the 32-bit DLLs on Win32s.
+ *
+ */
+
+#if (OE_WIN16 && !defined(WOW)) || OE_WIN32 && defined(_X86_)
+# define USE_HOLDER 1
+#else
+# define USE_HOLDER 0
+#endif
+
+
+#if USE_HOLDER
+
+// This is a trivial interface-holder class
+class FAR CHolder : public IUnknown
+{
+public:
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ CHolder();
+ ~CHolder();
+
+ unsigned long m_cRefs;
+ IUnknown FAR* m_punk;
+};
+
+CHolder::CHolder()
+{
+ m_cRefs = 1;
+ m_punk = NULL;
+}
+
+CHolder::~CHolder()
+{
+ if(m_punk != NULL)
+ m_punk->Release();
+}
+
+STDMETHODIMP
+CHolder::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ if(riid == IID_IUnknown){
+ *ppv = this;
+ ++m_cRefs;
+ return NOERROR;
+ }
+ *ppv = NULL;
+ return RESULT(E_NOINTERFACE);
+}
+
+STDMETHODIMP_(unsigned long)
+CHolder::AddRef()
+{
+ return ++m_cRefs;
+}
+
+STDMETHODIMP_(unsigned long)
+CHolder::Release()
+{
+ if(--m_cRefs == 0){
+ delete this;
+ return 0;
+ }
+ return m_cRefs;
+}
+#endif
+
+/***
+*INTERNAL DispMarshalInterface
+*Purpose:
+* The ole routine CoMarshalInterface doesnt allow marshaling
+* NULL interface ptrs, so this wrapper adds some extra info to
+* the stream to allow us to do this.
+*
+*Entry:
+* pstm = the stream to marshal into
+* riid = the IID of the interface we are marshaling
+* punk = an IUnknown* of the interface being marshaled.
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+INTERNAL_(HRESULT)
+DispMarshalInterface(
+ IStream FAR* pstm,
+ REFIID riid,
+ IUnknown FAR* punk)
+{
+ HRESULT hresult;
+ unsigned char fIsNull;
+#if USE_HOLDER
+ CHolder FAR* pholder = NULL;
+#endif
+
+ if(punk == NULL){
+ fIsNull = TRUE;
+ IfFailRet(PUT(pstm, fIsNull));
+ return NOERROR;
+ }
+
+ fIsNull = FALSE;
+ IfFailRet(PUT(pstm, fIsNull));
+
+#if USE_HOLDER
+#if OE_WIN32
+ // Only do this on WIN32S
+ if (g_fWin32s) {
+#endif // OE_WIN32
+ // Create the holder
+ if((pholder = new FAR CHolder()) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto Error;
+ }
+
+ // stuff the interface were marshaling into the holder
+ punk->AddRef();
+ pholder->m_punk = punk;
+
+ // marshaler the holder
+ IfFailGo(CoMarshalInterface(pstm,
+ IID_IUnknown,
+ (IUnknown FAR*)pholder,
+ 0L,
+ NULL,
+ MSHLFLAGS_NORMAL), Error);
+#if OE_WIN32
+ }
+#endif // OE_WIN32
+#endif
+
+ // marshal the interface
+ IfFailGo(CoMarshalInterface(pstm,
+ riid,
+ punk,
+ 0L,
+ NULL,
+ MSHLFLAGS_NORMAL), Error);
+
+ hresult = NOERROR;
+
+Error:;
+#if USE_HOLDER
+ if(pholder != NULL)
+ pholder->Release();
+#endif
+ return hresult;
+}
+
+
+/***
+*INTERNAL HRESULT DispUnmarshalInterface
+*Purpose:
+* Unmarshal an interface from the given stream, properly handling
+* NULL interface ptrs. See comment for DispMarshalInterface().
+*
+*Entry:
+* pstm = the stream to unmarshal from
+* riid = the IID of the interface were unmarshaling
+*
+*Exit:
+* return value = HRESULT
+*
+* *ppv = the newly reconstituted interface
+*
+***********************************************************************/
+INTERNAL_(HRESULT)
+DispUnmarshalInterface(
+ IStream FAR* pstm,
+ REFIID riid,
+ void FAR* FAR* ppv)
+{
+ HRESULT hresult;
+ unsigned char fIsNull;
+#if USE_HOLDER
+ IUnknown FAR* punkHolder = NULL;
+#endif
+
+ IfFailRet(GET(pstm, fIsNull));
+
+ if(fIsNull){
+ *ppv = NULL;
+ return NOERROR;
+ }
+
+#if USE_HOLDER
+#if OE_WIN32
+ if (g_fWin32s)
+#endif // OE_WIN32
+ // extract the holder
+ IfFailGo(CoUnmarshalInterface(pstm,
+ IID_IUnknown,
+ (void FAR* FAR*)&punkHolder), Error);
+#endif
+
+ // extract the interface
+ IfFailGo(CoUnmarshalInterface(pstm, riid, ppv), Error);
+
+ hresult = NOERROR;
+
+Error:;
+#if USE_HOLDER
+ // Release the holder. This will in turn release the extra
+ // reference that it is holding onto in the other process.
+ if(punkHolder != NULL)
+ punkHolder->Release();
+#endif
+
+ return hresult;
+}
+#endif // !defined(NETDISP)
+
diff --git a/private/oleauto/src/dispatch/dispmrsh.h b/private/oleauto/src/dispatch/dispmrsh.h
new file mode 100644
index 000000000..934fa0419
--- /dev/null
+++ b/private/oleauto/src/dispatch/dispmrsh.h
@@ -0,0 +1,316 @@
+/***
+*dispmrsh.h
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file describes the marshaling utilities used by ole2disp.dll
+*
+*Revision History:
+*
+* [00] 05-Mar-93 bradlo: Created (split off from dispps.h).
+* [01] 06-Mar-93 bradlo: added structure marshaling stuff.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+// Shared macro definitions used by all OA proxy/stub/marshalling code.
+// Win32 builds based on Cario sources only supports buffer I/O whereas
+// Win16/Mac only supports simple stream. Buffered interfaces are not
+// publicly exposed, hence, their definitions here.
+
+#if ((OE_WIN32 || defined(WOW)) && defined(__cplusplus))
+ #define IPSFACTORY IPSFactoryBuffer
+ #define IPROXY IRpcProxyBuffer
+ #define ISTUB IRpcStubBuffer
+ #define ICHANNEL IRpcChannelBuffer
+ #define IID_IPSFACTORY IID_IPSFactoryBuffer
+ #define IID_IPROXY IID_IRpcProxyBuffer
+ #define IID_ISTUB IID_IRpcStubBuffer
+ #define IID_ICHANNEL IID_IRpcChannelBuffer
+
+ #define OPEN_STREAM(plrpc, pstm, iMeth, size, iid) \
+ RPCOLEMESSAGE message; \
+ \
+ pstm = new CStreamOnBuffer(plrpc, &message, iid, iMeth); \
+ if(pstm == NULL) \
+ return RESULT(E_OUTOFMEMORY); \
+ IfFailRet(((CStreamOnBuffer *) pstm)->ResizeBuffer(size));
+
+ #define OPEN_STUB_STREAM(pstm, pRpcChannel, pMessage, iid) \
+ pstm = new CStreamOnBuffer(pRpcChannel, pMessage, iid, 0xffffffff); \
+ if(pstm == NULL) \
+ return RESULT(E_OUTOFMEMORY); \
+
+ #define INVOKE_CALL(plrpc, pstm, label) \
+ IfFailGo( \
+ (((CStreamOnBuffer *) pstm)->Call()), label)
+
+ #define RESET_STREAM(pstm) \
+ ((CStreamOnBuffer *) pstm)->ResetBuffer()
+
+ #define RESIZE_STREAM(pstm, size) \
+ ((CStreamOnBuffer *) pstm)->ResizeBuffer(size)
+
+ #define REWIND_STREAM(pstm) \
+ ((CStreamOnBuffer *) pstm)->RewindBuffer()
+
+ #define DELETE_STREAM(pstm) \
+ delete (CStreamOnBuffer *) pstm;
+
+ #define GET_IMETHOD(pmessage) \
+ pmessage->iMethod
+
+ extern "C" const IID IID_IPSFactoryBuffer;
+ extern "C" const IID IID_IRpcProxyBuffer;
+ extern "C" const IID IID_IRpcStubBuffer;
+ extern "C" const IID IID_IRpcChannelBuffer;
+
+ typedef unsigned long RPCOLEDATAREP;
+ #define NDR_LOCAL_DATA_REPRESENTATION (unsigned long)0X00000010L
+
+#ifndef WIN32 // already defined in new header files
+ typedef struct tagRPCOLEMESSAGE
+ {
+ void *reserved1;
+ RPCOLEDATAREP dataRepresentation;
+ void *Buffer;
+ ULONG cbBuffer;
+ ULONG iMethod;
+ void *reserved2[5];
+ ULONG rpcFlags;
+ } RPCOLEMESSAGE;
+
+ typedef RPCOLEMESSAGE *PRPCOLEMESSAGE;
+
+ interface IRpcChannelBuffer : IUnknown
+ {
+ STDMETHOD(GetBuffer)(RPCOLEMESSAGE FAR* pMessage,
+ REFIID riid) = 0;
+ STDMETHOD(SendReceive)(RPCOLEMESSAGE FAR* pMessage,
+ ULONG FAR* pStatus) = 0;
+ STDMETHOD(FreeBuffer)(RPCOLEMESSAGE FAR* pMessage) = 0;
+ STDMETHOD(GetDestCtx)(DWORD FAR* lpdwDestCtx,
+ LPVOID FAR* lplpvDestCtx) = 0;
+ STDMETHOD(IsConnected)(void) = 0;
+ };
+
+ interface IRpcProxyBuffer : IUnknown
+ {
+ STDMETHOD(Connect)(IRpcChannelBuffer FAR* pRpcChannel) = 0;
+ STDMETHOD_(void, Disconnect)(void) = 0;
+ };
+
+ interface IRpcStubBuffer : IUnknown
+ {
+ STDMETHOD(Connect)(IUnknown FAR* pUnk) = 0;
+ STDMETHOD_(void, Disconnect)(void) = 0;
+ /*STDMETHOD(Invoke)(REFIID iid, int iMethod, IStream FAR* pIStream,
+ DWORD dwDestCtx, LPVOID lpvDestCtx) = 0;*/
+ STDMETHOD(Invoke)(RPCOLEMESSAGE FAR* pRpcMsg,
+ IRpcChannelBuffer FAR* pRpcChannel) = 0;
+ STDMETHOD_(IRpcStubBuffer *, IsIIDSupported)(REFIID iid) = 0;
+ STDMETHOD_(ULONG, CountRefs)(void) = 0;
+
+ STDMETHOD(DebugServerQueryInterface)(void FAR* FAR* ppv) = 0;
+ STDMETHOD_(void, DebugServerRelease)(void FAR* pv) = 0;
+ };
+
+ interface IPSFactoryBuffer : IUnknown
+ {
+ STDMETHOD(CreateProxy)(IUnknown FAR* pUnkOuter, REFIID riid,
+ IRpcProxyBuffer FAR* FAR* ppProxy, void FAR* FAR* ppv) = 0;
+ STDMETHOD(CreateStub)(REFIID riid, IUnknown FAR* pUnkServer,
+ IRpcStubBuffer FAR* FAR* ppStub) = 0;
+ };
+#endif //!WIN32
+
+ #include "dispstrm.h"
+
+#else
+ #define IPSFACTORY IPSFactory
+ #define IPROXY IRpcProxy
+ #define ISTUB IRpcStub
+ #define ICHANNEL IRpcChannel
+ #define IID_IPSFACTORY IID_IPSFactory
+ #define IID_IPROXY IID_IRpcProxy
+ #define IID_ISTUB IID_IRpcStub
+ #define IID_ICHANNEL IID_IRpcChannel
+
+ #define OPEN_STREAM(plrpc, pstm, iMeth, size, iid) \
+ IfFailRet(plrpc->GetStream(iid, iMeth, FALSE, FALSE, size, &pstm))
+ #define INVOKE_CALL(plrpc, pstm, label) \
+ IfFailGo(plrpc->Call(pstm), label)
+
+ #define RESET_STREAM(pstm)
+
+ #define RESIZE_STREAM(pstm, size)
+
+ #define REWIND_STREAM(pstm) (Rewind(pstm))
+
+ #define DELETE_STREAM(pstm)
+
+ #define GET_IMETHOD(pmessage) iMethod
+
+#endif
+
+
+
+
+
+// VARIANT marshaling utilities
+
+HRESULT VariantWrite(IStream FAR*, VARIANTARG FAR*, SYSKIND);
+HRESULT VariantReadType(IStream FAR*, VARIANTARG FAR*, SYSKIND);
+HRESULT VariantRead(IStream FAR*, VARIANTARG FAR*, VARIANT FAR*, SYSKIND);
+
+// BSTR marshaling utilities
+
+HRESULT BstrWrite(IStream FAR* pstm, BSTR bstr, SYSKIND);
+HRESULT BstrRead(IStream FAR* pstm, BSTR FAR* pbstr, SYSKIND);
+
+
+// SafeArray marshaling utilities
+
+HRESULT SafeArrayRead(IStream FAR* pstm, SAFEARRAY FAR* FAR* ppsarray, SYSKIND syskind);
+HRESULT SafeArrayWrite(IStream FAR* pstm, SAFEARRAY FAR* psarray, SYSKIND syskind);
+
+
+// EXCEPINFO marshaling utilities
+
+HRESULT ExcepinfoRead(IStream FAR* pstm, EXCEPINFO FAR* pexcepinfo, SYSKIND syskind);
+HRESULT ExcepinfoWrite(IStream FAR* pstm, EXCEPINFO FAR* pexcepinfo, SYSKIND syskind);
+
+// Rich Error state marhsaling utilities
+HRESULT MarshalErrorInfo(IStream FAR* pstm, SYSKIND syskind);
+HRESULT UnmarshalErrorInfo(IStream FAR* pstm, SYSKIND syskind);
+
+
+// helpful macros used by the marshaling/unmarshaling code.
+
+#define GET(PSTREAM, X) ((PSTREAM)->Read(&(X), sizeof(X), NULL))
+#define PUT(PSTREAM, X) ((PSTREAM)->Write(&(X), sizeof(X), NULL))
+
+
+// structure marshaling support
+
+enum FIELD_TYPE {
+ FT_NONE = 0,
+ FT_CHAR,
+ FT_UCHAR,
+ FT_SHORT,
+ FT_USHORT,
+ FT_LONG,
+ FT_ULONG,
+ FT_INT,
+ FT_UINT,
+ FT_ENUM,
+ FT_MBYTE, // multi-byte member (array)
+ FT_STRUCT, // nested struct
+ FT_BSTR,
+ FT_WBSTR,
+ FT_SPECIAL,
+ FT_MAX,
+
+ // following based on definitions from windows.h
+
+ FT_BYTE = FT_UCHAR,
+ FT_WORD = FT_USHORT,
+ FT_DWORD = FT_ULONG
+};
+
+// The following structure contains the description of a
+// single structure field. An array of these descriptions
+// describes a structure for the table driven struct marshalers.
+
+typedef struct tagFIELDDESC FIELDDESC;
+struct tagFIELDDESC{
+ long ftype; // field machine type
+ long oField; // field offset
+ long cbField; // field size
+ union {
+ void FAR* pv;
+ FIELDDESC FAR* prgfdesc; // for FT_STRUCT
+
+ HRESULT (FAR* pfnSpecial)( // for FT_SPECIAL
+ IStream FAR* pstm,
+ BOOL fRead, // read or write?
+ void FAR* pvField);
+ }u;
+};
+
+// FIELDDESC accessor macros
+//
+#define FD_FTYPE(X) ((X)->ftype)
+#define FD_OFIELD(X) ((X)->oField)
+#define FD_CBFIELD(X) ((X)->cbField)
+
+#define FD_PV(X) ((X)->u.pv)
+#define FD_PRGFDESC(X) ((X)->u.prgfdesc)
+#define FD_PFNSPECIAL(X) ((X)->u.pfnSpecial)
+
+
+#define OA_FIELD_SIZE(TYPE, FIELD) (sizeof(((TYPE NEAR*)1)->FIELD))
+
+#define OA_FIELD_OFFSET(TYPE, FIELD) ((int)(&((TYPE NEAR*)1)->FIELD)-1)
+
+// the following macro is used to initialize a single entry in
+// a structure marshal info array.
+
+#define FIELDDAT(TYPE, FTYPE, FIELD, PRGFDESC) \
+ { FTYPE, OA_FIELD_OFFSET(TYPE, FIELD), OA_FIELD_SIZE(TYPE, FIELD), PRGFDESC }
+
+// end if table marker
+#define FIELDEND() \
+ { FT_NONE, -1, -1, NULL }
+
+// table driver structure marshaler
+
+HRESULT
+StructWrite(
+ IStream FAR* pstm,
+ FIELDDESC FAR* prgfdesc,
+ void FAR* pvStruct,
+ SYSKIND);
+
+// table driven structure unmarshaler
+
+HRESULT
+StructRead(
+ IStream FAR* pstm,
+ FIELDDESC FAR* prgfdesc,
+ void FAR* pvStruct,
+ SYSKIND);
+
+
+#ifdef __cplusplus /* { */
+
+/***
+*PRIVATE HRESULT Rewind(IStream*)
+*Purpose:
+* Rewind the given stream (seek to offset 0LL). This function really
+* only exists due to the hassles of setting up a large int (longlong)
+* constant - so we abstract it out here.
+*
+*
+*Entry:
+* pstm = the stream to rewind.
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+inline HRESULT Rewind(IStream FAR* pstm)
+{
+#if (OE_WIN32 || HC_MPW)
+ LARGE_INTEGER ll0;
+ LISet32(ll0, 0);
+#else
+static const LARGE_INTEGER NEAR ll0 = {0,0};
+#endif
+ return pstm->Seek(ll0, STREAM_SEEK_SET, NULL);
+}
+
+#endif /* } */
diff --git a/private/oleauto/src/dispatch/disppch.cpp b/private/oleauto/src/dispatch/disppch.cpp
new file mode 100644
index 000000000..ddbae05ca
--- /dev/null
+++ b/private/oleauto/src/dispatch/disppch.cpp
@@ -0,0 +1,3 @@
+// This file is used to construct the oledisp precompiled header.
+
+#include "oledisp.h"
diff --git a/private/oleauto/src/dispatch/dispprox.cpp b/private/oleauto/src/dispatch/dispprox.cpp
new file mode 100644
index 000000000..2c160b95f
--- /dev/null
+++ b/private/oleauto/src/dispatch/dispprox.cpp
@@ -0,0 +1,707 @@
+/***
+*dispprox.cpp
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Implements custom proxy support for the IDispatch interface.
+*
+*Revision History:
+*
+* [00] 18-Sep-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+* There are assumptions in the following marshaling code that the
+* endianness of the caller and callee are the same.
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#ifndef WIN32
+#include <cobjps.h>
+#endif //!WIN32
+
+#include "dispmrsh.h"
+#include "dispps.h"
+
+
+static EXCEPINFO NEARDATA g_excepinfoNull = {0};
+
+
+CProxDisp::CProxDisp(IUnknown FAR* punkOuter, REFIID riid)
+ : m_unk(this), m_proxy(this), m_disp(this)
+{
+ if(punkOuter == NULL)
+ punkOuter = &m_unk;
+ m_punkOuter = punkOuter;
+ m_dispInterface = riid;
+}
+
+CProxDisp::~CProxDisp()
+{
+
+}
+
+
+IUnknown FAR*
+CProxDisp::Create(IUnknown FAR* punkOuter, REFIID riid)
+{
+ CProxDisp FAR* pproxdisp;
+
+ if(pproxdisp = new FAR CProxDisp(punkOuter, riid)){
+ pproxdisp->m_refs = 1;
+ return &pproxdisp->m_unk;
+ }
+ return NULL;
+}
+
+//---------------------------------------------------------------------
+// IDispatch proxy class IUnknown implementation
+//---------------------------------------------------------------------
+
+CPDUnkImpl::CPDUnkImpl(CProxDisp FAR* pproxdisp)
+{
+ m_pproxdisp = pproxdisp;
+}
+
+CPDUnkImpl::~CPDUnkImpl()
+{
+
+}
+
+STDMETHODIMP
+CPDUnkImpl::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ if(IsEqualIID(riid, IID_IUnknown)){
+ *ppv = (void FAR*)&m_pproxdisp->m_unk;
+ AddRef();
+ return NOERROR;
+ }
+
+ if(IsEqualIID(riid, IID_IPROXY)){
+ *ppv = (void FAR*)&(m_pproxdisp->m_proxy);
+ AddRef();
+ return NOERROR;
+ }
+
+ if(IsEqualIID(riid, IID_IDispatch) ||
+ IsEqualIID(riid, m_pproxdisp->m_dispInterface)){
+ *ppv = (void FAR*)&(m_pproxdisp->m_disp);
+ m_pproxdisp->m_punkOuter->AddRef();
+ return NOERROR;
+ }
+
+ *ppv = NULL;
+ return RESULT(E_NOINTERFACE);
+}
+
+
+STDMETHODIMP_(unsigned long)
+CPDUnkImpl::AddRef()
+{
+ return ++m_pproxdisp->m_refs;
+}
+
+
+STDMETHODIMP_(unsigned long)
+CPDUnkImpl::Release()
+{
+ if(--m_pproxdisp->m_refs==0){
+ delete m_pproxdisp;
+ return 0;
+ }
+ return m_pproxdisp->m_refs;
+}
+
+
+//---------------------------------------------------------------------
+// IDispatch proxy class' IRpcProxy implementation
+//---------------------------------------------------------------------
+
+CPDProxImpl::CPDProxImpl(CProxDisp FAR* pproxdisp)
+{
+ m_pproxdisp = pproxdisp;
+}
+
+CPDProxImpl::~CPDProxImpl()
+{
+ if(m_pproxdisp->m_plrpc)
+ m_pproxdisp->m_plrpc->Release();
+ m_pproxdisp->m_plrpc = NULL;
+}
+
+STDMETHODIMP
+CPDProxImpl::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ return m_pproxdisp->m_unk.QueryInterface(riid, ppv);
+}
+
+STDMETHODIMP_(unsigned long)
+CPDProxImpl::AddRef()
+{
+ return m_pproxdisp->m_unk.AddRef();
+}
+
+STDMETHODIMP_(unsigned long)
+CPDProxImpl::Release()
+{
+ return m_pproxdisp->m_unk.Release();
+}
+
+STDMETHODIMP
+CPDProxImpl::Connect(ICHANNEL FAR* plrpc)
+{
+ if(plrpc){
+ plrpc->AddRef();
+ m_pproxdisp->m_plrpc = plrpc;
+ m_pproxdisp->m_disp.SysKind();
+ return NOERROR;
+ }
+ return RESULT(E_FAIL);
+}
+
+
+STDMETHODIMP_(void)
+CPDProxImpl::Disconnect(void)
+{
+ if(m_pproxdisp->m_plrpc)
+ m_pproxdisp->m_plrpc->Release();
+ m_pproxdisp->m_plrpc = NULL;
+}
+
+//---------------------------------------------------------------------
+// IDispatch proxy class' IDispatch implementation
+//---------------------------------------------------------------------
+
+CPDDispImpl::CPDDispImpl(CProxDisp FAR* pproxdisp)
+{
+ m_pproxdisp = pproxdisp;
+}
+
+CPDDispImpl::~CPDDispImpl()
+{
+
+}
+
+
+STDMETHODIMP
+CPDDispImpl::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ return m_pproxdisp->m_punkOuter->QueryInterface(riid, ppv);
+}
+
+STDMETHODIMP_(unsigned long)
+CPDDispImpl::AddRef()
+{
+ return m_pproxdisp->m_punkOuter->AddRef();
+}
+
+STDMETHODIMP_(unsigned long)
+CPDDispImpl::Release()
+{
+ return m_pproxdisp->m_punkOuter->Release();
+}
+
+STDMETHODIMP
+CPDDispImpl::SysKind()
+{
+ ICHANNEL FAR* plrpc;
+ IStream FAR* pstm;
+ HRESULT hresult;
+ unsigned long _stubSysKind;
+
+ if((plrpc = m_pproxdisp->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_SYSKIND, 32, IID_IDispatch);
+
+ INVOKE_CALL(plrpc, pstm, LRelease);
+
+ IfFailGo(GET(pstm, _stubSysKind), LRelease);
+ m_syskindStub = (SYSKIND) _stubSysKind;
+
+LRelease:
+
+ pstm->Release();
+ return hresult;
+}
+
+
+/***
+*HRESULT CPDDispImpl::GetTypeInfoCount(unsigned int*)
+*Purpose:
+*
+* Out:
+* <nothing>
+*
+* In:
+* <HRESULT = return value>
+* <unsigned int = count>
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+* *pctinfo = count of TypeInfos
+*
+***********************************************************************/
+HRESULT
+ProxyGetTypeInfoCount(ICHANNEL FAR* plrpc,
+ SYSKIND syskindStub,
+ unsigned int FAR* pctinfo)
+{
+ IStream FAR* pstm;
+ HRESULT hresult, hresultRet;
+ unsigned long _ctinfo;
+
+#ifdef _DEBUG
+ IfFailRet(ValidateWritePtr(pctinfo, sizeof(*pctinfo)));
+#endif
+
+ if(plrpc == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_GETTYPEINFOCOUNT, 32, IID_IDispatch);
+
+ INVOKE_CALL(plrpc, pstm, LRelease);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LRelease);
+
+ if(HRESULT_FAILED(hresultRet)){
+ hresult = hresultRet;
+ goto LRelease;
+ }
+
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ IfFailGo(pstm->Read(&_ctinfo, sizeof(unsigned long), NULL), LRelease);
+ *pctinfo = (unsigned int) _ctinfo;
+
+ hresult = hresultRet;
+
+LRelease:
+ pstm->Release();
+ return hresult;
+}
+
+STDMETHODIMP
+CPDDispImpl::GetTypeInfoCount(unsigned int FAR* pctinfo)
+{
+ return ProxyGetTypeInfoCount(m_pproxdisp->m_plrpc,
+ m_syskindStub,
+ pctinfo);
+
+}
+
+/***
+*HRESULT CPDDispImpl::GetTypeInfo(unsigned int, LCID, ITypeInfo**)
+*Purpose:
+*
+* Out:
+* <unsigned int = itinfo>
+* <LCID = lcid>
+* <HRESULT = return value>
+* <ITypeInfo* = pptinfo>
+*
+*Entry:
+* itinfo = index of the TypeInfo to retrieve
+* lcid = the locale ID of the caller
+*
+*Exit:
+* return value = HRESULT
+*
+* *pptinfo = TypeInfo of the given index
+*
+***********************************************************************/
+HRESULT
+ProxyGetTypeInfo(ICHANNEL FAR* plrpc,
+ SYSKIND syskindStub,
+ unsigned int itinfo,
+ LCID lcid,
+ ITypeInfo FAR* FAR* pptinfo)
+{
+ IStream FAR* pstm;
+ unsigned long _itinfo;
+ HRESULT hresult, hresultRet;
+
+#ifdef _DEBUG
+ IfFailRet(ValidateWritePtr(pptinfo, sizeof(*pptinfo)));
+#endif
+
+ if(plrpc == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm,
+ IMETH_GETTYPEINFO,
+ 256, /* (sizeof(SCODE)+sizeof(IID)), */
+ IID_IDispatch);
+
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ _itinfo = itinfo;
+ IfFailGo(PUT(pstm, _itinfo), LRelease);
+
+ IfFailGo(PUT(pstm, lcid), LRelease);
+
+ INVOKE_CALL(plrpc, pstm, LRelease);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LRelease);
+
+ if(HRESULT_FAILED(hresultRet)){
+ hresult = hresultRet;
+ goto LRelease;
+ }
+
+ IfFailGo(DispUnmarshalInterface(
+ pstm, IID_ITypeInfo, (void FAR* FAR*)pptinfo), LRelease);
+
+ hresult = hresultRet;
+
+LRelease:
+ pstm->Release();
+ return hresult;
+}
+
+STDMETHODIMP
+CPDDispImpl::GetTypeInfo(unsigned int itinfo,
+ LCID lcid,
+ ITypeInfo FAR* FAR* pptinfo)
+{
+ return ProxyGetTypeInfo(m_pproxdisp->m_plrpc,
+ m_syskindStub,
+ itinfo,
+ lcid,
+ pptinfo);
+}
+
+
+/***
+*HRESULT CPDDispImpl::GetIDsOfNames(REFIID, char**, unsigned int, LCID, DISPID*)
+*
+*Purpose:
+* Out:
+* <REFIID riid>
+* <LCID = lcid>
+* <unsigned int = cNames>
+* [(len, sz)]+ ; names
+*
+* In:
+* <HRESULT = return value>
+* [DISPID]+
+*
+*Entry:
+* riid = reference to an interface ID
+* rgszNames = array of names to find the DISPIDs for
+* cNames = count of names in the rgszNames array
+* lcid = the locale id
+*
+*Exit:
+* return value = HRESULT
+* [UNDONE: enumerate return codes]
+* rgdispid = array of DISPIDs corresponding to the passed in array of names.
+*
+***********************************************************************/
+HRESULT
+ProxyGetIDsOfNames(ICHANNEL FAR* plrpc,
+ SYSKIND syskindStub,
+ REFIID riid,
+ OLECHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ LCID lcid,
+ DISPID FAR* rgdispid)
+{
+ unsigned int i;
+ unsigned long len;
+ unsigned long _cNames;
+ unsigned long _proxySysKind;
+
+ IStream FAR* pstm;
+ HRESULT hresult, hresultRet;
+ int size = sizeof(IID) + sizeof(lcid) + sizeof(_cNames) + 64;
+
+ if(cNames == 0)
+ return RESULT(E_INVALIDARG);
+
+#ifdef _DEBUG
+ if(IsBadReadPtr(rgszNames, cNames * sizeof(OLECHAR FAR*)))
+ return RESULT(E_INVALIDARG);
+
+ // make sure each of the entries in the name array is valid.
+ for(i = 0; i < cNames; ++i)
+ if(IsBadReadPtr(rgszNames[i], sizeof(OLECHAR)))
+ return RESULT(E_INVALIDARG);
+
+ if(IsBadWritePtr(rgdispid, cNames * sizeof(DISPID)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ if(plrpc == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ // calculate the size needed for stream
+ for(i = 0; i < cNames; ++i)
+ size += BYTELEN(rgszNames[i]) + sizeof(len);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_GETIDSOFNAMES, size, IID_IDispatch);
+
+ _proxySysKind = (unsigned long)SYS_CURRENT;
+ IfFailGo(PUT(pstm, _proxySysKind), LRelease);
+
+ IfFailGo(pstm->Write((const void FAR*)&riid, sizeof(IID), NULL), LRelease);
+ IfFailGo(PUT(pstm, lcid), LRelease);
+
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ _cNames = cNames;
+ IfFailGo(PUT (pstm, _cNames), LRelease);
+
+#if OE_WIN32 /* enable 16/32 interoperablity support */
+ if (syskindStub == SYS_WIN16) {
+ char buf[128];
+ char *pBuf = buf;
+
+ for(i=0; i<cNames; ++i){
+ len = STRLEN(rgszNames[i])+1;
+ IfFailGo(PUT(pstm, len), LRelease);
+
+ // optimization for names under 128 bytes
+ if (len > 128) {
+ if ((pBuf = new FAR char [len]) == NULL) {
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LRelease;
+ }
+ }
+
+ // convert UNICODE string to ANSI and stream it
+ WideCharToMultiByte(CP_ACP, NULL, rgszNames[i], -1,
+ pBuf, len, NULL, NULL);
+ IfFailGo(pstm->Write((void FAR*) pBuf, len, NULL), LRelease);
+
+ if (len > 128)
+ delete pBuf;
+ }
+ } else
+#endif
+ {
+ for(i=0; i<cNames; ++i){
+ len = BYTELEN(rgszNames[i]);
+ IfFailGo(PUT(pstm, len), LRelease);
+ IfFailGo(pstm->Write((const void FAR*) rgszNames[i], len, NULL), LRelease);
+ }
+ }
+
+ INVOKE_CALL(plrpc, pstm, LRelease);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LRelease);
+
+ for(i=0; i<cNames; ++i)
+ IfFailGo(pstm->Read(&rgdispid[i], sizeof(rgdispid[0]), NULL), LRelease);
+
+ hresult = hresultRet;
+
+LRelease:;
+ pstm->Release();
+
+ return hresult;
+}
+
+STDMETHODIMP
+CPDDispImpl::GetIDsOfNames(REFIID riid,
+ OLECHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ LCID lcid,
+ DISPID FAR* rgdispid)
+{
+ return ProxyGetIDsOfNames(m_pproxdisp->m_plrpc,
+ m_syskindStub,
+ riid,
+ rgszNames,
+ cNames,
+ lcid,
+ rgdispid);
+}
+
+/***
+*HRESULT CPDDispImpl::Invoke()
+*
+*Purpose:
+* Marshal the parameters and invoke the remote method.
+*
+* Out:
+* <struct MARSHAL_INVOKE> ; fixed arguments - see dispps.h
+* <IID iid> ; Interface ID - required
+* <arguments>* [<VARTYPE vt><vargData>]
+* <name ids>* [DISPID id]
+* <VARIANT varResult>?
+* <EXCEPINFO excepinfo>?
+* <unsigned int uArgErr>?
+*
+* In:
+* <HRESULT = return value>
+* <Out params>* [<VARTYPE vt><vargData>]
+* <varResult>?
+* <excepinfo>?
+* <uArgErr>?
+*
+*Entry:
+* dispidMember = the DISPID of the requested member function or property
+* riid = the IID of the interface to which this member belongs
+* lcid = the locale ID of the caller
+* wFlags = the context of the call, method or property access, etc.
+* pdispparams = DISPPARAMS struct containing the method's args
+*
+*Exit:
+* return value = HRESULT
+*
+* pvarResult =
+* pexcepinfo =
+* puArgErr =
+*
+***********************************************************************/
+HRESULT
+ProxyInvoke(ICHANNEL FAR* plrpc,
+ SYSKIND syskindStub,
+ DISPID dispidMember,
+ REFIID riid,
+ LCID lcid,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pdispparams,
+ VARIANT FAR* pvarResult,
+ EXCEPINFO FAR* pexcepinfo,
+ unsigned int FAR* puArgErr)
+{
+ IStream FAR* pstm;
+ MARSHAL_INVOKE mi;
+ VARIANTARG FAR* pvarg;
+ HRESULT hresult, hresultRet;
+ unsigned long _proxySysKind;
+ unsigned long _uArgErr;
+
+#ifdef _DEBUG
+ if(IsBadDispParams(pdispparams))
+ return RESULT(E_INVALIDARG);
+ if(pvarResult != NULL && IsBadWritePtr(pvarResult, sizeof(*pvarResult)))
+ return RESULT(E_INVALIDARG);
+ if(pexcepinfo != NULL && IsBadWritePtr(pexcepinfo, sizeof(*pexcepinfo)))
+ return RESULT(E_INVALIDARG);
+ if(puArgErr != NULL && IsBadWritePtr(puArgErr, sizeof(*puArgErr)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ if(plrpc == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_INVOKE, 1024, IID_IDispatch);
+
+ _proxySysKind = (unsigned long) SYS_CURRENT;
+ IfFailGo(PUT(pstm, _proxySysKind), LRelease);
+
+ mi.dispidMember = dispidMember;
+ mi.lcid = lcid;
+ mi.wFlags = wFlags;
+ mi.cArgs = pdispparams->cArgs;
+ mi.cNamedArgs = pdispparams->cNamedArgs;
+ mi.flags = 0;
+
+ if(pvarResult != NULL)
+ mi.flags |= MARSHAL_INVOKE_fHasResult;
+ if(pexcepinfo != NULL)
+ mi.flags |= MARSHAL_INVOKE_fHasExcepinfo;
+ if(puArgErr != NULL)
+ mi.flags |= MARSHAL_INVOKE_fHasArgErr;
+
+ IfFailGo(PUT(pstm, mi), LRelease);
+
+ IfFailGo(pstm->Write((const void FAR*)&riid, sizeof(IID), NULL), LRelease);
+
+ // pdispparams->rgvarg
+ //
+ for(pvarg = pdispparams->rgvarg;
+ pvarg < &pdispparams->rgvarg[mi.cArgs]; ++pvarg)
+ {
+ IfFailGo(VariantWrite(pstm, pvarg, syskindStub), LRelease);
+ }
+
+ // pdispparams->rgdispid
+ //
+ if(mi.cNamedArgs > 0){
+ IfFailGo(
+ pstm->Write(
+ pdispparams->rgdispidNamedArgs,
+ mi.cNamedArgs * sizeof(pdispparams->rgdispidNamedArgs[0]),
+ NULL),
+ LRelease);
+ }
+
+ if(mi.flags & MARSHAL_INVOKE_fHasResult)
+ IfFailGo(VariantWrite(pstm, pvarResult, syskindStub), LRelease);
+
+ if(mi.flags & MARSHAL_INVOKE_fHasExcepinfo)
+ IfFailGo(ExcepinfoWrite(pstm, &g_excepinfoNull, syskindStub), LRelease);
+
+ if(mi.flags & MARSHAL_INVOKE_fHasArgErr) {
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ _uArgErr = *puArgErr;
+ IfFailGo(pstm->Write(&_uArgErr, sizeof(_uArgErr), NULL), LRelease);
+ }
+
+ INVOKE_CALL(plrpc, pstm, LRelease);
+
+ // the return value
+ //
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LRelease);
+
+ // read the ByRef (Out) params.
+ //
+ for(pvarg = pdispparams->rgvarg;
+ pvarg < &pdispparams->rgvarg[mi.cArgs]; ++pvarg)
+ {
+ if(V_ISBYREF(pvarg))
+ IfFailGo(VariantReadType(pstm, pvarg, syskindStub), LRelease);
+ }
+
+ if(mi.flags & MARSHAL_INVOKE_fHasResult)
+ IfFailGo(VariantRead(pstm, pvarResult, NULL, syskindStub), LRelease);
+
+ if(mi.flags & MARSHAL_INVOKE_fHasExcepinfo){
+ IfFailGo(ExcepinfoRead(pstm, pexcepinfo, syskindStub), LRelease);
+ }
+
+ if(mi.flags & MARSHAL_INVOKE_fHasArgErr) {
+ IfFailGo(pstm->Read(&_uArgErr, sizeof(_uArgErr), NULL), LRelease);
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ *puArgErr = (unsigned int)_uArgErr;
+ }
+
+ hresult = hresultRet;
+
+LRelease:;
+ pstm->Release();
+
+ return hresult;
+}
+
+STDMETHODIMP
+CPDDispImpl::Invoke(DISPID dispidMember,
+ REFIID riid,
+ LCID lcid,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pdispparams,
+ VARIANT FAR* pvarResult,
+ EXCEPINFO FAR* pexcepinfo,
+ unsigned int FAR* puArgErr)
+{
+ return ProxyInvoke(m_pproxdisp->m_plrpc,
+ m_syskindStub,
+ dispidMember,
+ riid,
+ lcid,
+ wFlags,
+ pdispparams,
+ pvarResult,
+ pexcepinfo,
+ puArgErr);
+}
+
diff --git a/private/oleauto/src/dispatch/dispps.h b/private/oleauto/src/dispatch/dispps.h
new file mode 100644
index 000000000..84017ccc8
--- /dev/null
+++ b/private/oleauto/src/dispatch/dispps.h
@@ -0,0 +1,267 @@
+/***
+*dispps.h - IDispatch Proxy and Stub object header.
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file describes the following IDispatch Proxy and Stub objects.
+*
+* CProxDisp -- the IDispatch proxy class
+* CPDUnkImpl - CProxDisp implementation of IUnknown
+* CPDProxImpl - CProxDisp implementation of IRpcProxy
+* CPDDispImpl - CProxDisp implementation of IDispatch
+*
+* CStubDisp -- the IDispatch stub class
+*
+*Revision History:
+*
+* [00] 24-Sep-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+#ifndef __dispps_h__
+#define __dispps_h__
+
+
+#pragma warning(4:4355)
+
+// forward declarations
+class FAR CProxDisp;
+class FAR CStubDisp;
+
+
+// IDispatch proxy class' IUnknown implementation
+class FAR CPDUnkImpl : public IUnknown
+{
+public:
+
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ CPDUnkImpl(CProxDisp FAR* pproxdisp);
+ ~CPDUnkImpl();
+
+private:
+ CProxDisp FAR* m_pproxdisp;
+};
+
+// IDispatch proxy class IRpcProxy implementation
+class FAR CPDProxImpl : public IPROXY
+{
+public:
+ CPDProxImpl(CProxDisp FAR* pproxdisp);
+ ~CPDProxImpl();
+
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ STDMETHOD(Connect)(ICHANNEL FAR* plrpc);
+ STDMETHOD_(void, Disconnect)(void);
+
+private:
+ CProxDisp FAR* m_pproxdisp;
+};
+
+// IDispatch proxy class IDispatch implementation
+class FAR CPDDispImpl : public IDispatch
+{
+public:
+
+ CPDDispImpl(CProxDisp FAR* pproxdisp);
+ ~CPDDispImpl();
+
+ // IUnknown methods
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ // IDispatch methods
+ STDMETHOD(GetTypeInfoCount)(unsigned int FAR* pctinfo);
+
+ STDMETHOD(GetTypeInfo)(
+ unsigned int itinfo,
+ LCID lcid,
+ ITypeInfo FAR* FAR* pptinfo);
+
+ STDMETHOD(GetIDsOfNames)(
+ REFIID riid,
+ OLECHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ LCID lcid,
+ DISPID FAR* rgdispid);
+
+ STDMETHOD(Invoke)(
+ DISPID dispidMember,
+ REFIID riid,
+ LCID lcid,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pdispparams,
+ VARIANT FAR* pvarResult,
+ EXCEPINFO FAR* pexcepinfo,
+ unsigned int FAR* puArgErr);
+
+ STDMETHOD(SysKind)();
+
+private:
+ CProxDisp FAR* m_pproxdisp;
+ SYSKIND m_syskindStub;
+};
+
+// the IDispatch Proxy Class
+class FAR CProxDisp
+{
+public:
+ static IUnknown FAR* Create(IUnknown FAR* punkOuter, REFIID riid);
+
+private:
+ CProxDisp(IUnknown FAR* punkOuter, REFIID riid);
+ ~CProxDisp();
+
+ friend CPDUnkImpl;
+ friend CPDProxImpl;
+ friend CPDDispImpl;
+
+ CPDUnkImpl m_unk;
+ CPDProxImpl m_proxy;
+ CPDDispImpl m_disp;
+ GUID m_dispInterface;
+
+private:
+ unsigned long m_refs;
+ ICHANNEL FAR* m_plrpc;
+ IUnknown FAR* m_punkOuter;
+};
+
+// IDispatch Stub Class
+//
+class FAR CStubDisp : public ISTUB
+{
+public:
+ static HRESULT Create(IUnknown FAR* punkServer,
+#if (defined(WIN32) || defined(WOW))
+ REFIID riid,
+#endif
+ ISTUB FAR* FAR* ppstub);
+
+ // IUnknown methods
+ //
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ // IRpcStub methods
+ //
+#if (OE_WIN32 || defined(WOW))
+ STDMETHOD(Connect)(IUnknown FAR* pUnk);
+ STDMETHOD_(void, Disconnect)(void);
+ STDMETHOD(Invoke)(RPCOLEMESSAGE FAR* pRpcMsg,
+ IRpcChannelBuffer FAR* pRpcChannel);
+ STDMETHOD_(IRpcStubBuffer *, IsIIDSupported)(REFIID iid);
+ STDMETHOD_(ULONG, CountRefs)(void);
+ STDMETHOD(DebugServerQueryInterface)(void FAR* FAR* ppv);
+ STDMETHOD_(void, DebugServerRelease)(void FAR* pv);
+#else
+ STDMETHOD(Connect)(IUnknown FAR* punkObject);
+ STDMETHOD_(void, Disconnect)(void);
+ STDMETHOD(Invoke)(
+ REFIID riid,
+ int imeth,
+ IStream FAR* pstm,
+ unsigned long dwDestCtx,
+ void FAR* pvDestCtx);
+#if OE_MAC
+ STDMETHOD_(unsigned long, IsIIDSupported)(REFIID riid);
+#else
+ STDMETHOD_(BOOL, IsIIDSupported)(REFIID riid);
+#endif
+ STDMETHOD_(unsigned long, CountRefs)(void);
+#endif
+
+private:
+ CStubDisp(void);
+ ~CStubDisp(void);
+
+ unsigned long m_refs;
+ IUnknown FAR* m_punkObj;
+ IDispatch FAR* m_pdispObj;
+#if (defined(WIN32) || defined(WOW))
+ IID m_iid;
+#endif
+};
+
+
+// IDispatch method indices
+//
+#define IMETH_QUERYINTERFACE 0 /* Placeholder */
+#define IMETH_ADDREF 1 /* Placeholder */
+#define IMETH_RELEASE 2 /* Placeholder */
+#define IMETH_GETTYPEINFOCOUNT 3
+#define IMETH_GETTYPEINFO 4
+#define IMETH_GETIDSOFNAMES 5
+#define IMETH_INVOKE 6
+#define IMETH_SYSKIND 7
+
+
+// the following structure is used to marshal the parameters
+// for IDispatch::Invoke().
+//
+typedef struct tagMARSHAL_INVOKE MARSHAL_INVOKE;
+struct tagMARSHAL_INVOKE {
+ DISPID dispidMember;
+ LCID lcid;
+ unsigned long cArgs;
+ unsigned long cNamedArgs;
+ unsigned short wFlags;
+ unsigned char flags;
+};
+
+#define MARSHAL_INVOKE_fHasResult 0x02
+#define MARSHAL_INVOKE_fHasExcepinfo 0x04
+#define MARSHAL_INVOKE_fHasArgErr 0x08
+
+
+// IDispatch proxy routines -
+// used by both the IDispatch proxy class and the Universal proxy class
+
+HRESULT ProxyGetTypeInfoCount(ICHANNEL FAR* plrpc,
+ SYSKIND syskindStub,
+ unsigned int FAR* pctinfo);
+
+HRESULT ProxyGetTypeInfo(ICHANNEL FAR* plrpc,
+ SYSKIND syskindStub,
+ unsigned int itinfo,
+ LCID lcid,
+ ITypeInfo FAR* FAR* pptinfo);
+
+HRESULT ProxyGetIDsOfNames(ICHANNEL FAR* plrpc,
+ SYSKIND syskindStub,
+ REFIID riid,
+ OLECHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ LCID lcid,
+ DISPID FAR* rgdispid);
+
+HRESULT ProxyInvoke(ICHANNEL FAR* plrpc,
+ SYSKIND syskindStub,
+ DISPID dispidMember,
+ REFIID riid,
+ LCID lcid,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pdispparams,
+ VARIANT FAR* pvarResult,
+ EXCEPINFO FAR* pexcepinfo,
+ unsigned int FAR* puArgErr);
+
+// IDispatch Stub routines -
+// Used by both the IDispatch stub class, and the Universal stub class
+
+HRESULT StubGetTypeInfoCount(IDispatch FAR* pdisp, IStream FAR* pstm);
+HRESULT StubGetTypeInfo(IDispatch FAR* pdisp, IStream FAR* pstm);
+HRESULT StubGetIDsOfNames(IDispatch FAR* pdisp, IStream FAR* pstm);
+HRESULT StubInvoke(IDispatch FAR* pdisp, IStream FAR* pstm);
+
+#endif __dispps_h__
diff --git a/private/oleauto/src/dispatch/dispstrm.cpp b/private/oleauto/src/dispatch/dispstrm.cpp
new file mode 100644
index 000000000..c048f4751
--- /dev/null
+++ b/private/oleauto/src/dispatch/dispstrm.cpp
@@ -0,0 +1,375 @@
+//+-------------------------------------------------------------------------
+//
+// Microsoft Windows
+// Copyright (C) Microsoft Corporation, 1992 - 1993.
+//
+// File: dipstrm.cpp
+//
+// Classes: CStreamOnBuffer
+//
+//--------------------------------------------------------------------------
+
+#include <oledisp.h>
+#include <dispmrsh.h>
+#include <dispstrm.h>
+
+#if OE_WIN32
+#include "oautil.h"
+#endif // OE_WIN32
+
+ASSERTDATA
+
+#if OE_WIN16
+#define HMEMCPY(DST, SRC, SIZE) hmemcpy(DST, SRC, SIZE)
+#else //OE_WIN16
+#define HMEMCPY(DST, SRC, SIZE) memcpy(DST, SRC, (size_t)SIZE)
+#endif //OE_WIN16
+
+CStreamOnBuffer::CStreamOnBuffer(ICHANNEL *pRpcChannel,
+ RPCOLEMESSAGE *pMessage,
+ REFIID riid,
+ ULONG iMeth)
+ : _refCount(1), _pMessage(pMessage),
+ _pRpcChannel(pRpcChannel)
+{
+ _riid = riid;
+ _pmalloc = NULL; // no iMalloc yet.
+
+ // write to an IMalloc'ed buffer (alloc'ed later on)
+ _writeBuffer = NULL; // no buffer allocated yet
+ _cbWriteBuffer = 0; // no data yet
+
+
+ // hack to see if we are being called from the proxy or the stub
+ if (iMeth != 0xffffffff) { // proxy side
+
+ // prepare the message packet
+ memset(_pMessage, 0, sizeof(RPCOLEMESSAGE));
+ _pMessage->dataRepresentation = NDR_LOCAL_DATA_REPRESENTATION;
+ _pMessage->iMethod = iMeth;
+ //_pMessage.cbBuffer = size; set to exact size later on
+
+ // can't read/write yet.
+ _buffer = NULL; // no current pointer yet
+ _cbBuffer = 0;
+
+ } else { // stub side
+ // can start reading right away. Read directly out of the
+ // incoming message buffer.
+ _buffer = (unsigned char FAR*)_pMessage->Buffer;
+ _cbBuffer = _pMessage->cbBuffer;
+ }
+ _bufferBase = _buffer; // starting offset of buffer
+}
+
+
+CStreamOnBuffer::~CStreamOnBuffer()
+{
+
+ // free any malloc'ed write buffer
+ if (_writeBuffer)
+ _pmalloc->Free(_writeBuffer);
+
+ // DON'T release the _pmalloc -- it wasn't addref'ed
+}
+
+
+STDMETHODIMP CStreamOnBuffer::QueryInterface( REFIID riid, LPVOID FAR* ppvObj)
+{
+ *ppvObj = NULL;
+ if (IsEqualIID(riid, IID_IUnknown))
+ *ppvObj = (IUnknown *) this;
+ else if (IsEqualIID(riid, IID_IStream))
+ *ppvObj = (IStream *) this;
+ else
+ return ResultFromScode(E_NOINTERFACE);
+
+ AddRef();
+ return ResultFromScode(S_OK);
+}
+
+
+STDMETHODIMP_(ULONG) CStreamOnBuffer::AddRef( THIS )
+{
+ return _refCount += 1;
+}
+
+
+STDMETHODIMP_(ULONG) CStreamOnBuffer::Release( THIS )
+{
+ _refCount -= 1;
+ if (_refCount == 0)
+ {
+ _pRpcChannel->FreeBuffer(_pMessage);
+ delete this;
+ return 0;
+ }
+ else
+ return _refCount;
+
+}
+
+
+STDMETHODIMP CStreamOnBuffer::Read(THIS_ VOID HUGEP *pv,
+ ULONG cb, ULONG *pcbRead)
+{
+
+ // must have set ourselves up for reading, or else we're in trouble....
+ ASSERT(_bufferBase == (unsigned char HUGEP*)_pMessage->Buffer);
+ ASSERT(_buffer != 0);
+
+ // verify that our message buffer isn't overrunned (shouldn't ever happen)
+ if (((char FAR*)_buffer + cb) > ((char FAR*)_pMessage->Buffer + _pMessage->cbBuffer)) {
+ ASSERT(FALSE);
+ return RESULT(RPC_E_INVALID_DATAPACKET);
+ }
+
+ // read data out of our local buffer
+ HMEMCPY( pv, _buffer, cb );
+ _buffer = _buffer + cb;
+
+ if (pcbRead != NULL)
+ *pcbRead = cb;
+ return ResultFromScode(S_OK);
+}
+
+
+STDMETHODIMP CStreamOnBuffer::Write(THIS_ VOID const HUGEP *pv,
+ ULONG cb,
+ ULONG *pcbWritten)
+{
+ ULONG size;
+
+ // verify that our local buffer isn't overrunned
+ if ((_buffer + cb) > (_bufferBase + _cbBuffer)) {
+ if (_bufferBase == _writeBuffer) {
+ // if we're writing, then we can grow our buffer
+ size = _cbWriteBuffer*2; // guess at doubling our size
+ if ((_buffer + cb) > (_writeBuffer + size))
+ size = _cbWriteBuffer + cb; // if it won't fit into the doubled value
+ IfFailRet(ResizeBuffer(size));
+ } else {
+ // writing into our read buffer (wierd, but CoUnMarshalInterface does
+ // this). Better not have to grow the buffer!
+ ASSERT(FALSE);
+ return RESULT(RPC_E_INVALID_DATAPACKET);
+ }
+ }
+
+ // put the data into our local buffer
+ HMEMCPY(_buffer, pv, cb );
+ _buffer = _buffer + cb;
+ if (pcbWritten != NULL)
+ *pcbWritten = cb;
+ return ResultFromScode(S_OK);
+}
+
+
+STDMETHODIMP CStreamOnBuffer::Seek(THIS_ LARGE_INTEGER dlibMove,
+ DWORD dwOrigin,
+ ULARGE_INTEGER *plibNewPosition)
+{
+ ULONG pos;
+
+ // Verify that the offset isn't out of range.
+ if (dlibMove.HighPart != 0)
+ return ResultFromScode( E_FAIL );
+
+ // Determine the new seek pointer.
+ switch (dwOrigin)
+ {
+ case STREAM_SEEK_SET:
+ pos = dlibMove.LowPart;
+ break;
+
+ case STREAM_SEEK_CUR:
+ /* Must use signed math here. */
+ pos = _buffer - _bufferBase;
+ if ((long) dlibMove.LowPart < 0 &&
+ pos < (unsigned long) - (long) dlibMove.LowPart)
+ return ResultFromScode( E_FAIL );
+ pos += (long) dlibMove.LowPart;
+ break;
+
+ case STREAM_SEEK_END:
+ return ResultFromScode(E_NOTIMPL);
+ break;
+
+ default:
+ return ResultFromScode( E_FAIL );
+ }
+
+ // Set the seek pointer.
+ _buffer = _bufferBase + pos;
+ if (plibNewPosition != NULL)
+ {
+ plibNewPosition->LowPart = pos;
+ plibNewPosition->HighPart = 0;
+ }
+ return ResultFromScode(S_OK);
+}
+
+
+STDMETHODIMP CStreamOnBuffer::SetSize(THIS_ ULARGE_INTEGER libNewSize)
+{
+ return ResultFromScode(E_NOTIMPL);
+}
+
+
+STDMETHODIMP CStreamOnBuffer::CopyTo(THIS_ IStream *pstm,
+ ULARGE_INTEGER cb,
+ ULARGE_INTEGER *pcbRead,
+ ULARGE_INTEGER *pcbWritten)
+{
+ return ResultFromScode(E_NOTIMPL);
+}
+
+
+STDMETHODIMP CStreamOnBuffer::Commit(THIS_ DWORD grfCommitFlags)
+{
+ return ResultFromScode(E_NOTIMPL);
+}
+
+
+STDMETHODIMP CStreamOnBuffer::Revert(THIS)
+{
+ return ResultFromScode(E_NOTIMPL);
+}
+
+
+STDMETHODIMP CStreamOnBuffer::LockRegion(THIS_ ULARGE_INTEGER libOffset,
+ ULARGE_INTEGER cb,
+ DWORD dwLockType)
+{
+ return ResultFromScode(E_NOTIMPL);
+}
+
+
+
+STDMETHODIMP CStreamOnBuffer::UnlockRegion(THIS_ ULARGE_INTEGER libOffset,
+ ULARGE_INTEGER cb,
+ DWORD dwLockType)
+{
+ return ResultFromScode(E_NOTIMPL);
+}
+
+
+STDMETHODIMP CStreamOnBuffer::Stat(THIS_ STATSTG *pstatstg, DWORD grfStatFlag)
+{
+ return ResultFromScode(E_NOTIMPL);
+}
+
+
+STDMETHODIMP CStreamOnBuffer::Clone(THIS_ IStream * *ppstm)
+{
+ return ResultFromScode(E_NOTIMPL);
+}
+
+
+STDMETHODIMP CStreamOnBuffer::Call( THIS )
+{
+ DWORD status;
+ HRESULT hresult;
+
+ ULONG cbSend;
+
+ // create the minimum size buffer
+ cbSend = (_buffer - _writeBuffer); // # of bytes to write
+
+ _pMessage->cbBuffer = max(cbSend, 16); // get the buffer & copy data into it
+ // zero-length buffers seem to be flakey
+ IfFailRet(_pRpcChannel->GetBuffer(_pMessage, _riid));
+ ASSERT(_pMessage->cbBuffer >= cbSend);
+
+ HMEMCPY(_pMessage->Buffer, _writeBuffer, cbSend);
+
+ // write the data, get the resulting data back.
+ hresult = _pRpcChannel->SendReceive(_pMessage, &status);
+ if (hresult != NOERROR) {
+ _pMessage->Buffer = NULL; // so we don't crash on FreeBuffer
+ return hresult;
+ }
+
+ // now switch over to read mode. We read directly out of the message buffer.
+ _buffer = (unsigned char FAR*)_pMessage->Buffer;
+ _cbBuffer = _pMessage->cbBuffer;
+ _bufferBase = _buffer;
+
+ // CONSIDER: throw away our malloc'ed buffer now (gets tossed later, but
+ // CONSIDER: we're done with it now).
+
+ return NOERROR;
+}
+
+
+// called from the stub side when it is done reading and wants to write
+STDMETHODIMP CStreamOnBuffer::RewindBuffer( THIS_)
+{
+ HRESULT hresult;
+ ULONG cbWriteBuffer;
+
+ // alloc a separate buffer so we can pass all our data back to the proxy
+ _buffer = NULL; // not reading anymore
+ ASSERT(_writeBuffer == NULL); // haven't written yet
+ // having both of these NULL will cause ResizeBuffer to alloc
+ // a new write buffer, and position us at the front.
+
+ // Start our write buffer at the size of the incoming RPC buffer (just
+ // an arbitrary guess). The incoming size may be zero, hence the 'max' check.
+ cbWriteBuffer = max(_pMessage->cbBuffer, 16);
+
+ hresult = ResizeBuffer(cbWriteBuffer); // alloc the write buffer
+ ASSERT(_buffer == _writeBuffer);
+ return hresult;
+}
+
+// called from the stub side when it is done writing, before the stream
+// is destroyed.
+STDMETHODIMP CStreamOnBuffer::ResetBuffer( THIS )
+{
+ ULONG cbSend;
+
+ ASSERT(_writeBuffer != NULL);
+ cbSend = (_buffer - _writeBuffer);
+
+ // get a new buffer to talk to the proxy.
+ _pMessage->cbBuffer = max(cbSend, 16); // get the buffer & copy data into it
+ // zero-length buffers seem to be flakey
+ IfFailRet(_pRpcChannel->GetBuffer(_pMessage, _riid));
+ ASSERT(_pMessage->cbBuffer >= cbSend);
+
+ // copy the data into the stream
+ HMEMCPY(_pMessage->Buffer, _writeBuffer, cbSend);
+
+ return NOERROR;
+}
+
+
+STDMETHODIMP CStreamOnBuffer::ResizeBuffer( THIS_ ULONG cbNew)
+{
+ void HUGEP* buffer;
+ ULONG oldOffset;
+
+ if (_pmalloc == NULL) {
+ // NOTE: this does not addref the malloc pointer
+ IfFailRet(GetMalloc(&_pmalloc));
+ // the realloc below is supposed to do Alloc if it the input parm is NULL.
+ }
+
+ ASSERT(cbNew != 0); // realloc(NULL) means free -- our caller should
+ // have checked for this condition.
+
+ // save current offset into buffer
+ oldOffset = _buffer - _writeBuffer;
+
+ buffer = _pmalloc->Realloc(_writeBuffer, cbNew);
+ if (buffer == NULL)
+ return RESULT(E_OUTOFMEMORY);
+ _writeBuffer = (unsigned char *)buffer; // point to new block
+ _cbWriteBuffer = cbNew;
+ _bufferBase = _writeBuffer; // new base pointer
+ _cbBuffer = _cbWriteBuffer;
+ _buffer = _writeBuffer + oldOffset; // update current pointer
+
+ return ResultFromScode(S_OK);
+}
diff --git a/private/oleauto/src/dispatch/dispstrm.h b/private/oleauto/src/dispatch/dispstrm.h
new file mode 100644
index 000000000..bc0630279
--- /dev/null
+++ b/private/oleauto/src/dispatch/dispstrm.h
@@ -0,0 +1,78 @@
+//+-------------------------------------------------------------------------
+//
+// Microsoft Windows
+// Copyright (C) Microsoft Corporation, 1992 - 1993.
+//
+// File: dispstrm.h
+//
+// Contents: Private header file for layering IStream on top of
+// IRpcChannelBuffer
+//
+//
+//--------------------------------------------------------------------------
+#ifndef __dispstrm_h__
+#define __dispstrm_h__
+
+
+#pragma warning(4:4355)
+
+class CStreamOnBuffer : public IStream
+{
+
+ public:
+
+ // IUnknown Methods
+ STDMETHOD (QueryInterface) ( THIS_ REFIID riid, LPVOID FAR* ppvObj);
+ STDMETHOD_(ULONG,AddRef) ( THIS );
+ STDMETHOD_(ULONG,Release) ( THIS );
+
+ // IStream Methods
+ STDMETHOD (Read) (THIS_ VOID HUGEP *pv,
+ ULONG cb, ULONG *pcbRead) ;
+ STDMETHOD (Write) (THIS_ VOID const HUGEP *pv,
+ ULONG cb,
+ ULONG *pcbWritten) ;
+ STDMETHOD (Seek) (THIS_ LARGE_INTEGER dlibMove,
+ DWORD dwOrigin,
+ ULARGE_INTEGER *plibNewPosition) ;
+ STDMETHOD (SetSize) (THIS_ ULARGE_INTEGER libNewSize) ;
+ STDMETHOD (CopyTo) (THIS_ IStream *pstm,
+ ULARGE_INTEGER cb,
+ ULARGE_INTEGER *pcbRead,
+ ULARGE_INTEGER *pcbWritten) ;
+ STDMETHOD (Commit) (THIS_ DWORD grfCommitFlags) ;
+ STDMETHOD (Revert) (THIS) ;
+ STDMETHOD (LockRegion) (THIS_ ULARGE_INTEGER libOffset,
+ ULARGE_INTEGER cb,
+ DWORD dwLockType) ;
+ STDMETHOD (UnlockRegion) (THIS_ ULARGE_INTEGER libOffset,
+ ULARGE_INTEGER cb,
+ DWORD dwLockType) ;
+ STDMETHOD (Stat) (THIS_ STATSTG *pstatstg, DWORD grfStatFlag) ;
+ STDMETHOD (Clone) (THIS_ IStream * *ppstm) ;
+
+ CStreamOnBuffer( ICHANNEL *pRpcChannel,
+ RPCOLEMESSAGE *pMessage,
+ REFIID riid,
+ ULONG iMeth);
+ ~CStreamOnBuffer();
+
+ STDMETHOD (Call) ();
+ STDMETHOD (ResetBuffer) ();
+ STDMETHOD (ResizeBuffer) (ULONG size);
+ STDMETHOD (RewindBuffer) ();
+
+
+ unsigned char HUGEP *_writeBuffer;
+ ULONG _cbWriteBuffer;
+ unsigned char HUGEP *_bufferBase;
+ unsigned char HUGEP *_buffer;
+ ULONG _cbBuffer;
+ IMalloc *_pmalloc;
+ RPCOLEMESSAGE *_pMessage;
+ ICHANNEL *_pRpcChannel;
+ ULONG _refCount;
+ GUID _riid;
+};
+
+#endif //__dispstrm_h__
diff --git a/private/oleauto/src/dispatch/dispstub.cpp b/private/oleauto/src/dispatch/dispstub.cpp
new file mode 100644
index 000000000..082d6b8cb
--- /dev/null
+++ b/private/oleauto/src/dispatch/dispstub.cpp
@@ -0,0 +1,803 @@
+/***
+*dispstub.cpp
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This module implements the custom 'stub', remoting support for
+* the IDispatch interface.
+*
+*Revision History:
+*
+* [00] 18-Sep-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+* There are assumptions in the following marshaling code that the
+* endianness of the caller and callee are the same.
+*
+* The difference between the IDispatch vs. IDispatchW implementation
+* is a parameterized type. Unfortunately, C7/C8 doesn't support C++
+* templates, hence the near duplication of code between the IDispatch
+* and IDispatchW stub implementation (as well as common code between the
+* stubs of IDispatch & ITypeLib/ITypeInfo).
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#ifndef WIN32
+#include <cobjps.h>
+#endif //!WIN32
+
+#include "dispmrsh.h"
+#include "dispps.h"
+
+ASSERTDATA
+
+CStubDisp::CStubDisp()
+{
+ m_refs = 0;
+ m_punkObj = NULL;
+ m_pdispObj = NULL;
+#if (defined(WIN32) || defined(WOW))
+ m_iid = IID_NULL;
+#endif
+}
+
+CStubDisp::~CStubDisp()
+{
+ Disconnect();
+}
+
+HRESULT
+CStubDisp::Create(IUnknown FAR* punkServer,
+#if (defined(WIN32) || defined(WOW))
+ REFIID riid,
+#endif
+ ISTUB FAR* FAR* ppstub)
+{
+ CStubDisp FAR* pstub;
+
+ if((pstub = new FAR CStubDisp()) != NULL){
+ pstub->AddRef();
+ *ppstub = pstub;
+#if (defined(WIN32) || defined(WOW))
+ pstub->m_iid = riid;
+#endif
+ if (punkServer)
+ return pstub->Connect(punkServer);
+ return NOERROR;
+ }
+ return RESULT(E_OUTOFMEMORY);
+}
+
+
+//---------------------------------------------------------------------
+// IUnknown Methods
+//---------------------------------------------------------------------
+
+
+STDMETHODIMP
+CStubDisp::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ if(IsEqualIID(riid, IID_IUnknown)){
+ *ppv = this;
+ }else if(IsEqualIID(riid, IID_ISTUB)){
+ *ppv = this;
+ }else{
+ *ppv = NULL;
+ return RESULT(E_NOINTERFACE);
+ }
+ ++m_refs;
+ return NOERROR;
+}
+
+STDMETHODIMP_(unsigned long)
+CStubDisp::AddRef()
+{
+ return ++m_refs;
+}
+
+STDMETHODIMP_(unsigned long)
+CStubDisp::Release()
+{
+ if(--m_refs == 0){
+ delete this;
+ return 0;
+ }
+ return m_refs;
+}
+
+
+//---------------------------------------------------------------------
+// IRpcStub Methods
+//---------------------------------------------------------------------
+
+
+STDMETHODIMP
+CStubDisp::Connect(IUnknown FAR* punkObj)
+{
+#if (defined(WIN32) || defined(WOW))
+ ASSERT(m_punkObj == NULL && m_pdispObj == NULL);
+ //This will keep the server object alive until we disconnect.
+ IfFailRet(punkObj->QueryInterface(m_iid, (void FAR* FAR*)&m_pdispObj));
+ punkObj->AddRef();
+ m_punkObj = punkObj;
+ return NOERROR;
+#else
+ if(m_punkObj)
+ return RESULT(E_FAIL); // call Disconnect first
+
+ if (punkObj) {
+ punkObj->AddRef();
+ m_punkObj = punkObj;
+ }
+ return NOERROR;
+#endif
+}
+
+
+STDMETHODIMP_(void)
+CStubDisp::Disconnect()
+{
+ if(m_punkObj){
+ m_punkObj->Release();
+ m_punkObj = NULL;
+ }
+ if(m_pdispObj){
+ m_pdispObj->Release();
+ m_pdispObj = NULL;
+ }
+}
+
+PRIVATE_(HRESULT)
+DispatchGetSysKind(IStream FAR* pstm)
+{
+ unsigned long _sysKind;
+
+ REWIND_STREAM(pstm);
+
+ _sysKind = (unsigned long) SYS_CURRENT;
+ IfFailRet(PUT(pstm, _sysKind));
+
+ return NOERROR;
+}
+
+/***
+*PRIVATE HRESULT StubGetTypeInfoCount(IDispatch*, IStream*)
+*Purpose:
+*
+* In:
+* <nothing>
+*
+* Out:
+* <HRESULT = return value>
+* <unsigned int = ctinfo>
+*
+*Entry:
+* pdisp =
+* pstm =
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+StubGetTypeInfoCount(IDispatch FAR* pdisp, IStream FAR* pstm)
+{
+ unsigned int ctinfo;
+ unsigned long _ctinfo;
+ HRESULT hresultRet;
+
+ hresultRet = pdisp->GetTypeInfoCount(&ctinfo);
+
+ REWIND_STREAM(pstm);
+
+ IfFailRet(DispMarshalHresult(pstm, hresultRet));
+
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ _ctinfo = ctinfo;
+ IfFailRet(PUT(pstm, _ctinfo));
+
+ return NOERROR;
+}
+
+
+/***
+*PRIVATE HRESULT StubGetTypeInfo(IDispatch*, IStream*)
+*Purpose:
+*
+* In:
+* <unsigned int = itinfo>
+* <LCID = lcid>
+*
+* Out:
+* <HRESULT = return value>
+* <ITypeInfo* = pptinfo>
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+HRESULT
+StubGetTypeInfo(IDispatch FAR* pdisp, IStream FAR* pstm)
+{
+ LCID lcid;
+ unsigned int itinfo;
+ unsigned long _itinfo;
+ ITypeInfo FAR* ptinfo;
+ HRESULT hresult, hresultRet;
+
+
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ IfFailGo(GET(pstm, _itinfo), LExit);
+ itinfo = (unsigned int) _itinfo;
+
+ IfFailGo(GET(pstm, lcid), LExit);
+
+ hresultRet = pdisp->GetTypeInfo(itinfo, lcid, &ptinfo);
+
+ IfFailGo(REWIND_STREAM(pstm), LExit2);
+
+ IfFailGo(DispMarshalHresult(pstm, hresultRet), LExit2);
+
+ if(HRESULT_SUCCESS(hresultRet)){
+ // dont bother marhshaling the interface ptr unless the
+ // GetTypeInfo call succeeded.
+ //
+ hresult = DispMarshalInterface(pstm, IID_ITypeInfo, ptinfo);
+ }
+
+LExit2:
+ if(hresultRet == NOERROR)
+ ptinfo->Release();
+
+LExit:;
+ return hresult;
+}
+
+/***
+*PRIVATE HRESULT StubGetIDsOfNames(IDispatch*, IStream*)
+*
+*Purpose:
+*
+* In:
+* <REFIID = riid>
+* <LCID = lcid>
+* <unsigned int = cNames>
+* [(len,sz)]+
+*
+* Out:
+* <HRESULT = return value>
+* [DISPID]+
+*
+*Entry:
+* pdisp =
+* pstm =
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+StubGetIDsOfNames(IDispatch FAR* pdisp, IStream FAR* pstm)
+{
+ IID iid;
+ LCID lcid;
+ int iAlloc;
+ unsigned long len;
+ //REFIID riid = iid;
+ DISPID FAR* rgdispid;
+ unsigned int cNames;
+ OLECHAR FAR* FAR* rgszNames;
+ HRESULT hresult, hresultRet;
+ unsigned long _proxySysKind;
+ unsigned long _cNames;
+ unsigned int iName;
+
+ IfFailGo(GET(pstm, _proxySysKind), LExit);
+
+ IfFailGo(pstm->Read((void FAR*)&iid, sizeof(IID), NULL), LExit);
+
+ IfFailGo(GET(pstm, lcid), LExit);
+
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ IfFailGo(GET(pstm, _cNames), LExit);
+ cNames = (unsigned int) _cNames;
+
+ if((rgdispid = new FAR DISPID[cNames]) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LExit;
+ }
+
+ if((rgszNames = new FAR OLECHAR FAR* [cNames]) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LFreeRGID;
+ }
+
+ iAlloc = -1;
+
+#if OE_WIN32 /* enable 16/32 interoperablity support */
+ if ((SYSKIND) _proxySysKind == SYS_WIN16) {
+ char buf[128];
+ char *pBuf = buf;
+
+ for(iName = 0; iName<cNames; ++iName){
+ IfFailGo(GET(pstm, len), LFree);
+
+ // optimization for names under 128 bytes
+ if (len > 128) {
+ if ((pBuf = new FAR char [len]) == NULL) {
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LFree;
+ }
+ }
+
+ // Get ANSI string from stream and convert it to UNICODE
+ IfFailGo(pstm->Read((void FAR*) pBuf, len, NULL), LFree);
+ IfFailGo(ConvertStringToW(pBuf, &rgszNames[iName]), LFree);
+
+ // remember how far we got so we can unwind allocations on exit
+ ++iAlloc;
+
+ if (len > 128)
+ delete pBuf;
+ }
+ } else
+#endif
+ {
+ for(iName = 0; iName<cNames; ++iName){
+ IfFailGo(GET(pstm, len), LFree);
+
+ if((rgszNames[iName] = new FAR OLECHAR [CHLEN(len)]) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LFree;
+ }
+
+ // remember how far we got so we can unwind allocations on exit
+ ++iAlloc;
+
+ IfFailGo(pstm->Read((void FAR*) rgszNames[iName], len, NULL), LFree);
+ }
+
+ }
+
+ hresultRet = pdisp->GetIDsOfNames(iid, rgszNames, cNames, lcid, rgdispid);
+
+ IfFailGo(REWIND_STREAM(pstm), LFree);
+
+ IfFailGo(DispMarshalHresult(pstm, hresultRet), LFree);
+
+ unsigned int i;
+ for(i=0; i<cNames; ++i)
+ IfFailGo(pstm->Write(&rgdispid[i], sizeof(rgdispid[0]), NULL), LFree);
+
+ hresult = NOERROR;
+
+LFree:;
+ for(; iAlloc >= 0; --iAlloc)
+ delete rgszNames[iAlloc];
+ delete rgszNames;
+
+LFreeRGID:;
+ delete rgdispid;
+
+LExit:;
+ return hresult;
+}
+
+
+/***
+*PRIVATE HRESULT StubInvoke(IDispatch*, IStream*)
+*
+*Purpose:
+* Read the marshalled Invoke parameters from the given stream,
+* repackage them and pass them onto the Invoke member of the given
+* IDispatch interface pointer.
+*
+* Then reset the stream, gather the results of the Invoke call and
+* marshal them back into the given stream to be returned to the cross
+* process caller.
+*
+* Marshaling format for IDispatch::Invoke()
+*
+* In:
+* <struct MARSHAL_INVOKE>
+* <IID iid>
+* <arguments>*
+* <name DISPIDs>*
+* <VARIANT varResult>?
+* <EXCEPINFO excepinfo>?
+* <unsigned int uArgErr>?
+*
+* Out:
+* <HRESULT = return value>
+* <Out params>?
+* <VARIANT varResult>?
+* <EXCEPINFO excepinfo>?
+* <unsigned int uArgErr>?
+*
+*Entry:
+* pdisp = the IDispatch* to invoke on
+* pstm = the stream containing the marshaled actuals
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+StubInvoke(IDispatch FAR* pdisp, IStream FAR* pstm)
+{
+ unsigned int i;
+ IID iid;
+ //REFIID riid = iid; // WIN32 bug, references a temp object of class GUID
+ MARSHAL_INVOKE mi;
+ VARTYPE FAR* rgvtSaved;
+ DISPPARAMS dispparams;
+ HRESULT hresult, hresultRet;
+ unsigned long _uArgErr;
+ unsigned int FAR* puArgErr;
+ EXCEPINFO excepinfo, FAR* pexcepinfo;
+ VARIANT varResult, FAR* pvarResult;
+ VARIANTARG FAR* rgvargRef, FAR* pvarg;
+ unsigned long _proxySysKind;
+
+ rgvtSaved = NULL;
+ rgvargRef = NULL;
+ dispparams.rgvarg = (VARIANTARG FAR*)NULL;
+ dispparams.rgdispidNamedArgs = (DISPID FAR*)NULL;
+
+ // read the System Kind
+ //
+ IfFailGo(GET(pstm, _proxySysKind), LExit);
+
+ // read the MARSHAL_INTERFACE struct.
+ //
+ IfFailGo(GET(pstm, mi), LExit);
+
+ // Read the interface ID if it was non-null.
+ //
+ IfFailGo(pstm->Read((void FAR*)&iid, sizeof(IID), NULL), LExit);
+
+ if(mi.cArgs > 0){
+ if((rgvtSaved = new FAR VARTYPE[mi.cArgs]) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LExit;
+ }
+
+ // Allocate the max possible space required to hold the ByRef values.
+ // (this is cArgs * sizeof(VARIANTARG) in the case that each rgvarg
+ // entry is a VT_VARIANT).
+ //
+ if((rgvargRef = new FAR VARIANTARG[mi.cArgs]) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LFreeRgVtSaved;
+ }
+
+ // init the ByRef arg array
+ for(pvarg = rgvargRef; pvarg < &rgvargRef[mi.cArgs]; ++pvarg)
+ V_VT(pvarg) = VT_EMPTY;
+
+ if((dispparams.rgvarg = new FAR VARIANTARG[mi.cArgs]) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LFreeRgVargRef;
+ }
+
+ // read pdispparams->rgvarg[]
+ //
+ for(unsigned int i = 0; i < mi.cArgs; ++i){
+ IfFailGo(
+ VariantRead(pstm,
+ &dispparams.rgvarg[i],
+ &rgvargRef[i],
+ (SYSKIND) _proxySysKind),
+ LFreeRgVarg);
+
+ // stash away the passed-in vartype so we can verify later
+ // that the callee did not hammer the rgvarg arrary.
+ //
+ rgvtSaved[i] = V_VT(&dispparams.rgvarg[i]);
+ }
+ }
+
+ // read the named parameter DISPIDs
+ //
+ if(mi.cNamedArgs > 0){
+ dispparams.rgdispidNamedArgs = new FAR DISPID[mi.cNamedArgs];
+ if(dispparams.rgdispidNamedArgs == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LFreeRgVarg;
+ }
+ IfFailGo(
+ pstm->Read(
+ dispparams.rgdispidNamedArgs,
+ mi.cNamedArgs * sizeof(dispparams.rgdispidNamedArgs[0]), NULL),
+ LFree);
+ }
+
+ dispparams.cArgs = (unsigned int)mi.cArgs;
+ dispparams.cNamedArgs = (unsigned int)mi.cNamedArgs;
+
+ if((mi.flags & MARSHAL_INVOKE_fHasResult) == 0){
+ pvarResult = NULL;
+ }else{
+ pvarResult = &varResult;
+ IfFailGo(VariantRead(pstm, pvarResult, NULL, (SYSKIND) _proxySysKind), LFree);
+ }
+
+ if((mi.flags & MARSHAL_INVOKE_fHasExcepinfo) == 0){
+ pexcepinfo = NULL;
+ }else{
+ pexcepinfo = &excepinfo;
+ IfFailGo(ExcepinfoRead(pstm, pexcepinfo, (SYSKIND) _proxySysKind), LFree);
+ }
+
+ if((mi.flags & MARSHAL_INVOKE_fHasArgErr) == 0){
+ puArgErr = NULL;
+ }else{
+ puArgErr = (unsigned int FAR*)&_uArgErr;
+ IfFailGo(GET(pstm, _uArgErr), LFree);
+ }
+
+
+ hresultRet = pdisp->Invoke(
+ mi.dispidMember,
+ iid,
+ mi.lcid,
+ mi.wFlags,
+ &dispparams,
+ pvarResult,
+ pexcepinfo,
+ puArgErr);
+
+
+ // verify that the callee didnt hammer the rgvarg array.
+ for(i = 0; i < mi.cArgs; ++i){
+ if(V_VT(&dispparams.rgvarg[i]) != rgvtSaved[i]){
+ hresult = RESULT(DISP_E_BADCALLEE);
+ goto LFree;
+ }
+ }
+
+ IfFailGo(REWIND_STREAM(pstm), LFree);
+
+ // write the return value
+ //
+ IfFailGo(DispMarshalHresult(pstm, hresultRet), LFree);
+
+ // write back the ByRef params, freeing them as we go.
+ //
+ for(pvarg = dispparams.rgvarg;
+ pvarg < &dispparams.rgvarg[mi.cArgs]; ++pvarg)
+ {
+ if(V_ISBYREF(pvarg))
+ IfFailGo(VariantWrite(pstm, pvarg, (SYSKIND) _proxySysKind), LFree);
+ hresult = VariantClear(pvarg);
+ ASSERT(hresult == NOERROR);
+ }
+
+ if(mi.flags & MARSHAL_INVOKE_fHasResult){
+ // make sure the callee doesnt try to return a reference
+ if(V_ISBYREF(pvarResult)){
+ hresult = RESULT(DISP_E_BADCALLEE);
+ goto LFree;
+ }
+ IfFailGo(VariantWrite(pstm, pvarResult, (SYSKIND) _proxySysKind), LFree);
+ VariantClear(pvarResult);
+ }
+
+ if(mi.flags & MARSHAL_INVOKE_fHasExcepinfo){
+ IfFailGo(ExcepinfoWrite(pstm, pexcepinfo, (SYSKIND) _proxySysKind), LFree);
+ SysFreeString(pexcepinfo->bstrSource);
+ SysFreeString(pexcepinfo->bstrDescription);
+ SysFreeString(pexcepinfo->bstrHelpFile);
+ }
+
+ if(mi.flags & MARSHAL_INVOKE_fHasArgErr)
+ IfFailGo(PUT(pstm, _uArgErr), LFree);
+
+ hresult = NOERROR;
+
+LFree:;
+ delete dispparams.rgdispidNamedArgs;
+
+LFreeRgVarg:;
+ delete dispparams.rgvarg;
+
+LFreeRgVargRef:;
+ if(rgvargRef != NULL){
+ // clear the contents of the ByRef varg array
+ for(pvarg = rgvargRef; pvarg < &rgvargRef[mi.cArgs]; ++pvarg)
+ if(V_VT(pvarg) != VT_EMPTY) // speedup
+ VariantClear(pvarg);
+ delete rgvargRef;
+ }
+
+LFreeRgVtSaved:;
+ delete rgvtSaved;
+
+LExit:;
+ return hresult;
+}
+
+
+/***
+*HRESULT CStubDisp::Invoke(REFIID, int, IStream*, unsigned long, void*)
+*
+*Purpose:
+* Dispatch the method with the given index (iMethod) on the given
+* interface, using the arguments serialized in the given stream.
+*
+* This function is the callee side of an LRPC call.
+*
+*Entry:
+* riid = the IID of the interface on which we are to make the call
+* iMethod = the method index
+* pstm = the IStream containing the method's actuals
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDMETHODIMP
+CStubDisp::Invoke(
+#if (OE_WIN32 || defined(WOW))
+ RPCOLEMESSAGE *pMessage,
+ ICHANNEL *pRpcChannel)
+{
+ HRESULT hresult;
+ IStream FAR* pstm;
+
+ if(!m_punkObj)
+ return RESULT(E_FAIL);
+
+ OPEN_STUB_STREAM(pstm, pRpcChannel, pMessage, IID_IDispatch);
+
+#else
+ REFIID riid,
+ int iMethod,
+ IStream FAR* pstm,
+ unsigned long dwDestCtx,
+ void FAR* pvDestCtx)
+
+{
+ HRESULT hresult;
+
+ UNUSED(dwDestCtx);
+ UNUSED(pvDestCtx);
+
+
+ if(!IsEqualIID(riid,IID_IDispatch))
+ return RESULT(E_NOINTERFACE);
+
+ if(!m_punkObj)
+ return RESULT(E_FAIL);
+
+ if(m_pdispObj == NULL)
+ IfFailRet(m_punkObj->QueryInterface(riid, (void FAR* FAR*)&m_pdispObj));
+
+#endif
+
+ switch(GET_IMETHOD(pMessage)){
+ case IMETH_GETTYPEINFOCOUNT:
+ hresult = StubGetTypeInfoCount(m_pdispObj, pstm);
+ break;
+
+ case IMETH_GETTYPEINFO:
+ hresult = StubGetTypeInfo(m_pdispObj, pstm);
+ break;
+
+ case IMETH_GETIDSOFNAMES:
+ hresult = StubGetIDsOfNames(m_pdispObj, pstm);
+ break;
+
+ case IMETH_INVOKE:
+ hresult = StubInvoke(m_pdispObj, pstm);
+ break;
+
+ case IMETH_SYSKIND:
+ hresult = DispatchGetSysKind(pstm);
+ break;
+
+ default:
+ hresult = INVALIDARG;
+ break;
+ }
+
+ RESET_STREAM(pstm);
+
+ DELETE_STREAM(pstm);
+
+ return hresult;
+}
+
+
+/***
+*IRpcStubBuffer * CStubDisp::IsIIDSupported(REFIID)
+*
+*Purpose:
+* Answer if the given IID is supported by this stub.
+*
+*Entry:
+* riid = the IID to query for support
+*
+*Exit:
+* return value = IRpcStubBuffer
+*
+***********************************************************************/
+#if OE_MAC
+STDMETHODIMP_(unsigned long)
+#elif (OE_WIN32 || defined(WOW))
+STDMETHODIMP_(IRpcStubBuffer *)
+#else
+STDMETHODIMP_(BOOL)
+#endif
+CStubDisp::IsIIDSupported(REFIID riid)
+{
+#if (OE_WIN32 || defined(WOW))
+ IRpcStubBuffer *pStub = 0;
+ if (IsEqualIID(riid, IID_IDispatch)) {
+ AddRef();
+ pStub = (IRpcStubBuffer *) this;
+ }
+ return pStub;
+#else
+
+ // REVIEW: I don't understand this, but thats the way Ole does it...
+ if(m_punkObj == NULL)
+ return FALSE;
+
+ return(IsEqualIID(riid, IID_IDispatch));
+#endif
+}
+
+
+/***
+*unsigned long CStubDisp::CountRefs
+*Purpose:
+* Return a count of the object refs held by this stub.
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = unsigned long, the count of refs.
+*
+***********************************************************************/
+STDMETHODIMP_(unsigned long)
+CStubDisp::CountRefs()
+{
+ unsigned long refs;
+
+ refs = 0;
+
+ if(m_punkObj != NULL)
+ ++refs;
+
+ if(m_pdispObj != NULL)
+ ++refs;
+
+ return refs;
+}
+
+
+#if (OE_WIN32 || defined(WOW))
+
+STDMETHODIMP
+CStubDisp::DebugServerQueryInterface(void FAR* FAR* ppv)
+{
+ *ppv = m_pdispObj;
+ return S_OK;
+}
+
+
+STDMETHODIMP_(void)
+CStubDisp::DebugServerRelease(void FAR* ppv)
+{
+
+}
+
+#endif
diff --git a/private/oleauto/src/dispatch/errinfo.cpp b/private/oleauto/src/dispatch/errinfo.cpp
new file mode 100644
index 000000000..39ee45efd
--- /dev/null
+++ b/private/oleauto/src/dispatch/errinfo.cpp
@@ -0,0 +1,680 @@
+/***
+*errinfo.cpp
+*
+* Copyright (C) 1994, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Implementation of the System Error Info objects and APIs.
+*
+*Revision History:
+*
+* [00] 18-May-94 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#if OE_WIN32
+#include "oautil.h"
+#endif // OE_WIN32
+
+ASSERTDATA
+
+#if !OE_WIN32
+//---------------------------------------------------------------------
+// CProcessInfo
+//---------------------------------------------------------------------
+
+PROCESSINFO NEARDATA pinfoCache; // declare per-process data cache
+#if OE_WIN16 || _X86_
+WORD NEARDATA uProcessID;
+#else
+DWORD NEARDATA uProcessID;
+#endif
+
+#if _X86_
+DWORD NEARDATA dwWin32sPID; // only valid if running under win32s
+#endif
+
+// CProcessInfo
+//
+// Per-thread data class.
+//
+class FAR CProcessInfo : public IUnknown
+{
+public:
+ /* IUnknown methods */
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppvObj);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ CProcessInfo();
+ ~CProcessInfo();
+
+ PROCESSINFO m_info;
+
+private:
+ unsigned long m_cRefs;
+
+};
+
+CProcessInfo::CProcessInfo()
+{
+ m_cRefs = 0;
+ m_info.perrinfo = NULL;
+ m_info.pmalloc = NULL;
+#if OE_WIN16
+ m_info.hinstTypeLibDLL = NULL;
+ m_info.pfnLoadTypeLib = NULL;
+#endif //OE_WIN16
+}
+
+CProcessInfo::~CProcessInfo()
+{
+#if OE_WIN16
+ if (m_info.hinstTypeLibDLL != NULL)
+ FreeLibrary(m_info.hinstTypeLibDLL);
+#endif //OE_WIN16
+
+ if (m_info.perrinfo != NULL)
+ m_info.perrinfo->Release();
+
+ if (m_info.pmalloc != NULL)
+ m_info.pmalloc->Release();
+}
+
+STDMETHODIMP
+CProcessInfo::QueryInterface(REFIID riid, void FAR* FAR* ppvObj)
+{
+ if(riid != IID_IUnknown)
+ {
+ *ppvObj = NULL;
+ return RESULT(E_NOINTERFACE);
+ }
+
+ *ppvObj = this;
+ AddRef();
+ return NOERROR;
+}
+
+STDMETHODIMP_(unsigned long)
+CProcessInfo::AddRef()
+{
+ return ++m_cRefs;
+}
+
+STDMETHODIMP_(unsigned long)
+CProcessInfo::Release()
+{
+ ASSERT(m_cRefs > 0);
+
+ // Don't decrement ref count if we're releasing. This
+ // allows delete operator to use cache with recursing.
+ //
+ if(m_cRefs <= 1){
+ // do *not* want to ever get back into GetProcessInfo() -- it's bad news.
+ // most likely we are being called via OleUninitialize, and we don't want
+ // to end up re-caching the state.
+ IMalloc * pmalloc;
+
+ // get an IMalloc for use by the "delete this;" and everything it calls.
+ // The one in the cache might be ok, but then we've problems with when
+ // to free it. This is simpler.
+ if ( CoGetMalloc(MEMCTX_TASK, &pmalloc) != S_OK || pmalloc == NULL)
+ return 0; // on failure leak, but don't crash
+
+ pinfoCache.pmalloc = pmalloc; // pretend this one is in the cache
+#if _X86_
+ if (g_fWin32s) {
+ ASSERT(uProcessID == 0); // must remain 0 on win32s
+ dwWin32sPID = GetCurrentProcessId();
+ } else
+#endif //_X86_
+ uProcessID = GetPID(); // so cache lookup will always succeed,
+ // and GetProcessInfo won't ever be
+ // called.
+
+ // NOTE: assumes nothing that is done by the delete operator will yield
+ // NOTE: and cause uProcessID & pinfoCache.pmalloc to be changed
+
+ delete this; // free up everything, using the IMalloc
+ // we just got.
+
+#if _X86_
+ ASSERT(((g_fWin32s && dwWin32sPID == GetCurrentProcessId()) ||
+ (!g_fWin32s && uProcessID == GetPID()))
+ && pinfoCache.pmalloc == pmalloc);
+#else //_X86_
+ ASSERT(uProcessID == GetPID() && pinfoCache.pmalloc == pmalloc);
+#endif //_X86_
+ pmalloc->Release(); // done with the IMalloc
+
+ // Release is called when a process terminates. This is the
+ // whole reason the cache is tied into Co[G|S]etState() - to
+ // invalidate it on termination.
+ uProcessID = 0; // nothing in the cache anymore
+#if _X86_
+ dwWin32sPID = 0;
+#endif //_X86_
+ return 0;
+ }
+
+ return --m_cRefs;
+}
+
+
+#if _X86_
+// returns non-zero if process info cache loaded successfully
+CProcessInfo FAR * GetProcessInfoCache()
+{
+ if (g_fWin32s && dwWin32sPID == GetCurrentProcessId())
+ return (CProcessInfo FAR*)1; // cached data is already valid
+
+ return GetProcessInfo();
+}
+#endif //_X86_
+
+CProcessInfo FAR * GetProcessInfo()
+{
+ CProcessInfo FAR * pprocessinfo;
+
+#if _X86_
+ if (g_fWin32s)
+ dwWin32sPID = GetCurrentProcessId(); // indicate cache is valid
+ else
+#endif //_X86_
+ uProcessID = GetPID();
+
+ pprocessinfo = NULL;
+ DoCoGetState( (IUnknown FAR* FAR*)&pprocessinfo );
+
+ if (pprocessinfo == NULL)
+ {
+ // Don't have IMalloc or process info yet
+ //
+ if ( CoGetMalloc(MEMCTX_TASK, &pinfoCache.pmalloc) != S_OK ||
+ pinfoCache.pmalloc == NULL)
+ goto Failed;
+
+ // No process info is registered. Create one.
+ //
+ // Note that the NEW operator needs the IMalloc we just
+ // fetched above. We have set up the cache so it will
+ // find it without calling us recursively.
+ //
+ if( (pprocessinfo = new CProcessInfo) == NULL)
+ {
+ pinfoCache.pmalloc->Release(); // didn't keep it after all
+Failed:
+ uProcessID = 0;
+ return NULL;
+ }
+ DoCoSetState( (IUnknown FAR*)pprocessinfo );
+
+ pprocessinfo->m_info.pmalloc = pinfoCache.pmalloc;
+
+ } else {
+
+ ASSERT(pprocessinfo->m_info.pmalloc != NULL);
+
+ // Reverse the AddRef() done by DoCoGetState()
+ //
+ DWORD cRefs = pprocessinfo->Release();
+
+ // we should still be holding onto a reference for this guy
+ ASSERT(cRefs != 0);
+
+ }
+
+ // Copy info we have into cache
+ //
+ pinfoCache = pprocessinfo->m_info;
+
+ return pprocessinfo;
+}
+#endif // !OE_WIN32
+
+//---------------------------------------------------------------------
+// CErrorInfo
+//---------------------------------------------------------------------
+
+// Duplicate the given bstr.
+//
+static HRESULT
+HrDupBstr(BSTR bstrIn, BSTR FAR* pbstrOut)
+{
+ unsigned int len;
+ BSTR bstr;
+
+ if(bstrIn == NULL){
+ bstr = NULL;
+ }else{
+ // Note: the following makes sure we dont drop embedded NULLs.
+ len = SysStringLen(bstrIn);
+ if((bstr = SysAllocStringLen(NULL, len)) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+ memcpy(bstr, bstrIn, len*sizeof(OLECHAR));
+ }
+ *pbstrOut = bstr;
+ return NOERROR;
+}
+
+// CErrorInfo - 'errinfo'
+//
+// The standard system error object class.
+//
+class FAR CErrorInfo : public IErrorInfo, public ICreateErrorInfo
+{
+public:
+ static HRESULT Create(CErrorInfo FAR* FAR* pperrinfo);
+
+ /* IUnknown methods */
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppvObj);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ /* IErrorInfo methods */
+ STDMETHOD(GetGUID)(GUID FAR* pguid);
+ STDMETHOD(GetSource)(BSTR FAR* pbstrSource);
+ STDMETHOD(GetDescription)(BSTR FAR* pbstrDescription);
+ STDMETHOD(GetHelpFile)(BSTR FAR* pbstrHelpFile);
+ STDMETHOD(GetHelpContext)(unsigned long FAR* pdwHelpContext);
+
+ /* ICreateErrorInfo methods */
+ STDMETHOD(SetGUID)(REFGUID rguid);
+ STDMETHOD(SetSource)(LPOLESTR szSource);
+ STDMETHOD(SetDescription)(LPOLESTR szDescription);
+ STDMETHOD(SetHelpFile)(LPOLESTR szHelpFile);
+ STDMETHOD(SetHelpContext)(unsigned long dwHelpContext);
+
+ CErrorInfo();
+ ~CErrorInfo();
+
+private:
+ unsigned long m_cRefs;
+
+ GUID m_guid;
+ BSTR m_bstrSource;
+ BSTR m_bstrDescription;
+ BSTR m_bstrHelpFile;
+ unsigned long m_dwHelpContext;
+};
+
+CErrorInfo::CErrorInfo()
+{
+ m_cRefs = 0;
+ m_guid = GUID_NULL;
+ m_bstrSource = NULL;
+ m_bstrDescription = NULL;
+ m_bstrHelpFile = NULL;
+ m_dwHelpContext = 0;
+}
+
+CErrorInfo::~CErrorInfo()
+{
+ SysFreeString(m_bstrSource);
+ SysFreeString(m_bstrDescription);
+ SysFreeString(m_bstrHelpFile);
+}
+
+HRESULT
+CErrorInfo::Create(CErrorInfo FAR* FAR* pperrinfo)
+{
+ CErrorInfo FAR* perrinfo;
+
+ if((perrinfo = new CErrorInfo()) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+ perrinfo->m_cRefs = 1;
+ *pperrinfo = perrinfo;
+ return NOERROR;
+}
+
+STDMETHODIMP
+CErrorInfo::QueryInterface(REFIID riid, void FAR* FAR* ppvObj)
+{
+ *ppvObj = NULL;
+ if(riid == IID_IUnknown){
+ *ppvObj = this;
+ }else
+ if(riid == IID_IErrorInfo){
+ *ppvObj = (IErrorInfo FAR*)this;
+ }else
+ if(riid == IID_ICreateErrorInfo){
+ *ppvObj = (ICreateErrorInfo FAR*)this;
+ }
+
+ if(*ppvObj == NULL)
+ return RESULT(E_NOINTERFACE);
+
+ (*(IUnknown FAR* FAR*)ppvObj)->AddRef();
+ return NOERROR;
+}
+
+STDMETHODIMP_(unsigned long)
+CErrorInfo::AddRef()
+{
+ return ++m_cRefs;
+}
+
+STDMETHODIMP_(unsigned long)
+CErrorInfo::Release()
+{
+ ASSERT(m_cRefs > 0);
+ if(--m_cRefs == 0){
+ delete this;
+ return 0;
+ }
+ return m_cRefs;
+}
+
+//---------------------------------------------------------------------
+// IErrorInfo methods
+//---------------------------------------------------------------------
+
+STDMETHODIMP
+CErrorInfo::GetGUID(GUID FAR* pguid)
+{
+#ifdef _DEBUG
+ IfFailRet(ValidateWritePtr(pguid, sizeof(*pguid)));
+#endif
+ *pguid = m_guid;
+ return NOERROR;
+}
+
+STDMETHODIMP
+CErrorInfo::GetSource(BSTR FAR* pbstrSource)
+{
+#ifdef _DEBUG
+ IfFailRet(ValidateWritePtr(pbstrSource, sizeof(*pbstrSource)));
+#endif
+ return HrDupBstr(m_bstrSource, pbstrSource);
+}
+
+STDMETHODIMP
+CErrorInfo::GetDescription(BSTR FAR* pbstrDescription)
+{
+#ifdef _DEBUG
+ IfFailRet(ValidateWritePtr(pbstrDescription, sizeof(*pbstrDescription)));
+#endif
+ return HrDupBstr(m_bstrDescription, pbstrDescription);
+}
+
+STDMETHODIMP
+CErrorInfo::GetHelpFile(BSTR FAR* pbstrHelpFile)
+{
+#ifdef _DEBUG
+ IfFailRet(ValidateWritePtr(pbstrHelpFile, sizeof(*pbstrHelpFile)));
+#endif
+ return HrDupBstr(m_bstrHelpFile, pbstrHelpFile);
+}
+
+STDMETHODIMP
+CErrorInfo::GetHelpContext(unsigned long FAR* pdwHelpContext)
+{
+#ifdef _DEBUG
+ IfFailRet(ValidateWritePtr(pdwHelpContext, sizeof(*pdwHelpContext)));
+#endif
+ *pdwHelpContext = m_dwHelpContext;
+ return NOERROR;
+}
+
+
+//---------------------------------------------------------------------
+// ICreateErrorInfo methods
+//---------------------------------------------------------------------
+
+STDMETHODIMP
+CErrorInfo::SetGUID(REFGUID rguid)
+{
+#ifdef _DEBUG
+ IfFailRet(ValidateReadPtr(&rguid, sizeof(REFGUID)));
+#endif
+ m_guid = rguid;
+ return NOERROR;
+}
+
+STDMETHODIMP
+CErrorInfo::SetSource(LPOLESTR szSource)
+{
+#ifdef _DEBUG
+ if(szSource != NULL && FIsBadStringPtr(szSource, (UINT)-1))
+ return RESULT(E_INVALIDARG);
+#endif
+ SysFreeString(m_bstrSource);
+ m_bstrSource = NULL;
+ return ErrSysAllocString(szSource, &m_bstrSource);
+}
+
+STDMETHODIMP
+CErrorInfo::SetDescription(LPOLESTR szDescription)
+{
+#ifdef _DEBUG
+ if(szDescription != NULL && FIsBadStringPtr(szDescription, (UINT)-1))
+ return RESULT(E_INVALIDARG);
+#endif
+ SysFreeString(m_bstrDescription);
+ m_bstrDescription = NULL;
+ return ErrSysAllocString(szDescription, &m_bstrDescription);
+}
+
+STDMETHODIMP
+CErrorInfo::SetHelpFile(LPOLESTR szHelpFile)
+{
+#ifdef _DEBUG
+ if(szHelpFile != NULL && FIsBadStringPtr(szHelpFile, (UINT)-1))
+ return RESULT(E_INVALIDARG);
+#endif
+ SysFreeString(m_bstrHelpFile);
+ m_bstrHelpFile = NULL;
+ return ErrSysAllocString(szHelpFile, &m_bstrHelpFile);
+}
+
+STDMETHODIMP
+CErrorInfo::SetHelpContext(unsigned long dwHelpContext)
+{
+ m_dwHelpContext = dwHelpContext;
+ return NOERROR;
+}
+
+
+//---------------------------------------------------------------------
+// Error Info APIs
+//---------------------------------------------------------------------
+
+STDAPI
+SetErrorInfo(unsigned long dwReserved, IErrorInfo FAR* perrinfo)
+{
+#ifdef _DEBUG
+ if(dwReserved != 0)
+ return RESULT(E_INVALIDARG);
+ if(perrinfo != NULL && FIsBadInterface(perrinfo, CMETH_IErrorInfo))
+ return RESULT(E_INVALIDARG);
+#endif
+
+#if OE_WIN32
+ APP_DATA FAR *pappdata;
+ HRESULT hresult;
+
+ if (FAILED(hresult = GetAppData(&pappdata))) {
+ return hresult;
+ }
+
+ if (pappdata->m_perrinfo != NULL) {
+ pappdata->m_perrinfo->Release();
+ }
+
+ pappdata->m_perrinfo = perrinfo;
+
+ if (perrinfo) {
+ perrinfo->AddRef();
+ }
+#else // !OE_WIN32
+ CProcessInfo FAR * pprocessinfo;
+
+ pprocessinfo = GetProcessInfo();
+ if (pprocessinfo == NULL)
+ return RESULT(E_OUTOFMEMORY);
+
+ if (pinfoCache.perrinfo != NULL)
+ pinfoCache.perrinfo->Release();
+
+ pprocessinfo->m_info.perrinfo = perrinfo;
+ if (perrinfo != NULL)
+ perrinfo->AddRef();
+#endif // !OE_WIN32
+
+ return NOERROR;
+}
+
+STDAPI
+GetErrorInfo(unsigned long dwReserved, IErrorInfo FAR* FAR* pperrinfo)
+{
+#ifdef _DEBUG
+ if(dwReserved != 0)
+ return RESULT(E_INVALIDARG);
+ IfFailRet(ValidateWritePtr(pperrinfo, sizeof(*pperrinfo)));
+#endif
+
+#if OE_WIN32
+ APP_DATA FAR *pappdata;
+ HRESULT hresult;
+
+ if (FAILED(hresult = GetAppData(&pappdata))) {
+ return hresult;
+ }
+
+ *pperrinfo = pappdata->m_perrinfo;
+
+ if (*pperrinfo == NULL) {
+ return ResultFromScode(S_FALSE);
+ }
+
+ pappdata->m_perrinfo = NULL;
+#else // !OE_WIN32
+ CProcessInfo FAR * pprocessinfo;
+
+ *pperrinfo = NULL;
+ pprocessinfo = GetProcessInfo();
+ if (pprocessinfo == NULL)
+ return RESULT(E_OUTOFMEMORY);
+
+ if (pinfoCache.perrinfo == NULL)
+ return ResultFromScode(S_FALSE);
+
+ *pperrinfo = pinfoCache.perrinfo;
+ pprocessinfo->m_info.perrinfo = NULL;
+#endif // !OE_WIN32
+
+ return NOERROR;
+}
+
+STDAPI
+CreateErrorInfo(ICreateErrorInfo FAR* FAR* pperrinfo)
+{
+ CErrorInfo FAR* perrinfo;
+
+#ifdef _DEBUG
+ IfFailRet(ValidateWritePtr(pperrinfo, sizeof(*pperrinfo)));
+#endif
+
+ IfFailRet(CErrorInfo::Create(&perrinfo));
+ *pperrinfo = (ICreateErrorInfo FAR*)perrinfo;
+ return NOERROR;
+}
+
+
+#if OE_WIN16
+/***
+*PRIVATE HRESULT DoLoadTypeLib
+*Purpose:
+* Internal version of LoadTypeLib that dynamically binds to typelib.dll
+*
+*Entry:
+* szName = the szName arg for LoadTypeLib()
+* pptlib = the pptlib out param for LoadTypeLib()
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+#pragma code_seg("RPC2")
+INTERNAL_(HRESULT)
+DoLoadTypeLib(const OLECHAR FAR* szName, ITypeLib FAR* FAR* pptlib)
+{
+ CProcessInfo FAR * pprocessinfo;
+ HINSTANCE hinstTypeLibDLL;
+ PFNLOADTYPELIB pfnLoadTypeLib;
+ UINT emPrev;
+
+ pprocessinfo = GetProcessInfo();
+ if (pprocessinfo == NULL)
+ return RESULT(E_OUTOFMEMORY);
+
+ if (pinfoCache.pfnLoadTypeLib == NULL) {
+
+ ASSERT(pinfoCache.hinstTypeLibDLL == NULL);
+ // don't display the open file dialog if the LoadLibrary fails
+ emPrev = SetErrorMode(SEM_NOOPENFILEERRORBOX);
+ hinstTypeLibDLL = LoadLibrary("typelib.dll");
+ SetErrorMode(emPrev);
+ if(hinstTypeLibDLL <= HINSTANCE_ERROR){
+ // LoadLibrary failed...
+ // try to map some of the more common errors to something reasonable
+ switch(hinstTypeLibDLL){
+ case 0: // out of memory
+ case 8: // insufficient memory to start the application
+ return RESULT(E_OUTOFMEMORY);
+ case 2: // file not found
+ case 3: // path not found
+ case 11: // exe image invalid
+ case 20: // dll was invalid
+ default:
+ // UNDONE: should be able to give better errors for some of these
+ return RESULT(E_FAIL);
+ }
+ }
+
+ pfnLoadTypeLib = (PFNLOADTYPELIB)GetProcAddress(hinstTypeLibDLL,
+ "LoadTypeLib");
+ if(pfnLoadTypeLib == NULL) {
+ FreeLibrary(hinstTypeLibDLL);
+ return RESULT(E_FAIL);
+ }
+
+ // update process info structure, so next time this is fast.
+ pprocessinfo->m_info.hinstTypeLibDLL = hinstTypeLibDLL;
+ pprocessinfo->m_info.pfnLoadTypeLib = pfnLoadTypeLib;
+ pinfoCache.pfnLoadTypeLib = pfnLoadTypeLib; // update cache
+ }
+
+ return (pinfoCache.pfnLoadTypeLib)(szName, pptlib);
+
+}
+#pragma code_seg()
+
+#endif //OE_WIN16
+
+#if OE_MACPPC // UNDONE: TEMPORARY!!!!
+IUnknown FAR* g_punkTempHack = NULL;
+
+STDAPI CoSetState(IUnknown FAR* punk)
+{
+ if (g_punkTempHack)
+ g_punkTempHack->Release();
+
+ punk->AddRef();
+ g_punkTempHack = punk;
+ return NOERROR;
+}
+
+STDAPI CoGetState(IUnknown FAR* FAR* ppunk) {
+ if (g_punkTempHack)
+ g_punkTempHack->AddRef();
+ *ppunk = g_punkTempHack;
+ return NOERROR;
+}
+
+#endif //OE_MACPPC // UNDONE: TEMPORARY!!!!
diff --git a/private/oleauto/src/dispatch/evprox.cpp b/private/oleauto/src/dispatch/evprox.cpp
new file mode 100644
index 000000000..f9e8caf76
--- /dev/null
+++ b/private/oleauto/src/dispatch/evprox.cpp
@@ -0,0 +1,402 @@
+/***
+*evprox.cpp
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This module implements the IEnumVARIANT proxy class.
+*
+*Revision History:
+*
+* [00] 06-Dec-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#ifndef WIN32
+#include <cobjps.h>
+#endif //!WIN32
+
+#include "dispmrsh.h"
+#include "evps.h"
+
+
+CProxEnumVARIANT::CProxEnumVARIANT(IUnknown FAR* punkOuter)
+ : m_unk(this), m_proxy(this), m_enum(this)
+{
+ if(punkOuter == NULL)
+ punkOuter = &m_unk;
+ m_punkOuter = punkOuter;
+}
+
+IUnknown FAR*
+CProxEnumVARIANT::Create(IUnknown FAR* punkOuter)
+{
+ CProxEnumVARIANT FAR* pproxenum;
+
+ if(pproxenum = new FAR CProxEnumVARIANT(punkOuter)){
+ pproxenum->m_refs = 1;
+ return &pproxenum->m_unk;
+ }
+ return NULL;
+}
+
+
+//---------------------------------------------------------------------
+// IEnumVARIANT Proxy class' IUnknown implementation
+//---------------------------------------------------------------------
+
+CPEVUnkImpl::CPEVUnkImpl(CProxEnumVARIANT FAR* pproxenum)
+{
+ m_pproxenum = pproxenum;
+}
+
+STDMETHODIMP
+CPEVUnkImpl::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ if(IsEqualIID(riid, IID_IUnknown)){
+ *ppv = (void FAR*)&(m_pproxenum->m_unk);
+ AddRef();
+ return NOERROR;
+ }
+
+ if(IsEqualIID(riid, IID_IPROXY)){
+ *ppv = (void FAR*)&(m_pproxenum->m_proxy);
+ AddRef();
+ return NOERROR;
+ }
+
+ if(IsEqualIID(riid, IID_IEnumVARIANT)){
+ *ppv = (void FAR*)&(m_pproxenum->m_enum);
+ m_pproxenum->m_punkOuter->AddRef();
+ return NOERROR;
+ }
+
+ *ppv = NULL;
+ return RESULT(E_NOINTERFACE);
+}
+
+STDMETHODIMP_(unsigned long)
+CPEVUnkImpl::AddRef()
+{
+ return ++m_pproxenum->m_refs;
+}
+
+STDMETHODIMP_(unsigned long)
+CPEVUnkImpl::Release()
+{
+ if(--m_pproxenum->m_refs == 0){
+ delete m_pproxenum;
+ return 0;
+ }
+ return m_pproxenum->m_refs;
+}
+
+
+//---------------------------------------------------------------------
+// IEnumVARIANT proxy class' IRpcProxy implementation
+//---------------------------------------------------------------------
+
+CPEVProxImpl::CPEVProxImpl(CProxEnumVARIANT FAR* pproxenum)
+{
+ m_pproxenum = pproxenum;
+}
+
+CPEVProxImpl::~CPEVProxImpl()
+{
+ if(m_pproxenum->m_plrpc)
+ m_pproxenum->m_plrpc->Release();
+}
+
+STDMETHODIMP
+CPEVProxImpl::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ return m_pproxenum->m_unk.QueryInterface(riid, ppv);
+}
+
+STDMETHODIMP_(unsigned long)
+CPEVProxImpl::AddRef()
+{
+ return m_pproxenum->m_unk.AddRef();
+}
+
+STDMETHODIMP_(unsigned long)
+CPEVProxImpl::Release()
+{
+ return m_pproxenum->m_unk.Release();
+}
+
+STDMETHODIMP
+CPEVProxImpl::Connect(ICHANNEL FAR* plrpc)
+{
+ if(plrpc){
+ plrpc->AddRef();
+ m_pproxenum->m_plrpc = plrpc;
+ return NOERROR;
+ }
+ return RESULT(E_FAIL);
+}
+
+
+STDMETHODIMP_(void)
+CPEVProxImpl::Disconnect(void)
+{
+ if(m_pproxenum->m_plrpc)
+ m_pproxenum->m_plrpc->Release();
+ m_pproxenum->m_plrpc = NULL;
+}
+
+
+//---------------------------------------------------------------------
+// IEnumVARIANT proxy class' IEnumVARIANT implementation
+//---------------------------------------------------------------------
+
+CPEVEnumVARIANTImpl::CPEVEnumVARIANTImpl(CProxEnumVARIANT FAR* pproxenum)
+{
+ m_pproxenum = pproxenum;
+}
+
+STDMETHODIMP
+CPEVEnumVARIANTImpl::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ return m_pproxenum->m_punkOuter->QueryInterface(riid, ppv);
+}
+
+STDMETHODIMP_(unsigned long)
+CPEVEnumVARIANTImpl::AddRef()
+{
+ return m_pproxenum->m_punkOuter->AddRef();
+}
+
+STDMETHODIMP_(unsigned long)
+CPEVEnumVARIANTImpl::Release()
+{
+ return m_pproxenum->m_punkOuter->Release();
+}
+
+/***
+*HRESULT CPEVEnumVARIANTImpl::Next(unsigned long, VARAINT*, unsigned long*)
+*Purpose:
+* Proxy implementation of IEnumVARIANT::Next()
+*
+* Out:
+* <unsigned long celt>
+*
+* In:
+* <HRESULT = return value>
+* <unsigned long = celtFetched>
+* <VARIANT[] = rgvar[]>
+*
+*Entry:
+* celt = count of elements to fetch
+*
+*Exit:
+* return value = HRESULT
+*
+* rgvar = array of variants
+* *pceltFetched = count of elements fetched.
+*
+***********************************************************************/
+STDMETHODIMP
+CPEVEnumVARIANTImpl::Next(
+ unsigned long celt,
+ VARIANT FAR* rgvar,
+ unsigned long FAR* pceltFetched)
+{
+ ICHANNEL FAR* plrpc;
+ IStream FAR* pstm;
+ HRESULT hresult, hresultRet;
+ unsigned long i, celtTmp, celtFetched;
+ unsigned long _proxySysKind, _stubSysKind;
+
+ if(pceltFetched == NULL)
+ pceltFetched = &celtTmp;
+
+#ifdef _DEBUG
+ if(IsBadWritePtr(pceltFetched, sizeof(*pceltFetched)))
+ return RESULT(E_INVALIDARG);
+ if(IsBadWritePtr(rgvar, (size_t)celt * sizeof(VARIANT)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ if((plrpc = m_pproxenum->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_ENUMVARIANT_NEXT, 100, IID_IEnumVARIANT);
+
+ _proxySysKind = (unsigned long) SYS_CURRENT;
+ IfFailGo(PUT(pstm, _proxySysKind), LError0);
+
+ IfFailGo(PUT(pstm, celt), LError0);
+
+ INVOKE_CALL(plrpc, pstm, LError0);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError0);
+
+ if(FAILED(hresultRet)){
+ hresult = hresultRet;
+ goto LError0;
+ }
+
+ IfFailGo(GET(pstm, _stubSysKind), LError0);
+
+ IfFailGo(GET(pstm, celtFetched), LError0);
+
+ for(i = 0; i < celtFetched; ++i){
+ IfFailGo(VariantRead(pstm, &rgvar[i], NULL, (SYSKIND) _stubSysKind), LError0);
+ }
+
+ *pceltFetched = celtFetched;
+
+ hresult = hresultRet;
+
+LError0:
+ pstm->Release();
+ return hresult;
+}
+
+/***
+*HRESULT CPEVEnumVARIANTImpl::Skip(unsigned long)
+*Purpose:
+* Proxy implementation of IEnumVARIANT::Skip()
+*
+* Out:
+* <unsigned long = celt>
+*
+* In:
+* <HRESULT = return value>
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDMETHODIMP
+CPEVEnumVARIANTImpl::Skip(unsigned long celt)
+{
+ ICHANNEL FAR* plrpc;
+ IStream FAR* pstm;
+ HRESULT hresult, hresultRet;
+
+
+ if((plrpc = m_pproxenum->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+
+ OPEN_STREAM(plrpc, pstm, IMETH_ENUMVARIANT_SKIP, 100, IID_IEnumVARIANT);
+
+ IfFailGo(PUT(pstm, celt), LError0);
+
+ INVOKE_CALL(plrpc, pstm, LError0);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError0);
+
+ hresult = hresultRet;
+
+LError0:;
+ pstm->Release();
+ return hresult;
+}
+
+/***
+*HRESULT CPEVEnumVARIANTImpl::Reset()
+*Purpose:
+* Proxy implementation of IEnumVARIANT::Reset()
+*
+* Out:
+* None
+*
+* In:
+* <HRESULT = return value>
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDMETHODIMP
+CPEVEnumVARIANTImpl::Reset()
+{
+ ICHANNEL FAR* plrpc;
+ IStream FAR* pstm;
+ HRESULT hresult, hresultRet;
+
+
+ if((plrpc = m_pproxenum->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_ENUMVARIANT_RESET, 100, IID_IEnumVARIANT);
+
+ INVOKE_CALL(plrpc, pstm, LError0);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError0);
+
+ hresult = hresultRet;
+
+LError0:;
+ pstm->Release();
+ return hresult;
+}
+
+/***
+*HRESULT CPEVEnumVARIANTImpl::Clone(IEnumVARIANT**)
+*Purpose:
+* Proxy implementation of IEnumVARIANT::Clone()
+*
+* Out:
+* None
+*
+* In:
+* <HRESULT = return value>
+* <IEnumVARIANT = ppenum>
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+* *ppenum = pointer to a clone of this EnumVARIANT
+*
+***********************************************************************/
+STDMETHODIMP
+CPEVEnumVARIANTImpl::Clone(IEnumVARIANT FAR* FAR* ppenum)
+{
+ ICHANNEL FAR* plrpc;
+ IStream FAR* pstm;
+ HRESULT hresult, hresultRet;
+
+
+ if((plrpc = m_pproxenum->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_ENUMVARIANT_CLONE, 256, IID_IEnumVARIANT);
+
+ INVOKE_CALL(plrpc, pstm, LError0);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError0);
+
+ if(FAILED(hresultRet)){
+ hresult = hresultRet;
+ goto LError0;
+ }
+
+ IfFailGo(
+ DispUnmarshalInterface(
+ pstm, IID_IEnumVARIANT, (void FAR* FAR*)ppenum), LError0);
+
+ hresult = hresultRet;
+
+LError0:;
+ pstm->Release();
+ return hresult;
+}
+
diff --git a/private/oleauto/src/dispatch/evps.h b/private/oleauto/src/dispatch/evps.h
new file mode 100644
index 000000000..3fb2780ae
--- /dev/null
+++ b/private/oleauto/src/dispatch/evps.h
@@ -0,0 +1,179 @@
+/***
+*evps.h - IEnumVARIANT Proxy and Stub class definitions
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file describes the IEnumVARIANT Proxy and Stub classes.
+*
+* CProxEnumVARIANT -- the IEnumVARIANT proxy class
+* CPEVUnkImpl - CProxEnumVARIANT implementation of IUnknown
+* CPEVProxImpl - CProxEnumVARIANT implementation of IRpcProxy
+* CPEVEnumVARIANTImpl - CProxEnumVARIANT implementation of IEnumVARIANT
+*
+* CStubEnumVARIANT -- the IEnumVARIANT stub class
+*
+*Revision History:
+*
+* [00] 05-Nov-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#ifndef __evps_h__
+#define __evps_h__
+
+#pragma warning(4:4355)
+
+
+// forward declarations
+class FAR CProxEnumVARIANT;
+class FAR CStubEnumVARIANT;
+
+
+// IEnumVARIANT proxy class' IUnknown implementation
+class FAR CPEVUnkImpl : public IUnknown
+{
+public:
+ CPEVUnkImpl(CProxEnumVARIANT FAR* pproxenum);
+
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+private:
+ CProxEnumVARIANT FAR* m_pproxenum;
+};
+
+
+// IEnumVARIANT proxy class' IRpcProxy implementation
+class CPEVProxImpl : public IPROXY
+{
+public:
+ CPEVProxImpl(CProxEnumVARIANT FAR* pproxenum);
+ ~CPEVProxImpl();
+
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ STDMETHOD(Connect)(ICHANNEL FAR* plrpc);
+ STDMETHOD_(void, Disconnect)(void);
+
+private:
+ CProxEnumVARIANT FAR* m_pproxenum;
+};
+
+
+// IEnumVARIANT
+//
+class CPEVEnumVARIANTImpl : public IEnumVARIANT
+{
+public:
+ CPEVEnumVARIANTImpl(CProxEnumVARIANT FAR* pproxy);
+
+ // IUnknown methods
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ // IEnumVARIANT methods
+ STDMETHOD(Next)(unsigned long celt, VARIANT FAR* rgvar, unsigned long FAR* pceltFetched);
+ STDMETHOD(Skip)(unsigned long celt);
+ STDMETHOD(Reset)(void);
+ STDMETHOD(Clone)(IEnumVARIANT FAR* FAR* ppenum);
+
+private:
+ CProxEnumVARIANT FAR* m_pproxenum;
+};
+
+
+// IEnumVARIANT Proxy Class
+class FAR CProxEnumVARIANT
+{
+public:
+ static IUnknown FAR* Create(IUnknown FAR* punkOuter);
+
+private:
+ CProxEnumVARIANT(IUnknown FAR* punkOuter);
+
+ friend CPEVUnkImpl;
+ friend CPEVProxImpl;
+ friend CPEVEnumVARIANTImpl;
+
+ CPEVUnkImpl m_unk;
+ CPEVProxImpl m_proxy;
+ CPEVEnumVARIANTImpl m_enum;
+
+private:
+ unsigned long m_refs;
+ ICHANNEL FAR* m_plrpc;
+ IUnknown FAR* m_punkOuter;
+};
+
+
+// IEnumVARIANT Stub Class
+//
+class FAR CStubEnumVARIANT : public ISTUB
+{
+public:
+ static HRESULT Create(IUnknown FAR* punkServer, ISTUB FAR* FAR* ppstub);
+
+ // IUnknown methods
+ //
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ // IRpcStub methods
+ //
+#if (OE_WIN32 || defined(WOW))
+ STDMETHOD(Connect)(IUnknown FAR* pUnk);
+ STDMETHOD_(void, Disconnect)(void);
+ STDMETHOD(Invoke)(RPCOLEMESSAGE FAR* pRpcMsg,
+ IRpcChannelBuffer FAR* pRpcChannel);
+ STDMETHOD_(IRpcStubBuffer *, IsIIDSupported)(REFIID iid);
+ STDMETHOD_(ULONG, CountRefs)(void);
+ STDMETHOD(DebugServerQueryInterface)(void FAR* FAR* ppv);
+ STDMETHOD_(void, DebugServerRelease)(void FAR* pv);
+#else
+ STDMETHOD(Connect)(IUnknown FAR* punkObject);
+ STDMETHOD_(void, Disconnect)(void);
+ STDMETHOD(Invoke)(
+ REFIID riid,
+ int imeth,
+ IStream FAR* pstm,
+ unsigned long dwDestCtx,
+ void FAR* pvDestCtx);
+#if OE_MAC
+ STDMETHOD_(unsigned long, IsIIDSupported)(REFIID riid);
+#else
+ STDMETHOD_(BOOL, IsIIDSupported)(REFIID riid);
+#endif
+ STDMETHOD_(unsigned long, CountRefs)(void);
+#endif
+
+private:
+ CStubEnumVARIANT();
+ ~CStubEnumVARIANT();
+
+ unsigned long m_refs;
+ IUnknown FAR* m_punk;
+ IEnumVARIANT FAR* m_penum;
+};
+
+
+// IEnumVARIANT method indices
+//
+#define IMETH_ENUMVARIANT_QUERYINTERFACE 0 /* Placeholder */
+#define IMETH_ENUMVARIANT_ADDREF 1 /* Placeholder */
+#define IMETH_ENUMVARIANT_RELEASE 2 /* Placeholder */
+
+#define IMETH_ENUMVARIANT_NEXT 3
+#define IMETH_ENUMVARIANT_SKIP 4
+#define IMETH_ENUMVARIANT_RESET 5
+#define IMETH_ENUMVARIANT_CLONE 6
+
+#endif __evps_h__
diff --git a/private/oleauto/src/dispatch/evstub.cpp b/private/oleauto/src/dispatch/evstub.cpp
new file mode 100644
index 000000000..7989c31ca
--- /dev/null
+++ b/private/oleauto/src/dispatch/evstub.cpp
@@ -0,0 +1,500 @@
+/***
+*evstub.cpp
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This module implements the IEnumVARIANT stub class.
+*
+*Revision History:
+*
+* [00] 06-Dec-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#ifndef WIN32
+#include <cobjps.h>
+#endif //!WIN32
+
+#include "dispmrsh.h"
+#include "evps.h"
+
+ASSERTDATA
+
+CStubEnumVARIANT::CStubEnumVARIANT()
+{
+ m_refs = 0;
+ m_punk = NULL;
+ m_penum = NULL;
+}
+
+CStubEnumVARIANT::~CStubEnumVARIANT()
+{
+ Disconnect();
+}
+
+
+HRESULT
+CStubEnumVARIANT::Create(IUnknown FAR* punkServer, ISTUB FAR* FAR* ppstub)
+{
+ CStubEnumVARIANT FAR* pstub;
+
+ if(pstub = new FAR CStubEnumVARIANT()){
+ pstub->m_refs = 1;
+ *ppstub = pstub;
+ if (punkServer)
+ return pstub->Connect(punkServer);
+ return NOERROR;
+ }
+ return RESULT(E_OUTOFMEMORY);
+}
+
+
+//---------------------------------------------------------------------
+// IUnknown Methods
+//---------------------------------------------------------------------
+
+STDMETHODIMP
+CStubEnumVARIANT::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ if(IsEqualIID(riid, IID_IUnknown)){
+ *ppv = this;
+ }else if(IsEqualIID(riid, IID_ISTUB)){
+ *ppv = this;
+ }else{
+ *ppv = NULL;
+ return RESULT(E_NOINTERFACE);
+ }
+ ++m_refs;
+ return NOERROR;
+}
+
+
+STDMETHODIMP_(unsigned long)
+CStubEnumVARIANT::AddRef()
+{
+ return ++m_refs;
+}
+
+
+STDMETHODIMP_(unsigned long)
+CStubEnumVARIANT::Release()
+{
+ if(--m_refs == 0){
+ delete this;
+ return 0;
+ }
+ return m_refs;
+}
+
+
+//---------------------------------------------------------------------
+// IRpcStub Methods
+//---------------------------------------------------------------------
+
+
+STDMETHODIMP
+CStubEnumVARIANT::Connect(IUnknown FAR* punkObj)
+{
+#if (defined(WIN32) || defined(WOW))
+ ASSERT(m_punk == NULL && m_penum == NULL);
+ //This will keep the server object alive until we disconnect.
+ IfFailRet(punkObj->QueryInterface(IID_IEnumVARIANT, (void FAR* FAR*)&m_penum));
+ punkObj->AddRef();
+ m_punk = punkObj;
+ return NOERROR;
+#else
+ if(m_punk)
+ return RESULT(E_FAIL); // call Disconnect first
+
+ if (punkObj) {
+ punkObj->AddRef();
+ m_punk = punkObj;
+ }
+ return NOERROR;
+#endif
+}
+
+
+STDMETHODIMP_(void)
+CStubEnumVARIANT::Disconnect()
+{
+ if(m_punk){
+ m_punk->Release();
+ m_punk = NULL;
+ }
+ if(m_penum){
+ m_penum->Release();
+ m_penum = NULL;
+ }
+}
+
+
+/***
+*PRIVATE HRESULT DispatchNext(IEnumVARIANT FAR*, IStream*)
+*Purpose:
+* Stub implementation of IEnumVARIANT::Next()
+*
+* In:
+* <unsigned long = celt>
+*
+* Out:
+* <HRESULT = return value>
+* <unsigned long = pceltFetched>
+* <VARIANT[] = rgvar[]>
+*
+*Entry:
+* penum = the IEnumVARIANT* to dispatch on
+* pstm = the stream containing the actuals
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+PRIVATE_(HRESULT)
+DispatchNext(IEnumVARIANT FAR* penum, IStream FAR* pstm)
+{
+ unsigned int i;
+ VARIANT FAR* rgvar;
+ unsigned long celt, celtFetched;
+ HRESULT hresult, hresultRet;
+ unsigned long _proxySysKind, _stubSysKind;
+
+ IfFailGo(GET(pstm, _proxySysKind), LError0);
+
+ IfFailGo(GET(pstm, celt), LError0);
+
+ if((rgvar = new FAR VARIANT[(size_t)celt]) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LError0;
+ }
+
+ celtFetched = 0;
+ for(i = 0; i < celt; ++i)
+ VariantInit(&rgvar[i]);
+
+ hresultRet = penum->Next(celt, rgvar, &celtFetched);
+
+ IfFailGo(REWIND_STREAM(pstm), LError0);
+
+ IfFailGo(DispMarshalHresult(pstm, hresultRet), LError1);
+
+ // only marshal the out params if the call succeeded.
+ //
+ if(SUCCEEDED(hresultRet)){
+
+ _stubSysKind = (unsigned long) SYS_CURRENT;
+ IfFailGo(PUT(pstm, _stubSysKind), LError1);
+
+ IfFailGo(PUT(pstm, celtFetched), LError1);
+
+ for(i = 0; i < celtFetched; ++i){
+ IfFailGo(VariantWrite(pstm, &rgvar[i], (SYSKIND) _proxySysKind), LError1);
+ }
+ }
+
+ hresult = NOERROR;
+
+LError1:;
+ for(i = 0; i < celtFetched; ++i)
+ VariantClear(&rgvar[i]);
+
+ delete rgvar;
+
+LError0:;
+ return hresult;
+}
+
+
+/***
+*PRIVATE HRESULT DispatchSkip(IEnumVARIANT*, IStream*)
+*Purpose:
+* Stub implementation of IEnumVARIANT::Skip()
+*
+* In:
+* <unsigned long = celt>
+*
+* Out:
+* <HRESULT = return value>
+*
+*Entry:
+* penum = the IEnumVARIANT* to dispatch on
+* pstm = the stream containing the actuals
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+PRIVATE_(HRESULT)
+DispatchSkip(IEnumVARIANT FAR* penum, IStream FAR* pstm)
+{
+ unsigned long celt;
+ HRESULT hresult, hresultRet;
+
+
+ IfFailGo(GET(pstm, celt), LError0);
+
+ hresultRet = penum->Skip(celt);
+
+ IfFailGo(REWIND_STREAM(pstm), LError0);
+
+ IfFailGo(DispMarshalHresult(pstm, hresultRet), LError0);
+
+ hresult = NOERROR;
+
+LError0:;
+ return hresult;
+}
+
+
+/***
+*PRIVATE HRESULT DispatchReset(IEnumVARIANT*, IStream*)
+*Purpose:
+* Stub implementation of IEnumVARIANT::Reset()
+*
+* In:
+* None
+*
+* Out:
+* <HRESULT = return value>
+*
+*Entry:
+* penum = the IEnumVARIANT* to dispatch on
+* pstm = the stream containing the actuals
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+PRIVATE_(HRESULT)
+DispatchReset(IEnumVARIANT FAR* penum, IStream FAR* pstm)
+{
+ HRESULT hresultRet;
+
+ hresultRet = penum->Reset();
+
+ REWIND_STREAM(pstm);
+
+ return DispMarshalHresult(pstm, hresultRet);
+}
+
+
+/***
+*PRIVATE HRESULT DispatchClone(IEnumVARIANT*, IStream*)
+*Purpose:
+* Stub implementation of IEnumVARIANT::Clone()
+*
+* In:
+* None
+*
+* Out:
+* <HRESULT = return value>
+* <IEnumVARIANT = cloned enum>
+*
+*Entry:
+* penum = the IEnumVARIANT* to dispatch on
+* pstm = the stream containing the actuals
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+PRIVATE_(HRESULT)
+DispatchClone(IEnumVARIANT FAR* penum, IStream FAR* pstm)
+{
+ HRESULT hresult, hresultRet;
+ IEnumVARIANT FAR* penumClone;
+
+
+ hresultRet = penum->Clone(&penumClone);
+
+ REWIND_STREAM(pstm);
+
+ IfFailGo(DispMarshalHresult(pstm, hresultRet), LError0);
+
+ // dont bother marshaling the interface if the call failed.
+ if(SUCCEEDED(hresultRet)){
+ hresult = DispMarshalInterface(pstm, IID_IEnumVARIANT, penumClone);
+ }
+
+LError0:;
+ return hresult;
+}
+
+
+/***
+*PUBLIC HRESULT CStubEnumVARIANT::Invoke(REFIID, int, IStream*, unsigned long, void*)
+*
+*Purpose:
+* Dispatch the method with the given index (iMethod) on the given
+* interface, using the arguments serialized in the given stream.
+*
+* This function is the callee side of an LRPC call.
+*
+*Entry:
+* iid = the IID of the interface on which we are to make the call
+* iMethod = the method index
+* pstm = the IStream containing the method's actuals
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDMETHODIMP
+CStubEnumVARIANT::Invoke(
+#if (OE_WIN32 || defined(WOW))
+ RPCOLEMESSAGE *pMessage,
+ ICHANNEL *pRpcChannel)
+{
+ HRESULT hresult;
+ IStream FAR* pstm;
+
+ if(!m_punk)
+ return RESULT(E_FAIL);
+
+ OPEN_STUB_STREAM(pstm, pRpcChannel, pMessage, IID_IEnumVARIANT);
+
+#else
+ REFIID riid,
+ int iMethod,
+ IStream FAR* pstm,
+ unsigned long dwDestCtx,
+ void FAR* pvDestCtx)
+{
+ HRESULT hresult;
+
+ UNUSED(dwDestCtx);
+ UNUSED(pvDestCtx);
+
+ if(!IsEqualIID(riid, IID_IEnumVARIANT))
+ return RESULT(E_NOINTERFACE);
+
+ if(!m_punk)
+ return RESULT(E_FAIL);
+
+ if(m_penum == NULL)
+ IfFailRet(m_punk->QueryInterface(IID_IEnumVARIANT, (void FAR* FAR*)&m_penum));
+
+#endif
+
+ switch(GET_IMETHOD(pMessage)){
+ case IMETH_ENUMVARIANT_NEXT:
+ hresult = DispatchNext(m_penum, pstm);
+ break;
+
+ case IMETH_ENUMVARIANT_SKIP:
+ hresult = DispatchSkip(m_penum, pstm);
+ break;
+
+ case IMETH_ENUMVARIANT_RESET:
+ hresult = DispatchReset(m_penum, pstm);
+ break;
+
+ case IMETH_ENUMVARIANT_CLONE:
+ hresult = DispatchClone(m_penum, pstm);
+ break;
+
+ default:
+ hresult = INVALIDARG;
+ break;
+ }
+
+ RESET_STREAM(pstm);
+
+ DELETE_STREAM(pstm);
+
+ return hresult;
+}
+
+
+/***
+*PUBLIC BOOL CStubEnumVARIANT::IsIIDSupported(REFIID)
+*
+*Purpose:
+* Answer if the given IID is supported by this stub.
+*
+*Entry:
+* iid = the IID to query for support
+*
+*Exit:
+* return value = BOOL. TRUE if IID is supported, FALSE otherwise.
+*
+***********************************************************************/
+#if OE_MAC
+STDMETHODIMP_(unsigned long)
+#elif (OE_WIN32 || defined(WOW))
+STDMETHODIMP_(IRpcStubBuffer *)
+#else
+STDMETHODIMP_(BOOL)
+#endif
+CStubEnumVARIANT::IsIIDSupported(REFIID riid)
+{
+#if (OE_WIN32 || defined(WOW))
+ IRpcStubBuffer *pStub = 0;
+ if (IsEqualIID(riid, IID_IEnumVARIANT)) {
+ AddRef();
+ pStub = (IRpcStubBuffer *) this;
+ }
+ return pStub;
+#else
+
+ // REVIEW: I don't understand this, but thats the way Ole does it...
+ if(m_punk == NULL)
+ return FALSE;
+
+ return(IsEqualIID(riid, IID_IEnumVARIANT));
+#endif
+}
+
+
+/***
+*unsigned long CStubEnumVARIANT::CountRefs
+*Purpose:
+* Return the count of references held by this stub.
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = unsigned long, the count of references.
+*
+***********************************************************************/
+STDMETHODIMP_(unsigned long)
+CStubEnumVARIANT::CountRefs()
+{
+ unsigned long refs;
+
+ refs = 0;
+
+ if(m_punk != NULL)
+ ++refs;
+
+ if(m_penum != NULL)
+ ++refs;
+
+ return refs;
+}
+
+
+#if (OE_WIN32 || defined(WOW))
+
+STDMETHODIMP
+CStubEnumVARIANT::DebugServerQueryInterface(void FAR* FAR* ppv)
+{
+ *ppv = m_penum;
+ return S_OK;
+}
+
+
+STDMETHODIMP_(void)
+CStubEnumVARIANT::DebugServerRelease(void FAR* ppv)
+{
+
+}
+
+#endif
diff --git a/private/oleauto/src/dispatch/getobj.cpp b/private/oleauto/src/dispatch/getobj.cpp
new file mode 100644
index 000000000..bd7839845
--- /dev/null
+++ b/private/oleauto/src/dispatch/getobj.cpp
@@ -0,0 +1,202 @@
+/***
+*getobj.cpp
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file implements the Get Active Object API.
+*
+*
+*Revision History:
+*
+* [00] 02-Mar-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+* This is done with a bit of a hack. We use a file moniker, and
+* create a fake file name by stringizing the CLSID. The "right"
+* solution is to create a "real" active object moniker.
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+
+/***
+*PRIVATE CreateActiveObjectMoniker
+*Purpose:
+* Create an ActiveObject moniker from the given CLSID.
+*
+* Note: this is really a FileMoniker with a stringized clsid
+* as the pseudo-filename. Someday we should probably have a
+* real moniker for this.
+*
+*Entry:
+* rclsid = the clsid
+*
+*Exit:
+* return value = HRESULT
+*
+* *ppmk = the newly created active object moniker
+*
+***********************************************************************/
+PRIVATE_(HRESULT)
+CreateActiveObjectMoniker(REFCLSID rclsid, IMoniker FAR* FAR* ppmk)
+{
+ OLECHAR FAR* psz;
+ HRESULT hresult;
+
+
+ IfFailGo(StringFromCLSID(rclsid, &psz), LError0);
+
+ IfFailGo(CreateFileMoniker(psz, ppmk), LError1);
+
+ hresult = NOERROR;
+
+LError1:;
+ // delete with the standard task allocator
+ delete psz;
+
+LError0:;
+ return hresult;
+}
+
+
+/***
+*PUBLIC HRESULT RegisterActiveObject
+*Purpose:
+* Register the given IUnknown, with the given CLSID as running
+* in the running object table.
+*
+*Entry:
+* punk = the object to register as active
+* rclsid = the clsid of the object
+* pvReserved = reserved for future use
+*
+*Exit:
+* return value = HRESULT
+*
+* *pdwReserved = registration value (used to revoke the object).
+*
+***********************************************************************/
+STDAPI
+RegisterActiveObject(
+ IUnknown FAR* punk,
+ REFCLSID rclsid,
+#if VBA2
+ unsigned long dwFlags,
+#else
+ void FAR* pvReserved,
+#endif
+ unsigned long FAR* pdwRegister)
+{
+ HRESULT hresult;
+ IMoniker FAR* pmk;
+ IRunningObjectTable FAR* prot;
+
+#ifndef VBA2
+ UNUSED(pvReserved);
+#endif //!VBA2
+
+#ifdef _DEBUG
+ if(IsBadWritePtr(pdwRegister, sizeof(*pdwRegister)))
+ return RESULT(E_INVALIDARG);
+#if VBA2
+ if (dwFlags > ACTIVEOBJECT_WEAK) // only support 0 and 1 now
+ return RESULT(E_INVALIDARG);
+#endif //VBA2
+#endif //_DEBUG
+
+#if VBA2
+ unsigned long rotFlags = 1; // strong
+ if (dwFlags == ACTIVEOBJECT_WEAK)
+ rotFlags = 0; // weak
+#else //!VBA2
+ #define rotFlags 1 // always strong
+#endif //!VBA2
+
+ IfFailGo(CreateActiveObjectMoniker(rclsid, &pmk), LError0);
+
+ IfFailGo(GetRunningObjectTable(0, &prot), LError1);
+
+ // the first param indicates strong or weak reference (0=weak, 1=strong)
+ IfFailGo(prot->Register(rotFlags, punk, pmk, pdwRegister), LError2);
+
+ hresult = NOERROR;
+
+LError2:;
+ prot->Release();
+
+LError1:;
+ pmk->Release();
+
+LError0:;
+ return hresult;
+}
+
+
+/***
+*PUBLIC HRESULT RevokeActiveObject
+*Purpose:
+* Remove the object identified with the given registration value
+* from the running object table.
+*
+*Entry:
+* dwRegister = registration value of the object to revoke.
+* pvReserved = reserved for future use
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDAPI
+RevokeActiveObject(
+ unsigned long dwRegister,
+ void FAR* pvReserved)
+{
+ HRESULT hresult;
+ IRunningObjectTable FAR* prot;
+
+ UNUSED(pvReserved);
+
+ IfFailGo(GetRunningObjectTable(0, &prot), LError0);
+
+ IfFailGo(prot->Revoke(dwRegister), LError1);
+
+ hresult = NOERROR;
+
+LError1:;
+ prot->Release();
+
+LError0:;
+ return hresult;
+}
+
+
+STDAPI
+GetActiveObject(
+ REFCLSID rclsid,
+ void FAR* pvReserved,
+ IUnknown FAR* FAR* ppunk)
+{
+ HRESULT hresult;
+ IMoniker FAR* pmk;
+ IRunningObjectTable FAR* prot;
+
+ UNUSED(pvReserved);
+
+ IfFailGo(CreateActiveObjectMoniker(rclsid, &pmk), LError0);
+
+ IfFailGo(GetRunningObjectTable(0, &prot), LError1);
+
+ hresult = prot->GetObject(pmk, ppunk);
+
+ prot->Release();
+
+LError1:;
+ pmk->Release();
+
+LError0:;
+ return hresult;
+}
diff --git a/private/oleauto/src/dispatch/idispiid.c b/private/oleauto/src/dispatch/idispiid.c
new file mode 100644
index 000000000..8f6b91212
--- /dev/null
+++ b/private/oleauto/src/dispatch/idispiid.c
@@ -0,0 +1,58 @@
+/***
+*dispiid.c
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file allocates (via Ole macro mania) the IDispatch related IIDs.
+*
+*Revision History:
+*
+* [00] 07-May-93 tomteng: Created.
+*
+*****************************************************************************/
+#ifdef _MAC
+# ifdef _MSC_VER
+# include <macos/types.h>
+# include <macos/packages.h>
+# include <macos/resource.h>
+# include <macos/menus.h>
+# include <macos/windows.h>
+# include <macos/osutils.h>
+# include <macos/appleeve.h>
+# define far
+# define FAR far
+# define near
+# define NEAR near
+# define pascal _pascal
+# define PASCAL pascal
+# define cdecl _cdecl
+# define CDECL cdecl
+# else
+# include <types.h>
+# include <packages.h>
+# include <resources.h>
+# include <menus.h>
+# include <windows.h>
+# include <appleevents.h>
+# include <osutils.h>
+# include <AppleEvents.h>
+# endif
+#else
+# include <windows.h>
+#endif
+#include <ole2.h>
+
+// this redefines the Ole DEFINE_GUID() macro to do allocation.
+//
+#include <initguid.h>
+
+// due to the previous header, including this causes our DEFINE_GUID
+// definitions in the following headers to actually allocate data.
+//
+
+// Exported IDispatch & IEnumVARIANT GUIDs for Win32
+DEFINE_OLEGUID(IID_IDispatch, 0x00020400L, 0, 0);
+DEFINE_OLEGUID(IID_IDispatchW, 0x00020407L, 0, 0);
+DEFINE_OLEGUID(IID_IEnumVARIANT, 0x00020404L, 0, 0);
diff --git a/private/oleauto/src/dispatch/invhelp.cpp b/private/oleauto/src/dispatch/invhelp.cpp
new file mode 100644
index 000000000..7b7d348c2
--- /dev/null
+++ b/private/oleauto/src/dispatch/invhelp.cpp
@@ -0,0 +1,154 @@
+/***
+*invhelp.cpp
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file interfaces with the assembly invocation helpers.
+*
+*Revision History:
+*
+* [00] 23-Mar-93 bradlo: Created.
+* [01] 29-Jun-93 bradlo: Added Mac support
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+
+// the following data is referenced by assembly support routines.
+//
+extern "C" {
+
+SCODE g_S_OK = S_OK;
+SCODE g_E_INVALIDARG = E_INVALIDARG;
+
+// typedef for the low-level assembly invoke helper
+#if HC_MPW
+typedef SCODE (INVPROC)
+#else
+typedef SCODE (__cdecl FAR INVPROC)
+#endif
+(
+ void FAR* _this,
+#if OE_MAC68K
+ CALLCONV cc,
+#endif
+ unsigned int oVft,
+ unsigned int vtReturn,
+ unsigned int cActuals,
+ VARTYPE FAR* rgvt,
+ VARIANTARG FAR* FAR* rgpvarg,
+ VARIANT FAR* pvarResult
+);
+
+#if OE_WIN16
+
+extern INVPROC InvokePascal;
+extern INVPROC InvokeCdecl;
+
+#elif OE_WIN32 && _X86_
+
+extern INVPROC InvokeCdecl;
+extern INVPROC InvokeStdCall;
+
+#elif OE_WIN32 && !_X86
+
+extern INVPROC InvokeStdCall;
+
+#elif OE_MAC68K
+
+extern INVPROC InvokePascal;
+extern INVPROC InvokeCdecl;
+
+#elif OE_MACPPC
+
+extern INVPROC InvokeStdCall;
+
+#endif
+
+}
+
+
+STDAPI
+DoInvokeMethod(
+ void FAR* pvInstance,
+ unsigned int oVft,
+ CALLCONV cc,
+ VARTYPE vtReturn,
+ unsigned int cActuals,
+ VARTYPE FAR* rgvt,
+ VARIANTARG FAR* FAR* rgpvarg,
+ VARIANT FAR* pvarResult)
+{
+ SCODE sc;
+
+ INVPROC FAR* pfnInvoke;
+
+ if((vtReturn & (VT_BYREF)) != 0)
+ return RESULT(E_INVALIDARG);
+
+ switch(cc){
+#if OE_WIN16
+ case CC_CDECL:
+ pfnInvoke = InvokeCdecl;
+ break;
+ case CC_MSCPASCAL:
+ pfnInvoke = InvokePascal;
+ break;
+#elif OE_WIN32 && _X86_
+ case CC_CDECL:
+ pfnInvoke = InvokeCdecl;
+ break;
+ case CC_STDCALL:
+ pfnInvoke = InvokeStdCall;
+ break;
+#elif OE_WIN32 && !_X86_
+ case CC_CDECL:
+ case CC_STDCALL:
+ pfnInvoke = InvokeStdCall;
+ break;
+#elif OE_MAC68K
+ case CC_CDECL:
+ case CC_MPWCDECL:
+ pfnInvoke = InvokeCdecl;
+ break;
+ case CC_MSCPASCAL:
+ case CC_MACPASCAL:
+ case CC_MPWPASCAL:
+ pfnInvoke = InvokePascal;
+ break;
+#elif OE_MACPPC
+ case CC_CDECL:
+ case CC_STDCALL:
+ pfnInvoke = InvokeStdCall;
+ break;
+#endif
+ default:
+ return RESULT(E_INVALIDARG);
+ }
+
+#if OE_MAC68K || OE_MACPPC // UNDONE: PPC version seems to
+ // UNDONE: want the +4 too. Why?
+ // Mac-MPW Vtables have an extra "pad" word at the top
+ oVft += 4;
+#endif
+
+ sc = pfnInvoke(
+ pvInstance,
+#if OE_MAC68K
+ cc,
+#endif
+ oVft,
+ (unsigned int)vtReturn,
+ cActuals,
+ rgvt,
+ rgpvarg,
+ pvarResult);
+
+ return (sc == S_OK) ? NOERROR : RESULT(sc);
+}
+
diff --git a/private/oleauto/src/dispatch/memory.cpp b/private/oleauto/src/dispatch/memory.cpp
new file mode 100644
index 000000000..727308fd2
--- /dev/null
+++ b/private/oleauto/src/dispatch/memory.cpp
@@ -0,0 +1,64 @@
+/***
+*memory.cpp
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* memory allocation routines for oledisp.dll
+*
+*Revision History:
+*
+* [00] 15-Oct-92 Bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#if OE_WIN32
+#include "oautil.h"
+#endif // OE_WIN32
+
+#include <new.h>
+
+#if OE_WIN16
+ASSERTDATA
+#endif
+
+#if OE_WIN16
+void NEAR* operator new(size_t )
+{
+ ASSERT(UNREACHED);
+ return NULL;
+}
+
+void operator delete(void NEAR* )
+{
+ ASSERT(UNREACHED);
+}
+#endif
+
+void FAR* operator new(size_t size)
+{
+ void FAR* pv;
+ IMalloc FAR* pMalloc;
+
+ if(GetMalloc(&pMalloc) == 0){
+ pv = pMalloc->Alloc(size);
+ return pv;
+ }
+ return NULL;
+}
+
+void operator delete(void FAR* pv)
+{
+ if(pv == NULL)
+ return;
+
+ IMalloc FAR* pMalloc;
+ if(GetMalloc(&pMalloc) == 0)
+ pMalloc->Free(pv);
+}
+
diff --git a/private/oleauto/src/dispatch/namemacs.h b/private/oleauto/src/dispatch/namemacs.h
new file mode 100644
index 000000000..9c0f32771
--- /dev/null
+++ b/private/oleauto/src/dispatch/namemacs.h
@@ -0,0 +1,1305 @@
+ #undef StgCreateDocfile
+ #undef StgCreateDocfileOnILockBytes
+ #undef StgOpenStorage
+ #undef StgOpenStorageOnILockBytes
+ #undef StgIsStorageFile
+ #undef StgIsStorageILockBytes
+ #undef StgSetTimes
+ #undef StgSetTimesMac
+ #undef StgSetTimesFSp
+ #undef DllGetClassObject
+ #undef StgCreateDocfileFSp
+ #undef StgOpenStorageFSp
+ #undef StgCreateDocfileMac
+ #undef StgOpenStorageMac
+ #undef StgIsStorageFileMac
+ #undef StgIsStorageFileFSp
+ #undef StgGetFSpFromIStorage
+ #undef StgGetFRefFromIStorage
+ #undef OleregOpenRegistration
+ #undef OleregCloseRegistration
+ #undef OleregGetValue
+ #undef OleregSetValue
+ #undef OleregRemoveKey
+ #undef OleGlobalAddAtom
+ #undef OleGlobalDuplicateAtom
+ #undef OleGlobalDeleteAtom
+ #undef OleGlobalFindAtom
+ #undef OleGlobalGetAtomName
+ #undef OleGlobalAlloc
+ #undef OleGlobalCompact
+ #undef OleGlobalFree
+ #undef OleGlobalHandle
+ #undef OleGlobalLock
+ #undef OleGlobalReAlloc
+ #undef OleGlobalSize
+ #undef OleGlobalUnlock
+ #undef RegQueryValue
+ #undef RegOpenKey
+ #undef RegSetValue
+ #undef RegEnumKey
+ #undef RegEnumProgID
+ #undef RegDeleteKey
+ #undef RegCreateKey
+ #undef RegCloseKey
+ #undef RegInitialize
+ #undef InitUserData
+ #undef SendHighLevelEvent
+ #undef OleWinExec
+ #undef InitDB
+ #undef CloseDB
+ #undef OleGetCurrentTask
+ #undef OleGetProcAddress
+ #undef OleLoadLibrary
+ #undef OleFreeLibrary
+ #undef OutputDebugString
+ #undef SoftAssert
+ #undef FnAssert
+ #undef IsValidInterface
+ #undef IsValidIid
+ #undef IsValidHandle
+ #undef EnterOLEApi
+ #undef ExitOLEApi
+ #undef FnAssertOn
+ #undef GlobalFreePtr
+ #undef GlobalAllocPtr
+ #undef UserInitialize
+ #undef UserUninitialize
+ #undef IsValidInPtr
+ #undef IsValidOutPtr
+ #undef RegQueryValueEx
+ #undef RegFlush
+ #undef RegDeleteValue
+ #undef RegSetValueEx
+ #undef RegEnumValue
+ #undef OLEInitDBCSCountry
+ #undef IAnsiNext
+ #undef IAnsiPrev
+ #undef OleMakeFSSpec
+ #undef OleFullPathFromFSSpec
+ #undef OleGetFSSpecInfo
+ #undef DllGetClassObject
+ #undef SysAllocString
+ #undef SysReAllocString
+ #undef SysAllocStringLen
+ #undef SysReAllocStringLen
+ #undef SysFreeString
+ #undef SysStringLen
+ #undef VariantInit
+ #undef VariantClear
+ #undef VariantCopy
+ #undef VariantCopyInd
+ #undef VariantChangeType
+ #undef VarI2FromI4
+ #undef VarI2FromR4
+ #undef VarI2FromR8
+ #undef VarI2FromCy
+ #undef VarI2FromDate
+ #undef VarI2FromStr
+ #undef VarI2FromDisp
+ #undef VarI2FromBool
+ #undef VarI4FromI2
+ #undef VarI4FromR4
+ #undef VarI4FromR8
+ #undef VarI4FromCy
+ #undef VarI4FromDate
+ #undef VarI4FromStr
+ #undef VarI4FromDisp
+ #undef VarI4FromBool
+ #undef VarR4FromI2
+ #undef VarR4FromI4
+ #undef VarR4FromR8
+ #undef VarR4FromCy
+ #undef VarR4FromDate
+ #undef VarR4FromStr
+ #undef VarR4FromDisp
+ #undef VarR4FromBool
+ #undef VarR8FromI2
+ #undef VarR8FromI4
+ #undef VarR8FromR4
+ #undef VarR8FromCy
+ #undef VarR8FromDate
+ #undef VarR8FromStr
+ #undef VarR8FromDisp
+ #undef VarR8FromBool
+ #undef VarDateFromI2
+ #undef VarDateFromI4
+ #undef VarDateFromR4
+ #undef VarDateFromR8
+ #undef VarDateFromCy
+ #undef VarDateFromStr
+ #undef VarDateFromDisp
+ #undef VarDateFromBool
+ #undef VarCyFromI2
+ #undef VarCyFromI4
+ #undef VarCyFromR4
+ #undef VarCyFromR8
+ #undef VarCyFromDate
+ #undef VarCyFromStr
+ #undef VarCyFromDisp
+ #undef VarCyFromBool
+ #undef VarBstrFromI2
+ #undef VarBstrFromI4
+ #undef VarBstrFromR4
+ #undef VarBstrFromR8
+ #undef VarBstrFromCy
+ #undef VarBstrFromDate
+ #undef VarBstrFromDisp
+ #undef VarBstrFromBool
+ #undef VarBoolFromI2
+ #undef VarBoolFromI4
+ #undef VarBoolFromR4
+ #undef VarBoolFromR8
+ #undef VarBoolFromDate
+ #undef VarBoolFromCy
+ #undef VarBoolFromStr
+ #undef VarBoolFromDisp
+ #undef SafeArrayCreate
+ #undef SafeArrayDestroy
+ #undef SafeArrayGetDim
+ #undef SafeArrayGetElemsize
+ #undef SafeArrayGetUBound
+ #undef SafeArrayGetLBound
+ #undef SafeArrayLock
+ #undef SafeArrayUnlock
+ #undef SafeArrayAccessData
+ #undef SafeArrayUnaccessData
+ #undef SafeArrayGetElement
+ #undef SafeArrayPutElement
+ #undef SafeArrayCopy
+ #undef SafeArrayAllocDescriptor
+ #undef SafeArrayAllocData
+ #undef SafeArrayDestroyDescriptor
+ #undef SafeArrayDestroyData
+ #undef SafeArrayRedim
+ #undef VariantTimeToDosDateTime
+ #undef DosDateTimeToVariantTime
+ #undef DispGetParam
+ #undef DispGetIDsOfNames
+ #undef DispInvoke
+ #undef CreateDispTypeInfo
+ #undef CreateStdDispatch
+ #undef RegisterActiveObject
+ #undef RevokeActiveObject
+ #undef GetActiveObject
+ #undef DoInvokeMethod
+ #undef VariantChangeTypeEx
+ #undef SafeArrayPtrOfIndex
+ #undef MPWVarFromR4
+ #undef MPWVarFromR8
+ #undef MPWR4FromVar
+ #undef MPWR8FromVar
+ #undef CreateTypeLib
+ #undef LoadTypeLib
+ #undef LoadRegTypeLib
+ #undef RegisterTypeLib
+ #undef LHashValOfNameSys
+ #undef QueryPathOfRegTypeLib
+ #undef LoadTypeLibFSp
+ #undef RegisterTypeLibFolder
+ #undef QueryTypeLibFolder
+ #undef OleBuildVersion
+ #undef OleInitialize
+ #undef OleUninitialize
+ #undef DllGetClassObject
+ #undef OleQueryLinkFromData
+ #undef OleQueryCreateFromData
+ #undef OleCreateFromData
+ #undef OleCreateLinkFromData
+ #undef OleCreate
+ #undef OleCreateLink
+ #undef OleLoad
+ #undef OleSave
+ #undef OleRun
+ #undef OleIsRunning
+ #undef OleLockRunning
+ #undef ReadClassStg
+ #undef WriteClassStg
+ #undef ReadClassStm
+ #undef WriteClassStm
+ #undef BindMoniker
+ #undef MkParseDisplayName
+ #undef OleSaveToStream
+ #undef OleLoadFromStream
+ #undef CreateBindCtx
+ #undef CreateItemMoniker
+ #undef CreateFileMoniker
+ #undef CreateGenericComposite
+ #undef GetRunningObjectTable
+ #undef OleGetMalloc
+ #undef ReleaseStgMedium
+ #undef ReadStringStream
+ #undef WriteStringStream
+ #undef RegisterDragDrop
+ #undef RevokeDragDrop
+ #undef DoDragDrop
+ #undef CreateOleAdviseHolder
+ #undef CreateDataAdviseHolder
+ #undef OpenOrCreateStream
+ #undef CreateAntiMoniker
+ #undef CreatePointerMoniker
+ #undef MonikerRelativePathTo
+ #undef MonikerCommonPrefixWith
+ #undef OleSetClipboard
+ #undef OleGetClipboard
+ #undef OleDuplicateData
+ #undef CreateILockBytesOnHGlobal
+ #undef GetHGlobalFromILockBytes
+ #undef GetClassFile
+ #undef OleDraw
+ #undef OleCreateDefaultHandler
+ #undef OleCreateEmbeddingHelper
+ #undef OleConvertIStorageToOLESTREAMEx
+ #undef OleConvertOLESTREAMToIStorageEx
+ #undef SetDocumentBitStg
+ #undef GetDocumentBitStg
+ #undef WriteOleStg
+ #undef ReadOleStg
+ #undef OleCreateFromFile
+ #undef OleCreateLinkToFile
+ #undef CreateDataCache
+ #undef OleConvertIStorageToOLESTREAM
+ #undef OleConvertOLESTREAMToIStorage
+ #undef ReadFmtUserTypeStg
+ #undef WriteFmtUserTypeStg
+ #undef OleFlushClipboard
+ #undef OleIsCurrentClipboard
+ #undef OleTranslateAccelerator
+ #undef OleDoAutoConvert
+ #undef OleGetAutoConvert
+ #undef OleSetAutoConvert
+ #undef GetConvertStg
+ #undef SetConvertStg
+ #undef CreateStreamOnHGlobal
+ #undef GetHGlobalFromStream
+ #undef OleDuplicateMedium
+ #undef OleSetContainedObject
+ #undef OleNoteObjectVisible
+ #undef OleCreateStaticFromData
+ #undef OleRegGetUserType
+ #undef OleRegGetMiscStatus
+ #undef OleRegEnumFormatEtc
+ #undef OleRegEnumVerbs
+ #undef OleGetEnumFormatEtc
+ #undef OleSetEnumFormatEtc
+ #undef OleRemoveEnumFormatEtc
+ #undef OleSendLLE
+ #undef OleSetInPlaceWindow
+ #undef OleUnSetInPlaceWindow
+ #undef OleClipWindow
+ #undef OleClipWindows
+ #undef OleInsertMenus
+ #undef OleHashMenuID
+ #undef OleUnhashMenuID
+ #undef OlePatchGetMHandle
+ #undef OleUnpatchGetMHandle
+ #undef OleAddMBarMenu
+ #undef OleSetInPlaceRects
+ #undef OleMaskMouse
+ #undef OleMoveWindow
+ #undef OleSizeParentWindow
+ #undef OleSizeObjectWindow
+ #undef OleDragParentWindow
+ #undef OleDragObjectWindow
+ #undef OleGrowParentWindow
+ #undef OleGrowObjectWindow
+ #undef OleNewMBar
+ #undef OleDisposeMBar
+ #undef OleProcessDdeAE
+ #undef OleProcessClipboardAE
+ #undef InitializeClipboard
+ #undef UnInitializeClipboard
+ #undef OleIsClipboardFormatAvailable
+ #undef OleGetClipboardData
+ #undef OleSetClipboardData
+ #undef OleEnumClipboardFormats
+ #undef StoreClap
+ #undef OleCountClipboardFormats
+ #undef OleCloseClipboard
+ #undef OleEmptyClipboard
+ #undef OleSetClipboardEx
+ #undef OleZoomParentWindow
+ #undef OleSetParentRgns
+ #undef CreateFileMonikerFSp
+ #undef OleCreateFromFSp
+ #undef OleCreateLinkToFSp
+ #undef OleGetCursor
+ #undef OleSetCursor
+ #undef OleUpdateCursor
+ #undef GetClassFSp
+ #undef ReadOle1FmtProgIDStgMac
+ #undef WriteOle1FmtProgIDStgMac
+ #undef OleGetIconOfFile
+ #undef OleGetIconOfClass
+ #undef OleGetIconOfFSp
+ #undef OlePictFromIconAndLabel
+ #undef OleGetIconFromIconSuite
+ #undef OleUIPictIconFree
+ #undef OleUIPictIconDraw
+ #undef OleUIPictExtractIcon
+ #undef OleUIPictExtractLabel
+ #undef OleUIPictExtractIconSource
+ #undef OleMetaFileToPict
+ #undef OleQueryCreateAll
+ #undef OleWhichGrowHandle
+ #undef MkGetMacNetInfo
+ #undef CoBuildVersion
+ #undef CoInitialize
+ #undef CoUninitialize
+ #undef CoGetMalloc
+ #undef CoRegisterClassObject
+ #undef CoRevokeClassObject
+ #undef CoGetClassObject
+ #undef CoMarshalInterface
+ #undef CoUnmarshalInterface
+ #undef CoLoadLibrary
+ #undef CoFreeLibrary
+ #undef CoFreeAllLibraries
+ #undef CoCreateInstance
+ #undef StringFromIID
+ #undef CoDisconnectObject
+ #undef CoReleaseMarshalData
+ #undef CoFreeUnusedLibraries
+ #undef IsEqualGUID
+ #undef StringFromCLSID
+ #undef CLSIDFromString
+ #undef RESULTFROMSCODE
+ #undef GETSCODE
+ #undef CoRegisterMessageFilter
+ #undef CoIsHandlerConnected
+ #undef CoMarshalHresult
+ #undef CoUnmarshalHresult
+ #undef CoGetCurrentProcess
+ #undef CoIsOle1Class
+ #undef CLSIDFromProgID
+ #undef ProgIDFromCLSID
+ #undef CoLockObjectExternal
+ #undef CoGetTreatAsClass
+ #undef CoTreatAsClass
+ #undef CoGetStandardMarshal
+ #undef PropagateResult
+ #undef IIDFromString
+ #undef CoCreateStandardMalloc
+ #undef CoCreateGuid
+ #undef StringFromGUID2
+ #undef CoGetClassExt
+ #undef Ole1ClassFromCLSID2
+ #undef CLSIDFromOle1Class
+ #undef CoOpenClassKey
+ #undef GUIDFromString
+ #undef CoFileTimeNow
+ #undef RemAllocOID
+ #undef RemFreeOID
+ #undef RemCreateRemoteHandler
+ #undef RemConnectToObject
+ #undef RemGetInfoForCid
+ #undef LrpcCall
+ #undef LrpcDispatch
+ #undef LrpcRegisterMonitor
+ #undef LrpcRevokeMonitor
+ #undef LrpcGetThreadWindow
+ #undef LookupEtask
+ #undef SetEtask
+ #undef RemLookupSHUnk
+ #undef CoMemctxOf
+ #undef CoMemAlloc
+ #undef CoMemFree
+ #undef CoRunModalLoop
+ #undef CoHandleIncomingCall
+ #undef CoSetAckState
+ #undef OleProcessLrpcAE
+ #undef CoFileTimeToMacDateTime
+ #undef CoMacDateTimeToFileTime
+ #undef InternalCoInitialize
+ #undef CoHandlePendingMessage
+ #undef DllGetClassObject
+ #undef CompareStringA
+ #undef LCMapStringA
+ #undef GetLocaleInfoA
+ #undef GetStringTypeA
+ #undef GetSystemDefaultLangID
+ #undef GetUserDefaultLangID
+ #undef GetSystemDefaultLCID
+ #undef GetUserDefaultLCID
+#if ID_MUNGE_STAT_NAMES
+#if ID_OLE_STAT_DOCFILE
+ #define StgCreateDocfile StaticStgCreateDocfile
+ #define StgCreateDocfileOnILockBytes StaticStgCreateDocfileOnILockBytes
+ #define StgOpenStorage StaticStgOpenStorage
+ #define StgOpenStorageOnILockBytes StaticStgOpenStorageOnILockBytes
+ #define StgIsStorageFile StaticStgIsStorageFile
+ #define StgIsStorageILockBytes StaticStgIsStorageILockBytes
+ #define StgSetTimes StaticStgSetTimes
+ #define StgSetTimesMac StaticStgSetTimesMac
+ #define StgSetTimesFSp StaticStgSetTimesFSp
+ #define DllGetClassObject StaticDllGetClassObject
+ #define StgCreateDocfileFSp StaticStgCreateDocfileFSp
+ #define StgOpenStorageFSp StaticStgOpenStorageFSp
+ #define StgCreateDocfileMac StaticStgCreateDocfileMac
+ #define StgOpenStorageMac StaticStgOpenStorageMac
+ #define StgIsStorageFileMac StaticStgIsStorageFileMac
+ #define StgIsStorageFileFSp StaticStgIsStorageFileFSp
+ #define StgGetFSpFromIStorage StaticStgGetFSpFromIStorage
+ #define StgGetFRefFromIStorage StaticStgGetFRefFromIStorage
+#endif // ID_OLE_STAT_DOCFILE
+#if ID_OLE_STAT_USER
+ #define OleregOpenRegistration StaticOleregOpenRegistration
+ #define OleregCloseRegistration StaticOleregCloseRegistration
+ #define OleregGetValue StaticOleregGetValue
+ #define OleregSetValue StaticOleregSetValue
+ #define OleregRemoveKey StaticOleregRemoveKey
+ #define OleGlobalAddAtom StaticOleGlobalAddAtom
+ #define OleGlobalDuplicateAtom StaticOleGlobalDuplicateAtom
+ #define OleGlobalDeleteAtom StaticOleGlobalDeleteAtom
+ #define OleGlobalFindAtom StaticOleGlobalFindAtom
+ #define OleGlobalGetAtomName StaticOleGlobalGetAtomName
+ #define OleGlobalAlloc StaticOleGlobalAlloc
+ #define OleGlobalCompact StaticOleGlobalCompact
+ #define OleGlobalFree StaticOleGlobalFree
+ #define OleGlobalHandle StaticOleGlobalHandle
+ #define OleGlobalLock StaticOleGlobalLock
+ #define OleGlobalReAlloc StaticOleGlobalReAlloc
+ #define OleGlobalSize StaticOleGlobalSize
+ #define OleGlobalUnlock StaticOleGlobalUnlock
+ #define RegQueryValue StaticRegQueryValue
+ #define RegOpenKey StaticRegOpenKey
+ #define RegSetValue StaticRegSetValue
+ #define RegEnumKey StaticRegEnumKey
+ #define RegEnumProgID StaticRegEnumProgID
+ #define RegDeleteKey StaticRegDeleteKey
+ #define RegCreateKey StaticRegCreateKey
+ #define RegCloseKey StaticRegCloseKey
+ #define RegInitialize StaticRegInitialize
+ #define InitUserData StaticInitUserData
+ #define SendHighLevelEvent StaticSendHighLevelEvent
+ #define OleWinExec StaticOleWinExec
+ #define InitDB StaticInitDB
+ #define CloseDB StaticCloseDB
+ #define OleGetCurrentTask StaticOleGetCurrentTask
+ #define OleGetProcAddress StaticOleGetProcAddress
+ #define OleLoadLibrary StaticOleLoadLibrary
+ #define OleFreeLibrary StaticOleFreeLibrary
+ #define OutputDebugString StaticOutputDebugString
+ #define SoftAssert StaticSoftAssert
+ #define FnAssert StaticFnAssert
+ #define IsValidInterface StaticIsValidInterface
+ #define IsValidIid StaticIsValidIid
+ #define IsValidHandle StaticIsValidHandle
+ #define EnterOLEApi StaticEnterOLEApi
+ #define ExitOLEApi StaticExitOLEApi
+ #define FnAssertOn StaticFnAssertOn
+ #define GlobalFreePtr StaticGlobalFreePtr
+ #define GlobalAllocPtr StaticGlobalAllocPtr
+ #define UserInitialize StaticUserInitialize
+ #define UserUninitialize StaticUserUninitialize
+ #define IsValidInPtr StaticIsValidInPtr
+ #define IsValidOutPtr StaticIsValidOutPtr
+ #define RegQueryValueEx StaticRegQueryValueEx
+ #define RegFlush StaticRegFlush
+ #define RegDeleteValue StaticRegDeleteValue
+ #define RegSetValueEx StaticRegSetValueEx
+ #define RegEnumValue StaticRegEnumValue
+ #define OLEInitDBCSCountry StaticOLEInitDBCSCountry
+ #define IAnsiNext StaticIAnsiNext
+ #define IAnsiPrev StaticIAnsiPrev
+ #define OleMakeFSSpec StaticOleMakeFSSpec
+ #define OleFullPathFromFSSpec StaticOleFullPathFromFSSpec
+ #define OleGetFSSpecInfo StaticOleGetFSSpecInfo
+#endif //ID_OLE_STAT_USER
+#if ID_OLE_STAT_OLE2DISP
+ #define DllGetClassObject StaticDllGetClassObject
+ #define SysAllocString StaticSysAllocString
+ #define SysReAllocString StaticSysReAllocString
+ #define SysAllocStringLen StaticSysAllocStringLen
+ #define SysReAllocStringLen StaticSysReAllocStringLen
+ #define SysFreeString StaticSysFreeString
+ #define SysStringLen StaticSysStringLen
+ #define VariantInit StaticVariantInit
+ #define VariantClear StaticVariantClear
+ #define VariantCopy StaticVariantCopy
+ #define VariantCopyInd StaticVariantCopyInd
+ #define VariantChangeType StaticVariantChangeType
+ #define VarI2FromI4 StaticVarI2FromI4
+ #define VarI2FromR4 StaticVarI2FromR4
+ #define VarI2FromR8 StaticVarI2FromR8
+ #define VarI2FromCy StaticVarI2FromCy
+ #define VarI2FromDate StaticVarI2FromDate
+ #define VarI2FromStr StaticVarI2FromStr
+ #define VarI2FromDisp StaticVarI2FromDisp
+ #define VarI2FromBool StaticVarI2FromBool
+ #define VarI4FromI2 StaticVarI4FromI2
+ #define VarI4FromR4 StaticVarI4FromR4
+ #define VarI4FromR8 StaticVarI4FromR8
+ #define VarI4FromCy StaticVarI4FromCy
+ #define VarI4FromDate StaticVarI4FromDate
+ #define VarI4FromStr StaticVarI4FromStr
+ #define VarI4FromDisp StaticVarI4FromDisp
+ #define VarI4FromBool StaticVarI4FromBool
+ #define VarR4FromI2 StaticVarR4FromI2
+ #define VarR4FromI4 StaticVarR4FromI4
+ #define VarR4FromR8 StaticVarR4FromR8
+ #define VarR4FromCy StaticVarR4FromCy
+ #define VarR4FromDate StaticVarR4FromDate
+ #define VarR4FromStr StaticVarR4FromStr
+ #define VarR4FromDisp StaticVarR4FromDisp
+ #define VarR4FromBool StaticVarR4FromBool
+ #define VarR8FromI2 StaticVarR8FromI2
+ #define VarR8FromI4 StaticVarR8FromI4
+ #define VarR8FromR4 StaticVarR8FromR4
+ #define VarR8FromCy StaticVarR8FromCy
+ #define VarR8FromDate StaticVarR8FromDate
+ #define VarR8FromStr StaticVarR8FromStr
+ #define VarR8FromDisp StaticVarR8FromDisp
+ #define VarR8FromBool StaticVarR8FromBool
+ #define VarDateFromI2 StaticVarDateFromI2
+ #define VarDateFromI4 StaticVarDateFromI4
+ #define VarDateFromR4 StaticVarDateFromR4
+ #define VarDateFromR8 StaticVarDateFromR8
+ #define VarDateFromCy StaticVarDateFromCy
+ #define VarDateFromStr StaticVarDateFromStr
+ #define VarDateFromDisp StaticVarDateFromDisp
+ #define VarDateFromBool StaticVarDateFromBool
+ #define VarCyFromI2 StaticVarCyFromI2
+ #define VarCyFromI4 StaticVarCyFromI4
+ #define VarCyFromR4 StaticVarCyFromR4
+ #define VarCyFromR8 StaticVarCyFromR8
+ #define VarCyFromDate StaticVarCyFromDate
+ #define VarCyFromStr StaticVarCyFromStr
+ #define VarCyFromDisp StaticVarCyFromDisp
+ #define VarCyFromBool StaticVarCyFromBool
+ #define VarBstrFromI2 StaticVarBstrFromI2
+ #define VarBstrFromI4 StaticVarBstrFromI4
+ #define VarBstrFromR4 StaticVarBstrFromR4
+ #define VarBstrFromR8 StaticVarBstrFromR8
+ #define VarBstrFromCy StaticVarBstrFromCy
+ #define VarBstrFromDate StaticVarBstrFromDate
+ #define VarBstrFromDisp StaticVarBstrFromDisp
+ #define VarBstrFromBool StaticVarBstrFromBool
+ #define VarBoolFromI2 StaticVarBoolFromI2
+ #define VarBoolFromI4 StaticVarBoolFromI4
+ #define VarBoolFromR4 StaticVarBoolFromR4
+ #define VarBoolFromR8 StaticVarBoolFromR8
+ #define VarBoolFromDate StaticVarBoolFromDate
+ #define VarBoolFromCy StaticVarBoolFromCy
+ #define VarBoolFromStr StaticVarBoolFromStr
+ #define VarBoolFromDisp StaticVarBoolFromDisp
+ #define SafeArrayCreate StaticSafeArrayCreate
+ #define SafeArrayDestroy StaticSafeArrayDestroy
+ #define SafeArrayGetDim StaticSafeArrayGetDim
+ #define SafeArrayGetElemsize StaticSafeArrayGetElemsize
+ #define SafeArrayGetUBound StaticSafeArrayGetUBound
+ #define SafeArrayGetLBound StaticSafeArrayGetLBound
+ #define SafeArrayLock StaticSafeArrayLock
+ #define SafeArrayUnlock StaticSafeArrayUnlock
+ #define SafeArrayAccessData StaticSafeArrayAccessData
+ #define SafeArrayUnaccessData StaticSafeArrayUnaccessData
+ #define SafeArrayGetElement StaticSafeArrayGetElement
+ #define SafeArrayPutElement StaticSafeArrayPutElement
+ #define SafeArrayCopy StaticSafeArrayCopy
+ #define SafeArrayAllocDescriptor StaticSafeArrayAllocDescriptor
+ #define SafeArrayAllocData StaticSafeArrayAllocData
+ #define SafeArrayDestroyDescriptor StaticSafeArrayDestroyDescriptor
+ #define SafeArrayDestroyData StaticSafeArrayDestroyData
+ #define SafeArrayRedim StaticSafeArrayRedim
+ #define VariantTimeToDosDateTime StaticVariantTimeToDosDateTime
+ #define DosDateTimeToVariantTime StaticDosDateTimeToVariantTime
+ #define DispGetParam StaticDispGetParam
+ #define DispGetIDsOfNames StaticDispGetIDsOfNames
+ #define DispInvoke StaticDispInvoke
+ #define CreateDispTypeInfo StaticCreateDispTypeInfo
+ #define CreateStdDispatch StaticCreateStdDispatch
+ #define RegisterActiveObject StaticRegisterActiveObject
+ #define RevokeActiveObject StaticRevokeActiveObject
+ #define GetActiveObject StaticGetActiveObject
+ #define DoInvokeMethod StaticDoInvokeMethod
+ #define VariantChangeTypeEx StaticVariantChangeTypeEx
+ #define SafeArrayPtrOfIndex StaticSafeArrayPtrOfIndex
+ #define MPWVarFromR4 StaticMPWVarFromR4
+ #define MPWVarFromR8 StaticMPWVarFromR8
+ #define MPWR4FromVar StaticMPWR4FromVar
+ #define MPWR8FromVar StaticMPWR8FromVar
+#endif //ID_OLE_STAT_OLE2DISP
+#if ID_OLE_STAT_TYPELIB
+ #define CreateTypeLib StaticCreateTypeLib
+ #define LoadTypeLib StaticLoadTypeLib
+ #define LoadRegTypeLib StaticLoadRegTypeLib
+ #define RegisterTypeLib StaticRegisterTypeLib
+ #define LHashValOfNameSys StaticLHashValOfNameSys
+ #define QueryPathOfRegTypeLib StaticQueryPathOfRegTypeLib
+ #define LoadTypeLibFSp StaticLoadTypeLibFSp
+ #define RegisterTypeLibFolder StaticRegisterTypeLibFolder
+ #define QueryTypeLibFolder StaticQueryTypeLibFolder
+#endif //ID_OLE_STAT_TYPELIB
+#if ID_OLE_STAT_DEF
+ #define OleBuildVersion StaticOleBuildVersion
+ #define OleInitialize StaticOleInitialize
+ #define OleUninitialize StaticOleUninitialize
+ #define DllGetClassObject StaticDllGetClassObject
+ #define OleQueryLinkFromData StaticOleQueryLinkFromData
+ #define OleQueryCreateFromData StaticOleQueryCreateFromData
+ #define OleCreateFromData StaticOleCreateFromData
+ #define OleCreateLinkFromData StaticOleCreateLinkFromData
+ #define OleCreate StaticOleCreate
+ #define OleCreateLink StaticOleCreateLink
+ #define OleLoad StaticOleLoad
+ #define OleSave StaticOleSave
+ #define OleRun StaticOleRun
+ #define OleIsRunning StaticOleIsRunning
+ #define OleLockRunning StaticOleLockRunning
+ #define ReadClassStg StaticReadClassStg
+ #define WriteClassStg StaticWriteClassStg
+ #define ReadClassStm StaticReadClassStm
+ #define WriteClassStm StaticWriteClassStm
+ #define BindMoniker StaticBindMoniker
+ #define MkParseDisplayName StaticMkParseDisplayName
+ #define OleSaveToStream StaticOleSaveToStream
+ #define OleLoadFromStream StaticOleLoadFromStream
+ #define CreateBindCtx StaticCreateBindCtx
+ #define CreateItemMoniker StaticCreateItemMoniker
+ #define CreateFileMoniker StaticCreateFileMoniker
+ #define CreateGenericComposite StaticCreateGenericComposite
+ #define GetRunningObjectTable StaticGetRunningObjectTable
+ #define OleGetMalloc StaticOleGetMalloc
+ #define ReleaseStgMedium StaticReleaseStgMedium
+ #define ReadStringStream StaticReadStringStream
+ #define WriteStringStream StaticWriteStringStream
+ #define RegisterDragDrop StaticRegisterDragDrop
+ #define RevokeDragDrop StaticRevokeDragDrop
+ #define DoDragDrop StaticDoDragDrop
+ #define CreateOleAdviseHolder StaticCreateOleAdviseHolder
+ #define CreateDataAdviseHolder StaticCreateDataAdviseHolder
+ #define OpenOrCreateStream StaticOpenOrCreateStream
+ #define CreateAntiMoniker StaticCreateAntiMoniker
+ #define CreatePointerMoniker StaticCreatePointerMoniker
+ #define MonikerRelativePathTo StaticMonikerRelativePathTo
+ #define MonikerCommonPrefixWith StaticMonikerCommonPrefixWith
+ #define OleSetClipboard StaticOleSetClipboard
+ #define OleGetClipboard StaticOleGetClipboard
+ #define OleDuplicateData StaticOleDuplicateData
+ #define CreateILockBytesOnHGlobal StaticCreateILockBytesOnHGlobal
+ #define GetHGlobalFromILockBytes StaticGetHGlobalFromILockBytes
+ #define GetClassFile StaticGetClassFile
+ #define OleDraw StaticOleDraw
+ #define OleCreateDefaultHandler StaticOleCreateDefaultHandler
+ #define OleCreateEmbeddingHelper StaticOleCreateEmbeddingHelper
+ #define OleConvertIStorageToOLESTREAMEx StaticOleConvertIStorageToOLESTREAMEx
+ #define OleConvertOLESTREAMToIStorageEx StaticOleConvertOLESTREAMToIStorageEx
+ #define SetDocumentBitStg StaticSetDocumentBitStg
+ #define GetDocumentBitStg StaticGetDocumentBitStg
+ #define WriteOleStg StaticWriteOleStg
+ #define ReadOleStg StaticReadOleStg
+ #define OleCreateFromFile StaticOleCreateFromFile
+ #define OleCreateLinkToFile StaticOleCreateLinkToFile
+ #define CreateDataCache StaticCreateDataCache
+ #define OleConvertIStorageToOLESTREAM StaticOleConvertIStorageToOLESTREAM
+ #define OleConvertOLESTREAMToIStorage StaticOleConvertOLESTREAMToIStorage
+ #define ReadFmtUserTypeStg StaticReadFmtUserTypeStg
+ #define WriteFmtUserTypeStg StaticWriteFmtUserTypeStg
+ #define OleFlushClipboard StaticOleFlushClipboard
+ #define OleIsCurrentClipboard StaticOleIsCurrentClipboard
+ #define OleTranslateAccelerator StaticOleTranslateAccelerator
+ #define OleDoAutoConvert StaticOleDoAutoConvert
+ #define OleGetAutoConvert StaticOleGetAutoConvert
+ #define OleSetAutoConvert StaticOleSetAutoConvert
+ #define GetConvertStg StaticGetConvertStg
+ #define SetConvertStg StaticSetConvertStg
+ #define CreateStreamOnHGlobal StaticCreateStreamOnHGlobal
+ #define GetHGlobalFromStream StaticGetHGlobalFromStream
+ #define OleDuplicateMedium StaticOleDuplicateMedium
+ #define OleSetContainedObject StaticOleSetContainedObject
+ #define OleNoteObjectVisible StaticOleNoteObjectVisible
+ #define OleCreateStaticFromData StaticOleCreateStaticFromData
+ #define OleRegGetUserType StaticOleRegGetUserType
+ #define OleRegGetMiscStatus StaticOleRegGetMiscStatus
+ #define OleRegEnumFormatEtc StaticOleRegEnumFormatEtc
+ #define OleRegEnumVerbs StaticOleRegEnumVerbs
+ #define OleGetEnumFormatEtc StaticOleGetEnumFormatEtc
+ #define OleSetEnumFormatEtc StaticOleSetEnumFormatEtc
+ #define OleRemoveEnumFormatEtc StaticOleRemoveEnumFormatEtc
+ #define OleSendLLE StaticOleSendLLE
+ #define OleSetInPlaceWindow StaticOleSetInPlaceWindow
+ #define OleUnSetInPlaceWindow StaticOleUnSetInPlaceWindow
+ #define OleClipWindow StaticOleClipWindow
+ #define OleClipWindows StaticOleClipWindows
+ #define OleInsertMenus StaticOleInsertMenus
+ #define OleHashMenuID StaticOleHashMenuID
+ #define OleUnhashMenuID StaticOleUnhashMenuID
+ #define OlePatchGetMHandle StaticOlePatchGetMHandle
+ #define OleUnpatchGetMHandle StaticOleUnpatchGetMHandle
+ #define OleAddMBarMenu StaticOleAddMBarMenu
+ #define OleSetInPlaceRects StaticOleSetInPlaceRects
+ #define OleMaskMouse StaticOleMaskMouse
+ #define OleMoveWindow StaticOleMoveWindow
+ #define OleSizeParentWindow StaticOleSizeParentWindow
+ #define OleSizeObjectWindow StaticOleSizeObjectWindow
+ #define OleDragParentWindow StaticOleDragParentWindow
+ #define OleDragObjectWindow StaticOleDragObjectWindow
+ #define OleGrowParentWindow StaticOleGrowParentWindow
+ #define OleGrowObjectWindow StaticOleGrowObjectWindow
+ #define OleNewMBar StaticOleNewMBar
+ #define OleDisposeMBar StaticOleDisposeMBar
+ #define OleProcessDdeAE StaticOleProcessDdeAE
+ #define OleProcessClipboardAE StaticOleProcessClipboardAE
+ #define InitializeClipboard StaticInitializeClipboard
+ #define UnInitializeClipboard StaticUnInitializeClipboard
+ #define OleIsClipboardFormatAvailable StaticOleIsClipboardFormatAvailable
+ #define OleGetClipboardData StaticOleGetClipboardData
+ #define OleSetClipboardData StaticOleSetClipboardData
+ #define OleEnumClipboardFormats StaticOleEnumClipboardFormats
+ #define StoreClap StaticStoreClap
+ #define OleCountClipboardFormats StaticOleCountClipboardFormats
+ #define OleCloseClipboard StaticOleCloseClipboard
+ #define OleEmptyClipboard StaticOleEmptyClipboard
+ #define OleSetClipboardEx StaticOleSetClipboardEx
+ #define OleZoomParentWindow StaticOleZoomParentWindow
+ #define OleSetParentRgns StaticOleSetParentRgns
+ #define CreateFileMonikerFSp StaticCreateFileMonikerFSp
+ #define OleCreateFromFSp StaticOleCreateFromFSp
+ #define OleCreateLinkToFSp StaticOleCreateLinkToFSp
+ #define OleGetCursor StaticOleGetCursor
+ #define OleSetCursor StaticOleSetCursor
+ #define OleUpdateCursor StaticOleUpdateCursor
+ #define GetClassFSp StaticGetClassFSp
+ #define ReadOle1FmtProgIDStgMac StaticReadOle1FmtProgIDStgMac
+ #define WriteOle1FmtProgIDStgMac StaticWriteOle1FmtProgIDStgMac
+ #define OleGetIconOfFile StaticOleGetIconOfFile
+ #define OleGetIconOfClass StaticOleGetIconOfClass
+ #define OleGetIconOfFSp StaticOleGetIconOfFSp
+ #define OlePictFromIconAndLabel StaticOlePictFromIconAndLabel
+ #define OleGetIconFromIconSuite StaticOleGetIconFromIconSuite
+ #define OleUIPictIconFree StaticOleUIPictIconFree
+ #define OleUIPictIconDraw StaticOleUIPictIconDraw
+ #define OleUIPictExtractIcon StaticOleUIPictExtractIcon
+ #define OleUIPictExtractLabel StaticOleUIPictExtractLabel
+ #define OleUIPictExtractIconSource StaticOleUIPictExtractIconSource
+ #define OleMetaFileToPict StaticOleMetaFileToPict
+ #define OleQueryCreateAll StaticOleQueryCreateAll
+ #define OleWhichGrowHandle StaticOleWhichGrowHandle
+ #define MkGetMacNetInfo StaticMkGetMacNetInfo
+#endif //ID_OLE_STAT_DEF
+#if ID_OLE_STAT_COMPOBJ
+ #define CoBuildVersion StaticCoBuildVersion
+ #define CoInitialize StaticCoInitialize
+ #define CoUninitialize StaticCoUninitialize
+ #define CoGetMalloc StaticCoGetMalloc
+ #define CoRegisterClassObject StaticCoRegisterClassObject
+ #define CoRevokeClassObject StaticCoRevokeClassObject
+ #define CoGetClassObject StaticCoGetClassObject
+ #define CoMarshalInterface StaticCoMarshalInterface
+ #define CoUnmarshalInterface StaticCoUnmarshalInterface
+ #define CoLoadLibrary StaticCoLoadLibrary
+ #define CoFreeLibrary StaticCoFreeLibrary
+ #define CoFreeAllLibraries StaticCoFreeAllLibraries
+ #define CoCreateInstance StaticCoCreateInstance
+ #define StringFromIID StaticStringFromIID
+ #define CoDisconnectObject StaticCoDisconnectObject
+ #define CoReleaseMarshalData StaticCoReleaseMarshalData
+ #define CoFreeUnusedLibraries StaticCoFreeUnusedLibraries
+ #define IsEqualGUID StaticIsEqualGUID
+ #define StringFromCLSID StaticStringFromCLSID
+ #define CLSIDFromString StaticCLSIDFromString
+ #define RESULTFROMSCODE StaticRESULTFROMSCODE
+ #define GETSCODE StaticGETSCODE
+ #define CoRegisterMessageFilter StaticCoRegisterMessageFilter
+ #define CoIsHandlerConnected StaticCoIsHandlerConnected
+ #define CoMarshalHresult StaticCoMarshalHresult
+ #define CoUnmarshalHresult StaticCoUnmarshalHresult
+ #define CoGetCurrentProcess StaticCoGetCurrentProcess
+ #define CoIsOle1Class StaticCoIsOle1Class
+ #define CLSIDFromProgID StaticCLSIDFromProgID
+ #define ProgIDFromCLSID StaticProgIDFromCLSID
+ #define CoLockObjectExternal StaticCoLockObjectExternal
+ #define CoGetTreatAsClass StaticCoGetTreatAsClass
+ #define CoTreatAsClass StaticCoTreatAsClass
+ #define CoGetStandardMarshal StaticCoGetStandardMarshal
+ #define PropagateResult StaticPropagateResult
+ #define IIDFromString StaticIIDFromString
+ #define CoCreateStandardMalloc StaticCoCreateStandardMalloc
+ #define CoCreateGuid StaticCoCreateGuid
+ #define StringFromGUID2 StaticStringFromGUID2
+ #define CoGetClassExt StaticCoGetClassExt
+ #define Ole1ClassFromCLSID2 StaticOle1ClassFromCLSID2
+ #define CLSIDFromOle1Class StaticCLSIDFromOle1Class
+ #define CoOpenClassKey StaticCoOpenClassKey
+ #define GUIDFromString StaticGUIDFromString
+ #define CoFileTimeNow StaticCoFileTimeNow
+ #define RemAllocOID StaticRemAllocOID
+ #define RemFreeOID StaticRemFreeOID
+ #define RemCreateRemoteHandler StaticRemCreateRemoteHandler
+ #define RemConnectToObject StaticRemConnectToObject
+ #define RemGetInfoForCid StaticRemGetInfoForCid
+ #define LrpcCall StaticLrpcCall
+ #define LrpcDispatch StaticLrpcDispatch
+ #define LrpcRegisterMonitor StaticLrpcRegisterMonitor
+ #define LrpcRevokeMonitor StaticLrpcRevokeMonitor
+ #define LrpcGetThreadWindow StaticLrpcGetThreadWindow
+ #define LookupEtask StaticLookupEtask
+ #define SetEtask StaticSetEtask
+ #define RemLookupSHUnk StaticRemLookupSHUnk
+ #define CoMemctxOf StaticCoMemctxOf
+ #define CoMemAlloc StaticCoMemAlloc
+ #define CoMemFree StaticCoMemFree
+ #define CoRunModalLoop StaticCoRunModalLoop
+ #define CoHandleIncomingCall StaticCoHandleIncomingCall
+ #define CoSetAckState StaticCoSetAckState
+ #define OleProcessLrpcAE StaticOleProcessLrpcAE
+ #define CoFileTimeToMacDateTime StaticCoFileTimeToMacDateTime
+ #define CoMacDateTimeToFileTime StaticCoMacDateTimeToFileTime
+ #define InternalCoInitialize StaticInternalCoInitialize
+ #define CoHandlePendingMessage StaticCoHandlePendingMessage
+#endif //ID_OLE_STAT_COMPOBJ
+#if ID_OLE_STAT_PROXY
+ #define DllGetClassObject StaticDllGetClassObject
+#endif //ID_OLE_STAT_PROXY
+#if ID_OLE_STAT_OLE2NLS
+ #define CompareStringA StaticCompareStringA
+ #define LCMapStringA StaticLCMapStringA
+ #define GetLocaleInfoA StaticGetLocaleInfoA
+ #define GetStringTypeA StaticGetStringTypeA
+ #define GetSystemDefaultLangID StaticGetSystemDefaultLangID
+ #define GetUserDefaultLangID StaticGetUserDefaultLangID
+ #define GetSystemDefaultLCID StaticGetSystemDefaultLCID
+ #define GetUserDefaultLCID StaticGetUserDefaultLCID
+#endif //ID_OLE_STAT_OLE2NLS
+#endif //ID_MUNGE_STAT_NAMES
+#if ID_MUNGE_DLL_NAMES
+#if !ID_OLE_STAT_DOCFILE
+ #define StgCreateDocfile _DllStgCreateDocfile
+ #define StgCreateDocfileOnILockBytes _DllStgCreateDocfileOnILockBytes
+ #define StgOpenStorage _DllStgOpenStorage
+ #define StgOpenStorageOnILockBytes _DllStgOpenStorageOnILockBytes
+ #define StgIsStorageFile _DllStgIsStorageFile
+ #define StgIsStorageILockBytes _DllStgIsStorageILockBytes
+ #define StgSetTimes _DllStgSetTimes
+ #define StgSetTimesMac _DllStgSetTimesMac
+ #define StgSetTimesFSp _DllStgSetTimesFSp
+ #define DllGetClassObject _DllDllGetClassObject
+ #define StgCreateDocfileFSp _DllStgCreateDocfileFSp
+ #define StgOpenStorageFSp _DllStgOpenStorageFSp
+ #define StgCreateDocfileMac _DllStgCreateDocfileMac
+ #define StgOpenStorageMac _DllStgOpenStorageMac
+ #define StgIsStorageFileMac _DllStgIsStorageFileMac
+ #define StgIsStorageFileFSp _DllStgIsStorageFileFSp
+ #define StgGetFSpFromIStorage _DllStgGetFSpFromIStorage
+ #define StgGetFRefFromIStorage _DllStgGetFRefFromIStorage
+#endif // ID_OLE_STAT_DOCFILE
+#if !ID_OLE_STAT_USER
+ #define OleregOpenRegistration _DllOleregOpenRegistration
+ #define OleregCloseRegistration _DllOleregCloseRegistration
+ #define OleregGetValue _DllOleregGetValue
+ #define OleregSetValue _DllOleregSetValue
+ #define OleregRemoveKey _DllOleregRemoveKey
+ #define OleGlobalAddAtom _DllOleGlobalAddAtom
+ #define OleGlobalDuplicateAtom _DllOleGlobalDuplicateAtom
+ #define OleGlobalDeleteAtom _DllOleGlobalDeleteAtom
+ #define OleGlobalFindAtom _DllOleGlobalFindAtom
+ #define OleGlobalGetAtomName _DllOleGlobalGetAtomName
+ #define OleGlobalAlloc _DllOleGlobalAlloc
+ #define OleGlobalCompact _DllOleGlobalCompact
+ #define OleGlobalFree _DllOleGlobalFree
+ #define OleGlobalHandle _DllOleGlobalHandle
+ #define OleGlobalLock _DllOleGlobalLock
+ #define OleGlobalReAlloc _DllOleGlobalReAlloc
+ #define OleGlobalSize _DllOleGlobalSize
+ #define OleGlobalUnlock _DllOleGlobalUnlock
+ #define RegQueryValue _DllRegQueryValue
+ #define RegOpenKey _DllRegOpenKey
+ #define RegSetValue _DllRegSetValue
+ #define RegEnumKey _DllRegEnumKey
+ #define RegEnumProgID _DllRegEnumProgID
+ #define RegDeleteKey _DllRegDeleteKey
+ #define RegCreateKey _DllRegCreateKey
+ #define RegCloseKey _DllRegCloseKey
+ #define RegInitialize _DllRegInitialize
+ #define InitUserData _DllInitUserData
+ #define SendHighLevelEvent _DllSendHighLevelEvent
+ #define OleWinExec _DllOleWinExec
+ #define InitDB _DllInitDB
+ #define CloseDB _DllCloseDB
+ #define OleGetCurrentTask _DllOleGetCurrentTask
+ #define OleGetProcAddress _DllOleGetProcAddress
+ #define OleLoadLibrary _DllOleLoadLibrary
+ #define OleFreeLibrary _DllOleFreeLibrary
+ #define OutputDebugString _DllOutputDebugString
+ #define SoftAssert _DllSoftAssert
+ #define FnAssert _DllFnAssert
+ #define IsValidInterface _DllIsValidInterface
+ #define IsValidIid _DllIsValidIid
+ #define IsValidHandle _DllIsValidHandle
+ #define EnterOLEApi _DllEnterOLEApi
+ #define ExitOLEApi _DllExitOLEApi
+ #define FnAssertOn _DllFnAssertOn
+ #define GlobalFreePtr _DllGlobalFreePtr
+ #define GlobalAllocPtr _DllGlobalAllocPtr
+ #define UserInitialize _DllUserInitialize
+ #define UserUninitialize _DllUserUninitialize
+ #define IsValidInPtr _DllIsValidInPtr
+ #define IsValidOutPtr _DllIsValidOutPtr
+ #define RegQueryValueEx _DllRegQueryValueEx
+ #define RegFlush _DllRegFlush
+ #define RegDeleteValue _DllRegDeleteValue
+ #define RegSetValueEx _DllRegSetValueEx
+ #define RegEnumValue _DllRegEnumValue
+ #define OLEInitDBCSCountry _DllOLEInitDBCSCountry
+ #define IAnsiNext _DllIAnsiNext
+ #define IAnsiPrev _DllIAnsiPrev
+ #define OleMakeFSSpec _DllOleMakeFSSpec
+ #define OleFullPathFromFSSpec _DllOleFullPathFromFSSpec
+ #define OleGetFSSpecInfo _DllOleGetFSSpecInfo
+#endif //ID_OLE_STAT_USER
+#if !ID_OLE_STAT_OLE2DISP
+ #define DllGetClassObject _DllDllGetClassObject
+ #define SysAllocString _DllSysAllocString
+ #define SysReAllocString _DllSysReAllocString
+ #define SysAllocStringLen _DllSysAllocStringLen
+ #define SysReAllocStringLen _DllSysReAllocStringLen
+ #define SysFreeString _DllSysFreeString
+ #define SysStringLen _DllSysStringLen
+ #define VariantInit _DllVariantInit
+ #define VariantClear _DllVariantClear
+ #define VariantCopy _DllVariantCopy
+ #define VariantCopyInd _DllVariantCopyInd
+ #define VariantChangeType _DllVariantChangeType
+ #define VarI2FromI4 _DllVarI2FromI4
+ #define VarI2FromR4 _DllVarI2FromR4
+ #define VarI2FromR8 _DllVarI2FromR8
+ #define VarI2FromCy _DllVarI2FromCy
+ #define VarI2FromDate _DllVarI2FromDate
+ #define VarI2FromStr _DllVarI2FromStr
+ #define VarI2FromDisp _DllVarI2FromDisp
+ #define VarI2FromBool _DllVarI2FromBool
+ #define VarI4FromI2 _DllVarI4FromI2
+ #define VarI4FromR4 _DllVarI4FromR4
+ #define VarI4FromR8 _DllVarI4FromR8
+ #define VarI4FromCy _DllVarI4FromCy
+ #define VarI4FromDate _DllVarI4FromDate
+ #define VarI4FromStr _DllVarI4FromStr
+ #define VarI4FromDisp _DllVarI4FromDisp
+ #define VarI4FromBool _DllVarI4FromBool
+ #define VarR4FromI2 _DllVarR4FromI2
+ #define VarR4FromI4 _DllVarR4FromI4
+ #define VarR4FromR8 _DllVarR4FromR8
+ #define VarR4FromCy _DllVarR4FromCy
+ #define VarR4FromDate _DllVarR4FromDate
+ #define VarR4FromStr _DllVarR4FromStr
+ #define VarR4FromDisp _DllVarR4FromDisp
+ #define VarR4FromBool _DllVarR4FromBool
+ #define VarR8FromI2 _DllVarR8FromI2
+ #define VarR8FromI4 _DllVarR8FromI4
+ #define VarR8FromR4 _DllVarR8FromR4
+ #define VarR8FromCy _DllVarR8FromCy
+ #define VarR8FromDate _DllVarR8FromDate
+ #define VarR8FromStr _DllVarR8FromStr
+ #define VarR8FromDisp _DllVarR8FromDisp
+ #define VarR8FromBool _DllVarR8FromBool
+ #define VarDateFromI2 _DllVarDateFromI2
+ #define VarDateFromI4 _DllVarDateFromI4
+ #define VarDateFromR4 _DllVarDateFromR4
+ #define VarDateFromR8 _DllVarDateFromR8
+ #define VarDateFromCy _DllVarDateFromCy
+ #define VarDateFromStr _DllVarDateFromStr
+ #define VarDateFromDisp _DllVarDateFromDisp
+ #define VarDateFromBool _DllVarDateFromBool
+ #define VarCyFromI2 _DllVarCyFromI2
+ #define VarCyFromI4 _DllVarCyFromI4
+ #define VarCyFromR4 _DllVarCyFromR4
+ #define VarCyFromR8 _DllVarCyFromR8
+ #define VarCyFromDate _DllVarCyFromDate
+ #define VarCyFromStr _DllVarCyFromStr
+ #define VarCyFromDisp _DllVarCyFromDisp
+ #define VarCyFromBool _DllVarCyFromBool
+ #define VarBstrFromI2 _DllVarBstrFromI2
+ #define VarBstrFromI4 _DllVarBstrFromI4
+ #define VarBstrFromR4 _DllVarBstrFromR4
+ #define VarBstrFromR8 _DllVarBstrFromR8
+ #define VarBstrFromCy _DllVarBstrFromCy
+ #define VarBstrFromDate _DllVarBstrFromDate
+ #define VarBstrFromDisp _DllVarBstrFromDisp
+ #define VarBstrFromBool _DllVarBstrFromBool
+ #define VarBoolFromI2 _DllVarBoolFromI2
+ #define VarBoolFromI4 _DllVarBoolFromI4
+ #define VarBoolFromR4 _DllVarBoolFromR4
+ #define VarBoolFromR8 _DllVarBoolFromR8
+ #define VarBoolFromDate _DllVarBoolFromDate
+ #define VarBoolFromCy _DllVarBoolFromCy
+ #define VarBoolFromStr _DllVarBoolFromStr
+ #define VarBoolFromDisp _DllVarBoolFromDisp
+ #define SafeArrayCreate _DllSafeArrayCreate
+ #define SafeArrayDestroy _DllSafeArrayDestroy
+ #define SafeArrayGetDim _DllSafeArrayGetDim
+ #define SafeArrayGetElemsize _DllSafeArrayGetElemsize
+ #define SafeArrayGetUBound _DllSafeArrayGetUBound
+ #define SafeArrayGetLBound _DllSafeArrayGetLBound
+ #define SafeArrayLock _DllSafeArrayLock
+ #define SafeArrayUnlock _DllSafeArrayUnlock
+ #define SafeArrayAccessData _DllSafeArrayAccessData
+ #define SafeArrayUnaccessData _DllSafeArrayUnaccessData
+ #define SafeArrayGetElement _DllSafeArrayGetElement
+ #define SafeArrayPutElement _DllSafeArrayPutElement
+ #define SafeArrayCopy _DllSafeArrayCopy
+ #define SafeArrayAllocDescriptor _DllSafeArrayAllocDescriptor
+ #define SafeArrayAllocData _DllSafeArrayAllocData
+ #define SafeArrayDestroyDescriptor _DllSafeArrayDestroyDescriptor
+ #define SafeArrayDestroyData _DllSafeArrayDestroyData
+ #define SafeArrayRedim _DllSafeArrayRedim
+ #define VariantTimeToDosDateTime _DllVariantTimeToDosDateTime
+ #define DosDateTimeToVariantTime _DllDosDateTimeToVariantTime
+ #define DispGetParam _DllDispGetParam
+ #define DispGetIDsOfNames _DllDispGetIDsOfNames
+ #define DispInvoke _DllDispInvoke
+ #define CreateDispTypeInfo _DllCreateDispTypeInfo
+ #define CreateStdDispatch _DllCreateStdDispatch
+ #define RegisterActiveObject _DllRegisterActiveObject
+ #define RevokeActiveObject _DllRevokeActiveObject
+ #define GetActiveObject _DllGetActiveObject
+ #define DoInvokeMethod _DllDoInvokeMethod
+ #define VariantChangeTypeEx _DllVariantChangeTypeEx
+ #define SafeArrayPtrOfIndex _DllSafeArrayPtrOfIndex
+ #define MPWVarFromR4 _DllMPWVarFromR4
+ #define MPWVarFromR8 _DllMPWVarFromR8
+ #define MPWR4FromVar _DllMPWR4FromVar
+ #define MPWR8FromVar _DllMPWR8FromVar
+#endif //ID_OLE_STAT_OLE2DISP
+#if !ID_OLE_STAT_TYPELIB
+ #define CreateTypeLib _DllCreateTypeLib
+ #define LoadTypeLib _DllLoadTypeLib
+ #define LoadRegTypeLib _DllLoadRegTypeLib
+ #define RegisterTypeLib _DllRegisterTypeLib
+ #define LHashValOfNameSys _DllLHashValOfNameSys
+ #define QueryPathOfRegTypeLib _DllQueryPathOfRegTypeLib
+ #define LoadTypeLibFSp _DllLoadTypeLibFSp
+ #define RegisterTypeLibFolder _DllRegisterTypeLibFolder
+ #define QueryTypeLibFolder _DllQueryTypeLibFolder
+#endif //ID_OLE_STAT_TYPELIB
+#if !ID_OLE_STAT_DEF
+ #define OleBuildVersion _DllOleBuildVersion
+ #define OleInitialize _DllOleInitialize
+ #define OleUninitialize _DllOleUninitialize
+ #define DllGetClassObject _DllDllGetClassObject
+ #define OleQueryLinkFromData _DllOleQueryLinkFromData
+ #define OleQueryCreateFromData _DllOleQueryCreateFromData
+ #define OleCreateFromData _DllOleCreateFromData
+ #define OleCreateLinkFromData _DllOleCreateLinkFromData
+ #define OleCreate _DllOleCreate
+ #define OleCreateLink _DllOleCreateLink
+ #define OleLoad _DllOleLoad
+ #define OleSave _DllOleSave
+ #define OleRun _DllOleRun
+ #define OleIsRunning _DllOleIsRunning
+ #define OleLockRunning _DllOleLockRunning
+ #define ReadClassStg _DllReadClassStg
+ #define WriteClassStg _DllWriteClassStg
+ #define ReadClassStm _DllReadClassStm
+ #define WriteClassStm _DllWriteClassStm
+ #define BindMoniker _DllBindMoniker
+ #define MkParseDisplayName _DllMkParseDisplayName
+ #define OleSaveToStream _DllOleSaveToStream
+ #define OleLoadFromStream _DllOleLoadFromStream
+ #define CreateBindCtx _DllCreateBindCtx
+ #define CreateItemMoniker _DllCreateItemMoniker
+ #define CreateFileMoniker _DllCreateFileMoniker
+ #define CreateGenericComposite _DllCreateGenericComposite
+ #define GetRunningObjectTable _DllGetRunningObjectTable
+ #define OleGetMalloc _DllOleGetMalloc
+ #define ReleaseStgMedium _DllReleaseStgMedium
+ #define ReadStringStream _DllReadStringStream
+ #define WriteStringStream _DllWriteStringStream
+ #define RegisterDragDrop _DllRegisterDragDrop
+ #define RevokeDragDrop _DllRevokeDragDrop
+ #define DoDragDrop _DllDoDragDrop
+ #define CreateOleAdviseHolder _DllCreateOleAdviseHolder
+ #define CreateDataAdviseHolder _DllCreateDataAdviseHolder
+ #define OpenOrCreateStream _DllOpenOrCreateStream
+ #define CreateAntiMoniker _DllCreateAntiMoniker
+ #define CreatePointerMoniker _DllCreatePointerMoniker
+ #define MonikerRelativePathTo _DllMonikerRelativePathTo
+ #define MonikerCommonPrefixWith _DllMonikerCommonPrefixWith
+ #define OleSetClipboard _DllOleSetClipboard
+ #define OleGetClipboard _DllOleGetClipboard
+ #define OleDuplicateData _DllOleDuplicateData
+ #define CreateILockBytesOnHGlobal _DllCreateILockBytesOnHGlobal
+ #define GetHGlobalFromILockBytes _DllGetHGlobalFromILockBytes
+ #define GetClassFile _DllGetClassFile
+ #define OleDraw _DllOleDraw
+ #define OleCreateDefaultHandler _DllOleCreateDefaultHandler
+ #define OleCreateEmbeddingHelper _DllOleCreateEmbeddingHelper
+ #define OleConvertIStorageToOLESTREAMEx _DllOleConvertIStorageToOLESTREAMEx
+ #define OleConvertOLESTREAMToIStorageEx _DllOleConvertOLESTREAMToIStorageEx
+ #define SetDocumentBitStg _DllSetDocumentBitStg
+ #define GetDocumentBitStg _DllGetDocumentBitStg
+ #define WriteOleStg _DllWriteOleStg
+ #define ReadOleStg _DllReadOleStg
+ #define OleCreateFromFile _DllOleCreateFromFile
+ #define OleCreateLinkToFile _DllOleCreateLinkToFile
+ #define CreateDataCache _DllCreateDataCache
+ #define OleConvertIStorageToOLESTREAM _DllOleConvertIStorageToOLESTREAM
+ #define OleConvertOLESTREAMToIStorage _DllOleConvertOLESTREAMToIStorage
+ #define ReadFmtUserTypeStg _DllReadFmtUserTypeStg
+ #define WriteFmtUserTypeStg _DllWriteFmtUserTypeStg
+ #define OleFlushClipboard _DllOleFlushClipboard
+ #define OleIsCurrentClipboard _DllOleIsCurrentClipboard
+ #define OleTranslateAccelerator _DllOleTranslateAccelerator
+ #define OleDoAutoConvert _DllOleDoAutoConvert
+ #define OleGetAutoConvert _DllOleGetAutoConvert
+ #define OleSetAutoConvert _DllOleSetAutoConvert
+ #define GetConvertStg _DllGetConvertStg
+ #define SetConvertStg _DllSetConvertStg
+ #define CreateStreamOnHGlobal _DllCreateStreamOnHGlobal
+ #define GetHGlobalFromStream _DllGetHGlobalFromStream
+ #define OleDuplicateMedium _DllOleDuplicateMedium
+ #define OleSetContainedObject _DllOleSetContainedObject
+ #define OleNoteObjectVisible _DllOleNoteObjectVisible
+ #define OleCreateStaticFromData _DllOleCreateStaticFromData
+ #define OleRegGetUserType _DllOleRegGetUserType
+ #define OleRegGetMiscStatus _DllOleRegGetMiscStatus
+ #define OleRegEnumFormatEtc _DllOleRegEnumFormatEtc
+ #define OleRegEnumVerbs _DllOleRegEnumVerbs
+ #define OleGetEnumFormatEtc _DllOleGetEnumFormatEtc
+ #define OleSetEnumFormatEtc _DllOleSetEnumFormatEtc
+ #define OleRemoveEnumFormatEtc _DllOleRemoveEnumFormatEtc
+ #define OleSendLLE _DllOleSendLLE
+ #define OleSetInPlaceWindow _DllOleSetInPlaceWindow
+ #define OleUnSetInPlaceWindow _DllOleUnSetInPlaceWindow
+ #define OleClipWindow _DllOleClipWindow
+ #define OleClipWindows _DllOleClipWindows
+ #define OleInsertMenus _DllOleInsertMenus
+ #define OleHashMenuID _DllOleHashMenuID
+ #define OleUnhashMenuID _DllOleUnhashMenuID
+ #define OlePatchGetMHandle _DllOlePatchGetMHandle
+ #define OleUnpatchGetMHandle _DllOleUnpatchGetMHandle
+ #define OleAddMBarMenu _DllOleAddMBarMenu
+ #define OleSetInPlaceRects _DllOleSetInPlaceRects
+ #define OleMaskMouse _DllOleMaskMouse
+ #define OleMoveWindow _DllOleMoveWindow
+ #define OleSizeParentWindow _DllOleSizeParentWindow
+ #define OleSizeObjectWindow _DllOleSizeObjectWindow
+ #define OleDragParentWindow _DllOleDragParentWindow
+ #define OleDragObjectWindow _DllOleDragObjectWindow
+ #define OleGrowParentWindow _DllOleGrowParentWindow
+ #define OleGrowObjectWindow _DllOleGrowObjectWindow
+ #define OleNewMBar _DllOleNewMBar
+ #define OleDisposeMBar _DllOleDisposeMBar
+ #define OleProcessDdeAE _DllOleProcessDdeAE
+ #define OleProcessClipboardAE _DllOleProcessClipboardAE
+ #define InitializeClipboard _DllInitializeClipboard
+ #define UnInitializeClipboard _DllUnInitializeClipboard
+ #define OleIsClipboardFormatAvailable _DllOleIsClipboardFormatAvailable
+ #define OleGetClipboardData _DllOleGetClipboardData
+ #define OleSetClipboardData _DllOleSetClipboardData
+ #define OleEnumClipboardFormats _DllOleEnumClipboardFormats
+ #define StoreClap _DllStoreClap
+ #define OleCountClipboardFormats _DllOleCountClipboardFormats
+ #define OleCloseClipboard _DllOleCloseClipboard
+ #define OleEmptyClipboard _DllOleEmptyClipboard
+ #define OleSetClipboardEx _DllOleSetClipboardEx
+ #define OleZoomParentWindow _DllOleZoomParentWindow
+ #define OleSetParentRgns _DllOleSetParentRgns
+ #define CreateFileMonikerFSp _DllCreateFileMonikerFSp
+ #define OleCreateFromFSp _DllOleCreateFromFSp
+ #define OleCreateLinkToFSp _DllOleCreateLinkToFSp
+ #define OleGetCursor _DllOleGetCursor
+ #define OleSetCursor _DllOleSetCursor
+ #define OleUpdateCursor _DllOleUpdateCursor
+ #define GetClassFSp _DllGetClassFSp
+ #define ReadOle1FmtProgIDStgMac _DllReadOle1FmtProgIDStgMac
+ #define WriteOle1FmtProgIDStgMac _DllWriteOle1FmtProgIDStgMac
+ #define OleGetIconOfFile _DllOleGetIconOfFile
+ #define OleGetIconOfClass _DllOleGetIconOfClass
+ #define OleGetIconOfFSp _DllOleGetIconOfFSp
+ #define OlePictFromIconAndLabel _DllOlePictFromIconAndLabel
+ #define OleGetIconFromIconSuite _DllOleGetIconFromIconSuite
+ #define OleUIPictIconFree _DllOleUIPictIconFree
+ #define OleUIPictIconDraw _DllOleUIPictIconDraw
+ #define OleUIPictExtractIcon _DllOleUIPictExtractIcon
+ #define OleUIPictExtractLabel _DllOleUIPictExtractLabel
+ #define OleUIPictExtractIconSource _DllOleUIPictExtractIconSource
+ #define OleMetaFileToPict _DllOleMetaFileToPict
+ #define OleQueryCreateAll _DllOleQueryCreateAll
+ #define OleWhichGrowHandle _DllOleWhichGrowHandle
+ #define MkGetMacNetInfo _DllMkGetMacNetInfo
+#endif //ID_OLE_STAT_DEF
+#if !ID_OLE_STAT_COMPOBJ
+ #define CoBuildVersion _DllCoBuildVersion
+ #define CoInitialize _DllCoInitialize
+ #define CoUninitialize _DllCoUninitialize
+ #define CoGetMalloc _DllCoGetMalloc
+ #define CoRegisterClassObject _DllCoRegisterClassObject
+ #define CoRevokeClassObject _DllCoRevokeClassObject
+ #define CoGetClassObject _DllCoGetClassObject
+ #define CoMarshalInterface _DllCoMarshalInterface
+ #define CoUnmarshalInterface _DllCoUnmarshalInterface
+ #define CoLoadLibrary _DllCoLoadLibrary
+ #define CoFreeLibrary _DllCoFreeLibrary
+ #define CoFreeAllLibraries _DllCoFreeAllLibraries
+ #define CoCreateInstance _DllCoCreateInstance
+ #define StringFromIID _DllStringFromIID
+ #define CoDisconnectObject _DllCoDisconnectObject
+ #define CoReleaseMarshalData _DllCoReleaseMarshalData
+ #define CoFreeUnusedLibraries _DllCoFreeUnusedLibraries
+ #define IsEqualGUID _DllIsEqualGUID
+ #define StringFromCLSID _DllStringFromCLSID
+ #define CLSIDFromString _DllCLSIDFromString
+ #define RESULTFROMSCODE _DllRESULTFROMSCODE
+ #define GETSCODE _DllGETSCODE
+ #define CoRegisterMessageFilter _DllCoRegisterMessageFilter
+ #define CoIsHandlerConnected _DllCoIsHandlerConnected
+ #define CoMarshalHresult _DllCoMarshalHresult
+ #define CoUnmarshalHresult _DllCoUnmarshalHresult
+ #define CoGetCurrentProcess _DllCoGetCurrentProcess
+ #define CoIsOle1Class _DllCoIsOle1Class
+ #define CLSIDFromProgID _DllCLSIDFromProgID
+ #define ProgIDFromCLSID _DllProgIDFromCLSID
+ #define CoLockObjectExternal _DllCoLockObjectExternal
+ #define CoGetTreatAsClass _DllCoGetTreatAsClass
+ #define CoTreatAsClass _DllCoTreatAsClass
+ #define CoGetStandardMarshal _DllCoGetStandardMarshal
+ #define PropagateResult _DllPropagateResult
+ #define IIDFromString _DllIIDFromString
+ #define CoCreateStandardMalloc _DllCoCreateStandardMalloc
+ #define CoCreateGuid _DllCoCreateGuid
+ #define StringFromGUID2 _DllStringFromGUID2
+ #define CoGetClassExt _DllCoGetClassExt
+ #define Ole1ClassFromCLSID2 _DllOle1ClassFromCLSID2
+ #define CLSIDFromOle1Class _DllCLSIDFromOle1Class
+ #define CoOpenClassKey _DllCoOpenClassKey
+ #define GUIDFromString _DllGUIDFromString
+ #define CoFileTimeNow _DllCoFileTimeNow
+ #define RemAllocOID _DllRemAllocOID
+ #define RemFreeOID _DllRemFreeOID
+ #define RemCreateRemoteHandler _DllRemCreateRemoteHandler
+ #define RemConnectToObject _DllRemConnectToObject
+ #define RemGetInfoForCid _DllRemGetInfoForCid
+ #define LrpcCall _DllLrpcCall
+ #define LrpcDispatch _DllLrpcDispatch
+ #define LrpcRegisterMonitor _DllLrpcRegisterMonitor
+ #define LrpcRevokeMonitor _DllLrpcRevokeMonitor
+ #define LrpcGetThreadWindow _DllLrpcGetThreadWindow
+ #define LookupEtask _DllLookupEtask
+ #define SetEtask _DllSetEtask
+ #define RemLookupSHUnk _DllRemLookupSHUnk
+ #define CoMemctxOf _DllCoMemctxOf
+ #define CoMemAlloc _DllCoMemAlloc
+ #define CoMemFree _DllCoMemFree
+ #define CoRunModalLoop _DllCoRunModalLoop
+ #define CoHandleIncomingCall _DllCoHandleIncomingCall
+ #define CoSetAckState _DllCoSetAckState
+ #define OleProcessLrpcAE _DllOleProcessLrpcAE
+ #define CoFileTimeToMacDateTime _DllCoFileTimeToMacDateTime
+ #define CoMacDateTimeToFileTime _DllCoMacDateTimeToFileTime
+ #define InternalCoInitialize _DllInternalCoInitialize
+ #define CoHandlePendingMessage _DllCoHandlePendingMessage
+#endif //ID_OLE_STAT_COMPOBJ
+#if !ID_OLE_STAT_PROXY
+ #define DllGetClassObject _DllDllGetClassObject
+#endif //ID_OLE_STAT_PROXY
+#if !ID_OLE_STAT_OLE2NLS
+ #define CompareStringA _DllCompareStringA
+ #define LCMapStringA _DllLCMapStringA
+ #define GetLocaleInfoA _DllGetLocaleInfoA
+ #define GetStringTypeA _DllGetStringTypeA
+ #define GetSystemDefaultLangID _DllGetSystemDefaultLangID
+ #define GetUserDefaultLangID _DllGetUserDefaultLangID
+ #define GetSystemDefaultLCID _DllGetSystemDefaultLCID
+ #define GetUserDefaultLCID _DllGetUserDefaultLCID
+#endif //ID_OLE_STAT_OLE2NLS
+#endif //ID_MUNGE_DLL_NAMES
diff --git a/private/oleauto/src/dispatch/nlsapi.c b/private/oleauto/src/dispatch/nlsapi.c
new file mode 100644
index 000000000..17b16003b
--- /dev/null
+++ b/private/oleauto/src/dispatch/nlsapi.c
@@ -0,0 +1,3148 @@
+/***
+*nlsapi.c - National language support functions.
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file contains a partial implementation of the NLS API
+* from Win32 for the Win16/Mac platform platform.
+*
+*Revision History:
+*
+* [00] 12-Nov-92 petergo: Created.
+* [01] 14-Apr-93 petergo: Major revisions for performance.
+* [02] 01-Sep-93 bradlo: Major revisions to bring in line w/NT.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#if OE_WIN16
+# define FASTCALL /* __fastcall disable because of a c8 compiler bug */
+# define SSBASE __based(__segname("_STACK")) /* For stack based pointers */
+#elif OE_MAC
+ // REVIEW: is this definition of lstrlen correct?
+# define lstrlen strlen
+# define FASTCALL
+# define SSBASE
+typedef int BOOL;
+# define TRUE 1
+# define FALSE 0
+ // REVIEW: can we do something better with the following?
+# define LogParamError(A,B,C)
+#endif
+
+ASSERTDATA
+
+#include "nlsintrn.h"
+#ifdef FE_DBCS
+//# include <stdlib.h>
+# include "nlsdbcs.h"
+#endif
+
+
+// no C run-time library.
+#pragma intrinsic(MEMCPY, MEMCMP, MEMSET, STRCPY, STRLEN)
+
+
+#if OE_WIN
+# define NLSDAT(L, R, CCHICOUNTRY, SZICOUNTRY, CCHSABBREVLANG, SZSABBREVLANG) \
+ {0x ## L, \
+ {CCHICOUNTRY, SZICOUNTRY}, \
+ {CCHSABBREVLANG, SZSABBREVLANG}, \
+ g_rglcinfo ## L, (STRINFO FAR*)&g_strinfo ## L }
+#else
+# define NLSDAT(L, R, CCHICOUNTRY, SZICOUNTRY, CCHSABBREVLANG, SZSABBREVLANG) \
+ {0x ## L, R, LoadNlsInfo ## L, NULL }
+#endif
+
+
+#if OE_MAC // we now have to write to this...
+NLSDATA g_rgnls[] =
+#else
+static NLSDATA NEARDATA g_rgnls[] =
+#endif
+{
+ NLSDAT(0403, 8, 2, "34", 3, "CAT"), // UNDONE: verify MAC region code
+#ifdef FE_DBCS
+ NLSDAT(0404, 53, 3,"886", 3, "CHT"),
+#endif
+ NLSDAT(0405, -1, 2, "42", 3, "CSY"),
+ NLSDAT(0406, 9, 2, "45", 3, "DAN"),
+ NLSDAT(0407, 3, 2, "49", 3, "DEU"),
+ NLSDAT(0408, 20, 2, "30", 3, "ELL"),
+ NLSDAT(0409, 0, 1, "1", 3, "ENU"),
+ NLSDAT(040a, 8, 2, "34", 3, "ESP"),
+ NLSDAT(040b, 17, 3,"358", 3, "FIN"),
+ NLSDAT(040c, 1, 2, "33", 3, "FRA"),
+ NLSDAT(040e, 43, 2, "36", 3, "HUN"),
+ NLSDAT(040f, -1, 3,"354", 3, "ISL"), //UNDONE: change region = 21
+ // once CP ? is available
+ NLSDAT(0410, 4, 2, "39", 3, "ITA"),
+#ifdef FE_DBCS
+ NLSDAT(0411, 14, 2, "81", 3, "JPN"),
+ NLSDAT(0412, 51, 2, "82", 3, "KOR"),
+#endif
+ NLSDAT(0413, 5, 2, "31", 3, "NLD"),
+ NLSDAT(0414, 12, 2, "47", 3, "NOR"),
+ NLSDAT(0415, 42, 2, "48", 3, "PLK"),
+ NLSDAT(0816, 10, 3,"351", 3, "PTG"), // Mac: VerPort is 0816
+ NLSDAT(0416, 10, 2, "55", 3, "PTB"),
+ NLSDAT(0419, 49, 1, "7", 3, "RUS"),
+ NLSDAT(041b, -1, 2, "42", 3, "SKY"),
+ NLSDAT(041d, 7, 2, "46", 3, "SVE"),
+ NLSDAT(041f, 24, 2, "90", 3, "TRK"),
+#ifdef FE_DBCS
+ NLSDAT(0804, 52, 2, "86", 3, "CHS"),
+#endif
+ NLSDAT(0807, 19, 2, "41", 3, "DES"),
+ NLSDAT(0809, 2, 2, "44", 3, "ENG"),
+ NLSDAT(080a, -1, 2, "52", 3, "ESM"),
+ NLSDAT(080c, 6, 2, "32", 3, "FRB"),
+ NLSDAT(0810, -1, 2, "41", 3, "ITS"),
+ NLSDAT(0813, -1, 2, "32", 3, "NLB"),
+ NLSDAT(0814, 12, 2, "47", 3, "NON"),
+ NLSDAT(0c07, -1, 2, "43", 3, "DEA"),
+ NLSDAT(0c09, 15, 2, "61", 3, "ENA"),
+ NLSDAT(0c0a, -1, 2, "34", 3, "ESN"),
+ NLSDAT(0c0c, 11, 1, "2", 3, "FRC"),
+ NLSDAT(1009, -1, 1, "2", 3, "ENC"),
+ NLSDAT(100c, 18, 2, "41", 3, "FRS"),
+ NLSDAT(1409, -1, 2, "64", 3, "ENZ"),
+ NLSDAT(1809, 50, 3,"353", 3, "ENI"),
+
+ NLSDAT(040d, -1, 3,"972", 3, "HEB"), // UNDONE: verify MAC region code
+ NLSDAT(0401, -1, 3,"966", 3, "ARA"), // UNDONE: verify MAC region code
+ NLSDAT(0801, -1, 3,"964", 3, "ARI"), // UNDONE: verify MAC region code
+ NLSDAT(0c01, -1, 2, "20", 3, "ARE"), // UNDONE: verify MAC region code
+ NLSDAT(1001, -1, 3,"218", 3, "ARL"), // UNDONE: verify MAC region code
+ NLSDAT(1401, -1, 3,"213", 3, "ARG"), // UNDONE: verify MAC region code
+ NLSDAT(1801, -1, 3,"212", 3, "ARM"), // UNDONE: verify MAC region code
+ NLSDAT(1c01, -1, 3,"216", 3, "ART"), // UNDONE: verify MAC region code
+ NLSDAT(2001, -1, 3,"968", 3, "ARO"), // UNDONE: verify MAC region code
+ NLSDAT(2401, -1, 3,"967", 3, "ARY"), // UNDONE: verify MAC region code
+ NLSDAT(2801, -1, 3,"963", 3, "ARS"), // UNDONE: verify MAC region code
+ NLSDAT(2c01, -1, 3,"962", 3, "ARJ"), // UNDONE: verify MAC region code
+ NLSDAT(3001, -1, 3,"961", 3, "ARB"), // UNDONE: verify MAC region code
+ NLSDAT(3401, -1, 3,"965", 3, "ARK"), // UNDONE: verify MAC region code
+ NLSDAT(3801, -1, 3,"971", 3, "ARU"), // UNDONE: verify MAC region code
+ NLSDAT(3c01, -1, 3,"973", 3, "ARH"), // UNDONE: verify MAC region code
+ NLSDAT(4001, -1, 3,"974", 3, "ARQ"), // UNDONE: verify MAC region code
+ NLSDAT(0429, -1, 3,"981", 3, "FAR"), // UNDONE: verify MAC region code
+
+};
+#undef NLSDAT
+
+// cached nls info pointer
+#ifdef _MAC
+NLSDATA NEARDATA *g_pnls = NULL;
+STRINFO NEARDATA FAR* g_pstrinfo = NULL;
+#else
+NLSDATA * NEARDATA g_pnls = NULL;
+STRINFO FAR* NEARDATA g_pstrinfo = NULL;
+#endif
+
+static LCID NEARDATA g_lcidSystem = (LCID)-1; // current system lcid.
+
+// This is the "current" LCID; i.e., the LCID we have cached
+// information for. This is not necessarily the system default locale.
+static LCID NEARDATA g_lcidCurrent = (LCID)-1;
+
+#if OE_WIN // {
+
+// Windows specific globals
+
+HINSTANCE g_hinstDLL = (HINSTANCE)NULL; // Instance handle
+
+// Win.INI section with INTL setting.
+static char NEARDATA g_szIntl[] = "intl";
+
+// notification window.
+static HWND NEARDATA g_hwndNotify;
+
+// task of notification window.
+static HTASK NEARDATA g_htaskNotify;
+
+static LCID PASCAL LcidFromWinIni(void);
+
+// Cache characters needed for string<->number conversions
+static char g_chDecimal;
+static char g_chThousand;
+static char g_chILZERO;
+
+//REVIEW: caching only 10 chars of the currency symbol.
+//REVIEW: the control panel allows you to enter only 5.
+static char g_szCurrency[11];
+
+// Callback function into ole2disp.dll when WIN.INI changes
+static FARPROC g_pfnCacheNotifyProc;
+
+#endif // }
+
+
+#if OE_WIN /* { */
+
+/***
+*LibMain - library initialization
+*Purpose:
+* Called when the DLL is loaded.
+*
+*Entry:
+* hinst - instance handle
+* wDataSeg - data segment
+* cbHeapSize - size of default heap
+* lpszCmdLine - command line
+*
+*Exit:
+* returns 1 on success, 0 on failure.
+*
+***********************************************************************/
+
+int FAR PASCAL EXPORT
+LibMain(
+ HINSTANCE hinst,
+ unsigned short wDataSeg,
+ unsigned short cbHeapSize,
+ char FAR* lpszCmdLine)
+{
+ g_hinstDLL = hinst;
+
+ return 1; // Success.
+}
+
+/***
+*NotifyWindowProc
+*Purpose:
+* window proc for the window that we get Win.INI change notifications
+* from
+*
+***********************************************************************/
+LRESULT CALLBACK EXPORT
+NotifyWindowProc(HWND hwnd, unsigned int uMsg, WPARAM wp, LPARAM lp)
+{
+ switch (uMsg) {
+ case WM_CREATE:
+ case WM_WININICHANGE:
+ g_lcidSystem = LcidFromWinIni();
+ NotifyNLSInfoChanged();
+ return 0;
+ default:
+ return DefWindowProc(hwnd, uMsg, wp, lp);
+ }
+}
+
+/***
+*void WEP(BOOL)
+*
+*Purpose:
+* Handle exit notification from Windows.
+* This routine is called by Windows when the library is freed
+* by its last client.
+*
+* NOTE: other one time termination occurs in dtors for global objects
+*
+* REVIEW: this should be put in its own fixed segment to prevent a crash
+* when reloading this segment during shutdown. This may not be a problem
+* on Win31 and if we require Win31.
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value =
+*
+***********************************************************************/
+void FAR PASCAL EXPORT
+WEP(BOOL fSystemExit)
+{
+ if (fSystemExit == WEP_FREE_DLL) {
+ // Destroy the notification window.
+ if (g_hwndNotify
+ && IsWindow(g_hwndNotify)
+ && GetWindowWord(g_hwndNotify, GWW_HINSTANCE) == g_hinstDLL)
+ {
+ DestroyWindow(g_hwndNotify);
+ }
+ }
+}
+
+#endif /* } */
+
+#ifdef _MAC /* { */
+
+/***
+*PRIVATE LCID LcidFromIntl0
+*Purpose:
+* Determines the current system LCID by reading looking at
+* the region code in the intl0 resource.
+*
+* On the mac we scan our nlsdata structs for the entry with
+* a region code that matches the region code of the systems
+* intl0 resource, and return the lcid of that entry.
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = LCID. The current system locale ID.
+*
+***********************************************************************/
+PRIVATE_(LCID)
+LcidFromIntl0()
+{
+ Intl0Hndl intl0;
+ unsigned char region;
+ NLSDATA *pnls, *pnlsEnd;
+
+ intl0 = (Intl0Hndl)IUGetIntl(0);
+ region = ((*intl0)->intl0Vers >> 8) & 0xff;
+
+ pnlsEnd = &g_rgnls[DIM(g_rgnls)];
+ for(pnls = g_rgnls; pnls < pnlsEnd; ++pnls){
+ // (-1) means there is no mac region corresponding to this lcid
+ if(pnls->region == -1)
+ continue;
+ if(pnls->region == region)
+ return pnls->lcid;
+ }
+
+ return 0; // unknown
+}
+
+#else /* }{ */
+
+/***
+*LcidFromWinIni - determine current system LCID
+*Purpose:
+* Determines the current system LCID by reading the intl section
+* of WIN.INI.
+*
+* The mapping is made by looking at the language and country settings;
+* the language setting is given precidence if they conflict.
+*
+*Entry:
+* None.
+*
+*Exit:
+* Returns the system LCID. If WIN.INI information could not be
+* read, or the country/language information did not match any of the
+* locales in the resource, then 0 is returned.
+*
+***********************************************************************/
+
+PRIVATE_(LCID)
+LcidFromWinIni()
+{
+ LCID lcid; // Best match found so far.
+ char szCountry[6]; // Country code
+ char szLangAbbrev[4]; // Language abbreviation.
+#if OE_WIN
+ char szDecimal[2];
+#endif // OE_WIN
+ LCINFO FAR* plcinfo;
+ NLSDATA *pnls, *pnlsEnd;
+ int cchCountry, cchLangAbbrev;
+ int fLangMatch, fCountryMatch, fPartLangMatch;
+
+static char NEARDATA szLastSLang[4]; // last read sLanguage
+static char NEARDATA szLastICountry[6]; // last read iCountry
+static LCID NEARDATA lcidLastCur = (LCID)-1; // last known system LCID
+
+ enum {
+ NOMATCH,
+ PARTLANG,
+ FULLLANG,
+ PARTLANGCOUNTRY,
+ FULLLANGCOUNTRY
+ } matchBest; // kind of best match so far
+
+ lcid = 0; // Keeps track of best match so far.
+ matchBest = NOMATCH;
+
+#if OE_WIN
+ if ( GetProfileString(g_szIntl, "sDecimal", "", szDecimal, sizeof(szDecimal)) > 0 )
+ g_chDecimal = szDecimal[0];
+ else
+ g_chDecimal = '\0';
+
+ if ( GetProfileString(g_szIntl, "sThousand", "", szDecimal, sizeof(szDecimal)) > 0 )
+ g_chThousand = szDecimal[0];
+ else
+ g_chThousand = '\0';
+
+ if ( GetProfileString(g_szIntl, "iLzero", "", szDecimal, sizeof(szDecimal)) > 0 )
+ g_chILZERO = szDecimal[0];
+ else
+ g_chILZERO = '\0';
+
+ if ( GetProfileString(g_szIntl, "sCurrency", "", g_szCurrency, sizeof(g_szCurrency)) <= 0 )
+ g_szCurrency[0] = '\0';
+#endif // OE_WIN
+
+ // Get language code and country code to match against stored values.
+ cchLangAbbrev = GetProfileString(g_szIntl, "sLanguage", "",
+ szLangAbbrev, sizeof(szLangAbbrev));
+ if (cchLangAbbrev == 0)
+ return lcid;
+
+ AnsiUpper(szLangAbbrev);
+
+ // A few Win3.1 abbreviations don't match at all the "correct"
+ // ones. Translate them to match.
+ if (lstrcmpi(szLangAbbrev, "cro") == 0)
+ STRCPY(szLangAbbrev, "SHL"); // Croation.
+ if (lstrcmpi(szLangAbbrev, "cyr") == 0)
+ STRCPY(szLangAbbrev, "RUS"); // Russian.
+ if (lstrcmpi(szLangAbbrev, "grk") == 0)
+ STRCPY(szLangAbbrev, "ELL"); // Greek
+
+ cchCountry = GetProfileString(g_szIntl, "iCountry", "",
+ szCountry, sizeof(szCountry));
+ if (cchCountry == 0)
+ return lcid;
+
+ // Check if they match the last read ones, and if so, return
+ // last read lcid. This saves much extra processing.
+ if (lcidLastCur != (LCID) -1) {
+ if (MEMCMP(szLangAbbrev, szLastSLang, cchLangAbbrev) == 0 &&
+ MEMCMP(szCountry, szLastICountry, cchCountry) == 0)
+ return lcidLastCur;
+ }
+
+ // Next, try to match against stored values by going through values
+ // in order.
+ pnlsEnd = &g_rgnls[DIM(g_rgnls)];
+ for(pnls = g_rgnls; pnls < pnlsEnd; ++pnls){
+
+ fLangMatch = fPartLangMatch = fCountryMatch = FALSE;
+
+ // Check for language match.
+ plcinfo = &pnls->lcinfoSABBREVLANGNAME;
+#ifdef _DEBUG
+ // make sure that the local copy of the SABBREVLANGNAME
+ // matches that in the locale's lcinfo data.
+ { LCINFO FAR* plcinfoTmp;
+ plcinfoTmp = &pnls->prglcinfo[LOCALE_SABBREVLANGNAME];
+ ASSERT(plcinfo->cch == plcinfoTmp->cch);
+ ASSERT(MEMCMP(plcinfo->prgb, plcinfoTmp->prgb, plcinfo->cch) == 0);
+ }
+#endif
+ if (cchLangAbbrev == (int)plcinfo->cch
+ && MEMCMP(plcinfo->prgb, szLangAbbrev, cchLangAbbrev) == 0)
+ {
+ // Language match.
+ fLangMatch = TRUE;
+ }
+ else if (MEMCMP(plcinfo->prgb, szLangAbbrev, 2) == 0) {
+ // Partial (2-letter) language match
+ fPartLangMatch = TRUE;
+ }
+
+ // Check for country match.
+ plcinfo = &pnls->lcinfoICOUNTRY;
+#ifdef _DEBUG
+ // make sure that the local copy of the ICOUNTRY
+ // matches that in the locale's lcinfo data.
+ { LCINFO FAR* plcinfoTmp;
+ plcinfoTmp = &pnls->prglcinfo[LOCALE_ICOUNTRY];
+ ASSERT(plcinfo->cch == plcinfoTmp->cch);
+ ASSERT(MEMCMP(plcinfo->prgb, plcinfoTmp->prgb, plcinfo->cch) == 0);
+ }
+#endif
+ if (cchCountry == (int)plcinfo->cch
+ && MEMCMP(plcinfo->prgb, szCountry, cchCountry) == 0)
+ {
+ // Country match.
+ fCountryMatch = TRUE;
+ }
+
+ // Check if this locale matches better than previous best match.
+ if (fLangMatch && fCountryMatch && matchBest < FULLLANGCOUNTRY) {
+ matchBest = FULLLANGCOUNTRY;
+ lcid = pnls->lcid;
+ }
+ else if (fPartLangMatch && fCountryMatch && matchBest < PARTLANGCOUNTRY) {
+ matchBest = PARTLANGCOUNTRY;
+ lcid = pnls->lcid;
+ }
+ else if (fLangMatch && matchBest < FULLLANG) {
+ matchBest = FULLLANG;
+ lcid = pnls->lcid;
+ }
+ else if (fPartLangMatch && matchBest < PARTLANG) {
+ matchBest = PARTLANG;
+ lcid = pnls->lcid;
+ }
+ }
+
+ return lcid; // Return best matching LCID found.
+}
+
+#endif /* } */
+
+/***
+*SystemLcid
+*Purpose:
+* Get the system LCID
+*
+*Entry:
+* None.
+*
+*Exit:
+* Returns the system LCID. I
+*
+***********************************************************************/
+PRIVATE_(LCID)
+SystemLcid()
+{
+#ifdef _MAC /* { */
+
+ if(g_lcidSystem != (LCID)-1)
+ return g_lcidSystem;
+
+ return g_lcidSystem = LcidFromIntl0();
+
+#else /* }{ */
+
+ // When the client process that we created the notification window
+ // with goes away, Windows will kill the notification window too.
+ // So we must test to see if it is still there before using the
+ // cached value of g_lcidSystem. Note that window handles can be
+ // reused; hence the test of the hinstance.
+
+ if (g_hwndNotify && IsWindow(g_hwndNotify) &&
+ GetWindowWord(g_hwndNotify, GWW_HINSTANCE) == g_hinstDLL)
+ {
+ // The notification window is up and running. The cached
+ // LCID must be correct.
+ return g_lcidSystem;
+ }
+ else {
+ WNDCLASS wc;
+ char FAR* szClassName = "OLE2NLS";
+
+ // register window class.
+ if (! GetClassInfo(g_hinstDLL, szClassName, &wc)) {
+ wc.style = 0;
+ wc.lpfnWndProc = NotifyWindowProc;
+ wc.cbClsExtra = 0;
+ wc.cbWndExtra = 0;
+ wc.hInstance = g_hinstDLL;
+ wc.hIcon = 0;
+ wc.hCursor = 0;
+ wc.hbrBackground = 0;
+ wc.lpszMenuName = 0;
+ wc.lpszClassName = szClassName;
+ if (! RegisterClass(&wc))
+ return LcidFromWinIni();
+ }
+
+ g_hwndNotify = CreateWindow(
+ "OLE2NLS", NULL, WS_OVERLAPPED,
+ 0, 0, 0, 0,
+ (HWND) NULL, (HMENU) NULL,
+ g_hinstDLL, NULL);
+ if (! g_hwndNotify)
+ return LcidFromWinIni();
+ else
+ return g_lcidSystem; // updated by WM_CREATE processing.
+ }
+
+#endif /* } */
+}
+
+#ifdef _MAC /* { */
+
+static int
+StringNCopyQuote(char *szDst, char *szSrc, int max)
+{
+ int n;
+
+ if (*szSrc == '\0')
+ return 0;
+
+ n = 0;
+ *szDst++ = '\'';
+ while(*szSrc != '\0'){
+ *szDst++ = *szSrc++;
+ if(++n == max)
+ break;
+ }
+ *szDst++ = '\'';
+ return n+2;
+}
+
+static int
+StringNCopy(char *szDst, char *szSrc, int max)
+{
+ int n;
+
+ n = 0;
+ while(*szSrc != '\0'){
+ *szDst++ = *szSrc++;
+ if(++n == max)
+ return n;
+ }
+ *szDst = '\0';
+ return n;
+}
+
+
+/***
+*PRIVATE int LongDateFmtFromIntl1
+*Purpose:
+* Construct a long date format string from the information in
+* the intl1 resource. Because different versions of the MacOS
+* have different flavors of info (latter versions have additional
+* info) in the intl1 resource, we build this format string in
+* a two step process. First we build a template that describes
+* the components of this format string - the purpose of this
+* template is to factor out all the OS version specific info.
+* And then we use the template to build the actual long date
+* format string.
+*
+*Entry:
+* cchMax = the max allowable size for the format string.
+*
+*Exit:
+* return value = int, length of the format string (Not including
+* the Null terminator!)
+*
+* A return value of 0 means the string is not available for some reason.
+*
+* szBuf = the long date format string
+*
+***********************************************************************/
+static int
+LongDateFmtFromIntl1(char *szBuf, int cchMax)
+{
+ int i, j, len;
+ Intl1Hndl intl1;
+ unsigned char lngDateFmt, suppressDay;
+ char *pbuf, *pch, *szTmpl, szTmplBuf[5];
+ int fSupDay, fSupWeek, fSupMonth, fSupYear;
+
+// the following structure maps long date format bits to
+// template string characters.
+static rgchTmpl[] = {
+ 'D' // longDay = 0 (day of month)
+ , 'd' // longWeek = 1 (day of week - day name)
+ , 'M' // longMonth = 2 (month of the year)
+ , 'y' // longYear = 3 (year)
+};
+
+ szTmpl = szTmplBuf;
+
+ intl1 = (Intl1Hndl)IUGetIntl(1);
+ lngDateFmt = (*intl1)->lngDateFmt;
+ suppressDay = (*intl1)->suppressDay;
+
+ // build the format string template
+ switch(lngDateFmt){
+ case 0: // day_name-day-month-year
+ szTmpl = "dDMy";
+ break;
+ case 255: // day_name-month-day-year
+ szTmpl = "dMDy";
+ break;
+ default:
+ // for all other values, the field is interpreted as 4
+ // bitfields of 2 bits easch, specifying in textual order
+ // the individual components of the long date.
+ for(i = 0; i < 4; ++i)
+ szTmpl[i] = rgchTmpl[(lngDateFmt >> (i*2)) & 0x3];
+ szTmpl[4] = '\0';
+ break;
+ }
+ ASSERT(STRLEN(szTmpl) == 4);
+
+ switch(suppressDay){
+ case 0: // dont suppress name of day
+ case 255: // suppress name of day
+ fSupDay = FALSE;
+ fSupWeek = (suppressDay == 255);
+ fSupMonth = FALSE;
+ fSupYear = FALSE;
+ break;
+ default:
+ // all other values are interpreted as a bitmask specifying
+ // suppression of the individual components of the long date format
+ fSupDay = (suppressDay & supDay);
+ fSupWeek = (suppressDay & supWeek);
+ fSupMonth = (suppressDay & supMonth);
+ fSupYear = (suppressDay & supYear);
+ break;
+ }
+
+ // now use this template to build the long date format string
+
+ pbuf = szBuf;
+ pbuf += StringNCopyQuote(pbuf, (*intl1)->st0, 4);
+
+ for(i = 0; i < 4; ++i){
+ switch(szTmpl[i]){
+ case 'D': // day of month - "d" or "dd"
+ if(fSupDay)
+ continue;
+ *pbuf++ = 'd';
+ if((*intl1)->dayLeading0 == 255)
+ *pbuf++ = 'd';
+ break;
+ case 'd': // day of week - day name "dddd"
+ if(fSupWeek)
+ continue;
+ goto LCom;
+ case 'M': // month of year - "MMMM"
+ if(fSupMonth)
+ continue;
+ goto LCom;
+ case 'y': // year - "yyyy"
+ if(fSupYear)
+ continue;
+ goto LCom;
+LCom:;
+ for(j = 0; j < 4; ++j)
+ *pbuf++ = szTmpl[i];
+ break;
+ default:
+ ASSERT(UNREACHED);
+ break;
+ }
+
+ // determine which separator string to append
+ switch(i){
+ case 0: pch = (*intl1)->st1; break;
+ case 1: pch = (*intl1)->st2; break;
+ case 2: pch = (*intl1)->st3; break;
+ case 3: pch = (*intl1)->st4; break;
+ default:
+ ASSERT(UNREACHED);
+ break;
+ }
+ pbuf += StringNCopyQuote(pbuf, pch, 4);
+ }
+
+ *pbuf = '\0';
+ len = (pbuf - szBuf);
+ ASSERT(len < cchMax);
+ return len;
+}
+
+/***
+*GetIntlInfo - get a piece of locale info from the intl0 resource.
+*Purpose:
+* Retrieves a piece of locale info from intl0/1 resources. If
+* the requested type of information is not in intl resource 0
+* is returned.
+*
+*Entry:
+* lctype - type of locale info
+* szDest - buffer to place in
+* cchMax - size of buffer, or 0 to get required size of buffer.
+*
+*Exit:
+* returns number of characters copied (including NUL), or 0
+* if not enough room or other error.
+*
+* returns -1 if lctype is not a valid type of info to read
+* from intl0.
+*
+* returns size needed if cchMax was 0
+*
+***********************************************************************/
+
+static int
+GetIntlInfo(LCTYPE lctype, char FAR* szDest, int cchMax)
+{
+ int len;
+ char *pch;
+ char *pbuf;
+ char *szFmt;
+ char rgchBuf[100]; // > max size for any entry
+ Intl0Hndl intl0;
+
+ pbuf = rgchBuf;
+ intl0 = (Intl0Hndl)IUGetIntl(0);
+
+ switch((unsigned short)lctype){
+ // short date format ordering
+ // '0' - month-day-year
+ // '1' - day-month-year
+ // '2' - year-month-day
+ //
+ case LOCALE_IDATE:
+ switch((*intl0)->dateOrder){
+ case mdy: *pbuf = '0'; break;
+ case dmy: *pbuf = '1'; break;
+ case ymd: *pbuf = '2'; break;
+ default: // myd, dym, ydm
+ return -1;
+ }
+ pbuf++;
+ break;
+
+ // time format spec ('0'=12 hr, '1'=24hr)
+ case LOCALE_ITIME:
+ *pbuf++ = (((*intl0)->timeCycle) == 0) ? '1' : '0';
+ break;
+
+ // use leading zeros in time fields?
+ case LOCALE_ITLZERO:
+ *pbuf++ = ((*intl0)->timeFmt & hrLeadingZ) ? '1' : '0';
+ break;
+
+ // positive currency mode
+ // '0' - prefix, no separation
+ // '1' - suffix, no separation
+ // '2' - prefix, 1 char separation
+ // '3' - suffix, 1 char separation
+ //
+ case LOCALE_ICURRENCY:
+ // mac does not support space between currency symbol and the number
+ *pbuf++ = ((*intl0)->currFmt & currSymLead) ? '0' : '1';
+ break;
+
+ // Negative currency mode (most of these dont occur on the mac)
+ //
+ // '0' - ($1.1)
+ // '1' - -$1.1
+ // '2' - $-1.1
+ // '3' - $1.1-
+ // '4' - (1.1$)
+ // '5' - -1.1$
+ // '6' - 1.1-$
+ // '7' - 1.1$-
+ // '8' - -1.1 $ (space before $)
+ // '9' - -$ 1.1 (space after $)
+ // '10'- 1.1 $- (space before $)
+ //
+ case LOCALE_INEGCURR:
+ if((*intl0)->currFmt & currSymLead){
+ *pbuf++ = ((*intl0)->currFmt & currNegSym) ? '1' : '0';
+ }else{
+ *pbuf++ = ((*intl0)->currFmt & currNegSym) ? '5' : '4';
+ }
+ break;
+
+ // Leading zeros in decimal fields?
+ //
+ // '0' - use no leading zeros
+ // '1' - use leading zeros
+ //
+ case LOCALE_ILZERO:
+ // Note: Inside Mac Volume 1 says: "you can also apply the
+ // currency format's leading and trailing zero indicators to
+ // the number format if desired"
+ *pbuf++ = ((*intl0)->currFmt & currLeadingZ) ? '1' : '0';
+ break;
+
+ // System of measurement
+ //
+ // '0' - metric system (S.I.)
+ // '1' - U.S system of measurement
+ //
+ case LOCALE_IMEASURE:
+ *pbuf++ = (((*intl0)->metricSys) == 255) ? '0' : '1';
+ break;
+
+ // string for the Am designator
+ case LOCALE_S1159:
+ pch = (*intl0)->mornStr;
+ goto LAmpmStr;
+
+ // string for the Pm designator
+ case LOCALE_S2359:
+ pch = (*intl0)->eveStr;
+ goto LAmpmStr;
+
+LAmpmStr:;
+ len = 4;
+ if(*pch == ' '){ // skip leading space
+ len = 3; ++pch;
+ }
+ pbuf += StringNCopy(pbuf, pch, len);
+ break;
+
+ // string used as the local monetary symbol
+ case LOCALE_SCURRENCY:
+ *pbuf++ = (*intl0)->currSym1;
+ *pbuf++ = (*intl0)->currSym2;
+ *pbuf++ = (*intl0)->currSym3;
+ break;
+
+ // The character used as separator between
+ // groups of digits left of the decimal.
+ case LOCALE_STHOUSAND:
+ *pbuf++ = (*intl0)->thousSep;
+ break;
+
+ // The character used as the decimal separator
+ case LOCALE_SDECIMAL:
+ *pbuf++ = (*intl0)->decimalPt;
+ break;
+
+ // The character used as the date separator
+ case LOCALE_SDATE:
+ *pbuf++ = (*intl0)->dateSep;
+ break;
+
+ // The character used as the time separator
+ case LOCALE_STIME:
+ *pbuf++ = (*intl0)->timeSep;
+ break;
+
+ // The character used to separate list items
+ case LOCALE_SLIST:
+ *pbuf++ = (*intl0)->listSep;
+ break;
+
+ // The short and long date format strings use the following
+ // date format characters,
+ //
+ // M month, 1-12
+ // MM month with leading zero, 01-12
+ // MMMM month name
+ // d day, 1-31
+ // dd day with leading zero, 01-31
+ // dddd day of week name
+ // yy year as 2 digit number, 00-99 (if current century)
+ // yyyy year as 4 digit number, 100-9999
+ //
+ case LOCALE_SSHORTDATE:
+ switch((*intl0)->dateOrder){
+ case mdy: szFmt = "mdy"; break;
+ case dmy: szFmt = "dmy"; break;
+ case ymd: szFmt = "ymd"; break;
+ default:
+ return -1;
+ }
+ while(1){
+ switch(*szFmt){
+ case 'm':
+ *pbuf++ = 'M';
+ if((*intl0)->shrtDateFmt & mntLdingZ)
+ *pbuf++ = 'M';
+ break;
+ case 'd':
+ *pbuf++ = 'd';
+ if((*intl0)->shrtDateFmt & dayLdingZ)
+ *pbuf++ = 'd';
+ break;
+ case 'y':
+ *pbuf++ = 'y'; *pbuf++ = 'y';
+ if((*intl0)->shrtDateFmt & century){
+ *pbuf++ = 'y'; *pbuf++ = 'y';
+ }
+ break;
+ default:
+ ASSERT(UNREACHED);
+ }
+ if(*++szFmt == '\0')
+ break;
+ *pbuf++ = (*intl0)->dateSep;
+ }
+ break;
+
+ case LOCALE_SLONGDATE:
+ len = LongDateFmtFromIntl1(pbuf, sizeof(rgchBuf));
+ goto LHaveLength;
+
+ // number of fractional digits for the local monetary format
+ case LOCALE_ICURRDIGITS:
+ // The mac does not have an equiv of this. It does have a
+ // flag indicating if the currency representation should
+ // have a trailing zero - but Im not sure how we would use this.
+ return -1;
+
+ // number of fractional digits
+ case LOCALE_IDIGITS:
+ return -1; // not available on the mac
+
+ // full localized name of the country
+ case LOCALE_SCOUNTRY:
+ return -1; // not available on the mac
+
+ // the country code
+ case LOCALE_ICOUNTRY:
+ return -1; // not available on the mac
+
+ // abbreviated language name
+ case LOCALE_SABBREVLANGNAME:
+ return -1; // not available on the mac
+
+ default:
+ return -1;
+ }
+
+ *pbuf = '\0';
+ len = STRLEN(rgchBuf);
+
+LHaveLength:;
+ if(len == 0) // not available
+ return 0;
+
+ ++len; // we count the null
+
+ // if cchMax is 0, then the caller is just asking for the length
+ if(cchMax != 0){
+ if(len > cchMax)
+ return 0; // error: buffer too small
+ MEMCPY(szDest, rgchBuf, len);
+ }
+
+ return len;
+}
+
+#else /* }{ */
+
+/***
+*GetWinIniInfo - get a piece of locale info from Win.INI.
+*Purpose:
+* Retrieves a piece of locale info from WIN.INI. If the request
+* type of information is not in WIN.INI, 0 is returned.
+*
+*Entry:
+* lctype - type of locale info
+* szDest - buffer to place in
+* cchMax - size of buffer, or 0 to get required size of buffer.
+*
+*Exit:
+* returns number of characters copied (including NUL), or 0
+* if not enough room or other error.
+*
+* returns -1 if lctype is not a valid type of info to read from
+* WIN.INI
+*
+* returns size needed if cchMax was 0
+*
+***********************************************************************/
+static int
+GetWinIniInfo(LCTYPE lctype, char FAR* szDest, int cchMax)
+{
+ int cchCopy;
+ char szBuffer[100]; // > max size for any entry
+ const char FAR* psz;
+static char szDummy[] = "\xff\xac\0"; // default value
+
+ switch ((unsigned short)lctype) {
+ case LOCALE_SABBREVLANGNAME:
+ cchCopy = GetProfileString(g_szIntl, "sLanguage", szDummy,
+ szBuffer, sizeof(szBuffer));
+ // For consistency with internal values, always uppercase.
+ if (cchCopy)
+ AnsiUpperBuff(szBuffer, cchCopy);
+ break;
+
+ case LOCALE_SDECIMAL:
+#if OE_WIN
+ // Get decimal character from cache, if any
+ //
+ if (cchMax) {
+ if (g_chDecimal == '\0' || cchMax < 2)
+ return 0; // no cached value or buffer too small
+
+ szDest[0] = g_chDecimal;
+ szDest[1] = '\0';
+ }
+ return 2;
+#else // OE_WIN
+ psz = "sDecimal"; goto LGet;
+#endif // else OE_WIN
+
+ case LOCALE_STHOUSAND:
+#if OE_WIN
+ // Get Thousands character from cache, if any
+ //
+ if (cchMax) {
+ if (cchMax < 2)
+ return 0; // buffer too small
+
+ szDest[0] = g_chThousand;
+ szDest[1] = '\0';
+ }
+ return 2;
+#else // OE_WIN
+ psz = "sThousand"; goto LGet;
+#endif // else OE_WIN
+
+ case LOCALE_ILZERO:
+#if OE_WIN
+ // Get leading zero flag character from cache, if any
+ //
+ if (cchMax) {
+ if (g_chILZERO == '\0' || cchMax < 2)
+ return 0; // no cached value or buffer too small
+
+ szDest[0] = g_chILZERO;
+ szDest[1] = '\0';
+ }
+ return 2;
+#else // OE_WIN
+ psz = "iLzero"; goto LGet;
+#endif // else OE_WIN
+
+ case LOCALE_SCURRENCY:
+#if OE_WIN
+ // Get decimal character from cache, if any
+ //
+ if (cchMax) {
+ if (g_szCurrency[0] == '\0' || cchMax < STRLEN(g_szCurrency))
+ return 0; // no cached value or buffer too small
+
+ STRCPY(szDest, g_szCurrency);
+ }
+ return STRLEN(g_szCurrency);
+#else // OE_WIN
+ psz = "sCurrency"; goto LGet;
+#endif // else OE_WIN
+
+
+ case LOCALE_SCOUNTRY: psz = "sCountry"; goto LGet;
+ case LOCALE_ICOUNTRY: psz = "iCountry"; goto LGet;
+ case LOCALE_IDATE: psz = "iDate"; goto LGet;
+ case LOCALE_ITIME: psz = "iTime"; goto LGet;
+ case LOCALE_ITLZERO: psz = "iTLZero"; goto LGet;
+ case LOCALE_ICURRENCY: psz = "iCurrency"; goto LGet;
+ case LOCALE_ICURRDIGITS: psz = "iCurrDigits"; goto LGet;
+ case LOCALE_INEGCURR: psz = "iNegCurr"; goto LGet;
+ case LOCALE_IDIGITS: psz = "iDigits"; goto LGet;
+ case LOCALE_IMEASURE: psz = "iMeasure"; goto LGet;
+ case LOCALE_S1159: psz = "s1159"; goto LGet;
+ case LOCALE_S2359: psz = "s2359"; goto LGet;
+ case LOCALE_SDATE: psz = "sDate"; goto LGet;
+ case LOCALE_STIME: psz = "sTime"; goto LGet;
+ case LOCALE_SLIST: psz = "sList"; goto LGet;
+ case LOCALE_SSHORTDATE: psz = "sShortDate"; goto LGet;
+ case LOCALE_SLONGDATE: psz = "sLongDate"; goto LGet;
+LGet:;
+ cchCopy = GetProfileString(
+ g_szIntl, psz, szDummy, szBuffer, sizeof(szBuffer));
+ break;
+
+ default:
+ return -1;
+ }
+
+ if (cchCopy == 2 && szBuffer[0] == szDummy[0] && szBuffer[1] == szDummy[1])
+ return 0; // Got default value; not available.
+
+ // Copy string and return correct value.
+ ++cchCopy; // For trailing NUL.
+ if (cchMax != 0) {
+ if (cchMax >= cchCopy) {
+ MEMCPY(szDest, szBuffer, cchCopy);
+ }
+ else {
+ return 0; // Error: buffer too small
+ }
+ }
+ return cchCopy;
+}
+
+#endif /* } */
+
+/***
+*SetupLcid - normalize and setup LCID
+*Purpose:
+* Normalizes an LCID, by mapping the special values LOCALE_USER_DEFAULT
+* or LOCALE_SYSTEM_DEFAULT to the current system LCID.
+* Also handles SUBLANG_NEUTRAL by mapping it to SUBLANG 1.
+*
+* After that, gets the pointers to the correct locale info into
+* the global cache.
+*
+*Entry:
+* lcid - locale id to setup.
+*
+*Exit:
+* Returns TRUE on success, FALSE on failure.
+***********************************************************************/
+
+static int FASTCALL
+SetupLcid(LCID lcid)
+{
+ NLSDATA *pnls, *pnlsEnd;
+
+ if (lcid == LOCALE_USER_DEFAULT
+ || lcid == LOCALE_SYSTEM_DEFAULT
+ || lcid == MAKELCID(MAKELANGID(LANG_NEUTRAL, SUBLANG_NEUTRAL)))
+ {
+ lcid = SystemLcid();
+ if (lcid == (LCID)-1)
+ goto LError0; // Couldn't get lcid.
+ }
+ else if (SUBLANGID(LANGIDFROMLCID(lcid)) == SUBLANG_NEUTRAL)
+ {
+ lcid = MAKELCID(MAKELANGID(PRIMARYLANGID(LANGIDFROMLCID(lcid)), 1));
+ }
+
+#if 0 // Disable for Eastern European special generation
+ // default to USA Locale for stubs
+ for (i = 0; i < DIM(g_stubLCID); i++) {
+ if (lcid == g_stubLCID[i]) {
+ lcid = 0x0409;
+ break;
+ }
+ }
+#endif
+
+ if (lcid == g_lcidCurrent)
+ return TRUE; // already setup
+
+ pnlsEnd = &g_rgnls[DIM(g_rgnls)];
+ for(pnls = g_rgnls; pnls < pnlsEnd; ++pnls){
+ if(pnls->lcid == lcid){
+#ifdef FE_DBCS
+ // CONSIDER: this could be sped up by storing the FE bit in
+ // the NLS table. this would save us the following 4 long
+ // compares per cal to SetupLcid
+ if(lcid == LCID_JAPAN){
+ bFEflag = bitJapan;
+ }else if(lcid == LCID_KOREA){
+ bFEflag = bitKorea;
+ }else if(lcid == LCID_CHINA_T){
+ bFEflag = bitTaiwan;
+ }else if(lcid == LCID_CHINA_S){
+ bFEflag = bitPrc;
+ }else
+ bFEflag = 0;
+
+#endif
+ g_pnls = pnls;
+#if OE_MAC
+ // call into the proper NLS info file. This loads our tables
+ // for us. We rely on our client to have run a .R file that
+ // marks all these code segments as non-discardable.
+ pnls->LoadNlsInfo(&pnls->prglcinfo, &g_pstrinfo);
+#else //OE_MAC
+ g_pstrinfo = pnls->pstrinfo;
+#endif //OE_MAC
+ g_lcidCurrent = lcid;
+ return TRUE;
+ }
+ }
+
+LError0:;
+#ifdef FE_DBCS
+ bFEflag = 0;
+#endif
+ g_pnls = NULL;
+ g_pstrinfo = NULL;
+ g_lcidCurrent = (LCID) -1;
+ return FALSE;
+}
+
+
+/***
+*GetUserDefaultLCID, GetSystemDefaultLCID - get system LCID
+*Purpose:
+* Returns the system LCID.
+*
+*Entry:
+* None.
+*
+*Exit:
+* Returns the system LCID.
+***********************************************************************/
+
+NLSAPI_(LCID) EXPORT
+GetUserDefaultLCID()
+{
+ return SystemLcid();
+}
+
+NLSAPI_(LCID) EXPORT
+GetSystemDefaultLCID()
+{
+ return SystemLcid();
+}
+
+
+/***
+*GetUserDefaultLangID, GetSystemDefaultLangID - get system LangID
+*Purpose:
+* Returns the system LangID.
+*
+*Entry:
+* None.
+*
+*Exit:
+* Returns the system LangID.
+***********************************************************************/
+NLSAPI_(LANGID) EXPORT
+GetUserDefaultLangID()
+{
+ LCID lcid;
+
+ lcid = SystemLcid();
+ return LANGIDFROMLCID(lcid);
+}
+
+NLSAPI_(LANGID) EXPORT
+GetSystemDefaultLangID()
+{
+ LCID lcid;
+
+ lcid = SystemLcid();
+ return LANGIDFROMLCID(lcid);
+}
+
+/***
+*GetLocaleInfoA - get a piece of locale information.
+*Purpose:
+* Gets a piece of locale information about the specified locale. The
+* information is always returns as a null-terminated string, with the
+* implied codepage being the ANSI codepage for that locale.
+*
+*Entry:
+* lcid - locale to get information for
+* lctype - type of information to get
+* szDest - buffer to store string in
+* cchMax - size of buffer. If 0, szDest is ignored and the number of
+* characters needed is returned.
+*Exit:
+* On success, returns the number of characters copied.
+* On failure, returns 0. Possible failure reasons are:
+* Unknown LCID
+* Unknown LCTYPE
+* Bad szDest pointer
+* Buffer too small.
+* Out of memory
+*
+* There is no way to determine which of these conditions caused the failure.
+*
+***********************************************************************/
+
+NLSAPI_(int) EXPORT
+GetLocaleInfoA(LCID lcid, LCTYPE lctype, char FAR* szDest, int cchMax)
+{
+ int cchCopy;
+ ILCINFO ilcinfo;
+ LCINFO FAR* plcinfo;
+ int fNoUserOverride;
+
+ cchCopy = 0; // for errors.
+
+#ifdef _DEBUG
+ // Parameter Validation.
+ if (cchMax != 0 && IsBadWritePtr(szDest, cchMax))
+ {LogParamError(ERR_BAD_PTR, GetLocaleInfoA, 0); return 0;}
+#endif
+
+ fNoUserOverride = ((lctype & LOCALE_NOUSEROVERRIDE) != 0);
+
+ // Except for the two exceptions (SENGCOUNT and SENGLANGUAGE)
+ // the LCTYPE can be used as the index into the locale info
+ // array (once the NOUSEROVERRIDE bit has been stripped).
+
+ lctype &= ~LOCALE_NOUSEROVERRIDE;
+ if (lctype == LOCALE_SENGCOUNTRY)
+ ilcinfo = ILCINFO_SENGCOUNTRY;
+ else if (lctype == LOCALE_SENGLANGUAGE)
+ ilcinfo = ILCINFO_SENGLANGUAGE;
+#if VBA2
+ else if (lctype == LOCALE_IFIRSTDAYOFWEEK)
+ ilcinfo = ILCINFO_IFIRSTDAYOFWEEK;
+ else if (lctype == LOCALE_IFIRSTWEEKOFYEAR)
+ ilcinfo = ILCINFO_IFIRSTWEEKOFYEAR;
+ else if (lctype == LOCALE_IDEFAULTANSICODEPAGE)
+ ilcinfo = ILCINFO_IDEFAULTANSICODEPAGE;
+ else if (lctype == LOCALE_INEGNUMBER)
+ ilcinfo = ILCINFO_INEGNUMBER;
+ else if (lctype == LOCALE_STIMEFORMAT)
+ ilcinfo = ILCINFO_STIMEFORMAT;
+ else if (lctype == LOCALE_ITIMEMARKPOSN)
+ ilcinfo = ILCINFO_ITIMEMARKPOSN;
+ else if (lctype == LOCALE_ICALENDARTYPE)
+ ilcinfo = ILCINFO_ICALENDARTYPE;
+ else if (lctype == LOCALE_IOPTIONALCALENDAR)
+ ilcinfo = ILCINFO_IOPTIONALCALENDAR;
+ else if (lctype == LOCALE_SMONTHNAME13)
+ ilcinfo = ILCINFO_SMONTHNAME13;
+ else if (lctype == LOCALE_SABBREVMONTHNAME13)
+ ilcinfo = ILCINFO_SABBREVMONTHNAME13;
+#endif
+ else if (lctype >= 1 && lctype < LCTYPE_MAX)
+ ilcinfo = (ILCINFO)(lctype);
+ else
+ return 0; // Error - bad lctype.
+
+ // Check for request for information that is in WIN.INI;
+ // only valid for current locale.
+ if (!fNoUserOverride) {
+ LCID lcidSystem;
+
+ if (lcid == LOCALE_USER_DEFAULT
+ || lcid == LOCALE_SYSTEM_DEFAULT
+ || lcid == MAKELCID(MAKELANGID(LANG_NEUTRAL, SUBLANG_NEUTRAL))
+ || lcid == (lcidSystem = SystemLcid())
+ || (SUBLANGID(LANGIDFROMLCID(lcid)) == SUBLANG_NEUTRAL
+ && PRIMARYLANGID(LANGIDFROMLCID(lcid)) ==
+ PRIMARYLANGID(LANGIDFROMLCID(lcidSystem))))
+ {
+#ifdef _MAC
+ if ((cchCopy = GetIntlInfo(lctype, szDest, cchMax)) >= 0)
+ return cchCopy;
+#else
+ if ((cchCopy = GetWinIniInfo(lctype, szDest, cchMax)) >= 0)
+ return cchCopy;
+#endif
+ }
+ }
+
+ if (lcid != g_lcidCurrent) {
+ if (!SetupLcid(lcid))
+ goto Error;
+ }
+
+ plcinfo = &g_pnls->prglcinfo[ilcinfo];
+
+ // Copy requested information, up to limit specified.
+ cchCopy = (int)plcinfo->cch + 1;
+ if (cchMax != 0) {
+ if (cchMax >= cchCopy) {
+ MEMCPY(szDest, plcinfo->prgb, cchCopy-1);
+ szDest[cchCopy-1] = '\0';
+ }
+ else {
+ return 0; // Error: buffer too small
+ }
+ }
+
+ /* DROP THRU */
+Error:
+ return cchCopy;
+}
+
+
+#ifdef FE_DBCS /* { */
+
+/***
+* GetSortWeightJ - get the sort weight for Japan.
+* ( handles diacritical merging )
+*Purpose:
+*
+*Entry:
+*
+*Exit:
+* returns TRUE :
+* FALSE :
+*Note:
+* Priwt : Word
+* Secwt : Byte, contains 2nd, 3rd .. 6th order sorting values
+* SecFlg: Byte, contains flags to say which orders to use
+*
+***********************************************************************/
+int
+GetSortWeightJ(
+ const unsigned char FAR* FAR*plpstr1,
+ int cch1,
+ COMPSTRINGINFO FAR *pcompstrinfo)
+{
+ STRINFO_J FAR* pstrinfo;
+ unsigned Priwt, NextCh;
+ unsigned char Secwt, SecFlg;
+ const unsigned char FAR* lpstr1 = *plpstr1;
+ unsigned char FAR* pbMasks;
+
+ pstrinfo = (STRINFO_J FAR*)g_pstrinfo;
+
+ /* first pick up the next whole character */
+ Priwt = *lpstr1++;
+ cch1--;
+
+ if (cch1 && isDbcsJ(Priwt, 0)) {
+ Priwt = (Priwt << 8) + *lpstr1++;
+ cch1--;
+ }
+
+ /* if this a Kanji outside our tables force the correct values */
+ if (Priwt >= 0x87A0) {
+ Priwt |= 0x4000; /* 0x8nnn -> 0xCnnn, 9->D, E->E, F->F */
+ Secwt = 0x00;
+ SecFlg = 0x04; /* for repeat character order */
+ goto AllDone;
+ }
+
+ /* Char can be sorted by table, so mask into range & get table values */
+ Priwt &= 0x0FFF; /* 0x00nn -> 0x00nn, 81->01, 82->02, 83->03 */
+
+ Secwt = pstrinfo->pbSecWgt[Priwt];
+ SecFlg = pstrinfo->pbSecFlg[Priwt];
+ Priwt = (pstrinfo->pbPriHi[Priwt] << 8) + pstrinfo->pbPriLo[Priwt];
+
+ /* Most characters now complete, but a few need extra processing */
+ /* eg. Kana that can have Daku-ten or Handaku-ten, Cho-on or repeat chars */
+ if ( (Priwt&0x00FF) != 0x00FF )
+ goto AllDone;
+
+ Priwt &= 0xFF00; /* mask off the special flag */
+
+ /* If we have a Kana, test for following Daku-ten or Handaku-ten */
+ if (Priwt >= 0x8700) {
+ if (cch1) {
+ NextCh = *lpstr1;
+ if (cch1>=2 && isDbcsJ(NextCh, 0))
+ NextCh = (NextCh << 8) + *(lpstr1+1);
+ if (NextCh==0x00DE || NextCh==0x814A) {
+ lpstr1 += (NextCh==0x00DE) ? 1 : 2;
+ cch1 -= (NextCh==0x00DE) ? 1 : 2;
+ Secwt |= 0x01;
+ } else if (NextCh==0x00DF || NextCh==0x814B) {
+ lpstr1 += (NextCh==0x00DF) ? 1 : 2;
+ cch1 -= (NextCh==0x00DF) ? 1 : 2;
+ Secwt |= 0x02;
+ }
+ }
+ goto AllDone;
+ }
+
+ /* If not kana, must be Cho-on or a repeat character - try Kanji repeat */
+ if (Priwt==0x3A00) {
+ if ( pcompstrinfo->priwt >= 0xC7A0 ) /* if prev was Kanji, use it */
+ Priwt = pcompstrinfo->priwt;
+ Secwt = pcompstrinfo->secwt | 0x08; /* with a repeat marker */
+ SecFlg = pcompstrinfo->secflg;
+ goto AllDone;
+ }
+
+ /* Cho-on and Kana repeat chars only used if they actually follow a kana */
+ if (pcompstrinfo->priwt<0x8700 || pcompstrinfo->priwt>0xB9FF)
+ goto AllDone;
+
+ /* Cho-on characters duplicate the vowel sound of the prev. charater */
+ /* except when they follow a N, in which case they act like repeat */
+ if ((Priwt==0x4400 || Priwt==0x3500) && pcompstrinfo->priwt<0xB900) {
+ Priwt = ((pcompstrinfo->priwt % 5) << 8) + 0x8700;
+ Secwt |= (pcompstrinfo->secwt&0x20);
+ SecFlg = 0x37;
+ goto AllDone;
+ }
+
+ /* Kana repeat is the only special character left */
+ /* second order values should be merged with those of previous character */
+ Priwt = pcompstrinfo->priwt;
+ Secwt = (pcompstrinfo->secwt&0xE4) | (Secwt&0x1B); /* merge minus some bits */
+ SecFlg = pcompstrinfo->secflg;
+
+AllDone: /* we have the full 50-on sorting values now */
+
+ /* mask off any bits that we want to ignore during this compare */
+ if (g_dwFlags & ~NORM_IGNORESYMBOLS) {
+ //Special kludges to make some pairs of full-pitch chars that
+ //sort as different chars both convert to the same half-pitch char
+ if (g_dwFlags & NORM_IGNOREWIDTH) {
+ if (SecFlg==0x22 && (Secwt&0x40))
+ Secwt = 0x04;
+ if (Priwt==0x3500)
+ Priwt = 0x4400;
+ }
+ for (pbMasks=pstrinfo->pbIgnore; *pbMasks; pbMasks+=4) {
+ unsigned nIgnore = (pbMasks[2] << 8) + pbMasks[3];
+ if( (g_dwFlags&nIgnore) && (SecFlg&pbMasks[1]) ){
+ Secwt &= ~pbMasks[0];
+ SecFlg &= ~pbMasks[1];
+ }
+ }
+ }
+
+ pcompstrinfo->priwt = Priwt;
+ pcompstrinfo->secwt = Secwt;
+ pcompstrinfo->secflg = SecFlg;
+ *plpstr1 = lpstr1;
+ return(cch1);
+}
+
+int
+CompareStringJ(
+ unsigned long dwFlags,
+ const unsigned char FAR* lpstr1, int cch1,
+ const unsigned char FAR* lpstr2, int cch2)
+{
+ STRINFO_J FAR* pstrinfo;
+ unsigned char FAR* pbMasks;
+ unsigned char b1stDiff, b1stDiffValue;
+ unsigned char bFlgMask, bWgtMask, bTemp;
+ COMPSTRINGINFO compstrinfo1, compstrinfo2;
+
+ ASSERT(fJapan);
+
+ pstrinfo = (STRINFO_J FAR*)g_pstrinfo;
+
+ b1stDiff=0;
+ b1stDiffValue=0;
+
+ /* initialise to indicate no previous character */
+ g_dwFlags = dwFlags;
+ compstrinfo1.priwt = compstrinfo1.secwt = 0;
+ compstrinfo2.priwt = compstrinfo2.secwt = 0;
+
+ /* must continue even if one string empty, to ignore trailing punc */
+ while (cch1 || cch2) {
+ /* get the sorting codes & if not equal, return the difference */
+ /* if we must ignore punc, then loop over them */
+ if (!cch1)
+ compstrinfo1.priwt = compstrinfo1.secwt = 0;
+ else{
+ do {
+ cch1 = GetSortWeightJ(&lpstr1, cch1, &compstrinfo1);
+ if ( (g_dwFlags&NORM_IGNORESYMBOLS) &&
+ compstrinfo1.priwt>=0x1400 &&
+ compstrinfo1.priwt<=0x54FF )
+ compstrinfo1.priwt = compstrinfo1.secwt = 0;
+ } while ( cch1 && compstrinfo1.priwt==0 );
+ }
+
+ if (!cch2)
+ compstrinfo2.priwt = compstrinfo2.secwt = 0;
+ else{
+ do {
+ cch2 = GetSortWeightJ(&lpstr2, cch2, &compstrinfo2);
+ if ( (g_dwFlags&NORM_IGNORESYMBOLS) &&
+ compstrinfo2.priwt>=0x1400 &&
+ compstrinfo2.priwt<=0x54FF )
+ compstrinfo2.priwt = compstrinfo2.secwt = 0;
+ } while ( cch2 && compstrinfo2.priwt==0 );
+ }
+
+ /* This exit path also used when just one string is empty */
+ if (compstrinfo1.priwt!=compstrinfo2.priwt)
+ return (compstrinfo1.priwt>compstrinfo2.priwt) ? 3 : 1;
+
+ /* first order values same, so check 2nd, 3rd .. 6th for differences */
+ /* stop scanning when we reach an order where we have a previous diff */
+ if (compstrinfo1.secwt!=compstrinfo2.secwt) {
+ for( pbMasks=pstrinfo->pbMasks;
+ (bFlgMask=pbMasks[1]) && bFlgMask!=b1stDiff; pbMasks+=4 ) {
+ if (bFlgMask & compstrinfo1.secflg) {
+ bWgtMask = pbMasks[0];
+ bTemp = (compstrinfo1.secwt & bWgtMask) - (compstrinfo2.secwt & bWgtMask);
+
+ /* if we find a difference it must be the most important so far */
+ /* so save it and remember which order it belongs to - then stop */
+ if (bTemp) {
+ b1stDiffValue = bTemp;
+ b1stDiff = bFlgMask;
+ break; /* move onto the next character pair */
+ }
+ }
+ }
+ }
+ }
+
+ /* no 1st order diffs, so ret by 2nd..6th order diff */
+ if (b1stDiff)
+ return (b1stDiffValue&0x80) ? 1 : 3;
+
+ return 2;
+}
+
+/***
+*BOOL GetSortWeightKTP - get the sort weight for most FE countries.
+* ( in the old style ) Japan is a seperate routine
+*Purpose:
+*
+*Entry:
+*
+*Exit:
+* returns TRUE : If we used up both ch, chNext ( DB char/Digraphs )
+* The caller should fill chNext with the next char.
+* FALSE : If we didn't use chNext.
+*Note:
+* Priwt : Word for Korea, Taiwan and Prc(Mainland China).
+* Secwt : Byte for all FE countries, but different meaning.
+***********************************************************************/
+BOOL
+GetSortWeightKTP(unsigned ch, unsigned chNext, COMPSTRINGINFO FAR *pcompstrinfo)
+{
+ unsigned Priwt;
+ unsigned char Secwt;
+ BOOL fNeedNextByte = FALSE;
+ SORTWEIGHT FAR* prgsortweight;
+ unsigned cSortweight, uMin, uMax, uMid, wOffset;
+
+ ASSERT(fKoreaTaiwanPrc);
+
+ cSortweight = ((STRINFO_KTP FAR*)g_pstrinfo)->cSortweight;
+ prgsortweight = ((STRINFO_KTP FAR*)g_pstrinfo)->prgsortweight;
+
+ if( (fKorea && isDbcsK(ch, chNext))
+ || (fTaiwan && isDbcsT(ch, chNext))
+ || (fPrc && isDbcsP(ch, chNext))) {
+ ch = (ch << 8) + chNext;
+ fNeedNextByte = TRUE;
+ }
+ uMin = 0;
+ // out of array bound - seems tricky, but we'll never look at [uMax] !!
+ uMax = cSortweight;
+
+ while( uMin + 1 < uMax ) { // binary search
+ uMid = (uMin + uMax)/2;
+
+ if(prgsortweight[uMid].wStart > ch)
+ uMax = uMid;
+ else // if (prgsortweight[uMid].wStart <= ch)
+ uMin = uMid;
+ }
+ // we'll use uMin, not uMid !!
+ wOffset = ch - prgsortweight[uMin].wStart;
+ Priwt = prgsortweight[uMin].wPriwt; // WORD ( unsigned int )
+ Secwt = prgsortweight[uMin].bSecwt; // unsigned char
+
+ switch(prgsortweight[uMin].bMode){
+ case MODE_1TO1:
+ // Normal mapping : add wOffset to Primary weight
+ Priwt += wOffset;
+ break;
+
+ case MODE_MTO1:
+ // Many-to-1 mapping : Use the same Priwt, add wOffset to Secwt
+ Secwt += wOffset;
+ break;
+
+ case MODE_CONV:
+ // Secwt has the case & pitch info
+ Priwt += wOffset;
+
+ if(g_dwFlags & NORM_IGNORECASE)
+ Secwt &= ~(unsigned)KOR_CASEBIT;
+
+ if(g_dwFlags & NORM_IGNOREWIDTH)
+ Secwt &= ~(unsigned)KOR_PITCHBIT;
+ break;
+ }
+ pcompstrinfo->priwt = Priwt;
+ pcompstrinfo->secwt = Secwt;
+ return(fNeedNextByte);
+}
+
+int
+CompareStringKTP(
+ unsigned long dwFlags,
+ const unsigned char FAR* lpstr1, int cch1,
+ const unsigned char FAR* lpstr2, int cch2)
+{
+ COMPSTRINGINFO compstrinfo1, compstrinfo2;
+ const char FAR *lpstrEnd1, FAR *lpstrEnd2;
+ unsigned char fEnd1, fEnd2, ch1, ch2, chNext1, chNext2, secresult;
+
+ ASSERT(fKoreaTaiwanPrc);
+
+ // parameter validation : NYI.
+
+ g_dwFlags = dwFlags;
+
+ fEnd1 = FALSE;
+ fEnd2 = FALSE;
+ secresult = 2;
+
+ lpstrEnd1 = lpstr1 + cch1;
+ lpstrEnd2 = lpstr2 + cch2;
+
+ if (cch1 > 0)
+ chNext1 = *lpstr1++;
+ else
+ fEnd1 = TRUE;
+
+ if (cch2 > 0)
+ chNext2 = *lpstr2++;
+ else
+ fEnd2 = TRUE;
+
+ for (;;) {
+ ch2 = chNext2;
+ ch1 = chNext1;
+ if (fEnd1){
+ if (fEnd2)
+ return secresult; // hit both ends of string at once
+ else
+ return 1; // hit end of 1 first.
+ }
+ if (fEnd2)
+ return 3; // hit end of 2 first.
+
+ if (lpstr2 < lpstrEnd2)
+ chNext2 = *lpstr2++;
+ else
+ fEnd2 = TRUE, chNext2 = 0;
+
+ if (lpstr1 < lpstrEnd1)
+ chNext1 = *lpstr1++;
+ else
+ fEnd1 = TRUE, chNext1 = 0;
+
+ if(GetSortWeightKTP(ch1, chNext1, &compstrinfo1)){
+ if (lpstr1 < lpstrEnd1)
+ chNext1 = *lpstr1++;
+ else
+ fEnd1 = TRUE; // don't need to update chNext (we'll break)
+ }
+
+ if(GetSortWeightKTP(ch2, chNext2, &compstrinfo2)){
+ if (lpstr2 < lpstrEnd2)
+ chNext2 = *lpstr2++;
+ else
+ fEnd2 = TRUE;
+ }
+
+ if (compstrinfo1.priwt != compstrinfo2.priwt) {
+ if (compstrinfo1.priwt > compstrinfo2.priwt)
+ return 3;
+ else
+ return 1;
+ }
+
+ // The results from the secondary weight check are stored in
+ // secresult, if not 2 then we've already found a secondary weight
+ // winner.
+ if (secresult == 2) {
+ if (compstrinfo1.secwt > compstrinfo2.secwt)
+ secresult = 3;
+ else if (compstrinfo1.secwt < compstrinfo2.secwt)
+ secresult = 1;
+ }
+ }
+
+ ASSERT(UNREACHED);
+}
+
+#endif /* } */
+
+/***
+*CompareStringA - compare two strings
+*Purpose:
+* Compares two strings for sorting order.
+*
+*Entry:
+* lcid - locale governing the mapping
+* dwFlags - zero or more of
+* NORM_IGNORECASE
+* NORM_IGNORENONSPACE
+* NORM_IGNORESYMBOLS
+* lpStr1 - pointer to string to compare
+* cch1 - length of string, or -1 for NULL terminated
+* lpStr2 - pointer to string to compare
+* cch2 - length of string, or -1 for NULL terminated
+*
+*Exit:
+* On Sucess: 1 = str1 < str2
+* 2 = str1 == str2
+* 3 = str1 > str2
+* On error, returns 0.
+*
+***********************************************************************/
+
+NLSAPI_(int) EXPORT
+CompareStringA(
+ LCID lcid,
+ unsigned long dwFlags,
+ const char FAR* pch1, int cch1,
+ const char FAR* pch2, int cch2)
+{
+#ifdef _DEBUG
+ // Parameter validation.
+ if (cch1 < -1 || cch2 < -1)
+ {LogParamError(ERR_BAD_VALUE, CompareStringA, 0); return 0;}
+ if (cch1 != -1 && IsBadReadPtr(pch1, cch1))
+ {LogParamError(ERR_BAD_PTR, CompareStringA, 0); return 0;}
+ if (cch1 == -1 && IsBadStringPtr(pch1, 0x7FFF))
+ {LogParamError(ERR_BAD_STRING_PTR, CompareStringA, 0); return 0;}
+ if (cch2 != -1 && IsBadReadPtr(pch2, cch2))
+ {LogParamError(ERR_BAD_PTR, CompareStringA, 0); return 0;}
+ if (cch2 == -1 && IsBadStringPtr(pch2, 0x7FFF))
+ {LogParamError(ERR_BAD_STRING_PTR, CompareStringA, 0); return 0;}
+ if ((dwFlags != 0) &&
+ (dwFlags & ~(NORM_IGNORECASE | NORM_IGNORENONSPACE |
+ NORM_IGNORESYMBOLS | NORM_IGNOREKANATYPE |
+ NORM_IGNOREWIDTH)))
+ {LogParamError(ERR_BAD_FLAGS, CompareStringA, 0); return 0;}
+#endif
+ // Set up for comparing routines.
+ if (lcid != g_lcidCurrent) {
+ if (!SetupLcid(lcid))
+ return 0; // error.
+ }
+
+#ifdef FE_DBCS
+ if(fDBCS){
+ if(cch1 == -1)
+ cch1 = STRLEN(pch1);
+ if(cch2 == -1)
+ cch2 = STRLEN(pch2);
+ return ((fJapan) ? CompareStringJ : CompareStringKTP)
+ (dwFlags, pch1, cch1, pch2, cch2);
+ }
+#endif
+
+ // use optimized routine, for non-FE locales when
+ // - both strings are zero terminated
+ // - we are *not* ignoring symbols
+ // - it is not a reverse-diacritic weight locale
+ // - the locale has no digraphs
+ //
+ if (cch1 == -1
+ && cch2 == -1
+ && (dwFlags & NORM_IGNORESYMBOLS) == 0
+ && g_pstrinfo->fRevDW == 0
+ && g_pstrinfo->prgdig == NULL)
+ {
+ return ZeroTermNoIgnoreSym(dwFlags, pch1, pch2);
+ }
+
+ if(cch1 == -1)
+ cch1 = STRLEN(pch1);
+ if(cch2 == -1)
+ cch2 = STRLEN(pch2);
+
+ // Default compare - less optimized, handles all cases (non FE locales).
+ return DefCompareStringA(dwFlags, pch1, cch1, pch2, cch2);
+}
+
+/***
+*CreateSortKey - map a string to its sort key
+*Purpose:
+* This is used from LCMapStringA for the LCMAP_SORTKEY option.
+* It creates a sort key.
+*
+* All parameters have been validated.
+*
+* The format of the sortkey for all single byte locales is,
+*
+* <AW>1<DW>1<CW>0
+*
+* where AW is the Arithmetic weight, DW is the diacritic weight
+* and CW is the case weight.
+*
+*Entry:
+* pchSrc - source string
+* cchSrc - length (-1 = null term)
+* pchDst - destination
+* cchDst - length, or zero to get needed length.
+* dwFlags - flags.
+*
+*Exit:
+* returns number of characters needed/written.
+*
+*Notes:
+* This routine makes up to 4 passes over the source string,
+*
+* pass 1 = calculate the size of the sort key
+* pass 2 = put down the AW field
+* pass 3 = put down the DW field
+* pass 4 = put down the CW field
+*
+***********************************************************************/
+static int
+CreateSortKey(
+ const char FAR* pchSrc,
+ int cchSrc,
+ char FAR* pchDst,
+ int cchDst,
+ unsigned long dwFlags)
+{
+ BYTE aw;
+ WORD FAR* prgw;
+ EXPANSION FAR* pexp;
+ int iPass, cb, cbTotal;
+ WORD w, wEx, wSymbolBit;
+ DIGRAPH FAR* pdig, FAR* pdigEnd;
+ const char FAR* pch, FAR* pchEnd;
+
+// the skip flags for each pass
+static DWORD rgdwSkip[] = {
+ 0, // calculate key size
+ 0, // AW
+ NORM_IGNORENONSPACE, // DW
+ NORM_IGNORECASE // CW
+};
+
+ // cchSrc must be set by caller
+ ASSERT(cchSrc != -1);
+
+ prgw = g_pstrinfo->prgwSort;
+
+ pchEnd = &pchSrc[cchSrc];
+
+ cb = 0;
+ wEx = 0;
+ wSymbolBit = (dwFlags & NORM_IGNORESYMBOLS) ? SYMBOLBIT : 0;
+
+ for(iPass = 0; iPass < 4; ++iPass){
+
+ if((rgdwSkip[iPass] & dwFlags) == 0){
+
+ for(pch = pchSrc; pch < pchEnd;){
+
+ // get the next weight
+ if(wEx){
+ // grab the second weight of the expansion, if there is one
+ w = wEx;
+ wEx = 0;
+ }else{
+ w = prgw[(BYTE)*pch++];
+ if(w & wSymbolBit)
+ continue; // ignore
+ }
+#if 1
+ if (w & SPECIALBIT)
+ continue; // these get no weight
+#endif //1
+
+ // handle special cases
+ aw = (BYTE)(w & AWMASK);
+ switch(aw){
+#if 0
+ case AW_SW1:
+ case AW_SW2:
+ case AW_SW3:
+#endif //0
+ case AW_UNSORTABLE:
+ continue; // these get no weight
+ case AW_EXPANSION:
+ pexp = &g_pstrinfo->prgexp[(w>>8)&0xff];
+ w = pexp->w1;
+ wEx = pexp->w2;
+ break;
+ case AW_DIGRAPH:
+ pdig = &g_pstrinfo->prgdig[(w>>8)&0xff];
+ pdigEnd = pdig + D_ENTRY(pdig);
+ w = pdig->w; // weight if not a digraph
+ if(pch < pchEnd){
+ for(++pdig; pdig <= pdigEnd; ++pdig){
+ if(D_CH(pdig) == *pch){
+ ++pch; // consume second char of digraph
+ w = pdig->w;
+ break;
+ }
+ }
+ }
+ break;
+ }
+
+ // take action according to pass
+ switch(iPass){
+ case 0:
+ ++cb;
+ break;
+ case 1:
+ *pchDst++ = aw;
+ break;
+ case 2:
+ *pchDst++ = (BYTE)((w & DWMASK) >> DWSHIFT);
+ break;
+ case 3:
+ *pchDst++ = (BYTE)((w & CWMASK) >> CWSHIFT);
+ break;
+ default:
+ ASSERT(UNREACHED);
+ break;
+ }
+ }
+ }
+
+ switch(iPass){
+ case 0: // End of pass#1: compute the total bytes required for the key
+ cbTotal = cb;
+ cbTotal += 1; // +1 for the AW separator
+ if((dwFlags & NORM_IGNORENONSPACE) == 0)
+ cbTotal += cb;
+ cbTotal += 1; // +1 for the DW separator
+ if((dwFlags & NORM_IGNORECASE) == 0)
+ cbTotal += cb;
+ cbTotal += 1; // +1 for the terminating NULL
+ if(cchDst == -1)
+ return cbTotal;
+ if(cbTotal > cchDst)
+ return 0;
+ break;
+ case 1:
+ case 2:
+ *pchDst++ = 1;
+ break;
+ case 3:
+ *pchDst++ = 0;
+ break;
+ }
+ }
+
+ return cbTotal;
+}
+
+#ifdef FE_DBCS /* { */
+
+// OK, here is the strategy. Japanese uses 6 levels of sort orders, where
+// the first sort order can be one or two bytes and the rest of the sort
+// orders are one or two bits.
+// To place the orders efficiently we traverse the string twice, once to
+// find out how many of each order we have, and then again to place the
+// bytes and bits in the correct string positions.
+//
+int
+CreateSortKeyJ(
+ const char FAR* lpSrcStr, int cchSrc,
+ char FAR* lpDestStr, int cchDest,
+ unsigned long dwFlags)
+{
+ STRINFO_J FAR* pstrinfo;
+ COMPSTRINGINFO compstrinfo;
+ unsigned char FAR* pbMasks;
+ int nOrder1, nOrder2[5], nShift[6], i;
+ char FAR* lpEndStr=lpDestStr+cchDest, FAR* lpOrder1, FAR* lpOrder2[6];
+ const char FAR* lpSrcTmp = lpSrcStr;
+ int cchTmp = cchSrc;
+
+ g_dwFlags = dwFlags;
+
+ pstrinfo = (STRINFO_J FAR*)g_pstrinfo;
+
+ // Initialize ready for the first scan
+ nOrder1 = nOrder2[0] = nOrder2[1] = nOrder2[2] =
+ nOrder2[3] = nOrder2[4] = 0;
+ // then loop around counting all of the sorting orders
+ compstrinfo.priwt = compstrinfo.secwt = 0;
+ while (cchTmp) {
+ do { // don't forget to skip punctuation if we want to
+ cchTmp = GetSortWeightJ(&lpSrcTmp, cchTmp, &compstrinfo);
+ if ( (g_dwFlags&NORM_IGNORESYMBOLS) &&
+ compstrinfo.priwt>=0x1400 && compstrinfo.priwt<=0x54FF )
+ compstrinfo.priwt = 0;
+ } while ( cchTmp && compstrinfo.priwt==0 );
+
+ if(compstrinfo.priwt) {
+ nOrder1 += (compstrinfo.priwt & 0xFF) ? 2 : 1;
+ for(i=0,pbMasks=pstrinfo->pbMasks; i<5; pbMasks+=4,i++){
+ if (pbMasks[1] & compstrinfo.secflg)
+ nOrder2[i] += pbMasks[3];
+ }
+ }
+ }
+
+ // Initialize ready for the second scan
+ // This includes working out the byte and bit offset positions for each
+ // of the sorting orders to be put into the output
+ //
+ lpOrder2[0] = lpDestStr + nOrder1 + 1;
+ nShift[0] = 7;
+ for( i=0,pbMasks=pstrinfo->pbMasks; i<5; pbMasks+=4,i++ ) {
+ // must adjust two bit orders so that both bits fit
+ if (pbMasks[3]==2) {
+ nShift[i]--;
+ if (nShift[i]&0x01) // avoid spanning byte boundries - for speed
+ nShift[i]--;
+ if (nShift[i]<0) {
+ lpOrder2[i]++;
+ nShift[i] += 8;
+ }
+ }
+ // the next order start is fixed by the number of bits in this order
+ // do this even for last order, so that we can find real end
+ nShift[i+1] = nShift[i] - nOrder2[i];
+ lpOrder2[i+1] = lpOrder2[i];
+ while (nShift[i+1]<0) {
+ lpOrder2[i+1]++;
+ nShift[i+1] += 8;
+ }
+ // final adjustment for end of buffer, to include final bits
+ if (i==4 && (nShift[5]+pbMasks[3])<8)
+ lpOrder2[5]++;
+ }
+ // Adjust the end point if the output buffer won't be filled
+ if (lpEndStr>lpOrder2[5])
+ lpEndStr = lpOrder2[5];
+
+ // blank out all of the secondary bits, before OR'ing in the parts
+ for (lpOrder1=lpOrder2[0]; lpOrder1<lpEndStr; lpOrder1++)
+ *lpOrder1 = 0;
+
+ // then loop around placing all of the sorting orders into the output
+ lpOrder1 = lpDestStr;
+ compstrinfo.priwt = compstrinfo.secwt = 0;
+ while (cchSrc && lpOrder1<lpEndStr) {
+ do { // don't forget to skip punctuation if we want to
+ cchSrc = GetSortWeightJ(&lpSrcStr, cchSrc, &compstrinfo);
+ if ( (g_dwFlags&NORM_IGNORESYMBOLS) &&
+ compstrinfo.priwt>=0x1400 && compstrinfo.priwt<=0x54FF )
+ compstrinfo.priwt = 0;
+ } while ( cchSrc && compstrinfo.priwt==0 );
+
+ if (compstrinfo.priwt) {
+ *lpOrder1++ = (compstrinfo.priwt>>8);
+ if (lpOrder1<lpEndStr && (compstrinfo.priwt&0xFF))
+ *lpOrder1++ = (compstrinfo.priwt&0xFF);
+
+ for( i=0,pbMasks=pstrinfo->pbMasks; pbMasks[1]; pbMasks+=4,i++ ) {
+ if (lpOrder2[i]>=lpEndStr)
+ break;
+ if (pbMasks[1] & compstrinfo.secflg) {
+ *lpOrder2[i] |= (char)(((pbMasks[0] & compstrinfo.secwt)
+ >> pbMasks[2]) << nShift[i]);
+ nShift[i] -= pbMasks[3];
+ if (nShift[i]<0) {
+ lpOrder2[i]++;
+ nShift[i] += 8;
+ }
+ }
+ }
+ }
+ }
+
+ // Finish the first order bytes with a seperator
+ if (lpOrder1<lpEndStr)
+ *lpOrder1 = 0x01;
+
+ return (int)(lpEndStr-lpDestStr);
+}
+
+int
+CreateSortKeyKTP(
+ const char FAR* lpSrcStr, int cchSrc,
+ char FAR* lpDestStr, int cchDest,
+ unsigned long dwFlags)
+{
+ // don't change ch,chNext to 16bit or you'll screw up FE features
+ unsigned char ch, chNext;
+#if 0
+ unsigned short wt;
+#endif
+ COMPSTRINGINFO compstrinfo;
+ unsigned char FAR* pbDest;
+ int fEnd, cNumWts, cOverall;
+ const unsigned char FAR* lpstr;
+ const unsigned char FAR* lpstrEnd;
+ unsigned char FAR *pbSecwt, FAR *lpDestBndry;
+
+
+ ASSERT(fKoreaTaiwanPrc);
+
+ // Let's turn off NORM_IGNORESYMBOLS for FE countries.
+ // CONSIDER: This is not needed for Japan, can switch on again for
+ // Korea/Taiwan if you want.
+ //
+ dwFlags &= ~(unsigned long)NORM_IGNORESYMBOLS;
+ g_dwFlags = dwFlags;
+
+ lpstr = lpSrcStr;
+ lpstrEnd = lpSrcStr + cchSrc;
+ cNumWts = 0;
+ fEnd = FALSE;
+
+ for (;;) { // Get next char, handle end of string and symbol skipping.
+ if(lpstr >= lpstrEnd){
+ fEnd = TRUE;
+ chNext = 0;
+ break;
+ }
+ chNext = *lpstr++;
+ break;
+ }
+
+ while(!fEnd){
+
+ ch = chNext;
+
+ // Get next char, handle end of string and symbol skipping.
+ for(;;){
+ if(lpstr >= lpstrEnd){
+ fEnd = TRUE;
+ chNext = 0;
+ break;
+ }
+ chNext = *lpstr++;
+ break;
+ }
+
+ if ((fKorea && isDbcsK(ch, chNext))
+ || (fTaiwan && isDbcsT(ch, chNext))
+ || (fPrc && isDbcsP(ch, chNext)))
+ {
+ if (lpstr >= lpstrEnd)
+ fEnd = TRUE;
+ else
+ chNext = *lpstr++;
+ }
+ cNumWts++;
+ }
+
+ // we use word-priwt & byte-secwt.
+ // so we need cNumWts*2 + 1 + cNumWts + 1.
+
+ pbSecwt = lpDestStr + (cNumWts << 1);
+ cOverall = (cNumWts << 1) + cNumWts + 2;
+
+ if(!cchDest)
+ return cOverall;
+
+ // ***********************************************************
+ //
+ // Now we'll WRITE weights into the dest string.
+ // Don't worry, we know the length !
+ //
+ // ***********************************************************
+
+ lpstr = (unsigned char FAR*) lpSrcStr;
+ lpstrEnd = lpstr + cchSrc;
+ fEnd = FALSE;
+
+ pbDest = (unsigned char FAR*) lpDestStr;
+
+ lpDestBndry = lpDestStr + cchDest;
+
+ if( pbSecwt < lpDestBndry )
+ *pbSecwt++ = 1; // separator
+
+ if( cOverall <= cchDest )
+ *(pbDest + cOverall - 1) = 0; // zero terminator
+
+ // ****************************
+ // Start of the second loop.
+ // ****************************
+
+ for (;;) { // Get next char, handle end of string and symbol skipping.
+ if (lpstr >= lpstrEnd) {
+ fEnd = TRUE;
+ chNext = 0;
+ break;
+ }
+ chNext = *lpstr;
+ break;
+ }
+ ++lpstr;
+
+ while(!fEnd){
+ ch = chNext;
+ for (;;){
+ if(lpstr >= lpstrEnd){
+ fEnd = TRUE;
+ chNext = 0;
+ break;
+ }
+ chNext = *lpstr;
+ break;
+ }
+ ++lpstr;
+
+ // Important note:
+ //
+ // - if 2 chars were treated as 1 char(DB or digraph)
+ // then you should read 1 char from lpstr into chNext.
+ // (also you should increase lpstr by 1)
+ // - if you see SB char, then you don't have to do anything.
+
+ if(GetSortWeightKTP(ch, chNext, &compstrinfo)){
+ if (lpstr >= lpstrEnd)
+ fEnd = TRUE; // don't need to update chNext, we'll break
+ else
+ chNext = *lpstr++;
+ }
+
+ // Let's write weights into the Dest string.
+
+ if(pbSecwt < lpDestBndry){ // writing priwt & secwt.
+ *pbSecwt++ = (unsigned char)compstrinfo.secwt + 2;
+ *pbDest++ = compstrinfo.priwt >> 8;
+ *pbDest++ = compstrinfo.priwt & 0xFF;
+ }
+ else if(pbDest < lpDestBndry - 1){ // writing priwt only
+ *pbDest++ = compstrinfo.priwt >> 8;
+ *pbDest++ = compstrinfo.priwt & 0xFF;
+ }
+ else{ // we don't have any room for writing weights
+ if(pbDest < lpDestBndry)
+ *pbDest++ = compstrinfo.priwt >> 8; // write the last 1 byte
+ break; // get out of this loop
+ }
+ }
+
+ // Return number of characters copied/needed, unless we ran out
+ // of space.
+
+ // Note : we already took care of the case (cchDest==0)
+ // *before* we entered the second loop.
+
+ if(cOverall <= cchDest)
+ return cOverall;
+ else
+ return 0; // fTooLittleSpace == TRUE.
+}
+
+int
+nDecodeSortWeightJ(COMPSTRINGINFO FAR *pcompstrinfo)
+{
+ int i;
+ STRINFO_J FAR* pstrinfo;
+ unsigned char bPriwtHi = (pcompstrinfo->priwt >> 8);
+ unsigned char bPriwtLo = (pcompstrinfo->priwt & 0x00FF);
+ unsigned char bSecwt = pcompstrinfo->secwt;
+ unsigned char bSecflg = pcompstrinfo->secflg;
+ unsigned char fKanaOn = 0;
+
+ pstrinfo = (STRINFO_J FAR*)g_pstrinfo;
+
+ /* if we are looking for half-pitch kana, then Daku-on or Handaku-on */
+ /* must be rendered as a seperate character. Adjust before & after */
+ if ((bSecflg&0x21)==0x21 && !(bSecwt&0x40)) {
+ fKanaOn = bSecwt&0x03;
+ bSecwt &= 0xFC;
+ }
+
+ /* scan for the character that we would like to get */
+ for (i=0; i<0x492; i++) {
+ if ((bPriwtHi==pstrinfo->pbPriHi[i]) &&
+ (bSecwt==pstrinfo->pbSecWgt[i]) &&
+ ((bPriwtLo==pstrinfo->pbPriLo[i]) ||
+ (!bPriwtLo && (pstrinfo->pbPriLo[i]==0xFF))))
+ break;
+ }
+ if (i==0x492)
+ return 0;
+
+ /* We found a character to return. If half-pitch kana and daku-on or */
+ /* handaku-on is required, then return the two 1-byte chars together */
+ if (i<0x00FF){
+ if (fKanaOn)
+ i = (i<<8) + ((fKanaOn==1) ? 0xDE : 0xDF);
+ return i;
+ }
+
+ /* force two byte chars back into the two byte range. */
+ return (i | 0x8000);
+}
+
+int
+MapStringJ(
+ unsigned long dwMapFlags,
+ const unsigned char FAR* lpSrcStr, int cchSrc,
+ unsigned char FAR* lpDestStr, int cchDest)
+{
+ STRINFO_J FAR* pstrinfo;
+ COMPSTRINGINFO compstrinfo;
+ int cchActDest = 0;
+ const char FAR * lpStrEnd;
+ BOOL fEnd = FALSE;
+
+ ASSERT(fJapan);
+
+ pstrinfo = (STRINFO_J FAR*)g_pstrinfo;
+
+ // Assumption :
+ // The caller must calculate the length of Src string,
+ // and give the result by cchSrc..
+
+ // we'll use sortweights for mapping strings.
+ // so let's turn off the global flag - to get CLEAN SortWeights.
+ // ( we should not ignore any info - case, pitch(SB/DB), etc. )
+
+ g_dwFlags = 0;
+
+ if (lpDestStr==lpSrcStr && (dwMapFlags & LCMAP_FULLWIDTH))
+ return 0; // dangerous - in this case src chars can be destroyed
+ // before we read them..
+
+ while (cchSrc) {
+ BOOL fSearch;
+ unsigned char FAR* pbMasks;
+
+ /* Save a copy of the next character in the string */
+ unsigned wCh = *lpSrcStr, wChNew;
+ int cch = (cchSrc>1 && isDbcsJ(wCh,0)) ? 2 : 1;
+ int cch2 = cch;
+ if (cch==2)
+ wCh = (wCh << 8) + *(lpSrcStr+1);
+
+ /* Special code to allow half pitch kana with accents to be */
+ /* comibined into a single full pitch character */
+ if ((dwMapFlags&LCMAP_FULLWIDTH) && cch==1) {
+ lpStrEnd = lpSrcStr;
+ compstrinfo.priwt = compstrinfo.secwt = 0;
+ cch2 = cchSrc - GetSortWeightJ(&lpStrEnd, cchSrc, &compstrinfo);
+
+ /* only use this code if we actually picked up an accent */
+ if (cch2!=cch) {
+ /* scan the table of conversions that we know how to do */
+ fSearch = FALSE;
+ /* special kludges to convert the kana repeat marks */
+ if (dwMapFlags&LCMAP_KATAKANA) {
+ if (compstrinfo.priwt==0x4100 || compstrinfo.priwt==0x4200 ) {
+ compstrinfo.priwt += 0x0400;
+ fSearch = TRUE;
+ }
+ }
+ if (dwMapFlags&LCMAP_HIRAGANA) {
+ if (compstrinfo.priwt==0x4500 || compstrinfo.priwt==0x4600 ) {
+ compstrinfo.priwt -= 0x0400;
+ fSearch = TRUE;
+ }
+ }
+ for (pbMasks=pstrinfo->pbMaps; *pbMasks; pbMasks+=6) {
+ if (compstrinfo.secflg & pbMasks[1]) {
+ unsigned nForceOn = (pbMasks[2] << 8) + pbMasks[3];
+ unsigned nForceOff = (pbMasks[4] << 8) + pbMasks[5];
+ if (dwMapFlags & nForceOn ) {
+ compstrinfo.secwt |= pbMasks[0];
+ fSearch = TRUE;
+ }
+ if (dwMapFlags & nForceOff) {
+ compstrinfo.secwt &= ~pbMasks[0];
+ fSearch = TRUE;
+ }
+ }
+ }
+ /* if a conversion is possible, look for a new char */
+ if (fSearch && (wChNew=nDecodeSortWeightJ(&compstrinfo))) {
+ /* Save the new 2 byte character */
+ cchActDest += 2;
+ if (cchDest && cchActDest>cchDest)
+ return 0;
+ if (cchDest) {
+ *lpDestStr++ = (wChNew >> 8);
+ *lpDestStr++ = wChNew;
+ }
+
+ /* Then go onto the next character */
+ cchSrc -= cch2;
+ lpSrcStr += cch2;
+ continue;
+ }
+ }
+ }
+
+ /* If the accent tests failed check for normal conversion in a */
+ /* character-by-character mode */
+ compstrinfo.priwt = compstrinfo.secwt = 0;
+ GetSortWeightJ(&lpSrcStr, cch, &compstrinfo);
+ cchSrc -= cch;
+
+ /* now scan the table of conversions that we know how to do */
+ /* check if one of these is requested & this char is elegible */
+ /* & that the char is not already in the mode requested */
+ fSearch = FALSE;
+ //
+ //Special kludges to make some pairs of full-pitch chars that
+ //sort as different chars both convert to the same half-pitch char
+ if (dwMapFlags&LCMAP_HALFWIDTH) {
+ /* the single & double quotation marks */
+ if (compstrinfo.secflg==0x22 && (compstrinfo.secwt&0x40)) {
+ compstrinfo.secwt = 0x04;
+ fSearch = TRUE;
+ }
+ /* the cho-on markers */
+ if (compstrinfo.priwt==0x3500) {
+ compstrinfo.priwt = 0x4400;
+ fSearch = TRUE;
+ }
+ }
+ /* special kludges to convert the kana repeat marks */
+ if (dwMapFlags&LCMAP_KATAKANA) {
+ if (compstrinfo.priwt==0x4100 || compstrinfo.priwt==0x4200 ) {
+ compstrinfo.priwt += 0x0400;
+ fSearch = TRUE;
+ }
+ }
+ if (dwMapFlags&LCMAP_HIRAGANA) {
+ if (compstrinfo.priwt==0x4500 || compstrinfo.priwt==0x4600 ) {
+ compstrinfo.priwt -= 0x0400;
+ fSearch = TRUE;
+ }
+ }
+ for (pbMasks=pstrinfo->pbMaps; *pbMasks; pbMasks+=6) {
+ if (compstrinfo.secflg & pbMasks[1]) {
+ unsigned nForceOn = (pbMasks[2] << 8) + pbMasks[3];
+ unsigned nForceOff = (pbMasks[4] << 8) + pbMasks[5];
+ if (dwMapFlags & nForceOn) {
+ if (pbMasks[1]==0x10) { /* some hiragana conversions bad */
+ /* don't do 'V' characters */
+ if (compstrinfo.priwt==0x8900 && (compstrinfo.secwt&0x03))
+ continue;
+ }
+ compstrinfo.secwt |= pbMasks[0];
+ fSearch = TRUE;
+ }
+ if (dwMapFlags & nForceOff) {
+ if (pbMasks[1]==0x20) { /* some halfwidth conversions bad */
+ /* don't do small 'WA' characters */
+ if (compstrinfo.priwt==0xB400 && !(compstrinfo.secwt&0x04))
+ continue;
+ /* don't do together with hiragana conversions (except V) */
+ if ((dwMapFlags&LCMAP_HIRAGANA) && (compstrinfo.secflg&0x10)
+ && !(compstrinfo.priwt==0x8900 && (compstrinfo.secwt&0x03)))
+ continue;
+ }
+ compstrinfo.secwt &= ~pbMasks[0];
+ fSearch = TRUE;
+ }
+ }
+ }
+
+ /* if a conversion is possible, look for a new char */
+ if (fSearch && (wChNew=nDecodeSortWeightJ(&compstrinfo)))
+ wCh = wChNew;
+
+ /* Save the new (or old) 1 or 2 byte character */
+ cchActDest += (wCh > 0x00FF) ? 2 : 1;
+ if (cchDest) {
+ if (cchActDest>cchDest)
+ return 0;
+ if (wCh > 0x00FF)
+ *lpDestStr++ = (wCh >> 8);
+ *lpDestStr++ = wCh;
+ }
+ }
+
+ // don't worry about NULL termination.
+ // it's already taken care of.. ( cchSrc = lstrlen(lpSrcStr) + 1 )
+ return cchActDest;
+}
+
+int
+MapStringKTP(
+ unsigned long dwMapFlags,
+ const unsigned char FAR* lpSrcStr, int cchSrc,
+ unsigned char FAR* lpDestStr, int cchDest)
+{
+ MAPTABLE FAR* prgmaptable;
+ COMPSTRINGINFO compstrinfo;
+ int cchActDest = 0;
+ const char FAR * lpStrEnd;
+ BOOL fEnd = FALSE;
+ unsigned cMaptable, uMin, uMax, uMid, wOffset, ch;
+ unsigned char chNext; // important.. not to get SIGN-EXTENDED int
+
+ ASSERT(fKoreaTaiwanPrc);
+
+ cMaptable = ((STRINFO_KTP FAR*)g_pstrinfo)->cMaptable;
+ prgmaptable = ((STRINFO_KTP FAR*)g_pstrinfo)->prgmaptable;
+
+ // Assumption :
+ // The caller must calculate the length of Src string,
+ // and give the result by cchSrc..
+
+ // we'll use sortweights for mapping strings.
+ // so let's turn off the global flag - to get CLEAN SortWeights.
+ // ( we should not ignore any info - case, pitch(SB/DB), etc. )
+
+ g_dwFlags = 0;
+
+ if (lpDestStr==lpSrcStr && (dwMapFlags & LCMAP_FULLWIDTH))
+ return 0; // dangerous - in this case src chars can be destroyed
+ // before we read them..
+
+ lpStrEnd = lpSrcStr + cchSrc;
+
+ if (lpSrcStr >= lpStrEnd)
+ fEnd = TRUE, chNext = 0;
+ else
+ chNext = (unsigned char)*lpSrcStr++;
+
+ while (!fEnd) {
+ ch = chNext;
+
+ if (lpSrcStr >= lpStrEnd)
+ fEnd = TRUE, chNext = 0;
+ else
+ chNext = *lpSrcStr++;
+
+ if(GetSortWeightKTP(ch, chNext, &compstrinfo)) { // DB ??
+
+ // ch will be re-used when we cannot convert the char.
+ ch = (ch << 8) + chNext;
+
+ if (lpSrcStr >= lpStrEnd)
+ fEnd = TRUE, chNext = 0;
+ else
+ chNext = *lpSrcStr++;
+ }
+
+ uMin = 0;
+ uMax = cMaptable; // out of array bound - seems tricky, too
+
+ while( uMin + 1 < uMax ) { // binary search
+ uMid = (uMin + uMax)/2;
+ if (prgmaptable[uMid].wPriwt > (unsigned)compstrinfo.priwt)
+ uMax = uMid;
+ else
+ uMin = uMid;
+ }
+
+ // we'll use uMin, not uMid !!
+ wOffset = (unsigned)compstrinfo.priwt - prgmaptable[uMin].wPriwt;
+
+ if( wOffset < prgmaptable[uMin].wCount ) { // There's a matching range
+ // just to be careful..
+ // iCase will be used as one of table indices.
+ int iCase = compstrinfo.secwt & (KOR_PITCHBIT | KOR_CASEBIT);
+
+ if (dwMapFlags & LCMAP_UPPERCASE)
+ iCase &= ~(unsigned)KOR_CASEBIT;
+ else if (dwMapFlags & LCMAP_LOWERCASE)
+ iCase |= (unsigned)KOR_CASEBIT;
+
+ if (dwMapFlags & LCMAP_HALFWIDTH)
+ iCase &= ~(unsigned)KOR_PITCHBIT;
+ else if (dwMapFlags & LCMAP_FULLWIDTH)
+ iCase |= (unsigned)KOR_PITCHBIT;
+
+ ch = prgmaptable[uMin].wCode[iCase] + wOffset; // Map a character
+ }
+
+ if(ch>0x100) { // DB char
+ if (cchDest == 0)
+ cchActDest+=2;
+ else if (cchActDest + 1 < cchDest ) {
+ *lpDestStr++ = ch >> 8;
+ *lpDestStr++ = ch & 0xFF;
+ cchActDest+=2;
+ } else
+ return 0;
+ } else {
+ if (cchDest == 0)
+ cchActDest++;
+ else if (cchActDest < cchDest ) {
+ *lpDestStr++ = ch;
+ cchActDest++;
+ } else
+ return 0;
+ }
+ }
+
+ // don't worry about NULL termination.
+ // it's already taken care of.. ( cchSrc = lstrlen(lpSrcStr) + 1 )
+
+ return cchActDest;
+}
+
+#endif /* } */
+
+/***
+*LCMapStringA - map a string
+*Purpose:
+* Maps a string to lowercase, uppercase, or to a sort key.
+*
+*Entry:
+* lcid - locale governing the mapping
+* dwMapFlags - one of
+* LCMAP_LOWERCASE
+* LCMAP_UPPERCASE
+* LCMAP_SORTKEY
+* if LCMAP_SORTKEY, can be or'ed with:
+* NORM_IGNORECASE
+* NORM_IGNORENONSPACE
+* NORM_IGNORESYMBOLS
+* lpSrcStr - pointer to sting to map
+* cchSrc - length of string, or -1 for NULL terminated
+* lpDestStr - pointer to destination, may not be lpSrcStr
+* cchDest - size of buffer. If cchDest is 0, the return value
+* is the number of characters needed.
+*
+* UNDONE: LCMAP_SORTKEY not yet implemented.
+*
+*Exit:
+* returns number of characters written, or number of characters
+* needed if cchDest is 0.
+* On error, returns 0.
+*
+***********************************************************************/
+
+NLSAPI_(int) EXPORT
+LCMapStringA(
+ LCID lcid,
+ unsigned long dwMapFlags,
+ const char FAR* lpSrcStr, int cchSrc,
+ char FAR* lpDestStr, int cchDest)
+{
+ int retval;
+ char FAR* pMap;
+
+#ifdef _DEBUG
+ // Parameter validation.
+ if (cchSrc < -1 || cchDest < 0)
+ {LogParamError(ERR_BAD_VALUE, LCMapStringA, 0); return 0;}
+ if (cchDest != 0 && IsBadWritePtr(lpDestStr, cchDest))
+ {LogParamError(ERR_BAD_PTR, LCMapStringA, 0); return 0;}
+ if (cchSrc != -1 && IsBadReadPtr(lpSrcStr, cchSrc))
+ {LogParamError(ERR_BAD_PTR, LCMapStringA, 0); return 0;}
+ if (cchSrc == -1 && IsBadStringPtr(lpSrcStr, 0x7FFF))
+ {LogParamError(ERR_BAD_STRING_PTR, LCMapStringA, 0); return 0;}
+#ifdef FE_DBCS
+ /* check for any flags not in the known set of flags */
+ if (dwMapFlags & ~(LCMAP_UPPERCASE | LCMAP_LOWERCASE |
+ LCMAP_HALFWIDTH | LCMAP_FULLWIDTH | LCMAP_HIRAGANA | LCMAP_KATAKANA |
+ LCMAP_SORTKEY | NORM_IGNORECASE | NORM_IGNORENONSPACE |
+ NORM_IGNORESYMBOLS | NORM_IGNOREWIDTH | NORM_IGNOREKANATYPE))
+ {LogParamError(ERR_BAD_FLAGS, LCMapStringA, 0); return 0;}
+
+ /* check for sortkey options combined with non-sortkey options */
+ if ((dwMapFlags & (LCMAP_UPPERCASE | LCMAP_LOWERCASE | LCMAP_HALFWIDTH |
+ LCMAP_FULLWIDTH | LCMAP_HIRAGANA | LCMAP_KATAKANA)) &&
+ (dwMapFlags & (LCMAP_SORTKEY | NORM_IGNORECASE | NORM_IGNORENONSPACE |
+ NORM_IGNORESYMBOLS | NORM_IGNOREWIDTH | NORM_IGNOREKANATYPE)))
+ {LogParamError(ERR_BAD_FLAGS, LCMapStringA, 0); return 0;}
+
+ /* check for bad pairs of flags */
+ if ((dwMapFlags & LCMAP_LOWERCASE) && (dwMapFlags & LCMAP_UPPERCASE))
+ {LogParamError(ERR_BAD_FLAGS, LCMapStringA, 0); return 0;}
+ if ((dwMapFlags & LCMAP_HALFWIDTH) && (dwMapFlags & LCMAP_FULLWIDTH))
+ {LogParamError(ERR_BAD_FLAGS, LCMapStringA, 0); return 0;}
+ if ((dwMapFlags & LCMAP_KATAKANA) && (dwMapFlags & LCMAP_HIRAGANA))
+ {LogParamError(ERR_BAD_FLAGS, LCMapStringA, 0); return 0;}
+
+// if ((dwMapFlags != 0) &&
+// ((dwMapFlags & (LCMAP_LOWERCASE | LCMAP_UPPERCASE | LCMAP_SORTKEY |
+// NORM_IGNORECASE | NORM_IGNORENONSPACE | NORM_IGNORESYMBOLS |
+// NORM_IGNOREWIDTH | NORM_IGNOREKANATYPE |
+// LCMAP_HALFWIDTH | LCMAP_FULLWIDTH | LCMAP_HIRAGANA | LCMAP_KATAKANA))
+// == 0))
+// {LogParamError(ERR_BAD_FLAGS, LCMapStringA, 0); return 0;}
+#else
+ if ((dwMapFlags & (LCMAP_UPPERCASE | LCMAP_LOWERCASE | LCMAP_SORTKEY |
+ NORM_IGNORECASE | NORM_IGNORENONSPACE | NORM_IGNORESYMBOLS)) == 0)
+ {LogParamError(ERR_BAD_FLAGS, LCMapStringA, 0); return 0;}
+ if ((dwMapFlags & LCMAP_LOWERCASE) && (dwMapFlags & ~LCMAP_LOWERCASE) != 0)
+ {LogParamError(ERR_BAD_FLAGS, LCMapStringA, 0); return 0;}
+ if ((dwMapFlags & LCMAP_UPPERCASE) && (dwMapFlags & ~LCMAP_UPPERCASE) != 0)
+ {LogParamError(ERR_BAD_FLAGS, LCMapStringA, 0); return 0;}
+ if ((dwMapFlags & LCMAP_SORTKEY) &&
+ (dwMapFlags & ~(LCMAP_SORTKEY | NORM_IGNORECASE |
+ NORM_IGNORENONSPACE | NORM_IGNORESYMBOLS)) != 0)
+ {LogParamError(ERR_BAD_FLAGS, LCMapStringA, 0); return 0;}
+#endif
+#endif
+
+ if (lcid != g_lcidCurrent) {
+ if (!SetupLcid(lcid))
+ {retval = 0; goto Finish; }
+ }
+
+ // Get length of string if needed.
+ if (cchSrc == -1)
+ cchSrc = STRLEN(lpSrcStr) + 1;
+
+ // Handle SortKey case with seperate routine.
+ if (dwMapFlags & LCMAP_SORTKEY) {
+#ifdef FE_DBCS
+ if(fDBCS){
+ return ((fJapan) ? CreateSortKeyJ : CreateSortKeyKTP)
+ (lpSrcStr, cchSrc, lpDestStr, cchDest, dwMapFlags);
+ }
+#endif
+ return CreateSortKey(
+ lpSrcStr, cchSrc, lpDestStr, cchDest, dwMapFlags);
+ }
+
+#ifdef FE_DBCS
+ if(fDBCS)
+ return ((fJapan) ? MapStringJ : MapStringKTP)
+ (dwMapFlags, lpSrcStr, cchSrc, lpDestStr, cchDest);
+
+ // else use the Single Byte code system.
+ //
+ // Note : in FE countries, we often map DB chars into SB chars.
+ // So we can map one string into the SHORTER length.
+ // This is why we don't compare cchDest with cchSrc...
+#endif
+
+ // See if user requested destination size, and check dest size big enough
+ if (cchDest == 0)
+ {retval = cchSrc; goto Finish;} // cchSrc = size needed including NUL
+ else if (cchDest < cchSrc)
+ {retval = 0; goto Finish;} // Error - dest too small
+
+ retval = cchSrc;
+
+ if (dwMapFlags & (LCMAP_LOWERCASE | LCMAP_UPPERCASE)) {
+ // Get pointer mapping table.
+ pMap = (dwMapFlags & LCMAP_LOWERCASE)
+ ? g_pstrinfo->prgbLCase : g_pstrinfo->prgbUCase;
+
+ // Loop through each character, and map.
+ while (cchSrc--) {
+ *lpDestStr++ = pMap[(unsigned char) *lpSrcStr++];
+ }
+ } else
+ MEMCPY(lpDestStr, lpSrcStr, cchSrc);
+
+
+ /* DROP THRU */
+Finish:
+ return retval;
+
+}
+
+#ifdef FE_DBCS /* { */
+
+int
+GetStringTypeJ(
+ unsigned long dwInfoType,
+ const unsigned char FAR* lpSrcStr, int cchSrc,
+ unsigned short FAR* lpwDest)
+{
+ STRINFO_J FAR* pstrinfo;
+
+ // Assumption : cchSrc should have the correct length.
+ // the caller is responsible for setting cchSrc.
+
+ ASSERT(fJapan);
+ g_dwFlags = 0;
+ pstrinfo = (STRINFO_J FAR*)g_pstrinfo;
+
+ while (cchSrc)
+ {
+ /* Get a copy of the next character in the string (inc ptrs later) */
+ unsigned wCh = *lpSrcStr;
+ int cch = (cchSrc>1 && isDbcsJ(wCh,0)) ? 2 : 1;
+ if (cch==2)
+ wCh = (wCh << 8) + *(lpSrcStr+1);
+
+ /* if it can map through the tables, convert to an index */
+ if (wCh < 0x87A0)
+ wCh &= 0x0FFF; /* 0x00nn -> 0x00nn, 81nn->01nn, etc.. */
+
+ /* Now convert the character to the required CTYPE value */
+ switch (dwInfoType) {
+ default: // CT_CTYPE1
+ if (wCh & 0x8000)
+ *lpwDest = C1_ALPHA; /* all Kanji are text */
+ else
+ {
+ wCh <<= 1; /* WORD offset, not BYTE */
+ *lpwDest = (unsigned short)
+ (pstrinfo->pbC1JPN[wCh]*256 + pstrinfo->pbC1JPN[wCh+1]);
+ }
+ break;
+
+ case CT_CTYPE2:
+ if (wCh & 0x8000)
+ *lpwDest = 0;
+ else
+ *lpwDest = (unsigned short)(pstrinfo->pbC2JPN[wCh]);
+ break;
+
+ case CT_CTYPE3:
+ if (wCh & 0x8000)
+ *lpwDest = C3_IDEOGRAPH+C3_ALPHA; /* All Kanji are text */
+ else
+ {
+ wCh <<= 1; /* WORD offset, not BYTE */
+ *lpwDest = (unsigned short)
+ (pstrinfo->pbC3JPN[wCh]*256 + pstrinfo->pbC3JPN[wCh+1]);
+ }
+ break;
+ }
+ /* Prepare for the next character in the stream (inc pointers) */
+ cchSrc -= cch;
+ lpSrcStr += cch;
+ lpwDest++;
+ }
+ return TRUE;
+}
+
+int
+GetStringTypeKTP(
+ unsigned long dwInfoType,
+ const unsigned char FAR* lpSrcStr, int cchSrc,
+ unsigned short FAR* lpwDest)
+{
+ TYPETABLE FAR* prgtypetable;
+ unsigned cTypetable, uMin, uMax, uMid, ch;
+
+ // Assumption : cchSrc should have the correct length.
+ // the caller is responsible for setting cchSrc.
+
+ ASSERT(fKoreaTaiwanPrc);
+
+ cTypetable = ((STRINFO_KTP FAR*)g_pstrinfo)->cTypetable;
+ prgtypetable = ((STRINFO_KTP FAR*)g_pstrinfo)->prgtypetable;
+
+ while (cchSrc--) {
+
+ ch = *lpSrcStr++;
+ if (cchSrc
+ && ( (fKorea && isDbcsK(ch, *lpSrcStr))
+ || (fTaiwan && isDbcsT(ch, *lpSrcStr))
+ || (fPrc && isDbcsP(ch, *lpSrcStr))))
+ cchSrc--, ch = (ch << 8) + *lpSrcStr++;
+
+ uMin = 0;
+ uMax = cTypetable; // out of array bound - seems tricky, too
+
+ while( uMin + 1 < uMax ) { // binary search
+ uMid = (uMin + uMax)/2;
+ if (prgtypetable[uMid].wStart > ch)
+ uMax = uMid;
+ else
+ uMin = uMid;
+ }
+
+ // we'll use uMin, not uMid !!
+ switch(dwInfoType){
+ case CT_CTYPE1:
+ *lpwDest = prgtypetable[uMin].TypeC1;
+ break;
+ case CT_CTYPE2:
+ *lpwDest = prgtypetable[uMin].TypeC2;
+ break;
+ case CT_CTYPE3:
+ *lpwDest = prgtypetable[uMin].TypeC3;
+ break;
+ }
+ ++lpwDest;
+ }
+
+ return TRUE;
+}
+
+#endif /* } */
+
+/***
+*GetStringTypeA - get character types
+*Purpose:
+* Gets character types for a string.
+*
+*Entry:
+* lcid - locale governing the mapping
+* dwInfoType - one of
+* CT_CTYPE1
+* CT_CTYPE2
+* CT_CTYPE3
+* lpSrcStr - pointer to sting to map
+* cchSrc - length of string, or -1 for NULL terminated
+* lpwDest - pointer to word array of length cchSrc
+*
+*Exit:
+* returns TRUE on succes, FALSE on failure.
+*
+***********************************************************************/
+NLSAPI_(int) EXPORT
+GetStringTypeA(
+ LCID lcid,
+ unsigned long dwInfoType,
+ const char FAR* lpSrcStr, int cchSrc,
+ unsigned short FAR* lpwDest)
+{
+ unsigned short FAR* pwCur;
+ const unsigned char FAR *pchCur;
+
+#ifdef _DEBUG
+ // Parameter validation.
+ if (cchSrc < -1)
+ {LogParamError(ERR_BAD_VALUE, GetStringTypeA, 0); return FALSE;}
+ if (cchSrc != -1 && IsBadReadPtr(lpSrcStr, cchSrc))
+ {LogParamError(ERR_BAD_PTR, GetStringTypeA, 0); return FALSE;}
+ if (cchSrc == -1 && IsBadStringPtr(lpSrcStr, 0x7FFF))
+ {LogParamError(ERR_BAD_STRING_PTR, GetStringTypeA, 0); return FALSE;}
+ if (dwInfoType != CT_CTYPE1 && dwInfoType != CT_CTYPE2 &&
+ dwInfoType != CT_CTYPE3)
+ {LogParamError(ERR_BAD_FLAGS, GetStringTypeA, 0); return FALSE;}
+#endif
+
+ // Get length of string if needed.
+ if (cchSrc == -1)
+ cchSrc = lstrlen(lpSrcStr);
+
+#ifdef _DEBUG
+ // More param validation.
+ if (IsBadWritePtr(lpwDest, cchSrc * sizeof(unsigned short)))
+ {LogParamError(ERR_BAD_PTR, GetStringTypeA, 0); return FALSE;}
+#endif
+
+ // Get pointer to tables.
+ if (lcid != g_lcidCurrent) {
+ if (!SetupLcid(lcid))
+ goto Error; // Error - bad lcid.
+ }
+
+#ifdef FE_DBCS
+ if(fDBCS)
+ return ((fJapan) ? GetStringTypeJ : GetStringTypeKTP)
+ (dwInfoType, lpSrcStr, cchSrc, lpwDest);
+#endif
+
+ // Loop through each character, and get type.
+ pwCur = lpwDest;
+ pchCur = lpSrcStr;
+
+ {
+ WORD w;
+ WORD FAR* prgw = (dwInfoType == CT_CTYPE3)
+ ? g_pstrinfo->prgwCType3 : g_pstrinfo->prgwCType12;
+ while (cchSrc--) {
+ w = prgw[(BYTE)*pchCur++];
+ // combining ctype1 and ctype2 into the same table saves 4K from the DLL
+ switch (dwInfoType) {
+ case CT_CTYPE1:
+ w = w & 0x0fff; // extract ctype1 bits
+ break;
+ case CT_CTYPE2:
+ w = (w & 0xf000) >> 12; // extract ctype2 bits
+ break;
+ default:
+ break;
+ }
+ *pwCur++ = w;
+ }
+ }
+
+ return TRUE;
+
+Error:
+ return FALSE;
+}
+
+
+#if OE_WIN
+/***
+*NotifyNLSInfoChanged - Notify ole2disp that WIN.INI has changed
+*Purpose:
+* BSTR->Date and Date->BSTR conversions in ole2disp make heavy use of
+* NLS functions. For speed, they cache NLS info, but if the WIN.INI
+* changes, the cache must be invalidated. This function calls a callback
+* in ole2disp, if the callback function is registered.
+*
+*Entry:
+* None
+*
+*Exit:
+* None
+*
+***********************************************************************/
+void NotifyNLSInfoChanged(void)
+{
+ // if the callback is registered, call it
+ if (g_pfnCacheNotifyProc)
+ (*g_pfnCacheNotifyProc)();
+}
+
+/***
+*RegisterNLSInfoChanged - Private API for ole2disp to get WM_WININICHANGED
+*Purpose:
+* ole2disp.dll calls this to register a callback function which will be
+* called whenever the WIN.INI file changes.
+*
+*Entry:
+* lpfnNotifyProc - pointer to notify callback function, or NULL to
+* unhook the callback
+*
+*Exit:
+* TRUE if callback function set or cleared successfully.
+* FALSE if another callback is already registered. Note that only one
+* callback can be registered (that is, only ole2disp can use it)
+*
+***********************************************************************/
+NLSAPI_(int) EXPORT
+RegisterNLSInfoChanged(FARPROC lpfnNotifyProc)
+{
+ if (lpfnNotifyProc == NULL) { // caller wants to un-register itself
+ g_pfnCacheNotifyProc = NULL;
+ return TRUE;
+ }
+
+ if (g_pfnCacheNotifyProc)
+ return FALSE;
+
+ g_pfnCacheNotifyProc = lpfnNotifyProc;
+ return TRUE;
+}
+
+#endif
diff --git a/private/oleauto/src/dispatch/nlsdbcs.h b/private/oleauto/src/dispatch/nlsdbcs.h
new file mode 100644
index 000000000..804e746fc
--- /dev/null
+++ b/private/oleauto/src/dispatch/nlsdbcs.h
@@ -0,0 +1,176 @@
+// FE specific flags
+
+// Country informations
+
+#define LCID_CHINA_T 0x404 // traditional
+#define LCID_CHINA_S 0x804 // simplified
+#define LCID_JAPAN 0x411
+#define LCID_KOREA 0x412
+
+unsigned char bFEflag;
+
+#define bitJapan 1
+#define bitKorea 2
+#define bitChinaT 4 // Traditional
+#define bitChinaS 8 // Simplified
+#define bitTaiwan bitChinaT
+#define bitPrc bitChinaS
+
+#define fDBCS (bFEflag)
+
+#define fJapan (bFEflag & bitJapan)
+#define fKorea (bFEflag & bitKorea)
+#define fTaiwan (bFEflag & bitTaiwan)
+#define fPrc (bFEflag & bitPrc)
+
+#define fJapanKorea (bFEflag & (bitJapan | bitKorea))
+#define fJapanTaiwan (bFEflag & (bitJapan | bitTaiwan))
+#define fKoreaTaiwan (bFEflag & (bitKorea | bitTaiwan))
+
+#define fJapanKoreaPrc (bFEflag & (bitJapan | bitKorea | bitPrc))
+#define fJapanTaiwanPrc (bFEflag & (bitJapan | bitTaiwan | bitPrc))
+#define fKoreaTaiwanPrc (bFEflag & (bitKorea | bitTaiwan | bitPrc))
+
+#define isDbcsJ( c, next) ((c >= 0x80 && c <= 0xA0) || (c >= 0xE0 && c <= 0xFF))
+#define isDbcsK( c1, c2 ) (c1 > 0xA0 && c1 < 0xFF && c2 > 0xA0 && c2 < 0xFF)
+#define isDbcsT( c1, c2 ) (c1 > 0x80 && c1 < 0xFF && c2 > 0x3F && c2 < 0xFF)
+#define isDbcsP( c1, c2 ) (c1 > 0xA0 && c1 < 0xFF && c2 > 0xA0 && c2 < 0xFF)
+
+
+// for FE string comparison
+
+unsigned long g_dwFlags; // global flag
+
+typedef struct tagCOMPSTRINGINFO{
+ unsigned priwt;
+ unsigned char secwt;
+ unsigned char secflg; //(only needed for Japan)
+} COMPSTRINGINFO;
+
+
+// Japanese specific constants, globals
+
+/* charcter type */
+//#define chTypePunc 0
+//#define chTypeNum 1
+//#define chTypeRoman 2
+//#define chTypeGreek 3
+//#define chTypeRuss 4
+//#define chTypeKana 5
+//#define chTypeKanji 6
+
+//typedef struct JPNConvCode
+//{
+// unsigned char bSrcHi; // 1st byte of source char
+// unsigned char bSrcLo; // 2nd
+// unsigned char bPriwt;
+// unsigned char bSecwt;
+//} JPNConvCode;
+
+//typedef struct JPNConvSort
+//{
+// unsigned char bPriwt;
+// unsigned char bSecwt;
+// unsigned char bSrcHi;
+// unsigned char bSrcLo;
+//} JPNConvSort;
+
+// Indices of the masks in the sortmasks words
+//#define JPN_MASK_CHARTYPE 0 // Mask to give character type
+//#define JPN_MASK_NORMALKANA 1 // Mask to give normal naka
+//#define JPN_MASK_IGNORECASE 2 // Maks for ignoring case
+//#define JPN_MASK_IGNOREKANATYPE 3 // Maks for ignoring japanese kana type
+//#define JPN_MASK_IGNOREWIDTH 4 // Mask for ignoring width pitch character
+
+// japanese sort weight bit
+//#define JPN_PITCHBIT 0x01
+//#define JPN_CASEBIT 0x02
+//#define JPN_NORMALKANABIT 0x04
+
+//#define JPN_SB_KANA 0xA4 // single-byte katakana secondary weight
+//#define JPN_SB_TEN 0xDE // single-byte katakana ten
+//#define JPN_SB_MARU 0xDF // single-byte katakana maru
+
+//unsigned short cKana2Sort, cCode2Sort, cSort2Code;
+
+//#define isJpnKanjiPriwt(priwt) ((priwt >= 0xBF) && (priwt <= 0xFE))
+
+
+// Korean specific constants, globals
+
+typedef struct SORTWEIGHT
+{
+ unsigned wStart; // Starting code value of a segment
+ unsigned wPriwt; // Primary Weight
+ unsigned char bSecwt; // Secondary Weight
+ unsigned char bMode; // Mapping mode : 1to1, Many_to1, case/pitch
+} SORTWEIGHT;
+
+typedef struct MAPTABLE
+{
+ unsigned wPriwt; // Starting Priwt value of a segment
+ unsigned wCount; // Number of chars in one segment
+ unsigned wCode[4]; // Starting Code value of dst. segment
+} MAPTABLE;
+
+typedef struct TYPETABLE
+{
+ unsigned wStart;
+ unsigned int TypeC1;
+ unsigned char TypeC2;
+ unsigned char TypeC3;
+} TYPETABLE;
+
+#define MODE_1TO1 0 // Constants for SORTWEIGHT.bMode field
+#define MODE_MTO1 1
+#define MODE_CONV 2
+
+#define KOR_CASEBIT 2
+#define KOR_PITCHBIT 1
+
+typedef struct tagSTRINFO_KTP
+{
+ SORTWEIGHT FAR* prgsortweight;
+ MAPTABLE FAR* prgmaptable;
+ TYPETABLE FAR* prgtypetable;
+
+ unsigned int cSortweight;
+ unsigned int cMaptable;
+ unsigned int cTypetable;
+}
+STRINFO_KTP;
+
+typedef struct tagSTRINFO_J
+{
+ unsigned char FAR* pbPriHi;
+ unsigned char FAR* pbPriLo;
+ unsigned char FAR* pbSecWgt;
+ unsigned char FAR* pbSecFlg;
+ unsigned char FAR* pbMasks;
+ unsigned char FAR* pbMaps;
+ unsigned char FAR* pbIgnore;
+ unsigned char FAR* pbC1JPN;
+ unsigned char FAR* pbC2JPN;
+ unsigned char FAR* pbC3JPN;
+}
+STRINFO_J;
+
+
+#if OE_MAC
+extern void LoadNlsInfo0404(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0411(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0412(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0804(LCINFO **, STRINFO **);
+#else //OE_MAC
+extern STRINFO_KTP NLSALLOC(0404) g_strinfo0404;
+extern LCINFO NLSALLOC(0404) g_rglcinfo0404[];
+
+extern STRINFO_J NLSALLOC(0411) g_strinfo0411;
+extern LCINFO NLSALLOC(0411) g_rglcinfo0411[];
+
+extern STRINFO_KTP NLSALLOC(0412) g_strinfo0412;
+extern LCINFO NLSALLOC(0412) g_rglcinfo0412[];
+
+extern STRINFO_KTP NLSALLOC(0804) g_strinfo0804;
+extern LCINFO NLSALLOC(0804) g_rglcinfo0804[];
+#endif //OE_MAC
diff --git a/private/oleauto/src/dispatch/nlshelp.cpp b/private/oleauto/src/dispatch/nlshelp.cpp
new file mode 100644
index 000000000..82ac54323
--- /dev/null
+++ b/private/oleauto/src/dispatch/nlshelp.cpp
@@ -0,0 +1,276 @@
+/***
+*nlshelp.cpp
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+*
+* This module implements Ansi NLS wrapper functions for WIN32
+*
+*Revision History:
+*
+* [00] 30-Jun-93 tomteng: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+ASSERTDATA
+
+#if OE_WIN32
+
+#if defined(_X86_) // only need this stuff if supporting Chicago
+
+// Chicago doesn't have these functions, hence we switch at run-time for speed
+// on Daytona.
+//---------------------------------------------------------------------
+// Unicode NLS Wrapper Functions (for Win32)
+//---------------------------------------------------------------------
+
+
+// REVIEW: The code page used in the MultiByteToWideChar & WideCharToMultByte
+// functions should really be the primary code page assoicated with
+// the inputed lcid instead of the default Ansi code page (CP_ACP).
+// Need to correct this.
+
+
+EXTERN_C INTERNAL_(int)
+CompareString(
+ LCID lcid,
+ unsigned long dwFlags,
+ LPWSTR lpwStr1, int cch1,
+ LPWSTR lpwStr2, int cch2)
+{
+ int iRet;
+ int cbStr1, cbStr2;
+ LPSTR lpStr1, lpStr2;
+ BOOL badConversion;
+
+ if (!g_fChicago) {
+ return CompareStringW(lcid, dwFlags, lpwStr1, cch1, lpwStr2, cch2);
+ }
+
+ iRet = 0;
+ lpStr1 = lpStr2 = NULL;
+ badConversion = FALSE;
+
+ // special case zero-length strings -- conversions below would screw up
+ // required behavior.
+
+ if (cch1 == 0) {
+ if (cch2 == 0)
+ return 2; // 1 == 2
+ else
+ return 1; // 1 < 2
+ } else if (cch2 == 0) {
+ return 3; // 1 > 2
+ }
+
+ cbStr1 = WideCharToMultiByte(CP_ACP, NULL, lpwStr1, cch1,
+ NULL, 0, NULL, &badConversion);
+ if (cbStr1 == 0 || badConversion)
+ goto LError0;
+
+ cbStr2 = WideCharToMultiByte(CP_ACP, NULL, lpwStr2, cch2,
+ NULL, 0, NULL, &badConversion);
+ if (cbStr2 == 0 || badConversion)
+ goto LError0;
+
+ if(DispAlloc(cbStr1, (VOID FAR* FAR*) &lpStr1) != NOERROR)
+ goto LError0;
+
+ if(DispAlloc(cbStr2, (VOID FAR* FAR*) &lpStr2) != NOERROR)
+ goto LError0;
+
+ WideCharToMultiByte(CP_ACP, NULL, lpwStr1, cch1,
+ lpStr1, cbStr1, NULL, &badConversion);
+ if (badConversion) // UNDONE: need to check the 2nd time?
+ goto LError0;
+
+ WideCharToMultiByte(CP_ACP, NULL, lpwStr2, cch2,
+ lpStr2, cbStr2, NULL, &badConversion);
+ if (badConversion) // UNDONE: need to check the 2nd time?
+ goto LError0;
+
+ iRet = CompareStringA(lcid, dwFlags, lpStr1, cbStr1, lpStr2, cbStr2);
+
+LError0:
+
+ DispFree(lpStr1);
+ DispFree(lpStr2);
+
+ return iRet;
+}
+
+
+EXTERN_C INTERNAL_(int)
+LCMapString(
+ LCID lcid,
+ unsigned long dwMapFlags,
+ const WCHAR FAR* lpwSrcStr,
+ int cchSrc,
+ WCHAR FAR* lpwDestStr,
+ int cchDest)
+{
+ BOOL badConversion;
+ LPSTR lpSrcStr, lpDestStr;
+ int iRet, cbSrcStr, cbDestStr;
+
+ if (!g_fChicago) {
+ return LCMapStringW(lcid, dwMapFlags,
+ lpwSrcStr, cchSrc,
+ lpwDestStr, cchDest);
+ }
+
+ iRet = 0;
+ badConversion = FALSE;
+ lpSrcStr = lpDestStr = NULL;
+
+ // Translate source string to ansi
+ cbSrcStr = WideCharToMultiByte(CP_ACP, NULL, lpwSrcStr, cchSrc,
+ NULL, 0, NULL, &badConversion);
+
+ // NOTE: a zero-length source string should fall out here & return 0
+ if (cbSrcStr == 0 || badConversion)
+ goto LError0;
+
+ if(DispAlloc(cbSrcStr, (VOID FAR* FAR*) &lpSrcStr) != NOERROR)
+ goto LError0;
+
+ WideCharToMultiByte(CP_ACP, NULL, lpwSrcStr, cchSrc,
+ lpSrcStr, cbSrcStr, NULL, &badConversion);
+ if (badConversion) // UNDONE: need to check the 2nd time?
+ goto LError0;
+
+ // Alloc Destination ANSI string space
+ if ((cbDestStr = LCMapStringA(lcid, dwMapFlags,
+ lpSrcStr, cbSrcStr, NULL, 0)) == 0)
+ goto LError0;
+
+ if(DispAlloc(cbDestStr, (VOID FAR* FAR*) &lpDestStr) != NOERROR)
+ goto LError0;
+
+ // Map characters
+ if ((iRet = LCMapStringA(lcid, dwMapFlags,
+ lpSrcStr, cbSrcStr,
+ lpDestStr, cbDestStr)) == 0)
+ goto LError0;
+
+ // Convert ansi character back to wide characters
+ if (MultiByteToWideChar(CP_ACP, MB_PRECOMPOSED,
+ lpDestStr, cbDestStr, lpwDestStr, cchDest) == 0)
+ iRet = 0;
+
+LError0:;
+ DispFree(lpDestStr);
+ DispFree(lpSrcStr);
+ return iRet;
+}
+
+
+EXTERN_C INTERNAL_(int)
+GetStringTypeEx(
+ LCID Locale,
+ DWORD dwInfoType,
+ const WCHAR FAR* lpwSrcStr,
+ int cchSrc,
+ LPWORD lpCharType)
+{
+ BOOL badConversion;
+ #define MAX_BUFSIZE 512
+ char lpStr[MAX_BUFSIZE];
+ int result, cbSrcStr;
+
+ if (!g_fChicago) {
+ return(GetStringTypeExW(Locale, dwInfoType, lpwSrcStr, cchSrc, lpCharType));
+ }
+
+ result=0;
+ badConversion = FALSE;
+
+ // Translate source string to ansi
+ cbSrcStr = WideCharToMultiByte(CP_ACP, NULL, lpwSrcStr, cchSrc,
+ lpStr, MAX_BUFSIZE, NULL, &badConversion);
+
+ // NOTE: a zero-length source string should fall out here & return 0
+ if (cbSrcStr == 0 || badConversion)
+ goto LError0;
+
+ result = GetStringTypeExA(Locale, dwInfoType, lpStr, cbSrcStr, lpCharType);
+
+LError0:;
+ return result;
+
+} /* GetStringTypeEx */
+
+EXTERN_C INTERNAL_(int)
+GetLocaleInfo(
+ LCID lcid,
+ LCTYPE lcType,
+ WCHAR FAR* lpwStr,
+ int cch)
+{
+ #define MAX_BUFSIZE 512
+ char lpStr[MAX_BUFSIZE];
+ int result;
+
+ if (!g_fChicago) {
+ return GetLocaleInfoW(lcid, lcType, lpwStr, cch);
+ }
+
+ result = GetLocaleInfoA(lcid, lcType, lpStr, MAX_BUFSIZE);
+
+ if (MultiByteToWideChar(CP_ACP, MB_PRECOMPOSED,
+ lpStr, -1, lpwStr, cch) == 0)
+ return 0;
+
+ return result;
+}
+
+EXTERN_C INTERNAL_(int)
+IsCharAlpha(WCHAR ch)
+{
+ char chA;
+ BOOL badConversion;
+
+ if (!g_fChicago) {
+ return IsCharAlphaW(ch);
+ }
+
+ badConversion = FALSE;
+
+ // Translate source char to ansi
+ WideCharToMultiByte(CP_ACP, NULL, &ch, 1, &chA, 1, NULL, &badConversion);
+ if (badConversion)
+ return 0;
+
+ return IsCharAlphaA(chA);
+}
+
+EXTERN_C INTERNAL_(int)
+IsCharAlphaNumeric(WCHAR ch)
+{
+ char chA;
+ BOOL badConversion;
+
+ if (!g_fChicago) {
+ return IsCharAlphaNumericW(ch);
+ }
+
+ badConversion = FALSE;
+
+ // Translate source char to ansi
+ WideCharToMultiByte(CP_ACP, NULL, &ch, 1, &chA, 1, NULL, &badConversion);
+ if (badConversion)
+ return 0;
+
+ return IsCharAlphaNumericA(chA);
+
+}
+
+#endif //_X86_
+
+#endif //OE_WIN32
diff --git a/private/oleauto/src/dispatch/nlsintrn.h b/private/oleauto/src/dispatch/nlsintrn.h
new file mode 100644
index 000000000..12af159f6
--- /dev/null
+++ b/private/oleauto/src/dispatch/nlsintrn.h
@@ -0,0 +1,409 @@
+/***
+*nlsintrn.h - National language support functions.
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file defines the layout of the NLS resource used by the
+* NLS functions.
+*
+*Revision History:
+*
+* [00] 12-Nov-92 petergo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#ifndef RC_INVOKED
+# pragma pack(1)
+#endif
+
+/***
+*types
+*
+***********************************************************************/
+
+typedef unsigned int ILCINFO; // index into rglcinfo array into header
+
+
+/***
+*constants
+*
+***********************************************************************/
+
+// Index 0 is unused
+#define ILCINFO_FIRST 1
+
+// maximum of the sequential LCTYPEs from olenls.h
+//
+#define LCTYPE_LAST LOCALE_INEGSEPBYSPACE
+#define LCTYPE_MAX LCTYPE_LAST+1
+
+#define ILCINFO_SENGCOUNTRY LCTYPE_LAST+1 // ILCINFO for LOCALE_SENGCOUNTRY
+#define ILCINFO_SENGLANGUAGE LCTYPE_LAST+2 // ILCINFO for LOCALE_SENGLANGUAGE
+
+#if VBA2
+#define ILCINFO_IFIRSTDAYOFWEEK LCTYPE_LAST+3
+#define ILCINFO_IFIRSTWEEKOFYEAR LCTYPE_LAST+4
+#define ILCINFO_IDEFAULTANSICODEPAGE LCTYPE_LAST+5
+#define ILCINFO_INEGNUMBER LCTYPE_LAST+6
+#define ILCINFO_STIMEFORMAT LCTYPE_LAST+7
+#define ILCINFO_ITIMEMARKPOSN LCTYPE_LAST+8
+#define ILCINFO_ICALENDARTYPE LCTYPE_LAST+9
+#define ILCINFO_IOPTIONALCALENDAR LCTYPE_LAST+10
+#define ILCINFO_SMONTHNAME13 LCTYPE_LAST+11
+#define ILCINFO_SABBREVMONTHNAME13 LCTYPE_LAST+12
+
+#define ILCINFO_LAST ILCINFO_SABBREVMONTHNAME13
+#else
+#define ILCINFO_LAST ILCINFO_SENGLANGUAGE
+#endif
+#define ILCINFO_MAX ILCINFO_LAST+1
+
+// A single item of locale info
+typedef struct tagLCINFO{
+ unsigned char cch;
+ BYTE FAR* prgb; // UNDONE: make NEAR, if possible!!!
+}LCINFO;
+
+
+// expansion table entry
+typedef struct tagEXPANSION{
+ WORD w1;
+ WORD w2;
+}EXPANSION;
+
+// digraph table entry
+typedef struct tagDIGRAPH{
+ WORD w;
+ union{
+ BYTE cEntries;
+ BYTE ch2;
+ }
+#if defined(NONAMELESSUNION) || (defined(_MAC) && !defined(__cplusplus) && !defined(_MSC_VER))
+ u
+#endif
+ ;
+}DIGRAPH;
+
+
+#if defined(NONAMELESSUNION) || (defined(_MAC) && !defined(__cplusplus) && !defined(_MSC_VER))
+# define D_UNION(X, Y) ((X)->u.Y)
+#else
+# define D_UNION(X, Y) ((X)->Y)
+#endif
+
+#define D_ENTRY(X) D_UNION(X, cEntries)
+#define D_CH(X) D_UNION(X, ch2)
+
+
+// The string info for a single locale
+//
+// (NOTE: the STRINFO struct for FE locales will be totally different
+// see nlsdbcs.h for the corresponding FE structs)
+//
+
+typedef struct tagSTRINFO
+{
+ BYTE FAR* prgbUCase;
+ BYTE FAR* prgbLCase;
+
+ WORD FAR* prgwCType12;
+ WORD FAR* prgwCType3;
+
+ WORD FAR* prgwSort;
+ EXPANSION FAR* prgexp;
+ DIGRAPH FAR* prgdig;
+
+ int fRevDW;
+
+} STRINFO;
+
+typedef struct tagNLSDATA {
+ LCID lcid;
+#if OE_MAC
+ int region; // mac region code
+#endif
+#if OE_WIN
+ LCINFO lcinfoICOUNTRY;
+ LCINFO lcinfoSABBREVLANGNAME;
+#endif
+#if OE_MAC
+ void (FAR* LoadNlsInfo) (LCINFO **, STRINFO **);
+#endif //OE_MAC
+ LCINFO FAR* prglcinfo;
+#if !OE_MAC // not needed for mac
+ STRINFO FAR* pstrinfo;
+#endif //!OE_MAC
+} NLSDATA;
+
+
+/*
+ * The sortweight WORD is organized as follows,
+ *
+ * +---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+
+ * | X | S | CW | DW | AW |
+ * +---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+
+ * 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0
+ *
+ * AW = Alphanumeric Weight
+ * DW = Diacritic Weight
+ * CW = Case Weight
+ * S = Symbol Bit
+ * X = Special Weight Bit
+ *
+ */
+
+#define AWMASK 0x00FF // Alphanumeric Weight field
+#define AWSHIFT 0
+
+#define DWMASK 0x0700 // Diacritic Weight field
+#define DWSHIFT 8
+
+#define CWMASK 0x3800 // Case Weight field
+#define CWSHIFT 11
+
+#define SYMBOLBIT 0x4000
+#define SPECIALBIT 0x8000 // Indicates Alphanumeric Weight field contains
+ // the special weight
+
+
+//
+// The following AW values have special meaning
+//
+
+// The following marks an "unsortable" character - this is totaly
+// ignored in a string compare.
+#define AW_UNSORTABLE 0 // indicates character is unsortable
+
+// 1 is not used as a weight, it is used as the sort key field separator
+#define AW_DONTUSE 1
+
+#if 0 // these are now encoded in the entire AlphaNumeric weight
+ // field, using the 'SPECIALBIT' field as an indicator.
+// The following special weights mark "unsortable" characters
+// that nudge the string compare slightly
+#define AW_SW1 2 // special weight #1
+#define AW_SW2 3 // special weight #2
+#define AW_SW3 4 // special weight #3
+#define AW_MAXSW 4 // the max special weight
+#endif //0
+
+// the marks an expansion character
+#define AW_EXPANSION 5 // hi byte gives index into expansion table
+
+// this special weight marks the first char of a possible digraph sequence
+#define AW_DIGRAPH 6 // hi byte gives index into compression table
+
+#define AW_MAXSPECIAL 6 // max special AW value
+
+
+
+#if OE_WIN
+# define STRING(X) #X
+# define NLSALLOC(X) __based(__segname(STRING(NLS ## X ## _TEXT)))
+#else
+# define NLSALLOC(X)
+#endif
+
+#if defined(_MAC) && !defined(_PPCMAC)
+#define MACCS __declspec(allocate("_CODE"))
+#else //_MAC
+#define MACCS
+#endif //_MAC
+
+#if OE_MAC
+extern void LoadNlsInfo0403(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0405(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0406(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0407(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0408(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0409(LCINFO **, STRINFO **);
+extern void LoadNlsInfo040a(LCINFO **, STRINFO **);
+extern void LoadNlsInfo040b(LCINFO **, STRINFO **);
+extern void LoadNlsInfo040c(LCINFO **, STRINFO **);
+extern void LoadNlsInfo040e(LCINFO **, STRINFO **);
+extern void LoadNlsInfo040f(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0410(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0413(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0414(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0415(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0416(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0419(LCINFO **, STRINFO **);
+extern void LoadNlsInfo041b(LCINFO **, STRINFO **);
+extern void LoadNlsInfo041d(LCINFO **, STRINFO **);
+extern void LoadNlsInfo041f(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0807(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0809(LCINFO **, STRINFO **);
+extern void LoadNlsInfo080a(LCINFO **, STRINFO **);
+extern void LoadNlsInfo080c(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0810(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0813(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0814(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0816(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0c07(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0c09(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0c0a(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0c0c(LCINFO **, STRINFO **);
+extern void LoadNlsInfo1009(LCINFO **, STRINFO **);
+extern void LoadNlsInfo100c(LCINFO **, STRINFO **);
+extern void LoadNlsInfo1409(LCINFO **, STRINFO **);
+extern void LoadNlsInfo1809(LCINFO **, STRINFO **);
+// BIDI locales
+extern void LoadNlsInfo040d(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0401(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0801(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0c01(LCINFO **, STRINFO **);
+extern void LoadNlsInfo1001(LCINFO **, STRINFO **);
+extern void LoadNlsInfo1401(LCINFO **, STRINFO **);
+extern void LoadNlsInfo1801(LCINFO **, STRINFO **);
+extern void LoadNlsInfo1c01(LCINFO **, STRINFO **);
+extern void LoadNlsInfo2001(LCINFO **, STRINFO **);
+extern void LoadNlsInfo2401(LCINFO **, STRINFO **);
+extern void LoadNlsInfo2801(LCINFO **, STRINFO **);
+extern void LoadNlsInfo2c01(LCINFO **, STRINFO **);
+extern void LoadNlsInfo3001(LCINFO **, STRINFO **);
+extern void LoadNlsInfo3401(LCINFO **, STRINFO **);
+extern void LoadNlsInfo3801(LCINFO **, STRINFO **);
+extern void LoadNlsInfo3c01(LCINFO **, STRINFO **);
+extern void LoadNlsInfo4001(LCINFO **, STRINFO **);
+extern void LoadNlsInfo0429(LCINFO **, STRINFO **);
+
+#else //OE_MAC
+extern LCINFO NLSALLOC(0403) g_rglcinfo0403[];
+extern LCINFO NLSALLOC(0405) g_rglcinfo0405[];
+extern LCINFO NLSALLOC(0406) g_rglcinfo0406[];
+extern LCINFO NLSALLOC(0407) g_rglcinfo0407[];
+extern LCINFO NLSALLOC(0408) g_rglcinfo0408[];
+extern LCINFO NLSALLOC(0409) g_rglcinfo0409[];
+extern LCINFO NLSALLOC(040a) g_rglcinfo040a[];
+extern LCINFO NLSALLOC(040b) g_rglcinfo040b[];
+extern LCINFO NLSALLOC(040c) g_rglcinfo040c[];
+extern LCINFO NLSALLOC(040e) g_rglcinfo040e[];
+extern LCINFO NLSALLOC(040f) g_rglcinfo040f[];
+extern LCINFO NLSALLOC(0410) g_rglcinfo0410[];
+extern LCINFO NLSALLOC(0413) g_rglcinfo0413[];
+extern LCINFO NLSALLOC(0414) g_rglcinfo0414[];
+extern LCINFO NLSALLOC(0415) g_rglcinfo0415[];
+extern LCINFO NLSALLOC(0416) g_rglcinfo0416[];
+extern LCINFO NLSALLOC(0419) g_rglcinfo0419[];
+extern LCINFO NLSALLOC(041b) g_rglcinfo041b[];
+extern LCINFO NLSALLOC(041d) g_rglcinfo041d[];
+extern LCINFO NLSALLOC(041f) g_rglcinfo041f[];
+extern LCINFO NLSALLOC(0807) g_rglcinfo0807[];
+extern LCINFO NLSALLOC(0809) g_rglcinfo0809[];
+extern LCINFO NLSALLOC(080a) g_rglcinfo080a[];
+extern LCINFO NLSALLOC(080c) g_rglcinfo080c[];
+extern LCINFO NLSALLOC(0810) g_rglcinfo0810[];
+extern LCINFO NLSALLOC(0813) g_rglcinfo0813[];
+extern LCINFO NLSALLOC(0814) g_rglcinfo0814[];
+extern LCINFO NLSALLOC(0816) g_rglcinfo0816[];
+extern LCINFO NLSALLOC(0c07) g_rglcinfo0c07[];
+extern LCINFO NLSALLOC(0c09) g_rglcinfo0c09[];
+extern LCINFO NLSALLOC(0c0a) g_rglcinfo0c0a[];
+extern LCINFO NLSALLOC(0c0c) g_rglcinfo0c0c[];
+extern LCINFO NLSALLOC(1009) g_rglcinfo1009[];
+extern LCINFO NLSALLOC(100c) g_rglcinfo100c[];
+extern LCINFO NLSALLOC(1409) g_rglcinfo1409[];
+extern LCINFO NLSALLOC(1809) g_rglcinfo1809[];
+// BIDI locales
+extern LCINFO NLSALLOC(040d) g_rglcinfo040d[];
+extern LCINFO NLSALLOC(0401) g_rglcinfo0401[];
+extern LCINFO NLSALLOC(0801) g_rglcinfo0801[];
+extern LCINFO NLSALLOC(0c01) g_rglcinfo0c01[];
+extern LCINFO NLSALLOC(1001) g_rglcinfo1001[];
+extern LCINFO NLSALLOC(1401) g_rglcinfo1401[];
+extern LCINFO NLSALLOC(1801) g_rglcinfo1801[];
+extern LCINFO NLSALLOC(1c01) g_rglcinfo1c01[];
+extern LCINFO NLSALLOC(2001) g_rglcinfo2001[];
+extern LCINFO NLSALLOC(2401) g_rglcinfo2401[];
+extern LCINFO NLSALLOC(2801) g_rglcinfo2801[];
+extern LCINFO NLSALLOC(2c01) g_rglcinfo2c01[];
+extern LCINFO NLSALLOC(3001) g_rglcinfo3001[];
+extern LCINFO NLSALLOC(3401) g_rglcinfo3401[];
+extern LCINFO NLSALLOC(3801) g_rglcinfo3801[];
+extern LCINFO NLSALLOC(3c01) g_rglcinfo3c01[];
+extern LCINFO NLSALLOC(4001) g_rglcinfo4001[];
+extern LCINFO NLSALLOC(0429) g_rglcinfo0429[];
+
+
+extern STRINFO NLSALLOC(0403) g_strinfo0403;
+extern STRINFO NLSALLOC(0405) g_strinfo0405;
+extern STRINFO NLSALLOC(0406) g_strinfo0406;
+extern STRINFO NLSALLOC(0407) g_strinfo0407;
+extern STRINFO NLSALLOC(0408) g_strinfo0408;
+extern STRINFO NLSALLOC(0409) g_strinfo0409;
+extern STRINFO NLSALLOC(040a) g_strinfo040a;
+extern STRINFO NLSALLOC(040b) g_strinfo040b;
+extern STRINFO NLSALLOC(040c) g_strinfo040c;
+extern STRINFO NLSALLOC(040e) g_strinfo040e;
+extern STRINFO NLSALLOC(040f) g_strinfo040f;
+extern STRINFO NLSALLOC(0410) g_strinfo0410;
+extern STRINFO NLSALLOC(0413) g_strinfo0413;
+extern STRINFO NLSALLOC(0414) g_strinfo0414;
+extern STRINFO NLSALLOC(0415) g_strinfo0415;
+extern STRINFO NLSALLOC(0416) g_strinfo0416;
+extern STRINFO NLSALLOC(0419) g_strinfo0419;
+extern STRINFO NLSALLOC(041b) g_strinfo041b;
+extern STRINFO NLSALLOC(041d) g_strinfo041d;
+extern STRINFO NLSALLOC(041f) g_strinfo041f;
+extern STRINFO NLSALLOC(0807) g_strinfo0807;
+extern STRINFO NLSALLOC(0809) g_strinfo0809;
+extern STRINFO NLSALLOC(080a) g_strinfo080a;
+extern STRINFO NLSALLOC(080c) g_strinfo080c;
+extern STRINFO NLSALLOC(0810) g_strinfo0810;
+extern STRINFO NLSALLOC(0813) g_strinfo0813;
+extern STRINFO NLSALLOC(0814) g_strinfo0814;
+extern STRINFO NLSALLOC(0816) g_strinfo0816;
+extern STRINFO NLSALLOC(0c07) g_strinfo0c07;
+extern STRINFO NLSALLOC(0c09) g_strinfo0c09;
+extern STRINFO NLSALLOC(0c0a) g_strinfo0c0a;
+extern STRINFO NLSALLOC(0c0c) g_strinfo0c0c;
+extern STRINFO NLSALLOC(1009) g_strinfo1009;
+extern STRINFO NLSALLOC(100c) g_strinfo100c;
+extern STRINFO NLSALLOC(1409) g_strinfo1409;
+extern STRINFO NLSALLOC(1809) g_strinfo1809;
+// BIDI locales
+extern STRINFO NLSALLOC(040d) g_strinfo040d;
+extern STRINFO NLSALLOC(0401) g_strinfo0401;
+extern STRINFO NLSALLOC(0801) g_strinfo0801;
+extern STRINFO NLSALLOC(0c01) g_strinfo0c01;
+extern STRINFO NLSALLOC(1001) g_strinfo1001;
+extern STRINFO NLSALLOC(1401) g_strinfo1401;
+extern STRINFO NLSALLOC(1801) g_strinfo1801;
+extern STRINFO NLSALLOC(1c01) g_strinfo1c01;
+extern STRINFO NLSALLOC(2001) g_strinfo2001;
+extern STRINFO NLSALLOC(2401) g_strinfo2401;
+extern STRINFO NLSALLOC(2801) g_strinfo2801;
+extern STRINFO NLSALLOC(2c01) g_strinfo2c01;
+extern STRINFO NLSALLOC(3001) g_strinfo3001;
+extern STRINFO NLSALLOC(3401) g_strinfo3401;
+extern STRINFO NLSALLOC(3801) g_strinfo3801;
+extern STRINFO NLSALLOC(3c01) g_strinfo3c01;
+extern STRINFO NLSALLOC(4001) g_strinfo4001;
+extern STRINFO NLSALLOC(0429) g_strinfo0429;
+
+#endif //OE_MAC
+
+
+#ifndef RC_INVOKED
+# pragma pack()
+#endif
+
+extern int
+DefCompareStringA(
+ unsigned long,
+ const char FAR* pch1, int cch1,
+ const char FAR* pch2, int cch2);
+
+extern int
+ZeroTermNoIgnoreSym(
+ unsigned long,
+ const char FAR* pch1,
+ const char FAR* pch2);
+
+#if OE_WIN
+void NotifyNLSInfoChanged(void);
+#endif
diff --git a/private/oleauto/src/dispatch/oaglue.c b/private/oleauto/src/dispatch/oaglue.c
new file mode 100644
index 000000000..b1f16b733
--- /dev/null
+++ b/private/oleauto/src/dispatch/oaglue.c
@@ -0,0 +1,664 @@
+#ifndef _PPCMAC
+#include <ole2.h>
+#include "olenls.h"
+#include "dispatch.h"
+
+#include "oavtbl.h"
+
+extern oavtbl * poavtbl; // initialized by OLE
+#define RETURN(x) return x
+#define RETURNVOID(x) x
+#define RETURN_(typ, x) return x
+
+#else //!_PPCMAC
+
+#include "oaimp.h" // stubs for all the types (simplifies build)
+
+#define RETURN(x) return (HRESULT)0
+#define RETURNVOID(x)
+#define RETURN_(typ, x) return (typ)0
+#endif //!_PPCMAC
+
+
+//********************
+// Items from OLENLS.H
+//********************
+
+STDAPI_(int)
+CompareStringA(LCID lcid, unsigned long ul1, const char FAR* pch1, int i1, const char FAR* pch2, int i2) {
+ RETURN_(int, poavtbl->CompareStringA(lcid, ul1, pch1, i1, pch2, i2));
+}
+
+STDAPI_(int)
+LCMapStringA(LCID lcid, unsigned long ul1, const char FAR* pch1, int i1, char FAR* pch2, int i2) {
+ RETURN_(int, poavtbl->LCMapStringA(lcid, ul1, pch1, i1, pch2, i2));
+}
+
+STDAPI_(int)
+GetLocaleInfoA(LCID lcid, LCTYPE lctype, char FAR* pch1, int i1) {
+ RETURN_(int, poavtbl->GetLocaleInfoA(lcid, lctype, pch1, i1));
+}
+
+STDAPI_(int)
+GetStringTypeA(LCID lcid, unsigned long ul1, const char FAR* pch1, int i1, unsigned short FAR* pus1) {
+ RETURN_(int, poavtbl->GetStringTypeA(lcid, ul1, pch1, i1, pus1));
+}
+
+STDAPI_(LANGID)
+GetSystemDefaultLangID(void) {
+ RETURN_(LANGID, poavtbl->GetSystemDefaultLangID());
+}
+
+STDAPI_(LANGID)
+GetUserDefaultLangID(void) {
+ RETURN_(LANGID, poavtbl->GetUserDefaultLangID());
+}
+
+STDAPI_(LCID)
+GetSystemDefaultLCID(void) {
+ RETURN_(LCID, poavtbl->GetSystemDefaultLCID());
+}
+
+STDAPI_(LCID)
+GetUserDefaultLCID(void) {
+ RETURN_(LCID, poavtbl->GetUserDefaultLCID());
+}
+
+//**********************
+// Items from DISPATCH.H
+//**********************
+STDAPI_(BSTR)
+SysAllocString(const OLECHAR FAR* pch) {
+ RETURN_(BSTR, poavtbl->SysAllocString(pch));
+}
+STDAPI_(int)
+SysReAllocString(BSTR FAR* pbstr, const OLECHAR FAR* pch) {
+ RETURN_(int, poavtbl->SysReAllocString(pbstr, pch));
+}
+STDAPI_(BSTR)
+SysAllocStringLen(const OLECHAR FAR* pch, unsigned int cb) {
+ RETURN_(BSTR, poavtbl->SysAllocStringLen(pch, cb));
+}
+STDAPI_(int)
+SysReAllocStringLen(BSTR FAR* pbstr, const OLECHAR FAR* pch, unsigned int cb) {
+ RETURN_(int, poavtbl->SysReAllocStringLen(pbstr, pch, cb));
+}
+STDAPI_(void) SysFreeString(BSTR bstr) {
+ RETURNVOID(poavtbl->SysFreeString(bstr));
+}
+STDAPI_(unsigned int) SysStringLen(BSTR bstr) {
+ RETURN_(unsigned int, poavtbl->SysStringLen(bstr));
+}
+
+STDAPI_(int)
+DosDateTimeToVariantTime(
+ unsigned short wDosDate,
+ unsigned short wDosTime,
+ double FAR* pvtime) {
+ RETURN_(int, poavtbl->DosDateTimeToVariantTime(wDosDate, wDosTime, pvtime));
+}
+
+STDAPI_(int)
+VariantTimeToDosDateTime(
+ double vtime,
+ unsigned short FAR* pwDosDate,
+ unsigned short FAR* pwDosTime) {
+ RETURN_(int, poavtbl->VariantTimeToDosDateTime(vtime, pwDosDate, pwDosTime));
+}
+
+STDAPI
+SafeArrayAllocDescriptor(unsigned int cDims, SAFEARRAY FAR* FAR* ppsaOut) {
+ RETURN(poavtbl->SafeArrayAllocDescriptor(cDims, ppsaOut));
+}
+
+STDAPI SafeArrayAllocData(SAFEARRAY FAR* psa) {
+ RETURN(poavtbl->SafeArrayAllocData(psa));
+}
+
+STDAPI_(SAFEARRAY FAR*)
+SafeArrayCreate(VARTYPE vt, unsigned int cDims, SAFEARRAYBOUND FAR* rgsabound) {
+ RETURN_(SAFEARRAY FAR*, poavtbl->SafeArrayCreate(vt, cDims, rgsabound));
+}
+
+STDAPI SafeArrayDestroyDescriptor(SAFEARRAY FAR* psa) {
+ RETURN(poavtbl->SafeArrayDestroyDescriptor(psa));
+}
+
+STDAPI SafeArrayDestroyData(SAFEARRAY FAR* psa) {
+ RETURN(poavtbl->SafeArrayDestroyData(psa));
+}
+
+STDAPI SafeArrayDestroy(SAFEARRAY FAR* psa) {
+ RETURN(poavtbl->SafeArrayDestroy(psa));
+}
+
+STDAPI SafeArrayRedim(SAFEARRAY FAR* psa, SAFEARRAYBOUND FAR* psaboundNew) {
+ RETURN(poavtbl->SafeArrayRedim(psa, psaboundNew));
+}
+
+STDAPI_(unsigned int) SafeArrayGetDim(SAFEARRAY FAR* psa) {
+ RETURN_(unsigned int, poavtbl->SafeArrayGetDim(psa));
+}
+
+STDAPI_(unsigned int) SafeArrayGetElemsize(SAFEARRAY FAR* psa) {
+ RETURN_(unsigned int, poavtbl->SafeArrayGetElemsize(psa));
+}
+
+STDAPI
+SafeArrayGetUBound(SAFEARRAY FAR* psa, unsigned int nDim, long FAR* plUbound) {
+ RETURN(poavtbl->SafeArrayGetUBound(psa, nDim, plUbound));
+}
+
+STDAPI
+SafeArrayGetLBound(SAFEARRAY FAR* psa, unsigned int nDim, long FAR* plLbound) {
+ RETURN(poavtbl->SafeArrayGetLBound(psa, nDim, plLbound));
+}
+
+STDAPI SafeArrayLock(SAFEARRAY FAR* psa) {
+ RETURN(poavtbl->SafeArrayLock(psa));
+}
+
+STDAPI SafeArrayUnlock(SAFEARRAY FAR* psa) {
+ RETURN(poavtbl->SafeArrayUnlock(psa));
+}
+
+STDAPI SafeArrayAccessData(SAFEARRAY FAR* psa, void HUGEP* FAR* ppvData) {
+ RETURN(poavtbl->SafeArrayAccessData(psa, ppvData));
+}
+
+STDAPI SafeArrayUnaccessData(SAFEARRAY FAR* psa) {
+ RETURN(poavtbl->SafeArrayUnaccessData(psa));
+}
+
+STDAPI
+SafeArrayGetElement(
+ SAFEARRAY FAR* psa,
+ long FAR* rgIndices,
+ void FAR* pv) {
+ RETURN(poavtbl->SafeArrayGetElement(psa, rgIndices, pv));
+}
+
+STDAPI
+SafeArrayPutElement(
+ SAFEARRAY FAR* psa,
+ long FAR* rgIndices,
+ void FAR* pv) {
+ RETURN(poavtbl->SafeArrayPutElement(psa, rgIndices, pv));
+}
+
+STDAPI
+SafeArrayCopy(
+ SAFEARRAY FAR* psa,
+ SAFEARRAY FAR* FAR* ppsaOut) {
+ RETURN(poavtbl->SafeArrayCopy( psa, ppsaOut));
+}
+
+STDAPI
+SafeArrayPtrOfIndex(
+ SAFEARRAY FAR* psa,
+ long FAR* rgIndices,
+ void HUGEP* FAR* ppvData) {
+ RETURN(poavtbl->SafeArrayPtrOfIndex(psa, rgIndices, ppvData));
+}
+
+
+STDAPI_(void)
+VariantInit(VARIANTARG FAR* pvarg) {
+ RETURNVOID(poavtbl->VariantInit(pvarg));
+}
+
+STDAPI
+VariantClear(VARIANTARG FAR* pvarg) {
+ RETURN(poavtbl->VariantClear(pvarg));
+}
+
+STDAPI
+VariantCopy( VARIANTARG FAR* pvargDest, VARIANTARG FAR* pvargSrc) {
+ RETURN(poavtbl->VariantCopy(pvargDest, pvargSrc));
+}
+
+STDAPI
+VariantCopyInd( VARIANT FAR* pvarDest, VARIANTARG FAR* pvargSrc) {
+ RETURN(poavtbl->VariantCopyInd(pvarDest, pvargSrc));
+}
+
+STDAPI
+VariantChangeType(
+ VARIANTARG FAR* pvargDest,
+ VARIANTARG FAR* pvarSrc,
+ unsigned short wFlags,
+ VARTYPE vt) {
+ RETURN(poavtbl->VariantChangeType(pvargDest, pvarSrc, wFlags, vt));
+}
+
+STDAPI
+VariantChangeTypeEx(
+ VARIANTARG FAR* pvargDest,
+ VARIANTARG FAR* pvarSrc,
+ LCID lcid,
+ unsigned short wFlags,
+ VARTYPE vt) {
+ RETURN(poavtbl->VariantChangeTypeEx(pvargDest, pvarSrc, lcid, wFlags, vt));
+}
+
+STDAPI VarI2FromI4(long lIn, short FAR* psOut) {
+ RETURN(poavtbl->VarI2FromI4(lIn, psOut));
+}
+
+STDAPI VarI2FromR4(float fltIn, short FAR* psOut) {
+ RETURN(poavtbl->VarI2FromR4(fltIn, psOut));
+}
+
+STDAPI VarI2FromR8(double dblIn, short FAR* psOut) {
+ RETURN(poavtbl->VarI2FromR8(dblIn, psOut));
+}
+
+STDAPI VarI2FromCy(CY cyIn, short FAR* psOut) {
+ RETURN(poavtbl->VarI2FromCy(cyIn, psOut));
+}
+
+STDAPI VarI2FromDate(DATE dateIn, short FAR* psOut) {
+ RETURN(poavtbl->VarI2FromDate(dateIn, psOut));
+}
+
+STDAPI VarI2FromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, short FAR* psOut) {
+ RETURN(poavtbl->VarI2FromStr(strIn, lcid, dwFlags, psOut));
+}
+
+STDAPI VarI2FromDisp(IDispatch FAR* pdispIn, LCID lcid, short FAR* psOut) {
+ RETURN(poavtbl->VarI2FromDisp(pdispIn, lcid, psOut));
+}
+
+STDAPI VarI2FromBool(VARIANT_BOOL boolIn, short FAR* psOut) {
+ RETURN(poavtbl->VarI2FromBool(boolIn, psOut));
+}
+
+
+STDAPI VarI4FromI2(short sIn, long FAR* plOut) {
+ RETURN(poavtbl->VarI4FromI2(sIn, plOut));
+}
+
+STDAPI VarI4FromR4(float fltIn, long FAR* plOut) {
+ RETURN(poavtbl->VarI4FromR4(fltIn, plOut));
+}
+
+STDAPI VarI4FromR8(double dblIn, long FAR* plOut) {
+ RETURN(poavtbl->VarI4FromR8(dblIn, plOut));
+}
+
+STDAPI VarI4FromCy(CY cyIn, long FAR* plOut) {
+ RETURN(poavtbl->VarI4FromCy(cyIn, plOut));
+}
+
+STDAPI VarI4FromDate(DATE dateIn, long FAR* plOut) {
+ RETURN(poavtbl->VarI4FromDate(dateIn, plOut));
+}
+
+STDAPI VarI4FromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, long FAR* plOut) {
+ RETURN(poavtbl->VarI4FromStr(strIn, lcid, dwFlags, plOut));
+}
+
+STDAPI VarI4FromDisp(IDispatch FAR* pdispIn, LCID lcid, long FAR* plOut) {
+ RETURN(poavtbl->VarI4FromDisp(pdispIn, lcid, plOut));
+}
+
+STDAPI VarI4FromBool(VARIANT_BOOL boolIn, long FAR* plOut) {
+ RETURN(poavtbl->VarI4FromBool(boolIn, plOut));
+}
+
+
+STDAPI VarR4FromI2(short sIn, float FAR* pfltOut) {
+ RETURN(poavtbl->VarR4FromI2(sIn, pfltOut));
+}
+
+STDAPI VarR4FromI4(long lIn, float FAR* pfltOut) {
+ RETURN(poavtbl->VarR4FromI4(lIn, pfltOut));
+}
+
+STDAPI VarR4FromR8(double dblIn, float FAR* pfltOut) {
+ RETURN(poavtbl->VarR4FromR8(dblIn, pfltOut));
+}
+
+STDAPI VarR4FromCy(CY cyIn, float FAR* pfltOut) {
+ RETURN(poavtbl->VarR4FromCy(cyIn, pfltOut));
+}
+
+STDAPI VarR4FromDate(DATE dateIn, float FAR* pfltOut) {
+ RETURN(poavtbl->VarR4FromDate(dateIn, pfltOut));
+}
+
+STDAPI VarR4FromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, float FAR* pfltOut) {
+ RETURN(poavtbl->VarR4FromStr(strIn, lcid, dwFlags, pfltOut));
+}
+
+STDAPI VarR4FromDisp(IDispatch FAR* pdispIn, LCID lcid, float FAR* pfltOut) {
+ RETURN(poavtbl->VarR4FromDisp(pdispIn, lcid, pfltOut));
+}
+
+STDAPI VarR4FromBool(VARIANT_BOOL boolIn, float FAR* pfltOut) {
+ RETURN(poavtbl->VarR4FromBool(boolIn, pfltOut));
+}
+
+
+STDAPI VarR8FromI2(short sIn, double FAR* pdblOut) {
+ RETURN(poavtbl->VarR8FromI2(sIn, pdblOut));
+}
+
+STDAPI VarR8FromI4(long lIn, double FAR* pdblOut) {
+ RETURN(poavtbl->VarR8FromI4(lIn, pdblOut));
+}
+
+STDAPI VarR8FromR4(float fltIn, double FAR* pdblOut) {
+ RETURN(poavtbl->VarR8FromR4(fltIn, pdblOut));
+}
+
+STDAPI VarR8FromCy(CY cyIn, double FAR* pdblOut) {
+ RETURN(poavtbl->VarR8FromCy(cyIn, pdblOut));
+}
+
+STDAPI VarR8FromDate(DATE dateIn, double FAR* pdblOut) {
+ RETURN(poavtbl->VarR8FromDate(dateIn, pdblOut));
+}
+
+STDAPI VarR8FromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, double FAR* pdblOut) {
+ RETURN(poavtbl->VarR8FromStr(strIn, lcid, dwFlags, pdblOut));
+}
+
+STDAPI VarR8FromDisp(IDispatch FAR* pdispIn, LCID lcid, double FAR* pdblOut) {
+ RETURN(poavtbl->VarR8FromDisp(pdispIn, lcid, pdblOut));
+}
+
+STDAPI VarR8FromBool(VARIANT_BOOL boolIn, double FAR* pdblOut) {
+ RETURN(poavtbl->VarR8FromBool(boolIn, pdblOut));
+}
+
+
+STDAPI VarDateFromI2(short sIn, DATE FAR* pdateOut) {
+ RETURN(poavtbl->VarDateFromI2(sIn, pdateOut));
+}
+
+STDAPI VarDateFromI4(long lIn, DATE FAR* pdateOut) {
+ RETURN(poavtbl->VarDateFromI4(lIn, pdateOut));
+}
+
+STDAPI VarDateFromR4(float fltIn, DATE FAR* pdateOut) {
+ RETURN(poavtbl->VarDateFromR4(fltIn, pdateOut));
+}
+
+STDAPI VarDateFromR8(double dblIn, DATE FAR* pdateOut) {
+ RETURN(poavtbl->VarDateFromR8(dblIn, pdateOut));
+}
+
+STDAPI VarDateFromCy(CY cyIn, DATE FAR* pdateOut) {
+ RETURN(poavtbl->VarDateFromCy(cyIn, pdateOut));
+}
+
+STDAPI VarDateFromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, DATE FAR* pdateOut) {
+ RETURN(poavtbl->VarDateFromStr(strIn, lcid, dwFlags, pdateOut));
+}
+
+STDAPI VarDateFromDisp(IDispatch FAR* pdispIn, LCID lcid, DATE FAR* pdateOut) {
+ RETURN(poavtbl->VarDateFromDisp(pdispIn, lcid, pdateOut));
+}
+
+STDAPI VarDateFromBool(VARIANT_BOOL boolIn, DATE FAR* pdateOut) {
+ RETURN(poavtbl->VarDateFromBool(boolIn, pdateOut));
+}
+
+
+STDAPI VarCyFromI2(short sIn, CY FAR* pcyOut) {
+ RETURN(poavtbl->VarCyFromI2(sIn, pcyOut));
+}
+
+STDAPI VarCyFromI4(long lIn, CY FAR* pcyOut) {
+ RETURN(poavtbl->VarCyFromI4(lIn, pcyOut));
+}
+
+STDAPI VarCyFromR4(float fltIn, CY FAR* pcyOut) {
+ RETURN(poavtbl->VarCyFromR4(fltIn, pcyOut));
+}
+
+STDAPI VarCyFromR8(double dblIn, CY FAR* pcyOut) {
+ RETURN(poavtbl->VarCyFromR8(dblIn, pcyOut));
+}
+
+STDAPI VarCyFromDate(DATE dateIn, CY FAR* pcyOut) {
+ RETURN(poavtbl->VarCyFromDate(dateIn, pcyOut));
+}
+
+STDAPI VarCyFromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, CY FAR* pcyOut) {
+ RETURN(poavtbl->VarCyFromStr(strIn, lcid, dwFlags, pcyOut));
+}
+
+STDAPI VarCyFromDisp(IDispatch FAR* pdispIn, LCID lcid, CY FAR* pcyOut) {
+ RETURN(poavtbl->VarCyFromDisp(pdispIn, lcid, pcyOut));
+}
+
+STDAPI VarCyFromBool(VARIANT_BOOL boolIn, CY FAR* pcyOut) {
+ RETURN(poavtbl->VarCyFromBool(boolIn, pcyOut));
+}
+
+
+STDAPI VarBstrFromI2(short iVal, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut) {
+ RETURN(poavtbl->VarBstrFromI2(iVal, lcid, dwFlags, pbstrOut));
+}
+
+STDAPI VarBstrFromI4(long lIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut) {
+ RETURN(poavtbl->VarBstrFromI4(lIn, lcid, dwFlags, pbstrOut));
+}
+
+STDAPI VarBstrFromR4(float fltIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut) {
+ RETURN(poavtbl->VarBstrFromR4(fltIn, lcid, dwFlags, pbstrOut));
+}
+
+STDAPI VarBstrFromR8(double dblIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut) {
+ RETURN(poavtbl->VarBstrFromR8(dblIn, lcid, dwFlags, pbstrOut));
+}
+
+STDAPI VarBstrFromCy(CY cyIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut) {
+ RETURN(poavtbl->VarBstrFromCy(cyIn, lcid, dwFlags, pbstrOut));
+}
+
+STDAPI VarBstrFromDate(DATE dateIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut) {
+ RETURN(poavtbl->VarBstrFromDate(dateIn, lcid, dwFlags, pbstrOut));
+}
+
+STDAPI VarBstrFromDisp(IDispatch FAR* pdispIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut) {
+ RETURN(poavtbl->VarBstrFromDisp(pdispIn, lcid, dwFlags, pbstrOut));
+}
+
+STDAPI VarBstrFromBool(VARIANT_BOOL boolIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut) {
+ RETURN(poavtbl->VarBstrFromBool(boolIn, lcid, dwFlags, pbstrOut));
+}
+
+
+STDAPI VarBoolFromI2(short sIn, VARIANT_BOOL FAR* pboolOut) {
+ RETURN(poavtbl->VarBoolFromI2(sIn, pboolOut));
+}
+
+STDAPI VarBoolFromI4(long lIn, VARIANT_BOOL FAR* pboolOut) {
+ RETURN(poavtbl->VarBoolFromI4(lIn, pboolOut));
+}
+
+STDAPI VarBoolFromR4(float fltIn, VARIANT_BOOL FAR* pboolOut) {
+ RETURN(poavtbl->VarBoolFromR4(fltIn, pboolOut));
+}
+
+STDAPI VarBoolFromR8(double dblIn, VARIANT_BOOL FAR* pboolOut) {
+ RETURN(poavtbl->VarBoolFromR8(dblIn, pboolOut));
+}
+
+STDAPI VarBoolFromDate(DATE dateIn, VARIANT_BOOL FAR* pboolOut) {
+ RETURN(poavtbl->VarBoolFromDate(dateIn, pboolOut));
+}
+
+STDAPI VarBoolFromCy(CY cyIn, VARIANT_BOOL FAR* pboolOut) {
+ RETURN(poavtbl->VarBoolFromCy(cyIn, pboolOut));
+}
+
+STDAPI VarBoolFromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, VARIANT_BOOL FAR* pboolOut) {
+ RETURN(poavtbl->VarBoolFromStr(strIn, lcid, dwFlags, pboolOut));
+}
+
+STDAPI VarBoolFromDisp(IDispatch FAR* pdispIn, LCID lcid, VARIANT_BOOL FAR* pboolOut) {
+ RETURN(poavtbl->VarBoolFromDisp(pdispIn, lcid, pboolOut));
+}
+
+
+STDAPI MPWVarFromR4(float FAR* pfltIn, VARIANT FAR* pvarOut) {
+ RETURN(poavtbl->MPWVarFromR4(pfltIn, pvarOut));
+}
+
+STDAPI MPWVarFromR8(double FAR* pdblIn, VARIANT FAR* pvarOut) {
+ RETURN(poavtbl->MPWVarFromR8(pdblIn, pvarOut));
+}
+
+STDAPI MPWR4FromVar(VARIANT FAR* pvarIn, float FAR* pfltOut) {
+ RETURN(poavtbl->MPWR4FromVar(pvarIn, pfltOut));
+}
+
+STDAPI MPWR8FromVar(VARIANT FAR* pvarIn, double FAR* pdblOut) {
+ RETURN(poavtbl->MPWR8FromVar(pvarIn, pdblOut));
+}
+
+
+STDAPI_(unsigned long)
+LHashValOfNameSys(SYSKIND syskind, LCID lcid, OLECHAR FAR* szName) {
+ RETURN_(unsigned long, poavtbl->LHashValOfNameSys(syskind, lcid, szName));
+}
+
+
+STDAPI
+LoadTypeLib(OLECHAR FAR* szFile, ITypeLib FAR* FAR* pptlib) {
+ RETURN(poavtbl->LoadTypeLib(szFile, pptlib));
+}
+
+STDAPI
+LoadRegTypeLib(
+ REFGUID rguid,
+ unsigned short wVerMajor,
+ unsigned short wVerMinor,
+ LCID lcid,
+ ITypeLib FAR* FAR* pptlib) {
+ RETURN(poavtbl->LoadRegTypeLib(rguid, wVerMajor, wVerMinor, lcid, pptlib));
+}
+
+STDAPI
+QueryPathOfRegTypeLib(
+ REFGUID guid,
+ unsigned short wMaj,
+ unsigned short wMin,
+ LCID lcid,
+ LPBSTR lpbstrPathName) {
+ RETURN(poavtbl->QueryPathOfRegTypeLib(guid, wMaj, wMin, lcid, lpbstrPathName));
+}
+
+STDAPI
+RegisterTypeLib(
+ ITypeLib FAR* ptlib,
+ OLECHAR FAR* szFullPath,
+ OLECHAR FAR* szHelpDir) {
+ RETURN(poavtbl->RegisterTypeLib(ptlib, szFullPath, szHelpDir));
+}
+
+STDAPI
+CreateTypeLib(SYSKIND syskind, OLECHAR FAR* szFile, ICreateTypeLib FAR* FAR* ppctlib) {
+ RETURN(poavtbl->CreateTypeLib(syskind, szFile, ppctlib));
+}
+
+STDAPI
+LoadTypeLibFSp(const FSSpec *pfsspec, ITypeLib FAR* FAR* pptlib) {
+ RETURN(poavtbl->LoadTypeLibFSp(pfsspec, pptlib));
+}
+
+STDAPI
+RegisterTypeLibFolder(OLECHAR FAR* szFullPath) {
+ RETURN(poavtbl->RegisterTypeLibFolder(szFullPath));
+}
+
+STDAPI
+QueryTypeLibFolder(LPBSTR pbstr) {
+ RETURN(poavtbl->QueryTypeLibFolder(pbstr));
+}
+
+
+STDAPI
+DispGetParam(
+ DISPPARAMS FAR* pdispparams,
+ unsigned int position,
+ VARTYPE vtTarg,
+ VARIANT FAR* pvarResult,
+ unsigned int FAR* puArgErr) {
+ RETURN(poavtbl->DispGetParam(pdispparams, position, vtTarg, pvarResult, puArgErr));
+}
+
+STDAPI
+DispGetIDsOfNames(
+ ITypeInfo FAR* ptinfo,
+ OLECHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ DISPID FAR* rgdispid) {
+ RETURN(poavtbl->DispGetIDsOfNames(ptinfo, rgszNames, cNames, rgdispid));
+}
+
+STDAPI
+DispInvoke(
+ void FAR* _this,
+ ITypeInfo FAR* ptinfo,
+ DISPID dispidMember,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pparams,
+ VARIANT FAR* pvarResult,
+ EXCEPINFO FAR* pexcepinfo,
+ unsigned int FAR* puArgErr) {
+ RETURN(poavtbl->DispInvoke(_this, ptinfo, dispidMember, wFlags, pparams,
+ pvarResult, pexcepinfo, puArgErr));
+}
+
+STDAPI
+CreateDispTypeInfo(
+ INTERFACEDATA FAR* pidata,
+ LCID lcid,
+ ITypeInfo FAR* FAR* pptinfo) {
+ RETURN(poavtbl->CreateDispTypeInfo(pidata, lcid, pptinfo));
+}
+
+STDAPI
+CreateStdDispatch(
+ IUnknown FAR* punkOuter,
+ void FAR* pvThis,
+ ITypeInfo FAR* ptinfo,
+ IUnknown FAR* FAR* ppunkStdDisp) {
+ RETURN(poavtbl->CreateStdDispatch(punkOuter, pvThis, ptinfo, ppunkStdDisp));
+}
+
+STDAPI
+RegisterActiveObject(
+ IUnknown FAR* punk,
+ REFCLSID rclsid,
+ void FAR* pvReserved,
+ unsigned long FAR* pdwRegister) {
+ RETURN(poavtbl->RegisterActiveObject(punk, rclsid, pvReserved, pdwRegister));
+}
+
+STDAPI
+RevokeActiveObject(
+ unsigned long dwRegister,
+ void FAR* pvReserved) {
+ RETURN(poavtbl->RevokeActiveObject(dwRegister, pvReserved));
+}
+
+STDAPI
+GetActiveObject(
+ REFCLSID rclsid,
+ void FAR* pvReserved,
+ IUnknown FAR* FAR* ppunk) {
+ RETURN(poavtbl->GetActiveObject(rclsid, pvReserved, ppunk));
+}
+
+#ifdef _PPCMAC
+// UNDONE: fix these right!!
+STDAPI DllGetClassObject(void) { return (HRESULT)0; };
+STDAPI_(void) IID_IDispatch(void) { return; };
+STDAPI_(void) IID_IEnumVARIANT(void) { return; };
+#endif
diff --git a/private/oleauto/src/dispatch/oaglue.v b/private/oleauto/src/dispatch/oaglue.v
new file mode 100644
index 000000000..416d94978
--- /dev/null
+++ b/private/oleauto/src/dispatch/oaglue.v
@@ -0,0 +1,126 @@
+CompareStringA
+LCMapStringA
+GetLocaleInfoA
+GetStringTypeA
+GetSystemDefaultLangID
+GetUserDefaultLangID
+GetSystemDefaultLCID
+GetUserDefaultLCID
+SysAllocString
+SysReAllocString
+SysAllocStringLen
+SysReAllocStringLen
+SysFreeString
+SysStringLen
+DosDateTimeToVariantTime
+VariantTimeToDosDateTime
+SafeArrayAllocDescriptor
+SafeArrayAllocData
+SafeArrayCreate
+SafeArrayDestroyDescriptor
+SafeArrayDestroyData
+SafeArrayDestroy
+SafeArrayRedim
+SafeArrayGetDim
+SafeArrayGetElemsize
+SafeArrayGetUBound
+SafeArrayGetLBound
+SafeArrayLock
+SafeArrayUnlock
+SafeArrayAccessData
+SafeArrayUnaccessData
+SafeArrayGetElement
+SafeArrayPutElement
+SafeArrayCopy
+SafeArrayPtrOfIndex
+VariantInit
+VariantClear
+VariantCopy
+VariantCopyInd
+VariantChangeType
+VariantChangeTypeEx
+VarI2FromI4
+VarI2FromR4
+VarI2FromR8
+VarI2FromCy
+VarI2FromDate
+VarI2FromStr
+VarI2FromDisp
+VarI2FromBool
+VarI4FromI2
+VarI4FromR4
+VarI4FromR8
+VarI4FromCy
+VarI4FromDate
+VarI4FromStr
+VarI4FromDisp
+VarI4FromBool
+VarR4FromI2
+VarR4FromI4
+VarR4FromR8
+VarR4FromCy
+VarR4FromDate
+VarR4FromStr
+VarR4FromDisp
+VarR4FromBool
+VarR8FromI2
+VarR8FromI4
+VarR8FromR4
+VarR8FromCy
+VarR8FromDate
+VarR8FromStr
+VarR8FromDisp
+VarR8FromBool
+VarDateFromI2
+VarDateFromI4
+VarDateFromR4
+VarDateFromR8
+VarDateFromCy
+VarDateFromStr
+VarDateFromDisp
+VarDateFromBool
+VarCyFromI2
+VarCyFromI4
+VarCyFromR4
+VarCyFromR8
+VarCyFromDate
+VarCyFromStr
+VarCyFromDisp
+VarCyFromBool
+VarBstrFromI2
+VarBstrFromI4
+VarBstrFromR4
+VarBstrFromR8
+VarBstrFromCy
+VarBstrFromDate
+VarBstrFromDisp
+VarBstrFromBool
+VarBoolFromI2
+VarBoolFromI4
+VarBoolFromR4
+VarBoolFromR8
+VarBoolFromDate
+VarBoolFromCy
+VarBoolFromStr
+VarBoolFromDisp
+MPWVarFromR4
+MPWVarFromR8
+MPWR4FromVar
+MPWR8FromVar
+LHashValOfNameSys
+LoadTypeLib
+LoadRegTypeLib
+QueryPathOfRegTypeLib
+RegisterTypeLib
+CreateTypeLib
+LoadTypeLibFSp
+RegisterTypeLibFolder
+QueryTypeLibFolder
+DispGetParam
+DispGetIDsOfNames
+DispInvoke
+CreateDispTypeInfo
+CreateStdDispatch
+RegisterActiveObject
+RevokeActiveObject
+GetActiveObject
diff --git a/private/oleauto/src/dispatch/oaimp.h b/private/oleauto/src/dispatch/oaimp.h
new file mode 100644
index 000000000..ff8294792
--- /dev/null
+++ b/private/oleauto/src/dispatch/oaimp.h
@@ -0,0 +1,164 @@
+/* ===========================================================================
+ = File: OLE2Impl.h
+ =
+ = Description: Header needed to build the MPW OLE2 Import library for
+ = the OLE2.02 CFM DLL
+ =
+ = Copyright: © 1994 Microsoft corporation Inc., All rights reserved
+ =========================================================================== */
+
+#ifndef __OLE2IMPL_H
+#define __OLE2IMPL_H
+
+#include "types.h"
+#include "fragload.h"
+#include "files.h"
+
+#ifdef __cplusplus
+ #define EXTERN_C extern "C"
+#else
+ #define EXTERN_C extern
+#endif
+
+#define STDAPI EXTERN_C HRESULT
+#define STDAPI_(type) EXTERN_C type
+
+#define RETURN_VALUE(type) return (type)0
+#define RETURN_VALUE_VOID return
+
+#define HRESULT void*
+#define OLEREG_HKEY long
+#define OLELONG long
+#define OLEREGSTATUS long
+#define OLEREG_VALUE char*
+#define OLEREG_ORDER long
+#define LPCSTR char*
+#define ATOM unsigned short
+#define WORD unsigned short
+#define LPSTR char*
+#define DWORD unsigned long
+#define PTR char*
+#define LONG long
+#define HKEY unsigned long
+#define HINSTANCE ConnectionID
+#define UINT unsigned int
+#define REFIID void*
+#define BYTE unsigned char
+#define ULONG unsigned long
+#define LPMALLOC void*
+#define REFCLSID void*
+#define LPUNKNOWN void*
+#define LPDWORD unsigned long*
+#define LPVOID void*
+#define LPSTREAM void*
+#define REFGUID void*
+#define LPCLSID void*
+#define SCODE long
+#define LPMESSAGEFILTER void*
+#define LPCLSID void*
+#define LPMARSHAL void*
+#define LPIID void*
+#define LPFILETIME void*
+#define OID long
+#define LPIStubManager void*
+#define LPILrpc void*
+#define LPFNI void*
+#define HWND void*
+#define LPTASK void*
+#define LPETASK void*
+#define HTASK long
+#define SHREG void*
+#define LPCALLINFO void*
+#define ProcessSerialNumberPtr void*
+#define LPINTERFACEINFO void*
+#define LPAppleEvent void*
+#define LPSTORAGE void*
+#define LPILockBytes void*
+#define SNB void*
+#define ScriptCode short
+#define LPDATAOBJECT void*
+#define LPOLECLIENTSITE void*
+#define LPFORMATETC void*
+#define LPMONIKER void*
+#define LPPERSISTSTORAGE void*
+#define LPOLEOBJECT void*
+#define LPBC void*
+#define LPRUNNINGOBJECTTABLE void*
+#define LPIMALLOC void*
+#define LPSTGMEDIUM void*
+#define LPDROPTARGET void*
+#define LPDROPSOURCE void*
+#define LPOLEADVISEHOLDER void*
+#define LPDATAADVISEHOLDER void*
+#define CLIPFORMAT ResType
+#define LPLOCKBYTES void*
+#define HGLOBAL Handle
+#define LPCRECT void*
+#define HDC void*
+#define LPCLASSFACTORY void*
+#define LPOLESTREAM void*
+#define LPDVTARGETDEVICE void*
+#define LPOLEOBJECT void*
+#define LPOLEINPLACEFRAME void*
+#define LPMSG void*
+#define LPENUMOLEVERB void*
+#define LPEVENTRECORD void*
+#define LPOLEINPLACEFRAMEINFO void*
+#define WindowPtr void*
+#define OleMBarHandle Handle
+#define MenuHandle Handle
+#define RgnHandle Handle
+#define Point void*
+#define ProcPtr void*
+#define BOOL unsigned long
+#define CursPtr void*
+#define PicHandle Handle
+#define LPOleIconSource void*
+#define GrafPtr void*
+#define HMODULE ConnectionID
+#define LPGUID void*
+#define LPPERSISTSTREAM void*
+#define LPENUMFORMATETC void*
+
+// stuff from olenls.h
+#define FAR
+#define HUGEP
+typedef unsigned long LCID;
+typedef unsigned short LANGID;
+typedef unsigned long LCTYPE;
+
+// stuff from variant.h
+typedef char OLECHAR;
+typedef OLECHAR FAR* LPOLESTR;
+typedef const OLECHAR FAR* LPCOLESTR;
+typedef unsigned short VARTYPE;
+#define VARIANTARG void
+#define VARIANT_BOOL short
+
+// stuff from dispatch.h
+typedef OLECHAR FAR* BSTR;
+typedef BSTR FAR* LPBSTR;
+#define SAFEARRAY void
+#define SAFEARRAYBOUND void
+#define CY double // close...
+#define DATE double
+#define SYSKIND int
+#define DISPID unsigned long
+
+#define IDispatch void
+#define IEnumVARIANT void
+#define ITypeInfo void
+#define ICreateTypeInfo void
+#define ITypeLib void
+#define ICreateTypeLib void
+#define ITypeComp void
+#define IUnknown void
+
+// bogus ones
+#define VARIANT void
+#define DISPPARAMS void
+#define EXCEPINFO void
+#define INTERFACEDATA void
+
+#endif // __OLE2IMPL_H
+
diff --git a/private/oleauto/src/dispatch/oaimp.mak b/private/oleauto/src/dispatch/oaimp.mak
new file mode 100644
index 000000000..040619a27
--- /dev/null
+++ b/private/oleauto/src/dispatch/oaimp.mak
@@ -0,0 +1,172 @@
+# ===============================================================================
+# = File: OaImp.make
+# =
+# = Description: This file is an MPW makefile that builds an XCOFF import
+# = library for the OLE 2.02 Shared Library
+# =
+# = History: 07/7/94 dtf Created
+# ===============================================================================
+
+# -------------------------------------------------------------------------------
+# - Variables
+# -------------------------------------------------------------------------------
+
+LibName = MicrosoftOLE2AutomationLib
+LibType = 'shlb'
+LibCreator = 'cfmg'
+LibObjects = OaImp.c.o
+LibHeader = OaImp.h
+LibSource = Oaglue.c
+
+LibExports = ¶
+ -export DllGetClassObject ¶
+ -export SysAllocString ¶
+ -export SysReAllocString ¶
+ -export SysAllocStringLen ¶
+ -export SysReAllocStringLen ¶
+ -export SysFreeString ¶
+ -export SysStringLen ¶
+ -export VariantInit ¶
+ -export VariantClear ¶
+ -export VariantCopy ¶
+ -export VariantCopyInd ¶
+ -export VariantChangeType ¶
+ -export VariantTimeToDosDateTime ¶
+ -export DosDateTimeToVariantTime ¶
+ -export SafeArrayCreate ¶
+ -export SafeArrayDestroy ¶
+ -export SafeArrayGetDim ¶
+ -export SafeArrayGetElemsize ¶
+ -export SafeArrayGetUBound ¶
+ -export SafeArrayGetLBound ¶
+ -export SafeArrayLock ¶
+ -export SafeArrayUnlock ¶
+ -export SafeArrayAccessData ¶
+ -export SafeArrayUnaccessData ¶
+ -export SafeArrayGetElement ¶
+ -export SafeArrayPutElement ¶
+ -export SafeArrayCopy ¶
+ -export DispGetParam ¶
+ -export DispGetIDsOfNames ¶
+ -export DispInvoke ¶
+ -export CreateDispTypeInfo ¶
+ -export CreateStdDispatch ¶
+ -export RegisterActiveObject ¶
+ -export RevokeActiveObject ¶
+ -export GetActiveObject ¶
+ -export SafeArrayAllocDescriptor ¶
+ -export SafeArrayAllocData ¶
+ -export SafeArrayDestroyDescriptor ¶
+ -export SafeArrayDestroyData ¶
+ -export SafeArrayRedim ¶
+ -export VarI2FromI4 ¶
+ -export VarI2FromR4 ¶
+ -export VarI2FromR8 ¶
+ -export VarI2FromCy ¶
+ -export VarI2FromDate ¶
+ -export VarI2FromStr ¶
+ -export VarI2FromDisp ¶
+ -export VarI2FromBool ¶
+ -export VarI4FromI2 ¶
+ -export VarI4FromR4 ¶
+ -export VarI4FromR8 ¶
+ -export VarI4FromCy ¶
+ -export VarI4FromDate ¶
+ -export VarI4FromStr ¶
+ -export VarI4FromDisp ¶
+ -export VarI4FromBool ¶
+ -export VarR4FromI2 ¶
+ -export VarR4FromI4 ¶
+ -export VarR4FromR8 ¶
+ -export VarR4FromCy ¶
+ -export VarR4FromDate ¶
+ -export VarR4FromStr ¶
+ -export VarR4FromDisp ¶
+ -export VarR4FromBool ¶
+ -export VarR8FromI2 ¶
+ -export VarR8FromI4 ¶
+ -export VarR8FromR4 ¶
+ -export VarR8FromCy ¶
+ -export VarR8FromDate ¶
+ -export VarR8FromStr ¶
+ -export VarR8FromDisp ¶
+ -export VarR8FromBool ¶
+ -export VarDateFromI2 ¶
+ -export VarDateFromI4 ¶
+ -export VarDateFromR4 ¶
+ -export VarDateFromR8 ¶
+ -export VarDateFromCy ¶
+ -export VarDateFromStr ¶
+ -export VarDateFromDisp ¶
+ -export VarDateFromBool ¶
+ -export VarCyFromI2 ¶
+ -export VarCyFromI4 ¶
+ -export VarCyFromR4 ¶
+ -export VarCyFromR8 ¶
+ -export VarCyFromDate ¶
+ -export VarCyFromStr ¶
+ -export VarCyFromDisp ¶
+ -export VarCyFromBool ¶
+ -export VarBstrFromI2 ¶
+ -export VarBstrFromI4 ¶
+ -export VarBstrFromR4 ¶
+ -export VarBstrFromR8 ¶
+ -export VarBstrFromCy ¶
+ -export VarBstrFromDate ¶
+ -export VarBstrFromDisp ¶
+ -export VarBstrFromBool ¶
+ -export VarBoolFromI2 ¶
+ -export VarBoolFromI4 ¶
+ -export VarBoolFromR4 ¶
+ -export VarBoolFromR8 ¶
+ -export VarBoolFromDate ¶
+ -export VarBoolFromCy ¶
+ -export VarBoolFromStr ¶
+ -export VarBoolFromDisp ¶
+ -export IID_IDispatch ¶
+ -export IID_IEnumVARIANT ¶
+ -export VariantChangeTypeEx ¶
+ -export SafeArrayPtrOfIndex ¶
+ -export CreateTypeLib ¶
+ -export LoadTypeLib ¶
+ -export LoadRegTypeLib ¶
+ -export RegisterTypeLib ¶
+ -export QueryPathOfRegTypeLib ¶
+ -export LHashValOfNameSys ¶
+ -export LoadTypeLibFSp ¶
+ -export QueryTypeLibFolder ¶
+ -export RegisterTypeLibFolder ¶
+ -export CompareStringA ¶
+ -export LCMapStringA ¶
+ -export GetLocaleInfoA ¶
+ -export GetStringTypeA ¶
+ -export GetSystemDefaultLangID ¶
+ -export GetUserDefaultLangID ¶
+ -export GetSystemDefaultLCID ¶
+ -export GetUserDefaultLCID
+
+PPCCOptions = -w conformance -appleext on
+
+PPCLibs = "{PPCLibraries}"InterfaceLib.xcoff ¶
+ "{PPCLibraries}"MathLib.xcoff ¶
+ "{PPCLibraries}"StdCLib.xcoff ¶
+ "{PPCLibraries}"StdCRuntime.o ¶
+ "{PPCLibraries}"PPCCRuntime.o
+
+PPCLibEquates = -l InterfaceLib.xcoff=InterfaceLib ¶
+ -l MathLib.xcoff=MathLib ¶
+ -l StdCLib.xcoff=StdCLib ¶
+ -l {LibName}.xcoff={LibName}
+
+# -------------------------------------------------------------------------------
+# - Productions
+# -------------------------------------------------------------------------------
+
+
+{LibName}.xcoff Ä {LibObjects}
+ PPCLink -xm s {LibExports} {LibObjects} {PPCLibs} -o {Targ}
+
+{LibObjects} Ä {LibSource} {LibHeader}
+ PPCC {PPCCOptions} {LibSource} -o {LibObjects}
+
+
diff --git a/private/oleauto/src/dispatch/oavtbl.c b/private/oleauto/src/dispatch/oavtbl.c
new file mode 100644
index 000000000..4e2acbacf
--- /dev/null
+++ b/private/oleauto/src/dispatch/oavtbl.c
@@ -0,0 +1,156 @@
+#include "oledisp.h"
+
+#include "oavtbl.h"
+
+oavtbl OAVtbl = {
+
+VTABLE_VERSION, // version
+
+//********************
+// Items from OLENLS.H
+//********************
+
+CompareStringA,
+LCMapStringA,
+GetLocaleInfoA,
+GetStringTypeA,
+GetSystemDefaultLangID,
+GetUserDefaultLangID,
+GetSystemDefaultLCID,
+GetUserDefaultLCID,
+
+//**********************
+// Items from DISPATCH.H
+//**********************
+SysAllocString,
+SysReAllocString,
+SysAllocStringLen,
+SysReAllocStringLen,
+SysFreeString,
+SysStringLen,
+DosDateTimeToVariantTime,
+VariantTimeToDosDateTime,
+SafeArrayAllocDescriptor,
+SafeArrayAllocData,
+SafeArrayCreate,
+SafeArrayDestroyDescriptor,
+SafeArrayDestroyData,
+SafeArrayDestroy,
+SafeArrayRedim,
+SafeArrayGetDim,
+SafeArrayGetElemsize,
+SafeArrayGetUBound,
+SafeArrayGetLBound,
+SafeArrayLock,
+SafeArrayUnlock,
+SafeArrayAccessData,
+SafeArrayUnaccessData,
+SafeArrayGetElement,
+SafeArrayPutElement,
+SafeArrayCopy,
+SafeArrayPtrOfIndex,
+VariantInit,
+VariantClear,
+VariantCopy,
+VariantCopyInd,
+VariantChangeType,
+VariantChangeTypeEx,
+
+VarI2FromI4,
+VarI2FromR4,
+VarI2FromR8,
+VarI2FromCy,
+VarI2FromDate,
+VarI2FromStr,
+VarI2FromDisp,
+VarI2FromBool,
+
+VarI4FromI2,
+VarI4FromR4,
+VarI4FromR8,
+VarI4FromCy,
+VarI4FromDate,
+VarI4FromStr,
+VarI4FromDisp,
+VarI4FromBool,
+
+VarR4FromI2,
+VarR4FromI4,
+VarR4FromR8,
+VarR4FromCy,
+VarR4FromDate,
+VarR4FromStr,
+VarR4FromDisp,
+VarR4FromBool,
+
+VarR8FromI2,
+VarR8FromI4,
+VarR8FromR4,
+VarR8FromCy,
+VarR8FromDate,
+VarR8FromStr,
+VarR8FromDisp,
+VarR8FromBool,
+
+VarDateFromI2,
+VarDateFromI4,
+VarDateFromR4,
+VarDateFromR8,
+VarDateFromCy,
+VarDateFromStr,
+VarDateFromDisp,
+VarDateFromBool,
+
+VarCyFromI2,
+VarCyFromI4,
+VarCyFromR4,
+VarCyFromR8,
+VarCyFromDate,
+VarCyFromStr,
+VarCyFromDisp,
+VarCyFromBool,
+VarBstrFromI2,
+VarBstrFromI4,
+VarBstrFromR4,
+VarBstrFromR8,
+VarBstrFromCy,
+VarBstrFromDate,
+VarBstrFromDisp,
+VarBstrFromBool,
+VarBoolFromI2,
+VarBoolFromI4,
+VarBoolFromR4,
+VarBoolFromR8,
+VarBoolFromDate,
+VarBoolFromCy,
+VarBoolFromStr,
+VarBoolFromDisp,
+
+MPWVarFromR4,
+MPWVarFromR8,
+MPWR4FromVar,
+MPWR8FromVar,
+
+LHashValOfNameSys,
+LoadTypeLib,
+LoadRegTypeLib,
+QueryPathOfRegTypeLib,
+RegisterTypeLib,
+CreateTypeLib,
+LoadTypeLibFSp,
+RegisterTypeLibFolder,
+QueryTypeLibFolder,
+
+DispGetParam,
+DispGetIDsOfNames,
+DispInvoke,
+CreateDispTypeInfo,
+CreateStdDispatch,
+RegisterActiveObject,
+RevokeActiveObject,
+GetActiveObject
+
+};
+
+void *pOAVtbl = (void *)&OAVtbl;
+
diff --git a/private/oleauto/src/dispatch/oavtbl.h b/private/oleauto/src/dispatch/oavtbl.h
new file mode 100644
index 000000000..4ee589aee
--- /dev/null
+++ b/private/oleauto/src/dispatch/oavtbl.h
@@ -0,0 +1,293 @@
+#define VTABLE_VERSION 1
+
+#ifndef _MSC_VER
+#define pSTDAPI(fcn) pascal HRESULT (* fcn)
+#define pSTDAPI_(fcn,type) pascal type (* fcn)
+#else
+#define pSTDAPI(fcn) HRESULT (STDAPICALLTYPE FAR* fcn)
+#define pSTDAPI_(fcn,type) type (STDAPICALLTYPE FAR* fcn)
+#endif
+
+
+typedef struct {
+
+long version;
+
+//********************
+// Items from OLENLS.H
+//********************
+
+pSTDAPI_(CompareStringA, int)(LCID, unsigned long, const char FAR*, int, const char FAR*, int);
+
+pSTDAPI_(LCMapStringA, int)(LCID, unsigned long, const char FAR*, int, char FAR*, int);
+
+pSTDAPI_(GetLocaleInfoA, int)(LCID, LCTYPE, char FAR*, int);
+
+pSTDAPI_(GetStringTypeA, int)(LCID, unsigned long, const char FAR*, int, unsigned short FAR*);
+
+pSTDAPI_(GetSystemDefaultLangID, LANGID)(void);
+
+pSTDAPI_(GetUserDefaultLangID, LANGID)(void);
+
+pSTDAPI_(GetSystemDefaultLCID, LCID)(void);
+
+pSTDAPI_(GetUserDefaultLCID, LCID)(void);
+
+//**********************
+// Items from DISPATCH.H
+//**********************
+pSTDAPI_(SysAllocString, BSTR)(const OLECHAR FAR*);
+pSTDAPI_(SysReAllocString, int)(BSTR FAR*, const OLECHAR FAR*);
+pSTDAPI_(SysAllocStringLen, BSTR)(const OLECHAR FAR*, unsigned int);
+pSTDAPI_(SysReAllocStringLen, int)(BSTR FAR*, const OLECHAR FAR*, unsigned int);
+pSTDAPI_(SysFreeString, void)(BSTR);
+pSTDAPI_(SysStringLen, unsigned int)(BSTR);
+
+pSTDAPI_(DosDateTimeToVariantTime, int)(
+ unsigned short wDosDate,
+ unsigned short wDosTime,
+ double FAR* pvtime);
+
+pSTDAPI_(VariantTimeToDosDateTime, int)(
+ double vtime,
+ unsigned short FAR* pwDosDate,
+ unsigned short FAR* pwDosTime);
+
+pSTDAPI(SafeArrayAllocDescriptor)(unsigned int cDims, SAFEARRAY FAR* FAR* ppsaOut);
+
+pSTDAPI(SafeArrayAllocData)(SAFEARRAY FAR* psa);
+
+pSTDAPI_(SafeArrayCreate, SAFEARRAY FAR*) (
+ VARTYPE vt,
+ unsigned int cDims,
+ SAFEARRAYBOUND FAR* rgsabound);
+
+pSTDAPI(SafeArrayDestroyDescriptor)(SAFEARRAY FAR* psa);
+
+pSTDAPI(SafeArrayDestroyData)(SAFEARRAY FAR* psa);
+
+pSTDAPI(SafeArrayDestroy)(SAFEARRAY FAR* psa);
+
+pSTDAPI(SafeArrayRedim)(SAFEARRAY FAR* psa, SAFEARRAYBOUND FAR* psaboundNew);
+
+pSTDAPI_(SafeArrayGetDim, unsigned int)(SAFEARRAY FAR* psa);
+
+pSTDAPI_(SafeArrayGetElemsize, unsigned int)(SAFEARRAY FAR* psa);
+
+pSTDAPI(SafeArrayGetUBound)(SAFEARRAY FAR* psa, unsigned int nDim, long FAR* plUbound);
+
+pSTDAPI(SafeArrayGetLBound)(SAFEARRAY FAR* psa, unsigned int nDim, long FAR* plLbound);
+
+pSTDAPI(SafeArrayLock)(SAFEARRAY FAR* psa);
+
+pSTDAPI(SafeArrayUnlock)(SAFEARRAY FAR* psa);
+
+pSTDAPI(SafeArrayAccessData)(SAFEARRAY FAR* psa, void HUGEP* FAR* ppvData);
+
+pSTDAPI(SafeArrayUnaccessData)(SAFEARRAY FAR* psa);
+
+pSTDAPI(SafeArrayGetElement)(
+ SAFEARRAY FAR* psa,
+ long FAR* rgIndices,
+ void FAR* pv);
+
+pSTDAPI(SafeArrayPutElement)(
+ SAFEARRAY FAR* psa,
+ long FAR* rgIndices,
+ void FAR* pv);
+
+pSTDAPI(SafeArrayCopy)(
+ SAFEARRAY FAR* psa,
+ SAFEARRAY FAR* FAR* ppsaOut);
+
+pSTDAPI(SafeArrayPtrOfIndex)(
+ SAFEARRAY FAR* psa,
+ long FAR* rgIndices,
+ void HUGEP* FAR* ppvData);
+
+
+pSTDAPI_(VariantInit, void)(VARIANTARG FAR* pvarg);
+
+pSTDAPI(VariantClear)(VARIANTARG FAR* pvarg);
+
+pSTDAPI(VariantCopy)(
+ VARIANTARG FAR* pvargDest,
+ VARIANTARG FAR* pvargSrc);
+
+pSTDAPI(VariantCopyInd)(
+ VARIANT FAR* pvarDest,
+ VARIANTARG FAR* pvargSrc);
+
+pSTDAPI(VariantChangeType)(
+ VARIANTARG FAR* pvargDest,
+ VARIANTARG FAR* pvarSrc,
+ unsigned short wFlags,
+ VARTYPE vt);
+
+pSTDAPI(VariantChangeTypeEx)(
+ VARIANTARG FAR* pvargDest,
+ VARIANTARG FAR* pvarSrc,
+ LCID lcid,
+ unsigned short wFlags,
+ VARTYPE vt);
+
+pSTDAPI(VarI2FromI4)(long lIn, short FAR* psOut);
+pSTDAPI(VarI2FromR4)(float fltIn, short FAR* psOut);
+pSTDAPI(VarI2FromR8)(double dblIn, short FAR* psOut);
+pSTDAPI(VarI2FromCy)(CY cyIn, short FAR* psOut);
+pSTDAPI(VarI2FromDate)(DATE dateIn, short FAR* psOut);
+pSTDAPI(VarI2FromStr)(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, short FAR* psOut);
+pSTDAPI(VarI2FromDisp)(IDispatch FAR* pdispIn, LCID lcid, short FAR* psOut);
+pSTDAPI(VarI2FromBool)(VARIANT_BOOL boolIn, short FAR* psOut);
+
+pSTDAPI(VarI4FromI2)(short sIn, long FAR* plOut);
+pSTDAPI(VarI4FromR4)(float fltIn, long FAR* plOut);
+pSTDAPI(VarI4FromR8)(double dblIn, long FAR* plOut);
+pSTDAPI(VarI4FromCy)(CY cyIn, long FAR* plOut);
+pSTDAPI(VarI4FromDate)(DATE dateIn, long FAR* plOut);
+pSTDAPI(VarI4FromStr)(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, long FAR* plOut);
+pSTDAPI(VarI4FromDisp)(IDispatch FAR* pdispIn, LCID lcid, long FAR* plOut);
+pSTDAPI(VarI4FromBool)(VARIANT_BOOL boolIn, long FAR* plOut);
+
+pSTDAPI(VarR4FromI2)(short sIn, float FAR* pfltOut);
+pSTDAPI(VarR4FromI4)(long lIn, float FAR* pfltOut);
+pSTDAPI(VarR4FromR8)(double dblIn, float FAR* pfltOut);
+pSTDAPI(VarR4FromCy)(CY cyIn, float FAR* pfltOut);
+pSTDAPI(VarR4FromDate)(DATE dateIn, float FAR* pfltOut);
+pSTDAPI(VarR4FromStr)(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, float FAR* pfltOut);
+pSTDAPI(VarR4FromDisp)(IDispatch FAR* pdispIn, LCID lcid, float FAR* pfltOut);
+pSTDAPI(VarR4FromBool)(VARIANT_BOOL boolIn, float FAR* pfltOut);
+
+pSTDAPI(VarR8FromI2)(short sIn, double FAR* pdblOut);
+pSTDAPI(VarR8FromI4)(long lIn, double FAR* pdblOut);
+pSTDAPI(VarR8FromR4)(float fltIn, double FAR* pdblOut);
+pSTDAPI(VarR8FromCy)(CY cyIn, double FAR* pdblOut);
+pSTDAPI(VarR8FromDate)(DATE dateIn, double FAR* pdblOut);
+pSTDAPI(VarR8FromStr)(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, double FAR* pdblOut);
+pSTDAPI(VarR8FromDisp)(IDispatch FAR* pdispIn, LCID lcid, double FAR* pdblOut);
+pSTDAPI(VarR8FromBool)(VARIANT_BOOL boolIn, double FAR* pdblOut);
+
+pSTDAPI(VarDateFromI2)(short sIn, DATE FAR* pdateOut);
+pSTDAPI(VarDateFromI4)(long lIn, DATE FAR* pdateOut);
+pSTDAPI(VarDateFromR4)(float fltIn, DATE FAR* pdateOut);
+pSTDAPI(VarDateFromR8)(double dblIn, DATE FAR* pdateOut);
+pSTDAPI(VarDateFromCy)(CY cyIn, DATE FAR* pdateOut);
+pSTDAPI(VarDateFromStr)(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, DATE FAR* pdateOut);
+pSTDAPI(VarDateFromDisp)(IDispatch FAR* pdispIn, LCID lcid, DATE FAR* pdateOut);
+pSTDAPI(VarDateFromBool)(VARIANT_BOOL boolIn, DATE FAR* pdateOut);
+
+pSTDAPI(VarCyFromI2)(short sIn, CY FAR* pcyOut);
+pSTDAPI(VarCyFromI4)(long lIn, CY FAR* pcyOut);
+pSTDAPI(VarCyFromR4)(float fltIn, CY FAR* pcyOut);
+pSTDAPI(VarCyFromR8)(double dblIn, CY FAR* pcyOut);
+pSTDAPI(VarCyFromDate)(DATE dateIn, CY FAR* pcyOut);
+pSTDAPI(VarCyFromStr)(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, CY FAR* pcyOut);
+pSTDAPI(VarCyFromDisp)(IDispatch FAR* pdispIn, LCID lcid, CY FAR* pcyOut);
+pSTDAPI(VarCyFromBool)(VARIANT_BOOL boolIn, CY FAR* pcyOut);
+
+pSTDAPI(VarBstrFromI2)(short iVal, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut);
+pSTDAPI(VarBstrFromI4)(long lIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut);
+pSTDAPI(VarBstrFromR4)(float fltIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut);
+pSTDAPI(VarBstrFromR8)(double dblIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut);
+pSTDAPI(VarBstrFromCy)(CY cyIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut);
+pSTDAPI(VarBstrFromDate)(DATE dateIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut);
+pSTDAPI(VarBstrFromDisp)(IDispatch FAR* pdispIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut);
+pSTDAPI(VarBstrFromBool)(VARIANT_BOOL boolIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut);
+
+pSTDAPI(VarBoolFromI2)(short sIn, VARIANT_BOOL FAR* pboolOut);
+pSTDAPI(VarBoolFromI4)(long lIn, VARIANT_BOOL FAR* pboolOut);
+pSTDAPI(VarBoolFromR4)(float fltIn, VARIANT_BOOL FAR* pboolOut);
+pSTDAPI(VarBoolFromR8)(double dblIn, VARIANT_BOOL FAR* pboolOut);
+pSTDAPI(VarBoolFromDate)(DATE dateIn, VARIANT_BOOL FAR* pboolOut);
+pSTDAPI(VarBoolFromCy)(CY cyIn, VARIANT_BOOL FAR* pboolOut);
+pSTDAPI(VarBoolFromStr)(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, VARIANT_BOOL FAR* pboolOut);
+pSTDAPI(VarBoolFromDisp)(IDispatch FAR* pdispIn, LCID lcid, VARIANT_BOOL FAR* pboolOut);
+
+pSTDAPI(MPWVarFromR4)(float FAR* pfltIn, VARIANT FAR* pvarOut);
+pSTDAPI(MPWVarFromR8)(double FAR* pdblIn, VARIANT FAR* pvarOut);
+pSTDAPI(MPWR4FromVar)(VARIANT FAR* pvarIn, float FAR* pfltOut);
+pSTDAPI(MPWR8FromVar)(VARIANT FAR* pvarIn, double FAR* pdblOut);
+
+pSTDAPI_(LHashValOfNameSys, unsigned long)(SYSKIND syskind, LCID lcid, OLECHAR FAR* szName);
+
+pSTDAPI(LoadTypeLib)(OLECHAR FAR* szFile, ITypeLib FAR* FAR* pptlib);
+
+pSTDAPI(LoadRegTypeLib)(
+ REFGUID rguid,
+ unsigned short wVerMajor,
+ unsigned short wVerMinor,
+ LCID lcid,
+ ITypeLib FAR* FAR* pptlib);
+
+pSTDAPI(QueryPathOfRegTypeLib)(
+ REFGUID guid,
+ unsigned short wMaj,
+ unsigned short wMin,
+ LCID lcid,
+ LPBSTR lpbstrPathName);
+
+pSTDAPI(RegisterTypeLib)(
+ ITypeLib FAR* ptlib,
+ OLECHAR FAR* szFullPath,
+ OLECHAR FAR* szHelpDir);
+
+pSTDAPI(CreateTypeLib)(SYSKIND syskind, OLECHAR FAR* szFile, ICreateTypeLib FAR* FAR* ppctlib);
+
+pSTDAPI(LoadTypeLibFSp)(const FSSpec *pfsspec, ITypeLib FAR* FAR* pptlib);
+
+pSTDAPI(RegisterTypeLibFolder)(OLECHAR FAR* szFullPath);
+
+pSTDAPI(QueryTypeLibFolder)(LPBSTR pbstr);
+
+pSTDAPI(DispGetParam)(
+ DISPPARAMS FAR* pdispparams,
+ unsigned int position,
+ VARTYPE vtTarg,
+ VARIANT FAR* pvarResult,
+ unsigned int FAR* puArgErr);
+
+pSTDAPI(DispGetIDsOfNames)(
+ ITypeInfo FAR* ptinfo,
+ OLECHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ DISPID FAR* rgdispid);
+
+pSTDAPI(DispInvoke)(
+ void FAR* _this,
+ ITypeInfo FAR* ptinfo,
+ DISPID dispidMember,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pparams,
+ VARIANT FAR* pvarResult,
+ EXCEPINFO FAR* pexcepinfo,
+ unsigned int FAR* puArgErr);
+
+pSTDAPI(CreateDispTypeInfo)(
+ INTERFACEDATA FAR* pidata,
+ LCID lcid,
+ ITypeInfo FAR* FAR* pptinfo);
+
+pSTDAPI(CreateStdDispatch)(
+ IUnknown FAR* punkOuter,
+ void FAR* pvThis,
+ ITypeInfo FAR* ptinfo,
+ IUnknown FAR* FAR* ppunkStdDisp);
+
+pSTDAPI(RegisterActiveObject)(
+ IUnknown FAR* punk,
+ REFCLSID rclsid,
+ void FAR* pvReserved,
+ unsigned long FAR* pdwRegister);
+
+pSTDAPI(RevokeActiveObject)(
+ unsigned long dwRegister,
+ void FAR* pvReserved);
+
+pSTDAPI(GetActiveObject)(
+ REFCLSID rclsid,
+ void FAR* pvReserved,
+ IUnknown FAR* FAR* ppunk);
+
+
+} oavtbl;
+
diff --git a/private/oleauto/src/dispatch/ole2.ini b/private/oleauto/src/dispatch/ole2.ini
new file mode 100644
index 000000000..4d02a080b
--- /dev/null
+++ b/private/oleauto/src/dispatch/ole2.ini
@@ -0,0 +1,275 @@
+// ole2.ini format:
+// -- list of names for the Insert New Object dialog
+// [insert]
+// <class name1>=
+// <class name2>=
+// <class name3>=
+//
+// --many instances of the following...
+// [<classname>]
+// handler=<dll name>
+// server=<exe name>
+// links=<class name>
+//
+// --one instance of the following (do not name a class "extensions")
+// [extensions]
+// xxx=<classname>
+// yyy=<classname>
+// ...
+
+[insert]
+
+// OLE2.0 servers
+EllipseWT=
+SDemo1=
+InPlaceSDemo1=
+OLineS=
+
+// Testing group's OLE2.0 servers
+Cl2Test=
+miCl2Test=
+Sr2Test=
+Sr2Inv=
+Sr2_1Test=
+miSr2Test=
+miSr2Inv=
+miSr2_1Test=
+
+
+// OLE1.0 servers
+ExcelWorksheet=
+ExcelChart=
+ExcelMacroSheet=
+MsGraph=
+MsDraw=
+WordArt=
+ServerDemo=
+SrTest=
+Shapes=
+MiShapes=
+WordDocument=
+SoundRec=
+PBrush=
+Equation=
+MSPowerPoint=
+MSPowerPointSho=
+Package=
+
+
+// Development's unit testing related stuff
+[TestServer1]
+handler=server1.dll
+
+[AltServer1]
+handler=server1.dll
+
+[CFileMoniker]
+handler=ole2.dll
+
+[CItemMoniker]
+handler=ole2.dll
+
+[CCompositeMoniker]
+handler=ole2.dll
+
+[TestRem]
+
+[MainTestRem]
+server=testrem.exe
+
+// IDispatch testing stuff
+[CDispTst]
+server=sdisptst.exe
+
+[CSArray]
+server=sdisptst.exe
+
+// IDispatch sample code stuff
+[CPoly]
+server=spoly.exe
+
+[CPoint]
+server=spoly.exe
+
+
+// OLE2.0 servers' info
+[EllipseWT]
+handler=ellipswt.dll
+
+[SDemo1]
+handler=ole2.dll
+server=sdemo1.exe
+verb 0=&Play
+verb 1=&Edit
+
+[InPlaceSDemo1]
+handler=ole2.dll
+server=ipsdemo1.exe
+
+[OLineS]
+handler=ole2.dll
+server=olines.exe
+
+[DfMarshal]
+handler=ole2.dll
+
+[StdMemStm]
+handler=ole2.dll
+
+[StdMemBytes]
+handler=ole2.dll
+
+[StdOleLink]
+handler=ole2.dll
+
+[CFileMoniker]
+handler=ole2.dll
+
+[CItemMoniker]
+handler=ole2.dll
+
+[CCompositeMoniker]
+handler=ole2.dll
+
+[CAntiMoniker]
+handler=ole2.dll
+
+
+// Testing group's OLE2.0 servers' info
+[Cl2Test]
+handler=ole2.dll
+server=cl2test.exe
+
+[miCl2Test]
+handler=ole2.dll
+server=micl2.exe
+
+
+[Sr2Test]
+handler=ole2.dll
+server=sr2test.exe
+verb 0=&Play
+verb 1=&Edit
+
+[Sr2Inv]
+handler=ole2.dll
+server=sr2test.exe
+verb 0=&Play
+verb 1=&Edit
+
+[Sr2_1Test]
+handler=ole2.dll
+server=sr2_1.exe
+verb 0=&Play
+verb 1=&Edit
+
+[miSr2Test]
+handler=ole2.dll
+server=misr2.exe
+verb 0=&Play
+verb 1=&Edit
+
+[miSr2Inv]
+handler=ole2.dll
+server=misr2.exe
+verb 0=&Play
+verb 1=&Edit
+
+[miSr2_1Test]
+handler=ole2.dll
+server=misr2_1.exe
+verb 0=&Play
+verb 1=&Edit
+
+
+// OLE1.0 servers' info
+[ExcelWorksheet]
+handler=ole2.dll
+ole10server=1
+
+[ExcelChart]
+handler=ole2.dll
+ole10server=1
+
+[ExcelMacroSheet]
+handler=ole2.dll
+ole10server=1
+
+[MsGraph]
+handler=ole2.dll
+ole10server=1
+
+[MsDraw]
+handler=ole2.dll
+ole10server=1
+
+[WordArt]
+handler=ole2.dll
+ole10server=1
+
+[ServerDemo]
+handler=ole2.dll
+ole10server=1
+
+[SrTest]
+handler=ole2.dll
+ole10server=1
+
+[Shapes]
+handler=ole2.dll
+ole10server=1
+
+[MiShapes]
+handler=ole2.dll
+ole10server=1
+
+[WordDocument]
+handler=ole2.dll
+ole10server=1
+
+[SoundRec]
+handler=ole2.dll
+ole10server=1
+
+[PBrush]
+handler=ole2.dll
+ole10server=1
+
+[Equation]
+handler=ole2.dll
+ole10server=1
+
+[MSPowerPoint]
+handler=ole2.dll
+ole10server=1
+
+[MSPowerPointSho]
+handler=ole2.dll
+ole10server=1
+
+[Package]
+handler=ole2.dll
+ole10server=1
+
+
+// Extensions
+[extensions]
+foo=CFoo
+sd=SDemo1
+oln=OLineS
+xlc=ExcelChart
+clt=Cl2Test
+mct=miCl2Test
+sr2=Sr2Test
+si2=Sr2Inv
+s21=Sr2_1Test
+mr2=miSr2Test
+mi2=miSr2Inv
+m21=miSr2_1Test
+
+// Interfaces
+[interfaces]
+IID(516 0 0 0 192 0 0 17920)=testprox.dll, ITestRem1
+
+IID(1024 2 0 0 192 0 0 17920)=oledisp.dll, IDispatch
+IID(1025 2 0 0 192 0 0 17920)=oledisp.dll, ITypeInfo
diff --git a/private/oleauto/src/dispatch/ole2auto.reg b/private/oleauto/src/dispatch/ole2auto.reg
new file mode 100644
index 000000000..c315a581a
--- /dev/null
+++ b/private/oleauto/src/dispatch/ole2auto.reg
@@ -0,0 +1,79 @@
+REGEDIT
+
+; registration info for the ole programmability component
+
+
+-- IDispatch
+
+HKEY_CLASSES_ROOT\Interface\{00020400-0000-0000-C000-000000000046} = IDispatch
+HKEY_CLASSES_ROOT\Interface\{00020400-0000-0000-C000-000000000046}\NumMethods = 7
+HKEY_CLASSES_ROOT\Interface\{00020400-0000-0000-C000-000000000046}\ProxyStubClsid = {00020420-0000-0000-C000-000000000046}
+
+
+-- IEnumVARIANT
+
+HKEY_CLASSES_ROOT\Interface\{00020404-0000-0000-C000-000000000046} = IEnumVARIANT
+HKEY_CLASSES_ROOT\Interface\{00020404-0000-0000-C000-000000000046}\NumMethods = 7
+HKEY_CLASSES_ROOT\Interface\{00020404-0000-0000-C000-000000000046}\ProxyStubClsid = {00020421-0000-0000-C000-000000000046}
+
+
+-- ITypeInfo
+
+HKEY_CLASSES_ROOT\Interface\{00020401-0000-0000-C000-000000000046} = ITypeInfo
+HKEY_CLASSES_ROOT\Interface\{00020401-0000-0000-C000-000000000046}\NumMethods = 22
+HKEY_CLASSES_ROOT\Interface\{00020401-0000-0000-C000-000000000046}\ProxyStubClsid = {00020422-0000-0000-C000-000000000046}
+
+
+-- ITypeLib
+
+HKEY_CLASSES_ROOT\Interface\{00020402-0000-0000-C000-000000000046} = ITypeLib
+HKEY_CLASSES_ROOT\Interface\{00020402-0000-0000-C000-000000000046}\NumMethods = 13
+HKEY_CLASSES_ROOT\Interface\{00020402-0000-0000-C000-000000000046}\ProxyStubClsid = {00020423-0000-0000-C000-000000000046}
+
+
+-- ITypeComp
+
+HKEY_CLASSES_ROOT\Interface\{00020403-0000-0000-C000-000000000046} = ITypeComp
+HKEY_CLASSES_ROOT\Interface\{00020403-0000-0000-C000-000000000046}\NumMethods = 5
+HKEY_CLASSES_ROOT\Interface\{00020403-0000-0000-C000-000000000046}\ProxyStubClsid = {00020425-0000-0000-C000-000000000046}
+
+-- ICreateTypeInfo
+
+HKEY_CLASSES_ROOT\Interface\{00020405-0000-0000-C000-000000000046} = ICreateTypeInfo
+HKEY_CLASSES_ROOT\Interface\{00020405-0000-0000-C000-000000000046}\NumMethods = 26
+
+
+-- ICreateTypeLib
+
+HKEY_CLASSES_ROOT\Interface\{00020406-0000-0000-C000-000000000046} = ICreateTypeLib
+HKEY_CLASSES_ROOT\Interface\{00020406-0000-0000-C000-000000000046}\NumMethods = 13
+
+
+-- OLE Automation stdole.tlb registration
+
+HKEY_CLASSES_ROOT\TypeLib\{00020430-0000-0000-C000-000000000046}
+HKEY_CLASSES_ROOT\TypeLib\{00020430-0000-0000-C000-000000000046}\1.0 = OLE Automation
+HKEY_CLASSES_ROOT\TypeLib\{00020430-0000-0000-C000-000000000046}\1.0\HELPDIR =
+HKEY_CLASSES_ROOT\TypeLib\{00020430-0000-0000-C000-000000000046}\1.0\0\win16 = stdole.tlb
+
+
+-- Registration info for OLE Automation private classes
+
+HKEY_CLASSES_ROOT\CLSID\{00020420-0000-0000-C000-000000000046} = PSDispatch
+HKEY_CLASSES_ROOT\CLSID\{00020420-0000-0000-C000-000000000046}\InprocServer = ole2disp.dll
+
+HKEY_CLASSES_ROOT\CLSID\{00020421-0000-0000-C000-000000000046} = PSEnumVARIANT
+HKEY_CLASSES_ROOT\CLSID\{00020421-0000-0000-C000-000000000046}\InprocServer = ole2disp.dll
+
+HKEY_CLASSES_ROOT\CLSID\{00020422-0000-0000-C000-000000000046} = PSTypeInfo
+HKEY_CLASSES_ROOT\CLSID\{00020422-0000-0000-C000-000000000046}\InprocServer = ole2disp.dll
+
+HKEY_CLASSES_ROOT\CLSID\{00020423-0000-0000-C000-000000000046} = PSTypeLib
+HKEY_CLASSES_ROOT\CLSID\{00020423-0000-0000-C000-000000000046}\InprocServer = ole2disp.dll
+
+HKEY_CLASSES_ROOT\CLSID\{00020425-0000-0000-C000-000000000046} = PSTypeComp
+HKEY_CLASSES_ROOT\CLSID\{00020425-0000-0000-C000-000000000046}\InprocServer = ole2disp.dll
+
+HKEY_CLASSES_ROOT\CLSID\{00020424-0000-0000-C000-000000000046} = PSAutomation
+HKEY_CLASSES_ROOT\CLSID\{00020424-0000-0000-C000-000000000046}\InprocServer = ole2disp.dll
+
diff --git a/private/oleauto/src/dispatch/oledate.c b/private/oleauto/src/dispatch/oledate.c
new file mode 100644
index 000000000..03a3b93a5
--- /dev/null
+++ b/private/oleauto/src/dispatch/oledate.c
@@ -0,0 +1,370 @@
+/***
+* Rtdate.c - Date/time support
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Purpose:
+* This source contains the date/time support that are exported
+* for use in the ole dlls.
+*
+* Revision History:
+*
+* [00] 17-Dec-92 bradlo: Split off from rtdate.c
+*
+* Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#include <stdio.h>
+#include <math.h>
+#include <time.h>
+#include <stdlib.h>
+
+ASSERTDATA
+
+
+#define HALF_SECOND (1.0/172800.0)
+
+// Map from month number (0-based) to day of year month starts (0-based)
+// Good for non-leap years. Last entry is 365 (days in a year)
+//
+const int NEARDATA mpmmdd[13] = {
+ 0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334, 365
+};
+
+/***
+*ErrPackDate - pack a UDS into a date/time serial number
+*
+*Purpose:
+* Generate a date/time serial number from a UDS
+*
+*Entry:
+* UDS *puds = pointer to UDS to pack
+* VARIANT *pvarDate = pointer to serial date to be filled
+* int fValidDate =
+* TRUE - the UDS is known to contain a valid date
+* FALSE - perform more checks and work to pack a possibly invalid date
+* dwFlags =
+* VAR_TIMEVALUEONLY - return only time value
+* VAR_DATEVALUEONLY - return only date value
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+EXTERN_C INTERNAL_(HRESULT)
+ErrPackDate(UDS FAR* puds, VARIANT FAR* pvarDate, int fValidDate, unsigned long dwFlags)
+{
+ long lDate;
+ double dblTime;
+ int fLeapYear;
+ short mm, dd, yy;
+
+ /* put uds stuff in local vars
+ also, make months zero based and adjust for out of range
+ months (for date calculations using DateSerial) */
+
+ yy = puds->Year;
+ mm = puds->Month - 1;
+
+ if(!fValidDate){
+ if (mm < 0) {
+ yy -= 1 + (-mm / 12);
+ mm = 12 - (-mm % 12);
+ } else {
+ yy += mm / 12;
+ mm = mm % 12;
+ }
+ }
+
+ if(yy < 100)
+ yy += 1900;
+
+ dd = puds->DayOfMonth;
+
+ /* Check for leap year */
+
+ fLeapYear = ((yy & 3) == 0) && ((yy % 100) != 0 || (yy % 400) == 0);
+
+ /* Check if it's a valid date */
+
+ if(yy < 0 || yy > 9999 || mm < 0 || mm > 12)
+ return RESULT(DISP_E_TYPEMISMATCH); /* REVIEW: correct error? */
+
+ if(fValidDate
+ && (mm > 11 || dd < 1 || dd > mpmmdd[mm + 1] - mpmmdd[mm])
+ && !(mm == 1 && dd == 29 && fLeapYear))
+ {
+ return RESULT(DISP_E_TYPEMISMATCH); /* REVIEW: correct error? */
+ }
+
+ /* It is a valid date; make Jan 1, 1AD be 1 */
+
+ lDate = yy * 365L + (yy / 4) - yy/100 + yy/400 + mpmmdd[mm] + dd;
+
+ /* If we are a leap year and it's before March, subtract 1:
+ we haven't leapt yet! */
+
+ if(mm < 2 && fLeapYear)
+ --lDate;
+
+ /* Offset so that 12/30/1899 is 0 */
+
+ lDate -= 693959L;
+
+ if(lDate > 2958465 || lDate < -657434)
+ return RESULT(DISP_E_TYPEMISMATCH); /* REVIEW: correct error? */
+
+ if (fValidDate
+ && (puds->Hour < 0 || puds->Hour > 23
+ || puds->Minute < 0 || puds->Minute > 59
+ || puds->Second < 0 || puds->Second > 59))
+ {
+ return RESULT(DISP_E_TYPEMISMATCH); /* REVIEW: correct error? */
+ }
+
+ dblTime = (((long)puds->Hour * 3600L) + // hrs in seconds
+ ((long)puds->Minute * 60L) + // mins in seconds
+ ((long)puds->Second)) * (1. / 86400.);
+
+ V_VT(pvarDate) = VT_DATE;
+ if (dwFlags & VAR_TIMEVALUEONLY)
+ V_DATE(pvarDate) = dblTime;
+ else if (dwFlags & VAR_DATEVALUEONLY)
+ V_DATE(pvarDate) = (double)lDate;
+ else
+ V_DATE(pvarDate) = (double)lDate + ((lDate >= 0) ? dblTime : -dblTime);
+
+ return NOERROR;
+}
+
+/***
+* ErrUnpackDate - unpack a date/time serial number into a UDS
+*
+* Purpose:
+* Generate a UDS from a packed date/time serial number
+*
+* Entry:
+* UDS *puds = pointer to UDS to unpack into
+* double serialDate = serial number to unpack
+*
+* Exit:
+* EBERR_None = *puds is the unpacked date
+* EBERR_IllegalFuncCall = serialDate is out-of-range
+*
+* Exceptions:
+*
+***********************************************************************/
+EXTERN_C INTERNAL_(HRESULT)
+ErrUnpackDate(UDS FAR* puds, VARIANT FAR* pvar)
+{
+ int mm;
+ int nTime;
+ int fLeapOly;
+ int const * lpdd;
+ double serialDate, roundDate;
+ long lDate, lTime;
+ int oly, nDate, y, c4, cty;
+
+ fLeapOly = TRUE; // assume true
+
+ if(V_VT(pvar) != VT_DATE && V_VT(pvar) != VT_R8)
+ return RESULT(E_INVALIDARG);
+
+ roundDate = serialDate = V_DATE(pvar);
+
+ /* Local variables:
+ *
+ * lDate day based on 0 as 1/1/0 (note different from input)
+ * so 1/1/1900 is 693961 under this system.
+ * lTime time in seconds since midnight
+ * c4 number of 400-year blocks since 1/1/0
+ * cty century within c4 (0-3)
+ * oly olympiad (starting with oly 0 is years AD 0-3)
+ * nDate day number within oly (0 is 1/1 of 1st year;
+ * 1460 is 12/31 of 4th)
+ * y year in oly (0-3)
+ * fLeapOly true if the date is in a leap oly
+ */
+
+ /* WARNING: DO NOT CAST serialDate TO A 'long' BEFORE VERIFYING
+ THAT IT WILL NOT CAUSE A FLOATING-POINT EXCEPTION DUE TO
+ OVERFLOW. _aFftol IS NOT FOLLOWED BY AN FWAIT INSTRUCTION,
+ SO THE FP EXCEPTION WON'T BE RAISED UNTIL SOME OTHER CODE
+ CALLS FWAIT. ErrUnpackDate() CANNOT RAISE EXCEPTIONS - IT
+ MUST RETURN AN ERROR CODE. VBA2 #1914
+ */
+ if(serialDate >= 2958466.0 || serialDate <= -657435.0)
+ return RESULT(DISP_E_TYPEMISMATCH); // REVIEW: correct error?
+
+ // prep for round to the sec
+ roundDate += (serialDate > 0.0) ? HALF_SECOND : -HALF_SECOND;
+
+ if(roundDate <= 2958465.0 && roundDate >= -657435.0)
+ serialDate = roundDate;
+
+ lDate = (long)serialDate + 693959L; // Add days from 1/1/0 to 12/30/1899
+
+ if(serialDate < 0)
+ serialDate = -serialDate;
+
+ lTime = (long)((serialDate - disp_floor(serialDate)) * 86400.);
+
+ if (lDate < 0)
+ lDate = 0;
+
+ /* Leap years are every 4 years except centuries that are
+ not multiples of 400. */
+
+ c4 = (int)(lDate / 146097L);
+
+ // Now lDate is day within 400-year block
+ lDate %= 146097L;
+
+ // -1 because first century has extra day
+ cty = (int)((lDate - 1) / 36524L);
+
+ if(cty != 0){ // Non-leap century
+
+ // Now lDate is day within century
+ lDate = (lDate - 1) % 36524L;
+
+ // +1 because 1st oly has 1460 days
+ oly = (int) ((lDate + 1) / 1461L);
+
+ if(oly != 0){
+
+ nDate = (int)((lDate + 1) % 1461L);
+
+ }else{
+
+ fLeapOly = FALSE;
+ nDate = (int)lDate;
+
+ }
+
+ } else { // Leap century - not special case!
+
+ oly = (int)(lDate / 1461L);
+ nDate = (int)(lDate % 1461L);
+
+ }
+
+ if (fLeapOly) {
+
+ y = (nDate - 1) / 365; // -1 because first year has 366 days
+ if(y != 0)
+ nDate = (nDate - 1) % 365;
+
+ } else {
+
+ y = nDate / 365;
+ nDate %= 365;
+
+ }
+
+ // nDate is now 0-based day of year. Save 1-based day of year, year number
+
+ puds->Year = c4 * 400 + cty * 100 + oly * 4 + y;
+
+ // Handle leap year: before, on, and after Feb. 29.
+
+ if (y == 0 && fLeapOly) { // Leap Year
+
+ if (nDate == 59) {
+
+ /* Feb. 29 */
+ puds->Month = 2;
+ puds->DayOfMonth = 29;
+ goto DoTime;
+
+ }
+
+ if (nDate >= 60)
+ --nDate; // Pretend it's not a leap year for month/day comp.
+ }
+
+ // Code from here to DoTime computes month/day for everything but Feb. 29.
+
+ ++nDate; /* Make it 1-based rather than 0-based */
+
+ // nDate is now 1-based day of non-leap year.
+
+ /* Month number will always be >= n/32, so save some loop time */
+
+ for (mm = (nDate >> 5) + 1, lpdd = &mpmmdd[mm];
+ nDate > *lpdd; mm++, lpdd++);
+
+ puds->Month = (short)mm;
+ puds->DayOfMonth = (short)(nDate - lpdd[-1]);
+
+DoTime:;
+
+ // We have all date info in uds.
+
+ if(lTime == 0){ // avoid the divisions
+
+ puds->Second = puds->Minute = puds->Hour = 0;
+
+ }else{
+ puds->Second = (short)(lTime % 60L);
+ nTime = (int)(lTime / 60L);
+ puds->Minute = (short)(nTime % 60);
+ puds->Hour = (short)(nTime / 60);
+ }
+
+ return NOERROR;
+}
+
+/***
+* int GetCurrentYear - returns the current year
+*
+* Purpose:
+* Get the current year
+*
+* Entry:
+* None
+*
+* Exit:
+* returns current year
+*
+*
+* Exceptions:
+*
+***********************************************************************/
+
+INTERNAL_(int)
+GetCurrentYear(void)
+{
+#if OE_MAC
+
+ DateTimeRec d;
+ unsigned long secs;
+
+ GetDateTime(&secs);
+ Secs2Date(secs, &d);
+ return (int)d.year;
+
+#elif OE_WIN32
+
+ SYSTEMTIME s;
+
+ GetLocalTime(&s);
+ return s.wYear;
+
+#else
+ void PASCAL DOS3CALL(void);
+ int iYear;
+
+ _asm {
+ mov ah, 0x2a // 2a = Get Date Function
+ call DOS3CALL // Int 21 call
+ mov iYear, cx
+ }
+
+ return iYear;
+#endif
+}
diff --git a/private/oleauto/src/dispatch/oledisp.h b/private/oleauto/src/dispatch/oledisp.h
new file mode 100644
index 000000000..a34576c7a
--- /dev/null
+++ b/private/oleauto/src/dispatch/oledisp.h
@@ -0,0 +1,817 @@
+/***
+*oledisp.h - misc Oledisp wide definitions.
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+*
+*
+*Revision History:
+*
+* [00] 07-Oct-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#ifndef _OLEDISP_H_ /* { */
+#define _OLEDISP_H_
+
+/* set Operating Environment switches */
+#define FE_DBCS // DBCS support for all platforms
+
+#ifdef _MAC
+# define OE_MAC 1
+# define OE_WIN 0
+# define OE_WIN16 0
+# define OE_WIN32 0
+#else
+# ifdef WIN32
+# define OE_WIN 1
+# define OE_MAC 0
+# define OE_WIN16 0
+# define OE_WIN32 1
+# else
+# define OE_WIN 1
+# define OE_MAC 0
+# define OE_WIN16 1
+# define OE_WIN32 0
+# endif
+#endif
+
+/* set Host Compiler Switches */
+
+#if OE_MAC
+# if defined(_PPCMAC)
+# define OE_MACPPC 1
+# define OE_MAC68K 0
+# else
+# define OE_MACPPC 0
+# define OE_MAC68K 1
+# endif
+# if defined(_MSC_VER)
+# define HC_MSC 1
+# define HC_MPW 0
+# else
+# define HC_MSC 0
+# define HC_MPW 1
+# endif
+# define IfWin(X)
+# define IfMac(X) (X)
+#else
+# define HC_MSC 1
+# define HC_MPW 0
+# define IfWin(X) (X)
+# define IfMac(X)
+#endif
+
+#include <stdio.h>
+#include <string.h>
+
+#if OE_WIN16
+# include <windows.h>
+# include <ole2.h>
+# include <olenls.h>
+# include <dispatch.h>
+# pragma warning(disable:4355)
+#else
+# if OE_WIN32
+#define _OLEAUT32_ // for the new oleauto.h when we pick it up
+// Yea, right...
+#define WIN32_LEAN_AND_MEAN
+# include <windows.h>
+# pragma warning(disable:4355)
+# else
+# if OE_MAC
+#ifdef STATIC_LIB
+ #define OLENAMES_MUNGE_FOR_STATIC 1
+# include "olenames.h"
+#endif
+typedef int BOOL;
+typedef unsigned char BYTE;
+typedef unsigned short WORD;
+typedef unsigned long DWORD;
+typedef unsigned short USHORT;
+typedef unsigned int UINT;
+# define TRUE 1
+# define FALSE 0
+# if HC_MPW
+# include <types.h>
+# include <packages.h>
+# include <resources.h>
+# include <menus.h>
+# include <windows.h>
+# include <appleevents.h>
+# include <osutils.h>
+# include <LibraryManager.h>
+# include <LibraryManagerUtilities.h>
+# else
+# include <macos/types.h>
+# include <macos/packages.h>
+# include <macos/script.h>
+# include <macos/resource.h>
+# include <macos/menus.h>
+# include <macos/windows.h>
+# include <macos/osutils.h>
+# include <macos/memory.h>
+# include <macos/appleeve.h>
+# define far
+# define FAR far
+# define near
+# define NEAR near
+# if !OE_MACPPC
+# define pascal _pascal
+# endif
+# define PASCAL pascal
+# define cdecl _cdecl
+# define CDECL cdecl
+# endif
+# include <ole2.h>
+# include <olenls.h>
+# include <dispatch.h>
+# else
+# error UNKNOWN OE
+# endif
+# endif
+#endif
+
+#if OE_MAC
+# ifdef _SLM
+ /* WARNING: Dont use the C runtime's version of sprintf from an ASLM Dll. */
+# undef sprintf
+# define sprintf USE_THIS_AND_DIE
+# define SPRINTF SLMsprintf
+# else
+# define SPRINTF sprintf
+# endif
+#else
+# define SPRINTF wsprintf
+#endif
+
+#if OE_WIN32
+# define SYS_CURRENT SYS_WIN32
+#elif OE_WIN16
+# define SYS_CURRENT SYS_WIN16
+#elif OE_MAC
+# define SYS_CURRENT SYS_MAC
+#endif
+
+#if OE_WIN16
+#pragma intrinsic(memcpy)
+#pragma intrinsic(memcmp)
+#pragma intrinsic(memset)
+#pragma intrinsic(strcpy)
+#pragma intrinsic(_fmemcpy)
+#pragma intrinsic(_fmemcmp)
+#pragma intrinsic(_fmemset)
+#pragma intrinsic(_fstrcpy)
+# define OLEBOOL BOOL
+# define STRLEN _fstrlen
+# define STRCPY _fstrcpy
+# define STRCAT _fstrcat
+# define STRCHR _fstrchr
+# define STRREV _fstrrev
+# define STRUPR _fstrupr
+# define STRCMP _fstrcmp
+# define STRNCMP _fstrncmp
+# define STRSTR _fstrstr
+# define STRTOD strtod
+# define TOLOWER tolower
+# define MEMCPY _fmemcpy
+# define MEMCMP _fmemcmp
+# define MEMSET _fmemset
+# define MEMMOVE _fmemmove
+# define STRICMP _fstricmp
+# define OASTR(str) str
+# define SIZEOFCH(x) sizeof(x)
+# define SIZEOFSTRING(x) (sizeof(x) - 1)
+# define BYTELEN(x) (STRLEN(x)+1)
+# define CHLEN(x) (x)
+# define CompareString CompareStringA
+# define GetLocaleInfo GetLocaleInfoA
+# define LCMapString LCMapStringA
+# define GETSTRINGTYPE GetStringTypeA
+# define STRCPY_A STRCPY
+# define STRCAT_A STRCAT
+# define STRICMP_A STRICMP
+#endif
+
+#if OE_WIN32
+# define OLEBOOL BOOL
+# define MEMCPY memcpy
+# define MEMCMP memcmp
+# define MEMSET memset
+# define MEMMOVE memmove
+# // all assume we are operating on unicode characters
+# define STRLEN wcslen
+# define STRCPY wcscpy
+# define STRCAT wcscat
+# define STRCMP wcscmp
+# define STRICMP wcsicmp
+# define STRSTR wcsstr
+# define STRREV _wcsrev
+# define STRCHR wcschr
+# define STRNCMP wcsncmp
+# define STRTOD wcstod
+# define TOLOWER towlower
+# define SIZEOFCH(x) (sizeof(x)/2)
+# define SIZEOFSTRING(x) (sizeof(x)/2 - 1)
+# define OASTR(str) L##str
+# define BYTELEN(x) (STRLEN(x)*2+2)
+# define CHLEN(x) (x/2)
+# define STRCPY_A strcpy
+# define STRCAT_A strcat
+# define STRICMP_A stricmp
+#endif
+
+#if OE_MAC
+# define OLEBOOL unsigned long
+# define STRLEN strlen
+# define STRCPY strcpy
+# define STRCAT strcat
+# define STRCHR strchr
+# define STRREV _strrev
+# define STRUPR _strupr
+# define STRCMP strcmp
+# define STRNCMP strncmp
+# define STRSTR strstr
+# define STRTOD strtod
+# define TOLOWER tolower
+# define MEMCPY memcpy
+# define MEMCMP memcmp
+# define MEMSET memset
+# define MEMMOVE memmove
+# define SIZEOFCH(x) sizeof(x)
+# define SIZEOFSTRING(x) (sizeof(x) - 1)
+# define OASTR(str) str
+# define BYTELEN(x) (STRLEN(x)+1)
+# define CHLEN(x) (x)
+# define CompareString CompareStringA
+# define GetLocaleInfo GetLocaleInfoA
+# define LCMapString LCMapStringA
+# define GETSTRINGTYPE GetStringTypeA
+# if HC_MPW
+# define STRICMP disp_stricmp
+# else
+# define STRICMP _stricmp
+# endif
+# define STRCPY_A STRCPY
+# define STRCAT_A STRCAT
+# define STRICMP_A STRICMP
+#endif
+
+#ifndef INLINE
+# define INLINE
+#endif
+
+#ifndef EXPORT
+# if OE_MAC || OE_WIN32
+# define EXPORT
+# else
+# define EXPORT __export
+# endif
+#endif
+
+#ifndef NEAR
+# if OE_MAC || OE_WIN32
+# define NEAR
+# else
+# define NEAR __near
+# endif
+#endif
+
+#ifndef NEARDATA
+# if OE_WIN16
+# define NEARDATA __near
+# elif OE_WIN32
+# define NEARDATA
+# elif OE_MAC
+# if HC_MPW
+# define NEARDATA /* REVIEW */
+# else
+# define NEARDATA /* __declspec(allocate("_DATA")) */
+# endif
+# endif
+#endif
+
+#if OE_WIN32
+# define CDECLMETHODCALLTYPE STDMETHODVCALLTYPE
+#else
+# define CDECLMETHODCALLTYPE STDMETHODCALLTYPE
+#endif
+
+
+// char count of a guid in ansi/unicode form (including trailing Null).
+#define CCH_SZGUID0 39
+
+// Method counts - used in validating interfaces
+#define CMETH_IUnknown 3
+#define CMETH_IDispatch 7
+#define CMETH_ITypeLib 13
+#define CMETH_ITypeInfo 22
+#define CMETH_IStorage 18
+#define CMETH_IMoniker 23
+#define CMETH_IBindCtx 13
+#define CMETH_IErrorInfo 8
+
+// UNDONE: Move this into variant.h
+#define FADF_FORCEFREE 0x1000 /* SafeArrayFree() ignores FADF_STATIC and frees anyway */
+
+
+#ifndef EXTERN_C
+# ifdef __cplusplus
+# define EXTERN_C extern "C"
+# else
+# define EXTERN_C extern
+# endif
+#endif
+
+#ifdef _DEBUG
+# define LOCAL
+
+STDAPI_(void)
+DispAssert(
+ char FAR* szMsg,
+ char FAR* szFile,
+ int line);
+
+# define ASSERT(X) \
+ if(!(X)){DispAssert(NULL, g_szFileName, __LINE__);}else{}
+# define ASSERTSZ(X, MSG) \
+ if(!(X)){DispAssert( MSG, g_szFileName, __LINE__);}else{}
+# define ASSERTDATA static char g_szFileName[] = __FILE__;
+#else
+# define LOCAL static
+# define ASSERT(X)
+# define ASSERTSZ(X, SZ)
+# define ASSERTDATA
+#endif
+
+// PRIVATE - a routine that is local to its module
+// INTERNAL - a routine that is local to the DLL
+
+#if OE_WIN16
+
+# define PRIVATECALLTYPE NEAR __pascal
+# define PRIVATECALL_(TYPE) TYPE PRIVATECALLTYPE
+# define INTERNALCALLTYPE FAR __pascal
+# define INTERNALCALL_(TYPE) TYPE INTERNALCALLTYPE
+
+#elif OE_WIN32
+
+# define PRIVATECALLTYPE __stdcall
+# define PRIVATECALL_(TYPE) TYPE PRIVATECALLTYPE
+# define INTERNALCALLTYPE __stdcall
+# define INTERNALCALL_(TYPE) TYPE INTERNALCALLTYPE
+
+#elif OE_MAC
+
+// Note: cdecl is used for the INTERNALCALLTYPE because this is
+// what is used for interfacing with assembly helpers, and the
+// cdecl return convention is much more reasonable on the mac.
+
+// REVIEW: investigate NEAR/FAR for mac build
+
+# ifdef _MSC_VER
+# define PRIVATECALLTYPE __pascal
+# define PRIVATECALL_(TYPE) TYPE PRIVATECALLTYPE
+# define INTERNALCALLTYPE __cdecl
+# define INTERNALCALL_(TYPE) TYPE INTERNALCALLTYPE
+# else
+# define PRIVATECALLTYPE pascal
+# define PRIVATECALL_(TYPE) PRIVATECALLTYPE TYPE
+# define INTERNALCALLTYPE
+# define INTERNALCALL_(TYPE) INTERNALCALLTYPE TYPE
+# endif
+#endif
+
+#define PRIVATE_(TYPE) LOCAL PRIVATECALL_(TYPE)
+#define INTERNAL_(TYPE) INTERNALCALL_(TYPE)
+
+/* VT_VMAX is the first VARENUM value that is *not* legal in a VARIANT.
+ * Currently, the legal vartypes that can appear in a variant can be
+ * expressed as (ignoring ByRef, Array, etc),
+ *
+ * 0 <= vt < VT_MAX
+ *
+ * Note: if the list of legal VARIANT types ever becomes non-
+ * contiguous, then there are a couple of places in the code that
+ * validate vartype by checking for < VT_VMAX that will have to be
+ * changed.
+ *
+ */
+#define VT_VMAX VT_UNKNOWN+1
+
+// The largest unused value in VARENUM enumeration
+#define VT_MAX VT_CLSID
+
+// This is a special value that is used internally for marshaling interfaces
+#define VT_INTERFACE VT_MAX
+
+// Following is the internal definition of a VARIANT of type VT_INTERFACE.
+// This contains an IUnknown*, and its IID. If a VARIANT is of type
+// VT_INTERFACE, it can be cast to this type and the appropriate components
+// extracted.
+//
+// Note: the following struct must correctly overlay a VARIANT
+//
+typedef struct FARSTRUCT tagVARIANTX VARIANTX;
+struct FARSTRUCT tagVARIANTX
+{
+ VARTYPE vt;
+ unsigned short wReserved3; // assumes sizeof(piid) == 4
+ IID FAR* piid; // ptr to IMalloc allocated IID
+ union{
+ IUnknown FAR* punk; // VT_INTERFACE
+ IUnknown FAR* FAR* ppunk; // VT_BYREF | VT_INTERFACE
+ };
+ unsigned long dwReserved; // assumes sizeof(punk) == 4
+};
+
+
+#define UNREACHED 0
+#if HC_MPW
+# define UNUSED(X) ((void)((void*)&(X)))
+#else
+# define UNUSED(X) (X)
+#endif
+
+#define DIM(X) (sizeof(X) / sizeof((X)[0]))
+
+#define MIN(X, Y) (((X) <= (Y)) ? (X) : (Y))
+
+#define MAX(X, Y) (((X) >= (Y)) ? (X) : (Y))
+
+
+#define HRESULT_FAILED(X) ((X) != NOERROR && FAILED(GetScode(X)))
+
+#define HRESULT_SUCCESS(X) ((X) == NOERROR || !FAILED(GetScode(X)))
+
+#define IfFailGo(expression, label) \
+ { hresult = (expression); \
+ if(HRESULT_FAILED(hresult)) \
+ goto label; \
+ }
+
+#define IfFailRet(expression) \
+ { HRESULT hresult = (expression); \
+ if(HRESULT_FAILED(hresult)) \
+ return hresult; \
+ }
+
+#define RESULT(X) ResultFromScode(X)
+
+// shortcut macro used by param validation code
+#define INVALIDARG RESULT(E_INVALIDARG)
+
+
+// C Runtime style helper functions
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+INTERNAL_(HRESULT) DispAlloc(size_t cb, void FAR* FAR* ppv);
+
+INTERNAL_(void) DispFree(void FAR* pv);
+
+INTERNAL_(OLECHAR FAR*) disp_itoa(int val, OLECHAR FAR* buf, int radix);
+
+INTERNAL_(OLECHAR FAR*) disp_ltoa(long val, OLECHAR FAR* buf, int radix);
+
+INTERNAL_(double) disp_floor(double dbl);
+
+INTERNAL_(void) disp_gcvt(double dblIn, int ndigits, OLECHAR FAR* pchOut, int bufSize);
+
+INTERNAL_(double) disp_strtod(OLECHAR FAR* strIn, OLECHAR FAR* FAR* pchEnd);
+
+#if HC_MPW
+
+INTERNAL_(int) disp_stricmp(char*, char*);
+
+#endif
+
+#ifdef __cplusplus
+}
+#endif
+
+
+// private SysAllocString helper that return an HRESULT
+
+EXTERN_C INTERNAL_(HRESULT)
+ErrSysAllocString(const OLECHAR FAR* psz, BSTR FAR* pbstrOut);
+
+EXTERN_C INTERNAL_(HRESULT)
+ErrSysAllocStringLen(const OLECHAR FAR* psz, unsigned int len, BSTR FAR* pbstrOut);
+
+#if !OE_WIN32
+#define ErrStringCopy(bstrSrc, pbstrOut) \
+ ErrSysAllocStringLen(bstrSrc, SysStringLen(bstrSrc), pbstrOut)
+#else
+EXTERN_C INTERNAL_(HRESULT)
+ErrStringCopy(BSTR bstrSrc, BSTR FAR * pbstrOut);
+#endif
+
+EXTERN_C INTERNAL_(HRESULT)
+DispMarshalInterface(IStream FAR* pstm, REFIID riid, IUnknown FAR* punk);
+
+EXTERN_C INTERNAL_(HRESULT)
+DispUnmarshalInterface(IStream FAR* pstm, REFIID riid, void FAR* FAR* ppunk);
+
+#if OE_WIN32
+EXTERN_C INTERNAL_(HRESULT)
+DispMarshalHresult(IStream FAR* pstm, HRESULT hresult);
+
+EXTERN_C INTERNAL_(HRESULT)
+DispUnmarshalHresult(IStream FAR* pstm, HRESULT FAR* phresult);
+
+#else //OE_WIN32
+// no special work to do
+#define DispMarshalHresult CoMarshalHresult
+#define DispUnmarshalHresult CoUnmarshalHresult
+#endif //OE_WIN32
+
+
+// private SafeArray helpers
+
+INTERNAL_(unsigned long)
+SafeArraySize(SAFEARRAY FAR* psa);
+
+
+// private date related helpers
+//
+
+// Unpacked Date Structure
+typedef struct tagUDS {
+ short Year;
+ short Month;
+ short DayOfMonth;
+ short Hour;
+ short Minute;
+ short Second;
+} UDS;
+
+EXTERN_C INTERNAL_(HRESULT)
+ErrPackDate(
+ UDS FAR* puds,
+ VARIANT FAR* pvar,
+ int fValidate,
+ unsigned long dwFlags);
+
+EXTERN_C INTERNAL_(HRESULT)
+ErrUnpackDate(
+ UDS FAR* puds,
+ VARIANT FAR* pvar);
+
+EXTERN_C INTERNAL_(int)
+GetCurrentYear(void);
+
+#ifdef FE_DBCS
+// DBCS: map full-width strings to half-width
+EXTERN_C
+INTERNAL_(HRESULT)
+MapHalfWidth(LCID lcid, OLECHAR FAR* strIn, OLECHAR FAR* FAR* ppv);
+#endif
+
+// answers S_OK if the given VARTYPE is legal, DISP_E_BADVARTYPE if not.
+// (variant.cpp)
+INTERNAL_(HRESULT)
+IsLegalVartype(VARTYPE vt);
+
+INTERNAL_(HRESULT)
+VariantChangeTypeInternal(VARIANT FAR* pvar, LCID lcid, VARTYPE vt);
+
+// convert.cpp
+//
+INTERNAL_(HRESULT)
+IsValidDate(DATE date);
+
+#ifdef FE_DBCS
+EXTERN_C INTERNAL_(int) IsDBCS(LCID lcid);
+EXTERN_C INTERNAL_(int) IsJapan(LCID lcid);
+EXTERN_C INTERNAL_(int) IsKorea(LCID lcid);
+EXTERN_C INTERNAL_(int) IsTaiwan(LCID lcid);
+EXTERN_C INTERNAL_(int) IsChina(LCID lcid);
+#endif
+
+
+// invhelp.cpp
+//
+STDAPI
+DoInvokeMethod(
+ void FAR* pvInstance,
+ unsigned int oVft,
+ CALLCONV cc,
+ VARTYPE vtReturn,
+ unsigned int cActuals,
+ VARTYPE FAR* prgvt,
+ VARIANTARG FAR* FAR* prgpvarg,
+ VARIANT FAR* pvargResult);
+
+// tiutil.cpp
+//
+INTERNAL_(HRESULT)
+GetPrimaryInterface(
+ ITypeInfo FAR* ptinfo,
+ ITypeInfo FAR* FAR* pptinfoPri);
+
+
+// On Win16, the typelib routines are in another DLL, so we dynamically
+// bind to them only if there needed. This saves clients who dont use
+// the functionality from loading typelib.dll just because they link
+// to ole2disp.dll. On all other platforms, there all in the same
+// DLL, so there is no need.
+//
+#if OE_WIN16
+typedef HRESULT (STDAPICALLTYPE FAR* PFNLOADTYPELIB)(const OLECHAR FAR*,
+ ITypeLib FAR* FAR*);
+EXTERN_C BOOL g_fbstpImplemented;
+INTERNAL_(HRESULT) DoLoadTypeLib(const OLECHAR FAR* szFile,
+ ITypeLib FAR* FAR* pptlib);
+#else
+# define DoLoadTypeLib LoadTypeLib
+#endif
+
+#if _X86_
+EXTERN_C BOOL g_fWin32s;
+EXTERN_C BOOL g_fChicago;
+#endif //_X86_
+
+// CoGetState/CoSetState are private core OLE APIs that are
+// exported specifically to enable the Automation DLL(s) to store
+// a single per-thread object, that gets released at OleUninitialize
+// time.
+//
+STDAPI CoSetState(IUnknown FAR* punk);
+STDAPI CoGetState(IUnknown FAR* FAR* ppunk);
+# define DoCoGetState CoGetState
+# define DoCoSetState CoSetState
+
+
+#if !defined(NO_PROCESS_CACHE) && !OE_WIN32
+// Per-process cache info.
+//
+#ifdef __cplusplus
+extern "C" {
+class CProcessInfo;
+#else
+typedef int CProcessInfo;
+#endif
+
+typedef struct
+{
+ IMalloc FAR* pmalloc;
+ IErrorInfo FAR* perrinfo; // this is NOT kept valid in the cache!
+#if OE_WIN16
+ HINSTANCE hinstTypeLibDLL; // this is NOT kept valid in the cache!
+ PFNLOADTYPELIB pfnLoadTypeLib;
+#endif //OE_WIN16
+} PROCESSINFO;
+
+extern PROCESSINFO NEARDATA pinfoCache; // declare per-process data cache
+#if OE_WIN16 || _X86_
+extern WORD NEARDATA uProcessID;
+#else
+extern DWORD NEARDATA uProcessID;
+#endif
+
+#if OE_MAC68K
+static const DWORD *pCurrentA5 = (DWORD *)(0x904);
+__inline DWORD GetPID() {return *pCurrentA5;}
+#elif OE_WIN16
+__inline WORD GetPID() {WORD tid; return (_segment)&tid;}
+#elif _X86_
+__inline WORD GetPID() {WORD tid; _asm {mov tid,ss} return tid;}
+#else
+__inline DWORD GetPID() {return 1;}
+#endif
+
+CProcessInfo FAR * GetProcessInfo();
+
+#if _X86_
+CProcessInfo FAR * GetProcessInfoCache();
+#else //_X86_
+#define GetProcessInfoCache GetProcessInfo
+#endif //_X86_
+
+__inline HRESULT GetMalloc(IMalloc FAR** ppmalloc)
+{
+ if ( GetPID() != uProcessID )
+ if (GetProcessInfoCache() == NULL)
+ return RESULT(E_FAIL);
+ *ppmalloc = pinfoCache.pmalloc;
+ return NOERROR;
+}
+
+#ifdef __cplusplus
+}
+#endif
+#elif !OE_WIN32 // !NO_PROCESS_CACHE
+// process cache is turned off for network automation
+HRESULT GetMalloc(IMalloc FAR** ppMalloc);
+#endif //NO_PROCESS_CACHE
+
+
+// private NLS wrapper functions (for WIN32)
+
+#if OE_WIN32
+
+// functions defined in ANSI wrapper helper modules
+#define FASTCALL __fastcall
+HRESULT FASTCALL ConvertStringToW(LPCSTR, LPOLESTR *);
+HRESULT FASTCALL ConvertStringToA(LPCOLESTR, LPSTR *);
+
+
+#ifdef _X86_ // only for Chicago-compatibility
+ // nuke the A/W versions if they exist
+ #undef CompareString
+ #undef LCMapString
+ #undef GetLocaleInfo
+ #undef IsCharAlpha
+ #undef IsCharAlphaNumeric
+ #undef GetStringTypeEx
+
+// real helpers that either call the Wide version or xlat & call the Ansi
+EXTERN_C INTERNAL_(int)
+CompareString(LCID lcid, DWORD dwFlags,
+ LPWSTR lpwStr1, int cch1,
+ LPWSTR lpwStr2, int cch2);
+
+EXTERN_C INTERNAL_(int)
+LCMapString(LCID, unsigned long, const WCHAR FAR*, int, WCHAR FAR*, int);
+
+EXTERN_C INTERNAL_(int)
+GetLocaleInfo(LCID, LCTYPE, WCHAR FAR*, int);
+
+EXTERN_C INTERNAL_(int)
+IsCharAlpha(WCHAR ch);
+
+EXTERN_C INTERNAL_(int)
+IsCharAlphaNumeric(WCHAR ch);
+EXTERN_C INTERNAL_(int) GetStringTypeEx(
+ LCID Locale,
+ DWORD dwInfoType,
+ LPCWSTR lpSrcStr,
+ int cchSrc,
+ LPWORD lpCharType);
+#define GETSTRINGTYPE GetStringTypeEx
+
+#else //_X86_
+#define GETSTRINGTYPE GetStringTypeEx
+#endif //_X86_
+
+#endif //OE_WIN32
+
+#if OE_WIN16
+// private function in ole2nls.dll for use by ole2disp.dll.
+NLSAPI_(int) EXPORT
+RegisterNLSInfoChanged(FARPROC lpfnNotifyProc);
+
+// callback function in ole2disp.dll, called by ole2nls.dll when WIN.INI changes
+EXTERN_C void CALLBACK NLSInfoChangedHandler(void);
+#endif //OE_WIN16
+
+
+// debugging functions
+#ifdef _DEBUG /* { */
+
+INTERNAL_(int) FIsBadReadPtr(const void FAR* pv, unsigned int cb);
+INTERNAL_(int) FIsBadWritePtr(void FAR* pv, unsigned int cb);
+INTERNAL_(int) FIsBadCodePtr(void FAR* pv);
+INTERNAL_(int) FIsBadStringPtr(OLECHAR FAR* psz, unsigned int cchMax);
+INTERNAL_(int) FIsBadInterface(void FAR* pv, unsigned int cMethods);
+
+INTERNAL_(int) IsBadDispParams(DISPPARAMS FAR* pdispparams);
+INTERNAL_(int) IsBadReadSA(SAFEARRAY FAR* psa);
+INTERNAL_(int) IsBadWriteSA(SAFEARRAY FAR* psa);
+
+#if OE_MAC /* { */
+// We supply the following APIs, which arent available on the MAC.
+EXTERN_C INTERNAL_(int) IsBadReadPtr(const void FAR* lp, unsigned int cb);
+EXTERN_C INTERNAL_(int) IsBadWritePtr(void FAR* lp, unsigned int cb);
+EXTERN_C INTERNAL_(int) IsBadStringPtr(const OLECHAR FAR* lpsz, unsigned int cchMax);
+#endif /* } */
+
+HRESULT __inline
+ValidateReadPtr(const void FAR* pv, unsigned int cb)
+{ return FIsBadReadPtr(pv, cb) ? RESULT(E_INVALIDARG) : NOERROR; }
+
+HRESULT __inline
+ValidateWritePtr(void FAR* pv, unsigned int cb)
+{ return FIsBadWritePtr(pv, cb) ? RESULT(E_INVALIDARG) : NOERROR; }
+
+HRESULT __inline
+ValidateCodePtr(void FAR* pv)
+{ return FIsBadCodePtr(pv) ? RESULT(E_INVALIDARG) : NOERROR; }
+
+HRESULT __inline
+ValidateStringPtr(OLECHAR FAR* pv, unsigned int cchMax)
+{ return FIsBadStringPtr(pv, cchMax) ? RESULT(E_INVALIDARG) : NOERROR; }
+
+HRESULT __inline
+ValidateInterface(void FAR* pv, unsigned int cMethods)
+{ return FIsBadInterface(pv, cMethods) ? RESULT(E_INVALIDARG) : NOERROR; }
+
+#endif /* } _DEBUG */
+#endif /* } _OLEDISP_H_ */
diff --git a/private/oleauto/src/dispatch/oleguids.c b/private/oleauto/src/dispatch/oleguids.c
new file mode 100644
index 000000000..f90212e84
--- /dev/null
+++ b/private/oleauto/src/dispatch/oleguids.c
@@ -0,0 +1,27 @@
+/***
+*oleguids.c
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file allocates (via Ole macro mania) the Ole GUIDS that are
+* referenced by the OLEDISP dll.
+*
+*Revision History:
+*
+* [00] 21-Jan-93 bradlo: Created.
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+// this redefines the Ole DEFINE_GUID() macro to do allocation.
+//
+#include <initguid.h>
+
+// due to the previous header, including this causes our DEFINE_GUID
+// definitions in the following headers to actually allocate data.
+
+// instantiate the ole2 guids that we use
+#include "oleguids.h"
diff --git a/private/oleauto/src/dispatch/oleguids.h b/private/oleauto/src/dispatch/oleguids.h
new file mode 100644
index 000000000..f4a73b321
--- /dev/null
+++ b/private/oleauto/src/dispatch/oleguids.h
@@ -0,0 +1,71 @@
+/***
+*oleguids.h
+*
+* Copyright (C) 1993, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file is a subset of the Ole2 guid header: coguid.h.
+*
+* This file is used to instantiate the data for the Ole2 IIDs that
+* are used in OLEDISP.DLL, rather than linking with the Ole2 implib,
+* which causes us to pull in way more IID and CLSID definitions than
+* we want.
+*
+* NOTE: the GUIDs below must be *exactly* the same as those assigned
+* by the Ole group - If the Ole group ever changes their numbers, we
+* must change accordingly.
+*
+*Revision History:
+*
+* [00] 19-Jan-93 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+
+DEFINE_GUID(GUID_NULL, 0L, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0);
+
+DEFINE_OLEGUID(IID_IUnknown, 0x00000000L, 0, 0);
+//DEFINE_OLEGUID(IID_IClassFactory, 0x00000001L, 0, 0);
+//DEFINE_OLEGUID(IID_IMalloc, 0x00000002L, 0, 0);
+//DEFINE_OLEGUID(IID_IMarshal, 0x00000003L, 0, 0);
+
+/* RPC related interfaces */
+//DEFINE_OLEGUID(IID_IRpcChannel, 0x00000004L, 0, 0);
+DEFINE_OLEGUID(IID_IRpcStub, 0x00000005L, 0, 0);
+//DEFINE_OLEGUID(IID_IStubManager, 0x00000006L, 0, 0);
+DEFINE_OLEGUID(IID_IRpcProxy, 0x00000007L, 0, 0);
+//DEFINE_OLEGUID(IID_IProxyManager, 0x00000008L, 0, 0);
+DEFINE_OLEGUID(IID_IPSFactory, 0x00000009L, 0, 0);
+
+DEFINE_GUID(IID_IPSFactoryBuffer,
+ 0xD5F569D0, 0x593B, 0x101A,
+ 0xB5,0x69,0x08,0x00,0x2B,0x2D,0xBF,0x7A);
+
+DEFINE_GUID(IID_IRpcProxyBuffer,
+ 0xD5F56A34,0x593B,0x101A,
+ 0xB5,0x69,0x08,0x00,0x2B,0x2D,0xBF,0x7A);
+
+DEFINE_GUID(IID_IRpcStubBuffer,
+ 0xD5F56AFC,0x593B,0x101A,
+ 0xB5,0x69,0x08,0x00,0x2B,0x2D,0xBF,0x7A);
+
+DEFINE_GUID(IID_IRpcChannelBuffer,
+ 0xD5F56B60,0x593B,0x101A,
+ 0xB5,0x69,0x08,0x00,0x2B,0x2D,0xBF,0x7A);
+
+
+/* storage related interfaces */
+//DEFINE_OLEGUID(IID_ILockBytes, 0x0000000aL, 0, 0);
+//DEFINE_OLEGUID(IID_IStorage, 0x0000000bL, 0, 0);
+DEFINE_OLEGUID(IID_IStream, 0x0000000cL, 0, 0);
+//DEFINE_OLEGUID(IID_IEnumSTATSTG, 0x0000000dL, 0, 0);
+
+/* moniker related interfaces */
+//DEFINE_OLEGUID(IID_IBindCtx, 0x0000000eL, 0, 0);
+//DEFINE_OLEGUID(IID_IMoniker, 0x0000000fL, 0, 0);
+//DEFINE_OLEGUID(IID_IRunningObjectTable, 0x00000010L, 0, 0);
+//DEFINE_OLEGUID(IID_IInternalMoniker, 0x00000011L, 0, 0);
+
diff --git a/private/oleauto/src/dispatch/olenames.h b/private/oleauto/src/dispatch/olenames.h
new file mode 100644
index 000000000..806384d6c
--- /dev/null
+++ b/private/oleauto/src/dispatch/olenames.h
@@ -0,0 +1,100 @@
+/*==========================================================================*
+ | olenames.h - redefinition of OLE function names for DLL entry points
+ |
+ | Purpose:
+ |
+ |
+ | Revision History:
+ |
+ |---------------------------------------------------------------------------
+ | Implementation Notes:
+ |
+ | The actual macros are generated via AWK from the OLE def files.
+ |
+ *==========================================================================*
+ | Copyright: (c) 1992, 1993 Microsoft Corporation, all rights reserved.
+ | Information Contained Herin is Proprietary and Confidential.
+ *==========================================================================*/
+
+
+
+#if !OE_MAC
+#error !This file is intended for Macintosh only
+#endif
+
+//==============================================================================
+//
+// MAC PPC Definitions
+//
+//==============================================================================
+#if OE_MACPPC
+#define ID_OLE_STAT_DOCFILE 0
+#define ID_OLE_STAT_USER 0
+#define ID_OLE_STAT_OLE2DISP 0
+#define ID_OLE_STAT_TYPELIB 0
+#define ID_OLE_STAT_DEF 0
+#define ID_OLE_STAT_COMPOBJ 0
+#define ID_OLE_STAT_PROXY 0
+#define ID_OLE_STAT_OLE2NLS 0
+
+#define ID_MUNGE_DLL_NAMES 0
+#define ID_MUNGE_STAT_NAMES 1
+
+#else // OE_MACPPC
+
+#if defined( OLENAMES_MUNGE_FOR_STATIC )
+
+#define ID_OLE_STAT_DOCFILE 1
+#define ID_OLE_STAT_USER 1
+#define ID_OLE_STAT_OLE2DISP 1
+#define ID_OLE_STAT_TYPELIB 1
+#define ID_OLE_STAT_DEF 1
+#define ID_OLE_STAT_COMPOBJ 1
+#define ID_OLE_STAT_PROXY 0
+#define ID_OLE_STAT_OLE2NLS 1
+
+#define ID_MUNGE_DLL_NAMES 0
+#define ID_MUNGE_STAT_NAMES 1
+
+#endif // OLENAMES_MUNGE_FOR_STATIC
+
+#if defined( OLENAMES_MUNGE_FOR_DLL ) // No DLL munging at this time,
+ // keep the functionality just in
+ // case we need it later!
+
+#define ID_OLE_STAT_DOCFILE 0
+#define ID_OLE_STAT_USER 0
+#define ID_OLE_STAT_OLE2DISP 0
+#define ID_OLE_STAT_TYPELIB 0
+#define ID_OLE_STAT_DEF 0
+#define ID_OLE_STAT_COMPOBJ 0
+#define ID_OLE_STAT_PROXY 0
+#define ID_OLE_STAT_OLE2NLS 0
+
+#define ID_MUNGE_DLL_NAMES 0
+#define ID_MUNGE_STAT_NAMES 0
+
+#endif // OLENAMES_MUNGE_FOR_DLL
+
+#endif// OE_MACPPC
+
+#include "namemacs.h"
+
+#if OE_MAC68K
+
+#undef ID_OLE_STAT_DOCFILE
+#undef ID_OLE_STAT_USER
+#undef ID_OLE_STAT_OLE2DISP
+#undef ID_OLE_STAT_TYPELIB
+#undef ID_OLE_STAT_DEF
+#undef ID_OLE_STAT_COMPOBJ
+#undef ID_OLE_STAT_PROXY
+#undef ID_OLE_STAT_OLE2NLS
+#undef ID_MUNGE_STAT_NAMES
+#undef ID_MUNGE_DLL_NAMES
+
+#undef OLENAMES_MUNGE_FOR_STATIC
+#undef OLENAMES_MUNGE_FOR_DLL
+
+#endif // OE_MAC68K
+
diff --git a/private/oleauto/src/dispatch/psfactry.cpp b/private/oleauto/src/dispatch/psfactry.cpp
new file mode 100644
index 000000000..94cb2d35f
--- /dev/null
+++ b/private/oleauto/src/dispatch/psfactry.cpp
@@ -0,0 +1,434 @@
+/***
+*psfactry.cpp - Implementation of the Ole programmability Proxy/Stub factory.
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file implements the Ole Programmability Proxy/Stub Factory
+* class. Ole binds to an instance of this object when a client does
+* a QueryInterface to IID_IDispatch, and calls methods on the IPSFactory
+* interface to create instances of the IDispatch Proxy and Stub objects.
+* (more or less).
+*
+*Revision History:
+*
+* [00] 18-Sep-92 bradlo: Created.
+* [01] 06-Dec-92 bradlo: Added support for IEnumVARIANT
+* [02] 06-Mar-93 bradlo: Added support for ITypeInfo
+* [03] 28-May-93 tomteng: Added Unicode support
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+ASSERTDATA
+
+#ifndef WIN32
+#include <cobjps.h>
+#endif //!WIN32
+
+#include "clsid.h"
+#include "dispmrsh.h"
+#include "dispps.h"
+#include "evps.h"
+#include "tips.h"
+#include "tlps.h"
+#include "tcps.h"
+#include "ups.h"
+#include "psfactry.h"
+
+#if OE_WIN16
+# include <shellapi.h>
+#endif
+
+HRESULT ProxyStubCLSIDOfInterface(REFIID riid, CLSID FAR* pclsid);
+
+#if OE_WIN32
+// use the one from the wrappers
+STDAPI_(int) StringFromGUID2A(REFGUID rguid, char FAR* lpsz, int cbMax);
+#else //OE_WIN32
+#define StringFromGUID2A StringFromGUID2
+#endif
+
+IPSFACTORY FAR*
+COleAutomationPSFactory::Create()
+{
+ COleAutomationPSFactory FAR* ppsf;
+
+ if((ppsf = new FAR COleAutomationPSFactory()) != NULL)
+ ppsf->AddRef();
+
+ return ppsf;
+}
+
+
+//---------------------------------------------------------------------
+// IUnknown Methods
+//---------------------------------------------------------------------
+
+
+STDMETHODIMP
+COleAutomationPSFactory::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ if(IsEqualIID(riid, IID_IUnknown)){
+ *ppv = this;
+ }else if(IsEqualIID(riid, IID_IPSFACTORY)){
+ *ppv = this;
+ }else{
+ *ppv = NULL;
+ return RESULT(E_NOINTERFACE);
+ }
+ ++m_refs;
+ return NOERROR;
+}
+
+
+STDMETHODIMP_(unsigned long)
+COleAutomationPSFactory::AddRef()
+{
+ return ++m_refs;
+}
+
+
+STDMETHODIMP_(unsigned long)
+COleAutomationPSFactory::Release()
+{
+ if(--m_refs == 0){
+ delete this;
+ return 0;
+ }
+ return m_refs;
+}
+
+
+//---------------------------------------------------------------------
+// IPSFactory Methods
+//---------------------------------------------------------------------
+
+
+STDMETHODIMP
+COleAutomationPSFactory::CreateProxy(
+ IUnknown FAR* punkOuter,
+ REFIID riid,
+ IPROXY FAR* FAR* ppproxy,
+ void FAR* FAR* ppv)
+{
+ HRESULT hresult;
+ IPROXY FAR* pproxy;
+ IUnknown FAR* punk;
+
+ *ppv = NULL;
+ *ppproxy = NULL;
+
+ if(IsEqualIID(riid, IID_IDispatch)){
+
+ punk = CProxDisp::Create(punkOuter, riid);
+
+ }else if(IsEqualIID(riid, IID_IEnumVARIANT)){
+
+ punk = CProxEnumVARIANT::Create(punkOuter);
+
+ }else if(IsEqualIID(riid, IID_ITypeInfo)){
+
+ punk = CProxTypeInfo::Create(punkOuter);
+
+ }else if(IsEqualIID(riid, IID_ITypeLib)){
+
+ punk = CProxTypeLib::Create(punkOuter);
+
+ }else if(IsEqualIID(riid, IID_ITypeComp)){
+
+ punk = CProxTypeComp::Create(punkOuter);
+
+ }else{
+
+ CLSID clsid;
+
+ IfFailRet(ProxyStubCLSIDOfInterface(riid, &clsid));
+
+ if(clsid == CLSID_PSDispatch){
+ punk = CProxDisp::Create(punkOuter, riid);
+ }
+ else
+ if(clsid == CLSID_PSAutomation){
+ IfFailRet(CProxUniv::Create(punkOuter, riid, &punk));
+ }
+ else{
+ return RESULT(E_FAIL);
+ }
+
+ }
+
+ if(punk == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LExit;
+ }
+
+ IfFailGo(
+ punk->QueryInterface(IID_IPROXY, (void FAR* FAR*)&pproxy),
+ LReleaseUnk);
+
+ IfFailGo(punk->QueryInterface(riid, ppv), LReleaseProxy);
+
+
+// Disable for now until OLE32.dll actual incorporate change
+#if defined(WIN32) && 0
+ // This code only applies to Daytona Beta1 (for backward compatibility)
+ // RemoteHandler will addref again, so release here...
+
+ DWORD dwBuildVersion;
+
+ dwBuildVersion = OleBuildVersion();
+ if ((HIWORD(dwBuildVersion) <= 23) && (LOWORD(dwBuildVersion) <= 772))
+ ((IUnknown FAR*) *ppv)->Release();
+#endif
+
+#if 0
+ ((IUnknown FAR*) *ppv)->Release();
+#endif
+
+ punk->Release();
+
+ *ppproxy = pproxy;
+
+ return NOERROR;
+
+LReleaseProxy:;
+ pproxy->Release();
+
+LReleaseUnk:;
+ punk->Release();
+
+LExit:;
+ return hresult;
+}
+
+
+STDMETHODIMP
+COleAutomationPSFactory::CreateStub(
+ REFIID riid,
+ IUnknown FAR* punkServer,
+ ISTUB FAR* FAR* ppstub)
+{
+ ISTUB FAR* pstub;
+ HRESULT hresult;
+
+ *ppstub = NULL;
+
+
+// Cario's CRemoteHdlr::CreateInterfaceStub implementation calls this
+// method with punkServer = NULL. Need to defer punkServer object assignment
+// until a Connect method is called on the stub.
+
+ if(punkServer != NULL) {
+
+ // Make sure that the requested riid is actually supported
+ // by the real server object.
+ //
+ IUnknown FAR* punkRequested;
+ IfFailRet(punkServer->QueryInterface(riid, (void FAR* FAR*)&punkRequested));
+ punkRequested->Release();
+ }
+
+ if(IsEqualIID(riid, IID_IDispatch)){
+
+ hresult = CStubDisp::Create(punkServer,
+#if (defined(WIN32) || defined(WOW))
+ riid,
+#endif
+ &pstub);
+
+ }else if(IsEqualIID(riid, IID_IEnumVARIANT)){
+
+ hresult = CStubEnumVARIANT::Create(punkServer, &pstub);
+
+ }else if(IsEqualIID(riid, IID_ITypeInfo)){
+
+ hresult = CStubTypeInfo::Create(punkServer, &pstub);
+
+ }else if(IsEqualIID(riid, IID_ITypeLib)){
+
+ hresult = CStubTypeLib::Create(punkServer, &pstub);
+
+ }else if(IsEqualIID(riid, IID_ITypeComp)){
+
+ hresult = CStubTypeComp::Create(punkServer, &pstub);
+
+ }else{
+
+ CLSID clsid;
+
+ IfFailRet(ProxyStubCLSIDOfInterface(riid, &clsid));
+
+ if(clsid == CLSID_PSDispatch){
+ hresult = CStubDisp::Create(punkServer,
+#if (defined(WIN32) || defined(WOW))
+ riid,
+#endif
+ &pstub);
+ }
+ else
+ if(clsid == CLSID_PSAutomation){
+ hresult = CStubUniv::Create(punkServer, riid, &pstub);
+ }
+ else{
+ hresult = RESULT(E_FAIL);
+ }
+ }
+
+ if(hresult != NOERROR)
+ return hresult;
+
+ *ppstub = pstub;
+
+ return NOERROR;
+}
+
+
+//---------------------------------------------------------------------
+// PSFactory API
+//---------------------------------------------------------------------
+
+// Is the given CLSID one that we know how to make a class factory for?
+
+#if OE_MAC68K
+// This is called by the OLE APPLET's DllGetClassObject to determine if
+// this is one of OLE Automation's CLSID's
+STDAPI_(int)
+#else
+int
+#endif
+IsAutomationCLSID(REFCLSID rclsid)
+{
+ // UNDONE: could speed this up since the guids are contiguious
+ if(IsEqualCLSID(rclsid, CLSID_PSDispatch))
+ return 1;
+ if(IsEqualCLSID(rclsid, CLSID_PSTypeInfo))
+ return 1;
+ if(IsEqualCLSID(rclsid, CLSID_PSTypeLib))
+ return 1;
+ if(IsEqualCLSID(rclsid, CLSID_PSTypeComp))
+ return 1;
+ if(IsEqualCLSID(rclsid, CLSID_PSAutomation))
+ return 1;
+ if(IsEqualCLSID(rclsid, CLSID_PSEnumVARIANT))
+ return 1;
+ return 0;
+}
+
+
+// network automation replaces this routine (netprxcf.cpp)
+#if !defined(NETDISP)
+/***
+*PUBLIC HRESULT DllGetClassObject(REFCLSID, REFIID, void**)
+*Purpose:
+* Return the Class Object for the given CLSID.
+*
+*Entry:
+* rclsid = class id
+* riid = interface id
+*
+*Exit:
+* return value = HRESULT
+*
+* *ppv = the class object for the given CLSID
+*
+***********************************************************************/
+STDAPI
+#if OE_MAC68K
+// This is called by the OLE APPLET's DllGetClassObject for our CLSID's
+AutomationDllGetClassObject(REFCLSID rclsid, REFIID riid, void FAR* FAR* ppv)
+#else
+DllGetClassObject(REFCLSID rclsid, REFIID riid, void FAR* FAR* ppv)
+#endif
+{
+
+#if OE_MAC68K
+ ASSERT(IsAutomationCLSID(rclsid));
+#else
+ *ppv = NULL;
+
+ if(!IsAutomationCLSID(rclsid))
+ return RESULT(E_UNEXPECTED);
+#endif
+
+ if((*ppv = (void FAR*) COleAutomationPSFactory::Create()) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+ return NOERROR;
+}
+#endif // !NETDISP
+
+
+/***
+* PUBLIC int IsValidDispInterface(REFIID)
+* Purpose:
+* Validate that the riid is a legal dispinterface.
+*
+* The registry database will have the following entries for dispinterface:
+* \Interface\{<iid of dispinterface>}= <dispinterface textual info>
+* \ProxyStubClsid={00020420-0000-0000-C000-000000000046}
+*
+* This routine queries the registry database using the riid passed in for
+* the above information. It return 0 if it fails and 1 if successful.
+***********************************************************************/
+
+// We want to use the ANSI Registry API here, so it's best if this function is
+// just pure ansi.
+// CONSIDER: use UNICODE registry api for UNICODE (RISC) builds?
+#ifdef UNICODE
+#undef UNICODE
+
+#undef STRCPY
+#define STRCPY strcpy
+#undef STRCAT
+#define STRCAT strcat
+#undef STRICMP
+#define STRICMP stricmp
+#undef RegQueryValue
+#define RegQueryValue RegQueryValueA
+
+#endif //UNICODE
+
+HRESULT
+ProxyStubCLSIDOfInterface(REFIID riid, CLSID FAR* pclsid)
+{
+ long cb;
+ char szKey[128], szValue[CCH_SZGUID0];
+static char szPSDispatch[] = "{00020420-0000-0000-C000-000000000046}";
+static char szPSAutomation[] = "{00020424-0000-0000-C000-000000000046}";
+
+ // Construct ProxyStubClsid key for dispinterface
+ STRCPY_A(szKey, "Interface\\");
+ StringFromGUID2A(riid, szKey+sizeof("Interface\\")-1, 40);
+#if OE_WIN32
+ STRCAT_A(szKey, "\\ProxyStubClsid32");
+#else
+ STRCAT_A(szKey, "\\ProxyStubClsid");
+#endif
+
+ // Check if valid dispinterface
+ cb = DIM(szValue);
+ if(RegQueryValue(HKEY_CLASSES_ROOT, szKey, szValue, &cb) != ERROR_SUCCESS)
+ return RESULT(REGDB_E_IIDNOTREG);
+
+ if(!STRICMP_A(szValue, szPSDispatch)){
+ *pclsid = CLSID_PSDispatch;
+ return NOERROR;
+ }
+
+ if(!STRICMP_A(szValue, szPSAutomation)){
+ *pclsid = CLSID_PSAutomation;
+ return NOERROR;
+ }
+
+ // No match
+ return RESULT(E_FAIL);
+}
+
+// WARNING: UNICODE is now turned OFF
+
+
+
diff --git a/private/oleauto/src/dispatch/psfactry.h b/private/oleauto/src/dispatch/psfactry.h
new file mode 100644
index 000000000..5c4dccf95
--- /dev/null
+++ b/private/oleauto/src/dispatch/psfactry.h
@@ -0,0 +1,52 @@
+/***
+*psfactry.h
+*
+* Copyright (C) 1994, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Definition of automation proxy/stub factory.
+*
+*Revision History:
+*
+* [00] 06-Sep-94 erikc: Added header.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+#ifndef _PSFACTRY_H_
+#define _PSFACTRY_H_
+
+class FAR COleAutomationPSFactory : public IPSFACTORY
+{
+public:
+ static IPSFACTORY FAR* Create(void);
+
+ // IUnknown Methods
+ //
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ // IPSFactory Methods
+ //
+ STDMETHOD(CreateProxy)(
+ IUnknown FAR* punkOuter,
+ REFIID riid,
+ IPROXY FAR* FAR* ppproxy,
+ void FAR* FAR* ppv);
+
+ STDMETHOD(CreateStub)(
+ REFIID riid, IUnknown FAR* punkServer, ISTUB FAR* FAR* ppstub);
+
+ COleAutomationPSFactory(){
+ m_refs = 0;
+ }
+
+private:
+
+ unsigned long m_refs;
+};
+
+#endif // _PSFACTRY_H_
+
diff --git a/private/oleauto/src/dispatch/sarray.cpp b/private/oleauto/src/dispatch/sarray.cpp
new file mode 100644
index 000000000..75b8997da
--- /dev/null
+++ b/private/oleauto/src/dispatch/sarray.cpp
@@ -0,0 +1,1713 @@
+/***
+sarray.cpp - SafeArray Runtime
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file implements the SafeArray runtime support for the Ole
+* programmability component.
+*
+*Revision History:
+*
+* [00] 27-Oct-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+* The bounds are indexed from 0, however the dimentions are
+* indexed from 1. ie, the first dimention is 1.
+*
+* The bounds are stored in the rgsabound array 'backwards', from N to 0.
+* (the bounds for array index N are at index 0 in the rgsabound array,
+* and so on). This was done to optimize array address computation.
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#if OE_WIN32
+#include "oautil.h"
+#endif // OE_WIN32
+
+#include <limits.h>
+
+#ifdef _MAC
+ #define PHDATA ((void *) psa->handle)
+ #define PVDATA *(psa->handle)
+ #define HANDLELOCK HLock(psa->handle); psa->pvData = *(psa->handle)
+ #define HANDLEUNLOCK HUnlock(psa->handle)
+#else
+ #define PHDATA psa->pvData
+ #define PVDATA psa->pvData
+ #define HANDLELOCK
+ #define HANDLEUNLOCK
+#endif
+
+#define SAFEARRAYOVERFLOW 0xffffffff
+
+ASSERTDATA
+
+
+// network automation does not need these routines
+#if !defined(NETDISP)
+#ifdef WIN16 // {
+
+
+// hSizeToAlloc & hAccessElement (from satishc) supports Win16 huge
+// arrays. Logic supports SafeArrays that can be allocated with
+// all elements up to 65535. Also support huge array that does not
+// neccessarily have to begin at a segment boundary. For example, EXCEL
+// put in a 6-byte data field before the beginning of the data array
+// (data array starts at SEMENT:0006).
+//
+
+INTERNAL_(unsigned long)
+hSizeToAlloc(LPSAFEARRAY psa, unsigned long iActual)
+{
+ unsigned long iSegPad = 65536 % psa->cbElements; // pad per segment.
+ unsigned long cSeg = iActual / (65536 - iSegPad); // number of segment
+ // needed for the array
+
+ // Since we are adding an extra element to take care of possible
+ // misalignment in the first segment, we can reduce the per segmemnt
+ // pad count by 1.
+ return (iActual + iSegPad*cSeg + psa->cbElements);
+}
+
+
+INTERNAL_(void HUGEP*)
+hAccessElement(
+ LPSAFEARRAY psa,
+ unsigned long lIndex
+)
+{
+ unsigned long cbFirst = (unsigned long) (65536 - LOWORD(psa->pvData));
+ unsigned long cElemFirst = cbFirst / psa->cbElements;
+ void HUGEP* pdata;
+ unsigned long offset;
+
+ if (cElemFirst > lIndex)
+ pdata = (void HUGEP*) ((BYTE HUGEP*) psa->pvData +
+ (lIndex * psa->cbElements));
+ else {
+ unsigned long cElemSeg = (unsigned long) (65536 / psa->cbElements);
+ unsigned long cbSeg;
+ lIndex -= cElemFirst;
+ cbSeg = (unsigned long) (lIndex / cElemSeg);
+ offset = (lIndex % cElemSeg) * psa->cbElements;
+ pdata = (void HUGEP*) ((BYTE HUGEP*) psa->pvData +
+ cbFirst +
+ (cbSeg * 65536) +
+ offset);
+
+ }
+ return pdata;
+}
+
+INTERNAL_(void HUGEP*)
+hAccessElement(
+ void HUGEP* pvData,
+ unsigned short cbElements,
+ unsigned long lIndex
+)
+{
+ unsigned long cbFirst = (unsigned long) (65536 - LOWORD(pvData));
+ unsigned long cElemFirst = cbFirst / cbElements;
+ void HUGEP* pdata;
+ unsigned long offset;
+
+ if (cElemFirst > lIndex)
+ pdata = (void HUGEP*) ((BYTE HUGEP*) pvData +
+ (lIndex * cbElements));
+ else {
+ unsigned long cElemSeg = (unsigned long) (65536 / cbElements);
+ unsigned long cbSeg;
+ lIndex -= cElemFirst;
+ cbSeg = (unsigned long) (lIndex / cElemSeg);
+ offset = (lIndex % cElemSeg) * cbElements;
+ pdata = (void HUGEP*) ((BYTE HUGEP*) pvData +
+ cbFirst +
+ (cbSeg * 65536) +
+ offset);
+ }
+ return pdata;
+}
+
+INTERNAL_(void)
+hmemset(void HUGEP* pv, int val, unsigned long size)
+{
+ size_t cb;
+ char HUGEP* pdata;
+
+ pdata = (char HUGEP*)pv;
+
+ // compute the # of bytes to the end of the current segment.
+ cb = (size_t)((unsigned long)UINT_MAX + (unsigned long)1 - ((unsigned long)pdata&(unsigned long)UINT_MAX));
+
+ if(size <= cb){
+ // easy, the entire area fits within the current segment
+ MEMSET(pdata, val, (size_t)size);
+ return;
+ }
+
+ // clear out to the end of the current segment.
+ MEMSET(pdata, val, cb);
+ size -= cb;
+ pdata += cb;
+
+ // loop through the remaining segments
+ while(size > 0){
+ // we assume were at the beginning of a segment here...
+ ASSERT((unsigned short)pdata == 0);
+
+ if(size <= UINT_MAX){
+ MEMSET(pdata, val, (size_t)size);
+ break;
+ }
+
+ // otherwise, fill as much as we can with one call to memset
+
+ MEMSET(pdata, val, UINT_MAX);
+
+ // the following leaves us pointing @ the last byte of the segment.
+ pdata += UINT_MAX;
+ ASSERT((unsigned short)pdata == 0xffff);
+
+ // fill the last byte of the segment, and move on to the next segment.
+ *pdata++ = (char)val;
+
+ size -= ((unsigned long)UINT_MAX+1UL);
+ }
+}
+
+
+
+#define HMEMSET(DST, VAL, SIZE) hmemset(DST, VAL, SIZE)
+#define HMEMCPY(DST, SRC, SIZE) hmemcpy(DST, SRC, SIZE)
+
+#else // }{
+
+#define HMEMSET(DST, VAL, SIZE) MEMSET(DST, VAL, (size_t)SIZE)
+#define HMEMCPY(DST, SRC, SIZE) MEMCPY(DST, SRC, (size_t)SIZE)
+
+#endif // }
+
+
+/***
+*PRIVATE SAFEARRAY* SafeArrayAllocDescriptor(unsigned int, SAFEARRAY**)
+*Purpose:
+* Allocate a SafeArray descriptor for an array with the given number
+* of dimentions.
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDAPI
+SafeArrayAllocDescriptor(unsigned int cDims, SAFEARRAY FAR* FAR* ppsaOut)
+{
+ int cb;
+ SAFEARRAY FAR* psa;
+
+#ifdef _DEBUG
+ if(cDims == 0)
+ return RESULT(E_INVALIDARG);
+#endif
+
+ cb = sizeof(SAFEARRAY) + (((int)cDims - 1) * sizeof(SAFEARRAYBOUND));
+
+ if((psa = (SAFEARRAY FAR*)new FAR unsigned char[cb]) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+
+ MEMSET(psa, 0, cb);
+
+ psa->cDims = cDims;
+
+ *ppsaOut = psa;
+
+ return NOERROR;
+}
+
+
+STDAPI
+SafeArrayAllocData(SAFEARRAY FAR* psa)
+{
+ unsigned long cbSize;
+
+ if(psa == NULL)
+ return RESULT(E_INVALIDARG);
+
+#ifdef _DEBUG
+ if(IsBadWriteSA(psa))
+ return RESULT(E_INVALIDARG);
+#endif
+
+#ifdef WIN16
+ unsigned long cbActual = SafeArraySize(psa);
+ if (cbActual == SAFEARRAYOVERFLOW) {
+ return RESULT(E_OUTOFMEMORY);
+ }
+ cbSize = hSizeToAlloc(psa, cbActual);
+ if (cbSize < cbActual) // error if adding padding overflowed us
+ return RESULT(E_OUTOFMEMORY);
+#else
+ cbSize = SafeArraySize(psa);
+ if (cbSize == SAFEARRAYOVERFLOW) {
+ return RESULT(E_OUTOFMEMORY);
+ }
+#endif
+
+#ifdef _MAC
+ psa->pvData = NULL;
+ if ((psa->handle = NewHandle(cbSize)) == 0)
+ return RESULT(E_OUTOFMEMORY);
+
+ // zero out the allocated data
+ HLock(psa->handle);
+ HMEMSET(*(psa->handle), 0, cbSize);
+ HUnlock(psa->handle);
+
+ return NOERROR;
+#else
+ IMalloc FAR* pmalloc;
+
+ IfFailRet(GetMalloc(&pmalloc));
+
+ psa->pvData = pmalloc->Alloc(cbSize);
+
+ if(psa->pvData == NULL)
+ return RESULT(E_OUTOFMEMORY);
+
+ // REVIEW: temporary until we allocate in moveable memory
+ //IfMac(psa->handle = (Handle)&psa->pvData);
+
+ // zero out the allocated data
+
+ HMEMSET(psa->pvData, 0, cbSize);
+
+ return NOERROR;
+#endif
+}
+
+
+/***
+*PUBLIC SAFEARRAY* SafeArrayCreate(VARTYPE, unsigned int, SAFEARRAYBOUND*)
+*Purpose:
+* Create and return a SafeArray of the given VARTYPE, with the
+* given number of dimentions and with the given bounds.
+*
+*Entry:
+* vt = the VARTYPE of the array that is to be created
+* cDims = count of the number of dimentions of the array
+* rgbound = the array bounds
+*
+*Exit:
+* return value = SAFEARRAY*, NULL if unable to create.
+*
+***********************************************************************/
+STDAPI_(SAFEARRAY FAR*)
+SafeArrayCreate(VARTYPE vt, unsigned int cDims, SAFEARRAYBOUND FAR* rgsabound)
+{
+ unsigned int i;
+ HRESULT hresult;
+ SAFEARRAY FAR* psa;
+ unsigned short size, features;
+
+#ifdef _DEBUG
+ if(IsBadReadPtr(rgsabound, sizeof(SAFEARRAYBOUND) * cDims))
+ return NULL;
+#endif
+
+ // Check that safearraybound dimension elements are greater than zero
+ // (Oleprog#302)
+ for (i = 0; i < cDims; i++)
+ if (rgsabound[i].cElements < 1)
+ return NULL;
+
+ if(cDims == 0)
+ return NULL;
+
+ features = 0;
+
+ // Note: the types that are legal for arrays are slightly different
+ // than the types that can be held by a VARIANT or VARIANTARG.
+ //
+ switch(vt){
+
+#if VBA2
+ case VT_UI1:
+ size = sizeof(char);
+ break;
+#endif
+
+ case VT_I2:
+ case VT_BOOL:
+ size = sizeof(short);
+ break;
+
+ case VT_I4:
+ case VT_ERROR:
+ case VT_R4:
+ size = sizeof(long);
+ break;
+
+ case VT_R8:
+ case VT_CY:
+ case VT_DATE:
+ size = sizeof(double);
+ break;
+
+ case VT_BSTR:
+ features = FADF_BSTR;
+ size = sizeof(BSTR);
+ break;
+
+ case VT_VARIANT:
+ features = FADF_VARIANT;
+ size = sizeof(VARIANT);
+ break;
+
+ case VT_UNKNOWN:
+ features = FADF_UNKNOWN;
+ size = sizeof(IUnknown FAR*);
+ break;
+
+ case VT_DISPATCH:
+ features = FADF_DISPATCH;
+ size = sizeof(IDispatch FAR*);
+ break;
+
+ default:
+ return NULL;
+ }
+
+ IfFailGo(SafeArrayAllocDescriptor(cDims, &psa), LError0);
+
+ psa->cDims = cDims;
+ psa->cbElements = size;
+ psa->fFeatures = features;
+
+ // the bounds are stored in the array descriptor in reverse-textual
+ // order, but are passed to this routine in textual order - so reverse
+ // as we copy them into the array
+
+ for(i = 0; i < cDims; ++i){
+ psa->rgsabound[i] = rgsabound[cDims-i-1];
+ }
+
+ IfFailGo(SafeArrayAllocData(psa), LError1);
+
+ return psa;
+
+LError1:;
+ SafeArrayDestroy(psa);
+
+LError0:;
+ return NULL;
+}
+
+
+/***
+*PRIVATE void ReleaseResources(void*, unsigned long, unsigned short, unsigned short/long)
+*Purpose:
+* Release any resources held by the given chunk of memory.
+*
+*Entry:
+* pv = the chunk
+* cbSize = the size of the chunk in bytes
+* fFeatures = features bits describing the chunk
+* cbElement = the size of each element of the chunk
+*
+*Exit:
+* return value =
+*
+***********************************************************************/
+// release the resources held by the given chunk of memory
+INTERNAL_(void)
+ReleaseResources(
+ void HUGEP* pv,
+ unsigned long cbSize,
+ unsigned short fFeatures,
+#ifdef WIN32
+ unsigned long cbElement
+#else //WIN32
+ unsigned short cbElement
+#endif //WIN32
+)
+{
+ unsigned long i, cElements;
+
+ cElements = cbSize / cbElement;
+
+ if(fFeatures & FADF_BSTR){
+#ifdef WIN16
+ for(i = 0; i < cElements; ++i)
+ SysFreeString(*(BSTR HUGEP*) hAccessElement(pv, cbElement, i));
+#else
+ BSTR HUGEP* pbstr;
+
+ pbstr = (BSTR HUGEP*)pv;
+ for(i = 0; i < cElements; ++i)
+ SysFreeString(*pbstr++);
+#endif
+
+
+ }else if(fFeatures & FADF_UNKNOWN){
+
+ IUnknown FAR* HUGEP* ppunk;
+
+#ifdef WIN16
+ for(i = 0; i < cElements; ++i) {
+ ppunk = (IUnknown FAR* HUGEP*) hAccessElement(pv, cbElement, i);
+ if(*ppunk != NULL)
+ (*ppunk)->Release();
+ }
+#else
+ ppunk = (IUnknown FAR* HUGEP*)pv;
+ for(i = 0; i < cElements; ++i){
+ if(*ppunk != NULL)
+ (*ppunk)->Release();
+ ++ppunk;
+ }
+#endif
+
+ }else if(fFeatures & FADF_DISPATCH){
+
+ IDispatch FAR* HUGEP* ppdisp;
+
+#ifdef WIN16
+ for(i = 0; i < cElements; ++i) {
+ ppdisp = (IDispatch FAR* HUGEP*) hAccessElement(pv, cbElement, i);
+ if(*ppdisp != NULL)
+ (*ppdisp)->Release();
+ }
+#else
+ ppdisp = (IDispatch FAR* HUGEP*)pv;
+ for(i = 0; i < cElements; ++i){
+ if(*ppdisp != NULL)
+ (*ppdisp)->Release();
+ ++ppdisp;
+ }
+#endif
+
+
+ }else if(fFeatures & FADF_VARIANT){
+#ifdef WIN16
+ for(i = 0; i < cElements; ++i)
+ VariantClear((VARIANT HUGEP*) hAccessElement(pv, cbElement, i));
+#else
+ VARIANT HUGEP* pvar;
+
+ pvar = (VARIANT HUGEP*)pv;
+ for(i = 0; i < cElements; ++i)
+ VariantClear(pvar++);
+#endif
+
+ }
+}
+
+
+/***
+*PRIVATE HRESULT SafeArrayDestroyData(SAFEARRAY*)
+*Purpose:
+* Release the contents of the given SafeArray.
+*
+*Entry:
+* psa = pointer the the array descriptor of the array to erase
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDAPI
+SafeArrayDestroyData(SAFEARRAY FAR* psa)
+{
+ unsigned long cbSize;
+
+ if(psa == NULL)
+ return NOERROR;
+
+ if(psa->cLocks > 0)
+ return RESULT(DISP_E_ARRAYISLOCKED);
+
+ if(PHDATA == NULL)
+ return NOERROR;
+
+#ifdef _DEBUG
+ if(IsBadWriteSA(psa))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ HANDLELOCK;
+
+ cbSize = SafeArraySize(psa);
+ ASSERT(cbSize != SAFEARRAYOVERFLOW); // existing array, no overflow possible
+
+#if ID_DEBUG
+ // only check the pointer if it points to a non-zero sized allocation.
+ // In this case, the Chicago IMalloc returns a valid pointer, but
+ // IsBadWritePtr fails.
+ if (cbSize) {
+#ifdef _MAC
+ HANDLELOCK;
+ if(IsBadWritePtr(psa->pvData, 1)) {
+ HANDLEUNLOCK;
+ return RESULT(E_INVALIDARG);
+ }
+ HANDLEUNLOCK;
+#else
+ if(IsBadWritePtr(psa->pvData, 1))
+ return RESULT(E_INVALIDARG);
+#endif
+ }
+#endif //ID_DEBUG
+
+ ReleaseResources(
+ psa->pvData,
+ cbSize,
+ psa->fFeatures,
+ psa->cbElements);
+
+ if(psa->fFeatures & FADF_STATIC){
+#ifdef WIN16
+ if (psa->fFeatures & FADF_EMBEDDED)
+ // Assume embedded can't be huge. Only zero out actual
+ // amount used.
+ MEMSET(psa->pvData, 0, (UINT)cbSize);
+ else
+ HMEMSET(psa->pvData, 0, hSizeToAlloc(psa, cbSize));
+ // hSizeToAlloc can't overflow here (couldn't have created it)
+#else
+ HMEMSET(psa->pvData, 0, cbSize);
+#endif
+ }
+
+ if((psa->fFeatures & (FADF_AUTO|FADF_STATIC|FADF_EMBEDDED)) == 0 ||
+ (psa->fFeatures & FADF_FORCEFREE)){
+
+ // If none of the allocation attribute bits are set, then the
+ // array is dynamically allocated, and we need to free it.
+
+ HANDLEUNLOCK;
+
+#ifdef _MAC
+ DisposeHandle(psa->handle);
+ psa->handle = 0;
+ psa->pvData = 0;
+#else
+ IMalloc FAR* pmalloc;
+ IfFailRet(GetMalloc(&pmalloc));
+ pmalloc->Free(psa->pvData);
+ psa->pvData = NULL;
+#endif
+ }
+ return NOERROR;
+}
+
+/***
+*PUBLIC HRESULT SafeArrayDestroyDescriptor(SAFEARRAY*)
+*Purpose:
+* Free the given SafeArray descriptor.
+*
+*Entry:
+* psa - the SafeArray descriptor to release.
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDAPI
+SafeArrayDestroyDescriptor(SAFEARRAY FAR* psa)
+{
+ if(psa == NULL)
+ return NOERROR;
+
+#ifdef _DEBUG
+ if(IsBadWriteSA(psa))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ // cannot destroy an array that is still locked
+ if(psa->cLocks > 0)
+ return RESULT(DISP_E_ARRAYISLOCKED);
+
+ delete psa;
+
+ return NOERROR;
+}
+
+
+/***
+*PUBLIC HRESULT SafeArrayDestroy(SAFEARRAY*)
+*Purpose:
+* Free the given SafeArray.
+*
+*REVIEW: what happens if we destroy an array that is locked?
+*
+*Entry:
+* psa = the SafeArray descriptor of the array to free.
+*
+*Exit:
+* return value = HRESULT,
+* S_OK
+* E_INVALIDARG
+* DISP_E_ARRAYISLOCKED
+*
+***********************************************************************/
+STDAPI
+SafeArrayDestroy(SAFEARRAY FAR* psa)
+{
+ if(psa == NULL)
+ return NOERROR;
+#ifdef _DEBUG
+ if(IsBadWriteSA(psa))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ // cannot destroy an array that is still locked
+ if(psa->cLocks > 0)
+ return RESULT(DISP_E_ARRAYISLOCKED);
+
+ if(PHDATA != NULL){
+ IfFailRet(SafeArrayDestroyData(psa));
+ }
+
+ if(!(psa->fFeatures & (FADF_AUTO|FADF_STATIC|FADF_EMBEDDED)) ||
+ (psa->fFeatures & FADF_FORCEFREE))
+ delete psa;
+
+ return NOERROR;
+}
+
+
+/***
+*HRESULT SafeArrayRedim(SAFEARRAY*, SAFEARRAYBOUND**)
+*Purpose:
+* Realloc the given array, using the given SAFEARRAYBOUND as
+* the new bounds for the least significant dimention of the
+* given array (the textually rightmost dimention).
+*
+* Note: this routine only supports changing the size of the
+* last dimention!
+*
+* The routine preserves the contents of the given array, that
+* fall within the bounds of the new array. If the new array
+* is smaller, then any resources held by the old array that
+* do not fall in the new array are released. If the new
+* array is larger, then the newly allocated memory is zero
+* filled.
+*
+*
+*Entry:
+* psa = the SafeArray to re-allocate
+* psabounds = the new bounds for the least significant index
+* (textually rightmost index)
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDAPI
+SafeArrayRedim(
+ SAFEARRAY FAR* psa,
+ SAFEARRAYBOUND FAR* psaboundNew)
+{
+ HRESULT hresult;
+ void HUGEP* pvTmp;
+ void HUGEP* pvData;
+ long cbDelta;
+ unsigned long cbSizeNew, cbSizeOld;
+#ifdef WIN16
+ void HUGEP* pvDataEnd;
+ unsigned long cb, i, cbOldActual, cbNewActual, cOld, cNew, cDelta;
+#endif
+ SAFEARRAYBOUND saboundOld;
+
+ if(psa == NULL)
+ return RESULT(E_INVALIDARG);
+#ifdef _DEBUG
+ if(IsBadWriteSA(psa))
+ return RESULT(E_INVALIDARG);
+ if(IsBadReadPtr(psaboundNew, sizeof(*psaboundNew)))
+ return RESULT(E_INVALIDARG);
+ if(psa->cDims == 0)
+ return RESULT(E_INVALIDARG);
+#endif
+
+ if(psa->cLocks > 0 || psa->fFeatures & FADF_FIXEDSIZE)
+ return RESULT(DISP_E_ARRAYISLOCKED);
+
+ pvTmp = NULL;
+
+#ifdef _MAC
+ Handle oldHandle = NULL, tmpHandle, reallocHandle;
+ HLock(psa->handle);
+ psa->pvData = *(psa->handle);
+#else
+ IMalloc FAR* pmalloc;
+ pmalloc = NULL;
+ IfFailGo(GetMalloc(&pmalloc), LError0);
+#endif
+
+#ifdef WIN16
+ cbOldActual = SafeArraySize(psa);
+ ASSERT(cbOldActual != SAFEARRAYOVERFLOW); // existing array, no overflow possible
+ cbSizeOld = hSizeToAlloc(psa, cbOldActual);
+ // hSizeToAlloc can't overflow here (couldn't have created it)
+ cOld = cbOldActual/psa->cbElements;
+#else
+ cbSizeOld = SafeArraySize(psa);
+ ASSERT(cbSizeOld != SAFEARRAYOVERFLOW); // existing array, no overflow possible
+#endif
+
+ // save the old bounds so we can restore if the realloc fails
+ saboundOld = psa->rgsabound[0];
+ psa->rgsabound[0] = *psaboundNew;
+
+
+#ifdef WIN16
+ cbNewActual = SafeArraySize(psa);
+ if (cbNewActual == SAFEARRAYOVERFLOW) {
+ goto OOMError;
+ }
+ cbSizeNew = hSizeToAlloc(psa, cbNewActual);
+
+ if (cbSizeNew < cbNewActual) { // error if adding padding overflowed us
+OOMError:
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LError0;
+ }
+ cNew = cbNewActual/psa->cbElements;
+ // needed for the copy if old has more elements than new.
+ cDelta = (cbOldActual - cbNewActual)/psa->cbElements;
+#else
+ cbSizeNew = SafeArraySize(psa);
+ if (cbSizeNew == SAFEARRAYOVERFLOW) {
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LError0;
+ }
+#endif
+
+ // Reallocing to size zero will return NULL, which we're not prepared
+ // to handle (VBA94 Bug #4665). So always alloc at least one byte.
+ //
+ if (cbSizeNew == 0) {
+ cbSizeNew = 1;
+ }
+
+ cbDelta = cbSizeNew - cbSizeOld;
+
+ if(cbDelta == 0){
+ hresult = NOERROR;
+ goto LError0;
+ }
+
+ if(cbDelta < 0){
+
+ // the new array is smaller, so copy any resources held by the
+ // old array that wont fit into the new array to a temporary
+ // location so that we can free them if the realloc succeeds.
+
+ if(psa->fFeatures & (FADF_BSTR|FADF_UNKNOWN|FADF_DISPATCH|FADF_VARIANT)) {
+
+#ifdef _MAC
+ if((tmpHandle = NewHandle(-cbDelta)) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LError0;
+ }
+ HLock(tmpHandle);
+ pvTmp = *tmpHandle;
+#else
+ if((pvTmp = (void HUGEP*)pmalloc->Alloc(-cbDelta)) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LError0;
+ }
+#endif
+
+#ifdef WIN16
+ cb = (unsigned long) psa->rgsabound[0].cElements;
+ for(i = 1; i < psa->cDims; ++i){
+ cb *= psa->rgsabound[i].cElements;
+ }
+ pvData = hAccessElement(psa, cb);
+ if(psa->fFeatures & (FADF_BSTR | FADF_UNKNOWN | FADF_DISPATCH) ){
+
+ // Since these are all pointer, we'll just copy them as 4 byte
+ // elements.
+ for(i = 0; i < cDelta; ++i)
+ *(unsigned long HUGEP*) hAccessElement(pvTmp, sizeof(unsigned long), i)=
+ *(unsigned long HUGEP*) hAccessElement(pvData, sizeof(unsigned long), i);
+
+ }else if(psa->fFeatures & FADF_VARIANT){
+
+ for(i = 0; i < cDelta; ++i)
+ *(VARIANT HUGEP*) hAccessElement(pvTmp, sizeof(VARIANT), i) =
+ *(VARIANT HUGEP*) hAccessElement(pvData, sizeof(VARIANT), i);
+ }
+#else
+ pvData = (void HUGEP*)((char HUGEP*)psa->pvData + cbSizeNew);
+ HMEMCPY(pvTmp, pvData, -cbDelta);
+#endif
+ }
+ }
+
+//[CSK]: Note that there will be a problem here if huge allocation
+//[CSK]: do not always begin at the same :OFFSET in the first
+//[CSK]: segment. With EbApp's & Excel's allocator this is
+//[CSK]: currently not a problem since they defer to Halloc
+//[CSK]: and prefixes are always of fixed size.
+//[CSK]: I am not sure if this will always be true.
+#ifdef _MAC
+ if ((reallocHandle = NewHandle(cbSizeNew)) == 0) {
+ psa->rgsabound[0] = saboundOld; // restore original state
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LError0;
+ }
+ HLock(reallocHandle);
+ if (cbSizeNew <= cbSizeOld)
+ HMEMCPY(*reallocHandle, *(psa->handle), cbSizeNew);
+ else
+ HMEMCPY(*reallocHandle, *(psa->handle), cbSizeOld);
+
+ oldHandle = psa->handle;
+ psa->handle = reallocHandle;
+ psa->pvData = *reallocHandle;
+
+
+#else
+ if((pvData = pmalloc->Realloc(psa->pvData, cbSizeNew)) == NULL){
+ psa->rgsabound[0] = saboundOld; // restore original state
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LError0;
+ }
+ psa->pvData = pvData;
+#endif
+
+
+ if(cbDelta < 0){
+
+ // new array is smaller, so release resources that got chopped off.
+ if(pvTmp != NULL){
+#ifdef WIN16
+ ReleaseResources(pvTmp, cbOldActual - cbNewActual, psa->fFeatures, psa->cbElements);
+#else
+ ReleaseResources(pvTmp, -cbDelta, psa->fFeatures, psa->cbElements);
+#endif
+ }
+
+ }else{ // cbDelta > 0
+
+ // the new array is large, so zero fill the newly allocated memory
+#ifdef WIN16
+ pvData = hAccessElement(psa, cOld);
+ pvDataEnd = hAccessElement(psa, cNew);
+ HMEMSET(pvData, 0, (BYTE HUGEP*) pvDataEnd - (BYTE HUGEP*) pvData);
+#else
+ pvData = (void HUGEP*)((char HUGEP*)psa->pvData + cbSizeOld);
+ HMEMSET(pvData, 0, cbDelta);
+#endif
+ }
+
+ hresult = NOERROR;
+
+LError0:;
+#ifndef _MAC
+ if(pvTmp != 0){
+ ASSERT(pmalloc != NULL);
+ pmalloc->Free(pvTmp);
+ }
+#else
+ if(pvTmp != 0){
+ HUnlock(tmpHandle);
+ DisposeHandle(tmpHandle);
+ }
+ if (oldHandle) {
+ HUnlock(oldHandle);
+ DisposeHandle(oldHandle);
+ }
+
+ HUnlock(psa->handle);
+#endif
+
+ return hresult;
+}
+
+
+/***
+*PUBLIC HRESULT SafeArrayCopy(SAFEARRAY*, SAFEARRAY**)
+*Purpose:
+* Return a copy of the given SafeArray.
+*
+*Entry:
+* psa = pointer to the SafeArray to copy
+*
+*Exit:
+* return value = HRESULT
+* S_OK
+* E_INVALIDARG
+* E_OUTOFMEMORY
+*
+* *ppsaOut = a copy of the given SafeArray
+*
+***********************************************************************/
+STDAPI
+SafeArrayCopy(SAFEARRAY FAR* psa, SAFEARRAY FAR* FAR* ppsaOut)
+{
+ unsigned long i;
+ unsigned long cbSize;
+ unsigned long cElements;
+ HRESULT hresult;
+ SAFEARRAY FAR* psaNew;
+
+ if(psa == NULL){
+ *ppsaOut = NULL;
+ return NOERROR;
+ }
+
+#ifdef _DEBUG
+ if(IsBadReadSA(psa))
+ return RESULT(E_INVALIDARG);
+ if(IsBadWritePtr(ppsaOut, sizeof(*ppsaOut)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ IfFailRet(SafeArrayAllocDescriptor(psa->cDims, &psaNew));
+
+ psaNew->cLocks = 0;
+ psaNew->cDims = psa->cDims;
+ psaNew->fFeatures = psa->fFeatures &
+ ~(FADF_AUTO|FADF_STATIC|FADF_EMBEDDED|FADF_FORCEFREE);
+
+ psaNew->cbElements = psa->cbElements;
+
+ MEMCPY(
+ psaNew->rgsabound,
+ psa->rgsabound,
+ sizeof(SAFEARRAYBOUND) * psa->cDims);
+
+ IfFailGo(SafeArrayAllocData(psaNew), LError0);
+
+ IfFailGo(SafeArrayLock(psa), LError0);
+
+ IfFailGo(SafeArrayLock(psaNew), LError1);
+
+ cbSize = SafeArraySize(psa);
+ ASSERT(cbSize != SAFEARRAYOVERFLOW); // existing array, no overflow possible
+
+ cElements = cbSize / psa->cbElements;
+
+ if(psa->fFeatures & FADF_BSTR){
+
+#ifdef WIN16
+ BSTR bstrSrc;
+ for(i = 0; i < cElements; ++i) {
+ bstrSrc = *(BSTR HUGEP*) hAccessElement(psa, i);
+ IfFailGo(ErrStringCopy(
+ bstrSrc,
+ (BSTR HUGEP*) hAccessElement(psaNew, i)),
+ LError2);
+ }
+#else
+ BSTR HUGEP* pbstrDst, HUGEP* pbstrSrc;
+
+ pbstrSrc = (BSTR HUGEP*)psa->pvData;
+ pbstrDst = (BSTR HUGEP*)psaNew->pvData;
+
+ for(i = 0; i < cElements; ++i){
+ IfFailGo(ErrStringCopy(*pbstrSrc, pbstrDst), LError2);
+ ++pbstrDst, ++pbstrSrc;
+ }
+#endif
+
+ }else if(psa->fFeatures & FADF_UNKNOWN){
+
+ IUnknown FAR* HUGEP* ppunkDst, FAR* HUGEP* ppunkSrc;
+
+#ifdef WIN16
+ for(i = 0; i < cElements; ++i) {
+ ppunkSrc = (IUnknown FAR* HUGEP*) hAccessElement(psa, i);
+ ppunkDst = (IUnknown FAR* HUGEP*) hAccessElement(psaNew, i);
+ if(*ppunkSrc != NULL)
+ (*ppunkSrc)->AddRef();
+ *ppunkDst = *ppunkSrc;
+ }
+#else
+ ppunkSrc = (IUnknown FAR* HUGEP*)psa->pvData;
+ ppunkDst = (IUnknown FAR* HUGEP*)psaNew->pvData;
+
+ for(i = 0; i < cElements; ++i){
+ if(*ppunkSrc != NULL)
+ (*ppunkSrc)->AddRef();
+ *ppunkDst = *ppunkSrc;
+ ++ppunkDst, ++ppunkSrc;
+ }
+#endif
+
+ }else if(psa->fFeatures & FADF_DISPATCH){
+
+ IDispatch FAR* HUGEP* ppdispDst, FAR* HUGEP* ppdispSrc;
+
+#ifdef WIN16
+ for(i = 0; i < cElements; ++i) {
+ ppdispSrc = (IDispatch FAR* HUGEP*) hAccessElement(psa, i);
+ ppdispDst = (IDispatch FAR* HUGEP*) hAccessElement(psaNew, i);
+ if(*ppdispSrc != NULL)
+ (*ppdispSrc)->AddRef();
+ *ppdispDst = *ppdispSrc;
+ }
+#else
+ ppdispSrc = (IDispatch FAR* HUGEP*)psa->pvData;
+ ppdispDst = (IDispatch FAR* HUGEP*)psaNew->pvData;
+
+ for(i = 0; i < cElements; ++i){
+ if(*ppdispSrc != NULL)
+ (*ppdispSrc)->AddRef();
+ *ppdispDst = *ppdispSrc;
+ ++ppdispDst, ++ppdispSrc;
+ }
+#endif
+
+ }else if(psa->fFeatures & FADF_VARIANT){
+
+#ifdef WIN16
+ for(i = 0; i < cElements; ++i)
+ IfFailGo(VariantCopy(
+ (VARIANT HUGEP*) hAccessElement(psaNew, i),
+ (VARIANT HUGEP*) hAccessElement(psa, i)),
+ LError2);
+#else
+ VARIANT HUGEP* pvarDst, HUGEP* pvarSrc;
+
+ pvarSrc = (VARIANT HUGEP*)psa->pvData;
+ pvarDst = (VARIANT HUGEP*)psaNew->pvData;
+
+ for(i = 0; i < cElements; ++i){
+ IfFailGo(VariantCopy(pvarDst, pvarSrc), LError2);
+ ++pvarDst, ++pvarSrc;
+ }
+#endif
+
+ }else{
+
+#ifdef WIN16
+ // hSizeToAlloc can't overflow here (couldn't have created original)
+ HMEMCPY(psaNew->pvData, psa->pvData, hSizeToAlloc(psa, cbSize));
+#else
+ HMEMCPY(psaNew->pvData, psa->pvData, cbSize);
+#endif
+
+ }
+
+
+ IfFailGo(SafeArrayUnlock(psaNew), LError1);
+
+ IfFailGo(SafeArrayUnlock(psa), LError0);
+
+ *ppsaOut = psaNew;
+
+ return NOERROR;
+
+
+LError2:;
+ SafeArrayUnlock(psaNew);
+
+LError1:;
+ SafeArrayUnlock(psa);
+
+LError0:;
+ SafeArrayDestroy(psaNew);
+
+ return hresult;
+}
+
+
+/***
+*PUBLIC unsigned int SafeArrayGetDim(SAFEARRAY*)
+*Purpose:
+* Return a count of the number of dimentions in the given array.
+*
+*Entry:
+* psa = the SafeArray descriptor
+*
+*Exit:
+* return value = unsigned int, count of dimentions in the array
+*
+***********************************************************************/
+STDAPI_(unsigned int)
+SafeArrayGetDim(SAFEARRAY FAR* psa)
+{
+ ASSERT(!IsBadReadSA(psa));
+
+ return psa->cDims;
+}
+
+
+/***
+*PUBLIC unsigned int SafeArrayGetElemsize(SAFEARRAY*)
+*Purpose:
+* Return the size in bytes of the elements of the given array.
+*
+*Entry:
+* psa = pointer to the SafeArray descriptor to return the elemsize of.
+*
+*Exit:
+* return value = unsigned int. size in bytes of the elements of the given array.
+*
+***********************************************************************/
+STDAPI_(unsigned int)
+SafeArrayGetElemsize(SAFEARRAY FAR* psa)
+{
+ ASSERT(!IsBadReadSA(psa));
+
+ return psa->cbElements;
+}
+
+
+/***
+*PUBLIC HRESULT SafeArrayGetUBound(SAFEARRAY*, unsigned int, unsigned int*)
+*Purpose:
+* Return the Upper bound for the given dimention, where the
+* upper bound is defined as the largest existant element of
+* the given dimention.
+*
+*Entry:
+* psa = the SafeArray descriptor
+* uDim = the dimention to return the upper bound for
+*
+*Exit:
+* return value = HRESULT,
+* S_OK
+* E_INVALIDARG
+* DISP_E_BADINDEX
+*
+***********************************************************************/
+STDAPI
+SafeArrayGetUBound(SAFEARRAY FAR* psa, unsigned int uDim, long FAR* pUbound)
+{
+ SAFEARRAYBOUND FAR* psb;
+
+ if(psa == NULL)
+ return RESULT(E_INVALIDARG);
+#ifdef _DEBUG
+ if(IsBadReadSA(psa))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ if(uDim == 0 || uDim > psa->cDims)
+ return RESULT(DISP_E_BADINDEX);
+
+ psb = &psa->rgsabound[psa->cDims - uDim];
+
+ *pUbound = (psb->lLbound + (long)psb->cElements - 1);
+
+ return NOERROR;
+}
+
+
+/***
+*PUBLIC HRESULT SafeArrayGetLBound(SAFEARRAY*, unsigned int, unsigned int*)
+*Purpose:
+* Return the Lower bound for the given dimention, where the
+* lower bound is defined as the smallest existant element
+* of the given dimention.
+*
+*Entry:
+* psa = the SafeArray Descriptor
+* uDim = the dimention to return the lower bound for
+*
+*Exit:
+* return value = HRESULT,
+* S_OK
+* E_INVALIDARG
+* DISP_E_BADINDEX
+*
+***********************************************************************/
+STDAPI
+SafeArrayGetLBound(SAFEARRAY FAR* psa, unsigned int uDim, long FAR* pLbound)
+{
+ if(psa == NULL)
+ return RESULT(E_INVALIDARG);
+#ifdef _DEBUG
+ if(IsBadReadSA(psa))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ if(uDim == 0 || uDim > psa->cDims)
+ return RESULT(DISP_E_BADINDEX);
+
+ *pLbound = psa->rgsabound[psa->cDims - uDim].lLbound;
+
+ return NOERROR;
+}
+
+
+/***
+*PUBLIC HRESULT SafeArrayLock(SAFEARRAY*)
+*Purpose:
+* Lock the given SafeArray.
+*
+*Entry:
+* psa = the SafeArray descriptor
+*
+*Exit:
+* return value = HRESULT,
+* S_OK
+* E_INVALIDARG
+* E_UNEXPECTED - if call would overflow lock count
+*
+***********************************************************************/
+STDAPI
+SafeArrayLock(SAFEARRAY FAR* psa)
+{
+ if(psa == NULL)
+ return RESULT(E_INVALIDARG);
+#ifdef _DEBUG
+ if(IsBadWriteSA(psa))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ // error if one more lock will cause the count to overflow
+ if(psa->cLocks == USHRT_MAX)
+ return RESULT(E_UNEXPECTED);
+
+ ++psa->cLocks;
+
+#ifdef _MAC
+ if (psa->cLocks == 1) {
+ HLock(psa->handle);
+ psa->pvData = *(psa->handle);
+ }
+#endif
+
+ return NOERROR;
+}
+
+
+/***
+*PUBLIC HRESULT SafeArrayUnlock(SAFEARRAY*)
+*Purpose:
+* Unlock the given SafeArray.
+*
+*Entry:
+* psa = the SafeArray descriptor of the array to unlock.
+*
+*Exit:
+* return value = HRESULT,
+* S_OK
+* E_INVALIDARG
+* E_UNEXPECTED - if call would underflow lock count
+*
+***********************************************************************/
+STDAPI
+SafeArrayUnlock(SAFEARRAY FAR* psa)
+{
+ if(psa == NULL)
+ return RESULT(E_INVALIDARG);
+#ifdef _DEBUG
+ if(IsBadWriteSA(psa))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ if(psa->cLocks == 0)
+ return RESULT(E_UNEXPECTED);
+
+ --psa->cLocks;
+
+#ifdef _MAC
+ if (psa->cLocks == 0) {
+ HUnlock(psa->handle);
+ psa->pvData = NULL;
+ }
+#endif
+
+ return NOERROR;
+}
+
+
+/***
+*HRESULT SafeArrayAccessData(SAFEARRAY*, void**)
+*Purpose:
+* Lock the given SafeArray and return a pointer to its data.
+*
+*Entry:
+* psa = the SafeArray to access
+*
+*Exit:
+* return value = HRESULT
+* S_OK
+* E_INVALIDARG
+* E_UNEXPECTED
+*
+* *ppvData = pointer to the arrary data
+*
+***********************************************************************/
+STDAPI
+SafeArrayAccessData(SAFEARRAY FAR* psa, void HUGEP* FAR* ppvData)
+{
+ IfFailRet(SafeArrayLock(psa));
+
+ *ppvData = psa->pvData;
+
+ return NOERROR;
+}
+
+
+/***
+*HRESULT SafeArrayUnaccessData(SAFEARRAY*)
+*Purpose:
+* Unaccess the given SafeArray's data.
+*
+*Entry:
+* psa = the SafeArray to unaccess.
+*
+*Exit:
+* return value = HRESULT
+* S_OK
+* E_INVALIDARG
+* E_UNEXPECTED
+*
+***********************************************************************/
+STDAPI
+SafeArrayUnaccessData(SAFEARRAY FAR* psa)
+{
+ return SafeArrayUnlock(psa);
+}
+
+
+/***
+*PRIVATE HRESULT SafeArrayPtrOfIndex(SAFEARRAY*, long*)
+*Purpose:
+* Return a pointer to the array element with the given indices.
+*
+*Entry:
+* psa = the SafeArray descriptor
+* rgIndices = array of indices
+*
+* Note: The indices are passed in textual order, while the array
+* of bounds is passed in reverse-textual order.
+*
+*Exit:
+* return value = HRESULT
+* S_OK
+* DISP_E_BADINDEX
+*
+* ppvData = pointer to the array element with the given indices
+*
+***********************************************************************/
+STDAPI
+SafeArrayPtrOfIndex(
+ SAFEARRAY FAR* psa,
+ long FAR* rgIndices,
+ void HUGEP* FAR* ppvData)
+{
+ unsigned long ofs;
+ long ix, FAR* pix;
+ SAFEARRAYBOUND FAR* pbound;
+
+ if(psa->cDims == 0)
+ return RESULT(DISP_E_BADINDEX);
+
+#ifdef _MAC
+ if(psa->cLocks == 0)
+ return RESULT(E_FAIL); // UNDONE: This needs to be a more descriptive
+ // HRESULT, probably DISP_E_ARRAYISNOTLOCK
+#endif
+
+
+ // compute the offset represented by the given indices
+
+ ofs = 0;
+ pbound = psa->rgsabound;
+ pix = &rgIndices[psa->cDims - 1];
+
+ while(1){
+
+ ix = *pix - pbound->lLbound;
+ if(ix < 0 || ix >= (long)pbound->cElements)
+ return RESULT(DISP_E_BADINDEX);
+
+ ofs += ix;
+
+ if(pix == rgIndices)
+ break;
+
+ --pix;
+ ++pbound;
+
+ ofs *= pbound->cElements;
+ }
+
+#ifdef WIN16
+ *ppvData = hAccessElement(psa, ofs);
+#else
+ ofs *= psa->cbElements;
+ *ppvData = ((unsigned char HUGEP*)psa->pvData) + ofs;
+#endif
+
+ return NOERROR;
+}
+
+
+/***
+*PUBLIC HRESULT SafeArrayGetElement(SAFEARRAY*, long*, void*)
+*Purpose:
+* Extract the element at the given indices from the given SafeArray.
+*
+*Entry:
+* psa = the SafeArray descriptor
+* rgIndices = an array of indices
+*
+*Exit:
+* return value = HRESULT,
+* S_OK
+* E_INVALIDARG
+* E_OUTOFMEMORY
+* DISP_E_BADINDEX
+*
+* pv = pointer to a copy of the extracted data
+*
+***********************************************************************/
+STDAPI
+SafeArrayGetElement(
+ SAFEARRAY FAR* psa,
+ long FAR* rgIndices,
+ void FAR* pv)
+{
+ HRESULT hresult;
+ void HUGEP* pvData;
+
+ if(psa == NULL)
+ return RESULT(E_INVALIDARG);
+#ifdef _DEBUG
+ if(IsBadReadSA(psa))
+ return RESULT(E_INVALIDARG);
+ if(IsBadWritePtr(pv, psa->cbElements))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ IfFailGo(SafeArrayLock(psa), LError0);
+
+ IfFailGo(SafeArrayPtrOfIndex(psa, rgIndices, &pvData), LError0);
+
+ if(psa->fFeatures & FADF_BSTR){
+
+ IfFailGo(ErrStringCopy(*(BSTR HUGEP*)pvData,
+ (BSTR FAR*)pv), LError0);
+
+ }else if(psa->fFeatures & FADF_UNKNOWN){
+
+ IUnknown FAR* punk = *(IUnknown FAR* HUGEP*)pvData;
+ *((IUnknown FAR* FAR*)pv) = punk;
+ if(punk != NULL)
+ punk->AddRef();
+
+ }else if(psa->fFeatures & FADF_DISPATCH){
+
+ IDispatch FAR* pdisp = *(IDispatch FAR* HUGEP*)pvData;
+ *((IDispatch FAR* FAR*)pv) = pdisp;
+ if(pdisp != NULL)
+ pdisp->AddRef();
+
+ }else if(psa->fFeatures & FADF_VARIANT){
+
+ VARIANT FAR* pvarTo;
+ VARIANT FAR* pvarFrom;
+
+ pvarTo = (VARIANT FAR*)pv;
+ pvarFrom = (VARIANT HUGEP*)pvData;
+
+ V_VT(pvarTo) = VT_EMPTY;
+ IfFailGo(VariantCopy(pvarTo, pvarFrom), LError0);
+
+ }else{
+
+ MEMCPY(pv, pvData, psa->cbElements);
+
+ }
+
+ hresult = NOERROR;
+
+LError0:;
+ SafeArrayUnlock(psa);
+
+ return hresult;
+}
+
+
+/***
+*PUBLIC HRESULT SafeArrayPutElement(SAFEARRAY*, long*, void*)
+*Purpose:
+* Put the given data at the given location in the given array.
+*
+*Entry:
+* psa = the SafeArray descriptor
+* rgIndices = an array of indices
+* pv = pointer to the data to copy into the array.
+*
+*Exit:
+* return value = HRESULT,
+* S_OK
+* E_INVALIDARG
+* E_OUTOFMEMORY
+* DISP_E_BADINDEX
+*
+***********************************************************************/
+STDAPI
+SafeArrayPutElement(
+ SAFEARRAY FAR* psa,
+ long FAR* rgIndices,
+ void FAR* pv)
+{
+ HRESULT hresult;
+ void HUGEP* pvData;
+
+ if(psa == NULL)
+ return RESULT(E_INVALIDARG);
+#ifdef _DEBUG
+ if(IsBadWriteSA(psa))
+ return RESULT(E_INVALIDARG);
+ if(IsBadReadPtr(pv, psa->cbElements))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ IfFailGo(SafeArrayLock(psa), LError0);
+
+ IfFailGo(SafeArrayPtrOfIndex(psa, rgIndices, &pvData), LError1);
+
+ if(psa->fFeatures & FADF_BSTR){
+
+ BSTR bstrNew;
+ BSTR FAR* pbstrOld;
+
+ bstrNew = (BSTR)pv;
+ pbstrOld = (BSTR HUGEP*)pvData;
+
+ BSTR bstrTmp = *pbstrOld;
+
+ IfFailGo(ErrStringCopy(bstrNew, pbstrOld), LError1);
+
+ SysFreeString(bstrTmp);
+
+ }else if(psa->fFeatures & FADF_UNKNOWN){
+
+ IUnknown FAR* punkNew;
+ IUnknown FAR* FAR* ppunkOld;
+
+ punkNew = (IUnknown FAR*)pv;
+ ppunkOld = (IUnknown FAR* HUGEP*)pvData;
+
+ if(*ppunkOld != NULL)
+ (*ppunkOld)->Release();
+ *ppunkOld = punkNew;
+ if(punkNew != NULL)
+ punkNew->AddRef();
+
+ }else if(psa->fFeatures & FADF_DISPATCH){
+
+ IDispatch FAR* pdispNew;
+ IDispatch FAR* FAR* ppdispOld;
+
+ pdispNew = (IDispatch FAR*)pv;
+ ppdispOld = (IDispatch FAR* HUGEP*)pvData;
+
+ if(*ppdispOld != NULL)
+ (*ppdispOld)->Release();
+ *ppdispOld = pdispNew;
+ if(pdispNew != NULL)
+ pdispNew->AddRef();
+
+ }else if(psa->fFeatures & FADF_VARIANT){
+
+ VARIANT FAR* pvarNew;
+ VARIANT FAR* pvarOld;
+
+ pvarNew = (VARIANT FAR*)pv;
+ pvarOld = (VARIANT HUGEP*)pvData;
+
+ IfFailGo(VariantCopy(pvarOld, pvarNew), LError1);
+
+ }else{
+
+ MEMCPY(pvData, pv, psa->cbElements);
+
+ }
+
+ hresult = NOERROR;
+
+LError1:;
+ SafeArrayUnlock(psa);
+
+LError0:;
+ return hresult;
+}
+
+#endif // !NETDISP
+
+#if OE_MAC && !defined(HIWORD)
+#define HIWORD(l) ((WORD)((((DWORD)(l)) >> 16) & 0xFFFF))
+#define LOWORD(l) ((WORD)(DWORD)(l))
+#define MAKELONG(low, high) ((DWORD)(((WORD)(low)) | (((DWORD)((WORD)(high))) << 16)))
+#endif //OE_MAC !defined(HIWORD)
+
+
+INTERNAL_(unsigned long)
+SafeArraySize(SAFEARRAY FAR* psa)
+{
+ unsigned long cb;
+ unsigned long dw1;
+ unsigned long dw2;
+ unsigned short us;
+ unsigned short cDims;
+ SAFEARRAYBOUND FAR* psabound;
+
+ cb = 0L;
+ if(cDims = psa->cDims){
+ psabound = &psa->rgsabound[cDims - 1];
+ cb = (unsigned long)psa->cbElements;
+ for(us = 0; us < cDims; ++us){
+ dw1 = cb;
+ dw2 = psabound->cElements;
+
+ // now do a 32x32 multiply, with overflow checking
+ // cb = dw1 * dw2;
+
+ // note: DWORD casts on all 16x16 multiplies so that we don't
+ // lose the high word of the result.
+
+ if (HIWORD(dw1) == 0 && HIWORD(dw2) == 0) {
+ // simple case of 16 x 16 -- can't overflow
+ cb = (DWORD)LOWORD(dw1) * LOWORD(dw2);
+ } else if (HIWORD(dw1) != 0 && HIWORD(dw2) != 0) {
+ // 32 x 32 -- no way
+ return SAFEARRAYOVERFLOW;
+ } else {
+ // 16 x 32 or 32 x 16
+ if (HIWORD(dw2) != 0) { // swap so dw2 is always 16 bit
+ cb = dw1;
+ dw1 = dw2;
+ dw2 = cb;
+ }
+ // 32(dw1) x 16(dw2)
+ ASSERT(HIWORD(dw2) == 0);
+
+ // do first 16 x 16 multiply
+ cb = ((DWORD)HIWORD(dw1)) * LOWORD(dw2);
+ if (HIWORD(cb) != 0)
+ return SAFEARRAYOVERFLOW;
+ // do second multiply
+ dw1 = ((DWORD)LOWORD(dw1)) * LOWORD(dw2); // dw1 = 2nd partial product
+ dw2 = MAKELONG(0, LOWORD(cb)); // dw2 = 1st partial product
+ cb = dw1+dw2; // cb = sum of partial products
+ if (cb < dw1) // check for overflow
+ return SAFEARRAYOVERFLOW;
+ }
+
+ --psabound;
+ }
+ }
+
+ return cb;
+}
diff --git a/private/oleauto/src/dispatch/stddisp.cpp b/private/oleauto/src/dispatch/stddisp.cpp
new file mode 100644
index 000000000..7db2e32c4
--- /dev/null
+++ b/private/oleauto/src/dispatch/stddisp.cpp
@@ -0,0 +1,856 @@
+/***
+*stddisp.cpp
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* UNDONE
+*
+*
+*Revision History:
+*
+* [00] 09-Feb-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "stddisp.h"
+
+
+STDAPI
+CreateStdDispatch(
+ IUnknown FAR* punkOuter,
+ void FAR* pvThis,
+ ITypeInfo FAR* ptinfo,
+ IUnknown FAR* FAR* ppunk)
+
+{
+#if OE_WIN32 && 0
+ return CDualStdDisp::Create(punkOuter, pvThis, ptinfo, ppunk);
+#else
+ return CStdDisp::Create(punkOuter, pvThis, ptinfo, ppunk);
+#endif
+}
+
+
+CStdDisp::CStdDisp() : m_unk(this)
+{
+ m_refs = 1;
+ m_punk = NULL;
+ m_this = NULL;
+ m_ptinfo = NULL;
+}
+
+
+/***
+, void*, LCID, ITypeInfo*, IDispatch**)
+*Purpose:
+* Create an instance of the standard IDispatch implementation and
+* initialize it with the given 'this' pointer, locale id (lcid) and
+* TypeInfo.
+*
+*Entry:
+* punkOuter - the controlling unknown (if any). NULL means use the
+* default CStdDisp IUnknown implementation (ie, were not nested).
+* pvThis - the this pointer of the object we will be dispatching on.
+* lcid - the single locale id supported by the object we are dispatching on.
+* ptinfo - the TypeInfo describing the single programmability interface
+* supported by the object we are dispatching on.
+*
+*Exit:
+* return value = HRESULT
+*
+* *pdisp = pointer to newly constructed IDispatch implementation.
+*
+***********************************************************************/
+HRESULT
+CStdDisp::Create(
+ IUnknown FAR* punkOuter,
+ void FAR* pvThis,
+ ITypeInfo FAR* ptinfo,
+ IUnknown FAR* FAR* ppunk)
+{
+ CStdDisp FAR* pdisp;
+
+#ifdef _DEBUG
+ // REVIEW: add parameter validation code
+#endif
+
+ if(ptinfo == NULL || pvThis == NULL)
+ return RESULT(E_INVALIDARG);
+
+ if((pdisp = new FAR CStdDisp()) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+
+ if(punkOuter == NULL)
+ punkOuter = &pdisp->m_unk;
+ pdisp->m_punk = punkOuter;
+ pdisp->m_this = pvThis;
+
+ ptinfo->AddRef();
+ pdisp->m_ptinfo = ptinfo;
+
+ *ppunk = &pdisp->m_unk;
+
+ return NOERROR;
+}
+
+
+//---------------------------------------------------------------------
+// default IUnknown implementation
+//---------------------------------------------------------------------
+
+CStdDispUnkImpl::CStdDispUnkImpl(CStdDisp FAR* pstddisp)
+{
+ m_pstddisp = pstddisp;
+}
+
+STDMETHODIMP
+CStdDispUnkImpl::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ if(IsEqualIID(riid, IID_IUnknown)){
+ *ppv = this;
+ AddRef();
+ }else if(IsEqualIID(riid, IID_IDispatch)){
+ *ppv = m_pstddisp;
+ m_pstddisp->AddRef();
+ }else{
+ *ppv = NULL;
+ return RESULT(E_NOINTERFACE);
+ }
+ return NOERROR;
+}
+
+STDMETHODIMP_(unsigned long)
+CStdDispUnkImpl::AddRef()
+{
+ return ++m_pstddisp->m_refs;
+}
+
+STDMETHODIMP_(unsigned long)
+CStdDispUnkImpl::Release()
+{
+ if(--m_pstddisp->m_refs == 0){
+ if(m_pstddisp->m_ptinfo != NULL)
+ m_pstddisp->m_ptinfo->Release();
+ delete m_pstddisp;
+ return 0;
+ }
+ return m_pstddisp->m_refs;
+}
+
+
+//---------------------------------------------------------------------
+// IDispatch implementation
+//---------------------------------------------------------------------
+
+
+STDMETHODIMP
+CStdDisp::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ return m_punk->QueryInterface(riid, ppv);
+}
+
+
+STDMETHODIMP_(unsigned long)
+CStdDisp::AddRef()
+{
+ return m_punk->AddRef();
+}
+
+
+STDMETHODIMP_(unsigned long)
+CStdDisp::Release()
+{
+ return m_punk->Release();
+}
+
+
+STDMETHODIMP
+CStdDisp::GetTypeInfoCount(unsigned int FAR* pctinfo)
+{
+ *pctinfo = (m_ptinfo == NULL) ? 0 : 1;
+
+ return NOERROR;
+}
+
+
+STDMETHODIMP
+CStdDisp::GetTypeInfo(
+ unsigned int itinfo,
+ LCID lcid,
+ ITypeInfo FAR* FAR* pptinfo)
+{
+ UNUSED(lcid);
+
+ if(itinfo != 0)
+ return RESULT(DISP_E_BADINDEX);
+
+ *pptinfo = m_ptinfo;
+ m_ptinfo->AddRef();
+
+ return NOERROR;
+}
+
+
+STDMETHODIMP
+CStdDisp::GetIDsOfNames(
+ REFIID riid,
+ OLECHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ LCID lcid,
+ DISPID FAR* rgdispid)
+{
+ UNUSED(lcid);
+
+ if(!IsEqualIID(riid, IID_NULL))
+ return RESULT(DISP_E_UNKNOWNINTERFACE);
+
+ return DispGetIDsOfNames(m_ptinfo, rgszNames, cNames, rgdispid);
+}
+
+
+STDMETHODIMP
+CStdDisp::Invoke(
+ DISPID dispidMember,
+ REFIID riid,
+ LCID lcid,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pdispparams,
+ VARIANT FAR* pvarResult,
+ EXCEPINFO FAR* pexcepinfo,
+ unsigned int FAR* puArgErr)
+{
+ UNUSED(lcid);
+
+ if(!IsEqualIID(riid, IID_NULL))
+ return RESULT(DISP_E_UNKNOWNINTERFACE);
+
+ return DispInvoke(
+ m_this, m_ptinfo,
+ dispidMember, wFlags, pdispparams,
+ pvarResult, pexcepinfo, puArgErr);
+}
+
+
+
+#if OE_WIN32 && 0 /* { */
+
+// IDispatchW Default Implementation
+
+STDAPI
+CreateStdDispatchW(
+ IUnknown FAR* punkOuter,
+ void FAR* pvThis,
+ ITypeInfoW FAR* ptinfo,
+ IUnknown FAR* FAR* ppunk)
+{
+ return CDualStdDisp::Create(punkOuter, pvThis, ptinfo, ppunk);
+}
+
+
+CStdDispW::CStdDispW() : m_unk(this)
+{
+ m_refs = 1;
+ m_punk = NULL;
+ m_this = NULL;
+ m_ptinfo = NULL;
+}
+
+
+/***
+*HRESULT CStdDispW::Create(IUnknown*, void*, LCID, ITypeInfo*, IDispatch**)
+*Purpose:
+* Create an instance of the standard IDispatch implementation and
+* initialize it with the given 'this' pointer, locale id (lcid) and
+* TypeInfo.
+*
+*Entry:
+* punkOuter - the controlling unknown (if any). NULL means use the
+* default CStdDispW IUnknown implementation (ie, were not nested).
+* pvThis - the this pointer of the object we will be dispatching on.
+* lcid - the single locale id supported by the object we are dispatching on.
+* ptinfo - the TypeInfo describing the single programmability interface
+* supported by the object we are dispatching on.
+*
+*Exit:
+* return value = HRESULT
+*
+* *pdisp = pointer to newly constructed IDispatch implementation.
+*
+***********************************************************************/
+HRESULT
+CStdDispW::Create(
+ IUnknown FAR* punkOuter,
+ void FAR* pvThis,
+ ITypeInfoW FAR* ptinfo,
+ IUnknown FAR* FAR* ppunk)
+{
+ CStdDispW FAR* pdisp;
+
+#ifdef _DEBUG
+ // REVIEW: add parameter validation code
+#endif
+
+ if(ptinfo == NULL || pvThis == NULL)
+ return RESULT(E_INVALIDARG);
+
+ if((pdisp = new FAR CStdDispW()) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+
+ if(punkOuter == NULL)
+ punkOuter = &pdisp->m_unk;
+ pdisp->m_punk = punkOuter;
+ pdisp->m_this = pvThis;
+
+ ptinfo->AddRef();
+ pdisp->m_ptinfo = ptinfo;
+
+ *ppunk = &pdisp->m_unk;
+
+ return NOERROR;
+}
+
+
+//---------------------------------------------------------------------
+// default IUnknown implementation
+//---------------------------------------------------------------------
+
+CStdDispWUnkImpl::CStdDispWUnkImpl(CStdDispW FAR* pstddisp)
+{
+ m_pstddisp = pstddisp;
+}
+
+STDMETHODIMP
+CStdDispWUnkImpl::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ if(IsEqualIID(riid, IID_IUnknown)){
+ *ppv = this;
+ AddRef();
+ }else if(IsEqualIID(riid, IID_IDispatchW)){
+ *ppv = m_pstddisp;
+ m_pstddisp->AddRef();
+ }else{
+ *ppv = NULL;
+ return RESULT(E_NOINTERFACE);
+ }
+ return NOERROR;
+}
+
+STDMETHODIMP_(unsigned long)
+CStdDispWUnkImpl::AddRef()
+{
+ return ++m_pstddisp->m_refs;
+}
+
+STDMETHODIMP_(unsigned long)
+CStdDispWUnkImpl::Release()
+{
+ if(--m_pstddisp->m_refs == 0){
+ if(m_pstddisp->m_ptinfo != NULL)
+ m_pstddisp->m_ptinfo->Release();
+ delete m_pstddisp;
+ return 0;
+ }
+ return m_pstddisp->m_refs;
+}
+
+
+//---------------------------------------------------------------------
+// IDispatch implementation
+//---------------------------------------------------------------------
+
+
+STDMETHODIMP
+CStdDispW::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ return m_punk->QueryInterface(riid, ppv);
+}
+
+
+STDMETHODIMP_(unsigned long)
+CStdDispW::AddRef()
+{
+ return m_punk->AddRef();
+}
+
+
+STDMETHODIMP_(unsigned long)
+CStdDispW::Release()
+{
+ return m_punk->Release();
+}
+
+
+STDMETHODIMP
+CStdDispW::GetTypeInfoCount(unsigned int FAR* pctinfo)
+{
+ *pctinfo = (m_ptinfo == NULL) ? 0 : 1;
+
+ return NOERROR;
+}
+
+
+STDMETHODIMP
+CStdDispW::GetTypeInfo(
+ unsigned int itinfo,
+ LCID lcid,
+ ITypeInfoW FAR* FAR* pptinfo)
+{
+ UNUSED(lcid);
+
+ if(itinfo != 0)
+ return RESULT(DISP_E_BADINDEX);
+
+ *pptinfo = m_ptinfo;
+ m_ptinfo->AddRef();
+
+ return NOERROR;
+}
+
+
+STDMETHODIMP
+CStdDispW::GetIDsOfNames(
+ REFIID riid,
+ WCHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ LCID lcid,
+ DISPID FAR* rgdispid)
+{
+ UNUSED(lcid);
+
+ if(riid != IID_NULL)
+ return RESULT(DISP_E_UNKNOWNINTERFACE);
+
+ return DispGetIDsOfNamesW(m_ptinfo, rgszNames, cNames, rgdispid);
+}
+
+
+STDMETHODIMP
+CStdDispW::Invoke(
+ DISPID dispidMember,
+ REFIID riid,
+ LCID lcid,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pdispparams,
+ VARIANT FAR* pvarResult,
+ WEXCEPINFO FAR* pexcepinfo,
+ unsigned int FAR* puArgErr)
+{
+ UNUSED(lcid);
+
+ if(riid != IID_NULL)
+ return RESULT(DISP_E_UNKNOWNINTERFACE);
+
+ return DispInvokeW(
+ m_this, m_ptinfo,
+ dispidMember, wFlags, pdispparams,
+ pvarResult, pexcepinfo, puArgErr);
+}
+
+
+
+//---------------------------------------------------------------------
+// CDualStdDisp Constructor/Creation Functions
+//---------------------------------------------------------------------
+
+CDualStdDisp::CDualStdDisp() : m_unk(this)
+{
+ m_refs = 1;
+ m_punk = NULL;
+ m_this = NULL;
+ m_pAnsiDispatch = NULL;
+ m_pUnicodeDispatch = NULL;
+}
+
+HRESULT
+CDualStdDisp::Create(
+ IUnknown FAR* pUnkOuter,
+ void FAR* pvThis,
+ ITypeInfo FAR* ptinfo,
+ IUnknown FAR* FAR* ppunk)
+{
+ CDualStdDisp FAR* pdisp;
+
+ if(ptinfo == NULL || pvThis == NULL)
+ return RESULT(E_INVALIDARG);
+
+ if((pdisp = new FAR CDualStdDisp()) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+
+ if(pUnkOuter == NULL)
+ pUnkOuter = &pdisp->m_unk;
+ pdisp->m_punk = pUnkOuter;
+ pdisp->m_this = pvThis;
+
+ IfFailRet(CStdDisp::Create(pUnkOuter,
+ pvThis,
+ ptinfo,
+ &(pdisp->m_pAnsiDispatch)));
+
+ *ppunk = &pdisp->m_unk;
+
+ return NOERROR;
+}
+
+HRESULT
+CDualStdDisp::Create(
+ IUnknown FAR* pUnkOuter,
+ void FAR* pvThis,
+ ITypeInfoW FAR* ptinfo,
+ IUnknown FAR* FAR* ppunk)
+{
+ CDualStdDisp FAR* pdisp;
+
+ if(ptinfo == NULL || pvThis == NULL)
+ return RESULT(E_INVALIDARG);
+
+ if((pdisp = new FAR CDualStdDisp()) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+
+ if(pUnkOuter == NULL)
+ pUnkOuter = &pdisp->m_unk;
+ pdisp->m_punk = pUnkOuter;
+ pdisp->m_this = pvThis;
+
+ IfFailRet(CStdDispW::Create(pUnkOuter,
+ pvThis,
+ ptinfo,
+ &(pdisp->m_pUnicodeDispatch)));
+
+ *ppunk = &pdisp->m_unk;
+
+ return NOERROR;
+}
+
+
+//---------------------------------------------------------------------
+// default IUnknown implementation
+//---------------------------------------------------------------------
+
+CDualStdDispUnkImpl::CDualStdDispUnkImpl(CDualStdDisp FAR* pstddisp)
+{
+ m_pstddisp = pstddisp;
+}
+
+STDMETHODIMP
+CDualStdDispUnkImpl::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ HRESULT hresult;
+
+ if(IsEqualIID(riid, IID_IUnknown)){
+ *ppv = this;
+ AddRef();
+ }else if(IsEqualIID(riid, IID_IDispatch)){
+ if ((m_pstddisp->m_pAnsiDispatch == NULL) &&
+ (hresult = m_pstddisp->CreateAnsiTable()) != NOERROR)
+ return(hresult);
+ return m_pstddisp->m_pAnsiDispatch->QueryInterface(riid, ppv);
+ }else if(IsEqualIID(riid, IID_IDispatchW)){
+ if ((m_pstddisp->m_pUnicodeDispatch == NULL) &&
+ (hresult = m_pstddisp->CreateUnicodeTable()) != NOERROR)
+ return(hresult);
+ return m_pstddisp->m_pUnicodeDispatch->QueryInterface(riid, ppv);
+ }else{
+ *ppv = NULL;
+ return RESULT(E_NOINTERFACE);
+ }
+ return NOERROR;
+}
+
+STDMETHODIMP_(unsigned long)
+CDualStdDispUnkImpl::AddRef()
+{
+ return ++m_pstddisp->m_refs;
+}
+
+STDMETHODIMP_(unsigned long)
+CDualStdDispUnkImpl::Release()
+{
+ if(--m_pstddisp->m_refs == 0){
+ if(m_pstddisp->m_pAnsiDispatch != NULL)
+ m_pstddisp->m_pAnsiDispatch->Release();
+ if(m_pstddisp->m_pUnicodeDispatch != NULL)
+ m_pstddisp->m_pUnicodeDispatch->Release();
+ delete m_pstddisp;
+ return 0;
+ }
+ return m_pstddisp->m_refs;
+}
+
+
+//---------------------------------------------------------------------
+// IDispatch implementation
+//---------------------------------------------------------------------
+
+
+STDMETHODIMP
+CDualStdDisp::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ return m_punk->QueryInterface(riid, ppv);
+}
+
+
+STDMETHODIMP_(unsigned long)
+CDualStdDisp::AddRef()
+{
+ return m_punk->AddRef();
+}
+
+
+STDMETHODIMP_(unsigned long)
+CDualStdDisp::Release()
+{
+ return m_punk->Release();
+}
+
+
+
+
+//---------------------------------------------------------------------
+// CDualStdDisp private implementation
+//---------------------------------------------------------------------
+
+STDMETHODIMP
+CDualStdDisp::CreateAnsiTable(void)
+{
+ HRESULT hresult;
+
+ IDispatchW FAR* pdisp;
+ ITypeInfo FAR* ptinfo;
+ ITypeInfoW FAR* ptinfoW, FAR* ptinfoW2;
+
+ WTYPEATTR FAR* ptattr;
+ WFUNCDESC *pfuncdesc;
+ unsigned int i, count, funcIndex, paramIndex;
+
+ const unsigned int rgbstrMax = 16; //REVIEW: Is this large enough?
+ WBSTR FAR rgbstrNames[rgbstrMax];
+ unsigned int lpcName;
+
+ INTERFACEDATA FAR *idata;
+ METHODDATA FAR* pmdata;
+
+
+ // TypeInfo must exists to create UnicodeTable
+ //
+ if (m_pUnicodeDispatch == NULL ||
+ m_pUnicodeDispatch->QueryInterface(IID_IDispatchW,
+ (void FAR* FAR*) &pdisp) != NOERROR)
+ return RESULT(E_FAIL);
+ if (pdisp->GetTypeInfoCount(&count) != NOERROR ||
+ count == 0 ||
+ pdisp->GetTypeInfo(0, LOCALE_USER_DEFAULT, &ptinfoW) != NOERROR) {
+ pdisp->Release();
+ return RESULT(E_FAIL);
+ }
+
+
+ // Query TypeInfo for members & generate equivalent
+ // INTERFACEDATA AnsiTable
+ //
+ IfFailGo(ptinfoW->GetRefTypeInfo(0, &ptinfoW2), LError0);
+ ptinfoW->Release();
+ IfFailGo(ptinfoW2->GetTypeAttr(&ptattr), LError0);
+ idata = new FAR INTERFACEDATA;
+ idata->cMembers = ptattr->cFuncs;
+ idata->pmethdata = new FAR METHODDATA[idata->cMembers];
+ for (funcIndex = 0; funcIndex < idata->cMembers; funcIndex++) {
+ IfFailGo(ptinfoW2->GetFuncDesc(funcIndex, &pfuncdesc), LError1);
+ IfFailGo(ptinfoW2->GetNames(pfuncdesc->memid,
+ rgbstrNames,
+ rgbstrMax,
+ &lpcName),
+ LError1);
+ if(lpcName != (unsigned int) pfuncdesc->cParams+1) goto LError2;
+
+ // Fill out methoddata info
+ //
+ pmdata = &(idata->pmethdata[funcIndex]);
+ pmdata->szName = SysStringWtoA(rgbstrNames[0], CP_ACP);
+ pmdata->cArgs = pfuncdesc->cParams;
+ pmdata->ppdata = pmdata->cArgs ?
+ new FAR PARAMDATA[pmdata->cArgs] : NULL;
+ pmdata->dispid = pfuncdesc->memid;
+ pmdata->iMeth = pfuncdesc->oVft / sizeof(void FAR*);
+ pmdata->cc = pfuncdesc->callconv;
+ pmdata->vtReturn = pfuncdesc->elemdescFunc.tdesc.vt;
+ for (paramIndex = 0; paramIndex < pmdata->cArgs; paramIndex++) {
+ pmdata->ppdata[paramIndex].szName =
+ SysStringWtoA(rgbstrNames[paramIndex+1], CP_ACP);
+ pmdata->ppdata[paramIndex].vt =
+ pfuncdesc->lprgelemdescParam[paramIndex].tdesc.vt;
+ }
+ switch(pfuncdesc->invkind) {
+ case INVOKE_FUNC:
+ pmdata->wFlags = DISPATCH_METHOD;
+ break;
+ case INVOKE_PROPERTYGET:
+ pmdata->wFlags = DISPATCH_PROPERTYGET;
+ break;
+ case INVOKE_PROPERTYPUT:
+ pmdata->wFlags = DISPATCH_PROPERTYPUT;
+ break;
+ case INVOKE_PROPERTYPUTREF:
+ pmdata->wFlags = DISPATCH_PROPERTYPUTREF;
+ break;
+ }
+
+ // Free temporary info
+ //
+ ptinfoW2->ReleaseFuncDesc(pfuncdesc);
+ for (i = 0; i < lpcName; i++)
+ SysFreeStringW(rgbstrNames[i]);
+ lpcName = 0;
+ }
+
+
+ // Create ITypeInfoW & IDispatchW Interfaces
+ //
+ IfFailGo(CreateDispTypeInfo(idata, LOCALE_USER_DEFAULT, &ptinfo),
+ LError1);
+ IfFailGo(CStdDisp::Create(this, m_this, ptinfo,
+ (IUnknown FAR* FAR*) &m_pAnsiDispatch),
+ LError3);
+ hresult = NOERROR;
+
+LError3:
+ ptinfo->Release();
+
+LError2:
+ for (i = 0; i < lpcName; i++)
+ SysFreeStringW(rgbstrNames[i]);
+
+LError1:
+ ptinfoW2->ReleaseTypeAttr(ptattr);
+
+LError0:
+ ptinfoW2->Release();
+ pdisp->Release();
+ return hresult;
+}
+
+STDMETHODIMP
+CDualStdDisp::CreateUnicodeTable(void)
+{
+ HRESULT hresult;
+
+ IDispatch FAR* pdisp;
+ ITypeInfo FAR* ptinfo, FAR* ptinfo2;
+ ITypeInfoW FAR* ptinfoW;
+
+ TYPEATTR FAR* ptattr;
+ FUNCDESC *pfuncdesc;
+ unsigned int i, count, funcIndex, paramIndex;
+
+ const unsigned int rgbstrMax = 16; //REVIEW: Is this large enough?
+ BSTR FAR rgbstrNames[rgbstrMax];
+ unsigned int lpcName;
+
+ WINTERFACEDATA FAR *widata;
+ WMETHODDATA FAR* pmdata;
+
+
+ // TypeInfo must exists to create UnicodeTable
+ //
+ if (m_pAnsiDispatch == NULL ||
+ m_pAnsiDispatch->QueryInterface(IID_IDispatch,
+ (void FAR* FAR*) &pdisp) != NOERROR)
+ return RESULT(E_FAIL);
+ if (pdisp->GetTypeInfoCount(&count) != NOERROR ||
+ count == 0 ||
+ pdisp->GetTypeInfo(0, LOCALE_USER_DEFAULT, &ptinfo) != NOERROR) {
+ pdisp->Release();
+ return RESULT(E_FAIL);
+ }
+
+
+ // Query TypeInfo for members & generate equivalent
+ // WINTERFACEDATA UnicodeTable
+ //
+ IfFailGo(ptinfo->GetRefTypeInfo(0, &ptinfo2), LError0);
+ ptinfo->Release();
+ IfFailGo(ptinfo2->GetTypeAttr(&ptattr), LError0);
+ widata = new FAR WINTERFACEDATA;
+ widata->cMembers = ptattr->cFuncs;
+ widata->pmethdata = new FAR WMETHODDATA[widata->cMembers];
+ for (funcIndex = 0; funcIndex < widata->cMembers; funcIndex++) {
+ IfFailGo(ptinfo2->GetFuncDesc(funcIndex, &pfuncdesc), LError1);
+ IfFailGo(ptinfo2->GetNames(pfuncdesc->memid,
+ rgbstrNames,
+ rgbstrMax,
+ &lpcName),
+ LError1);
+ if(lpcName != (unsigned int) pfuncdesc->cParams+1) goto LError2;
+
+ // Fill out methoddata info
+ //
+ pmdata = &(widata->pmethdata[funcIndex]);
+ pmdata->szName = SysStringAtoW(rgbstrNames[0], CP_ACP);
+ pmdata->cArgs = pfuncdesc->cParams;
+ pmdata->ppdata = pmdata->cArgs ?
+ new FAR WPARAMDATA[pmdata->cArgs] : NULL;
+ pmdata->dispid = pfuncdesc->memid;
+ pmdata->iMeth = pfuncdesc->oVft / sizeof(void FAR*);
+ pmdata->cc = pfuncdesc->callconv;
+ pmdata->vtReturn = pfuncdesc->elemdescFunc.tdesc.vt;
+ for (paramIndex = 0; paramIndex < pmdata->cArgs; paramIndex++) {
+ pmdata->ppdata[paramIndex].szName =
+ SysStringAtoW(rgbstrNames[paramIndex+1], CP_ACP);
+ pmdata->ppdata[paramIndex].vt =
+ pfuncdesc->lprgelemdescParam[paramIndex].tdesc.vt;
+ }
+ switch(pfuncdesc->invkind) {
+ case INVOKE_FUNC:
+ pmdata->wFlags = DISPATCH_METHOD;
+ break;
+ case INVOKE_PROPERTYGET:
+ pmdata->wFlags = DISPATCH_PROPERTYGET;
+ break;
+ case INVOKE_PROPERTYPUT:
+ pmdata->wFlags = DISPATCH_PROPERTYPUT;
+ break;
+ case INVOKE_PROPERTYPUTREF:
+ pmdata->wFlags = DISPATCH_PROPERTYPUTREF;
+ break;
+ }
+
+ // Free temporary info
+ //
+ ptinfo2->ReleaseFuncDesc(pfuncdesc);
+ for (i = 0; i < lpcName; i++)
+ SysFreeString(rgbstrNames[i]);
+ lpcName = 0;
+ }
+
+
+ // Create ITypeInfoW & IDispatchW Interfaces
+ //
+ IfFailGo(CreateDispTypeInfoW(widata, LOCALE_USER_DEFAULT, &ptinfoW),
+ LError1);
+ IfFailGo(CStdDispW::Create(this, m_this, ptinfoW,
+ (IUnknown FAR* FAR*) &m_pUnicodeDispatch),
+ LError3);
+ hresult = NOERROR;
+
+LError3:
+ ptinfoW->Release();
+
+LError2:
+ for (i = 0; i < lpcName; i++)
+ SysFreeString(rgbstrNames[i]);
+
+LError1:
+ ptinfo2->ReleaseTypeAttr(ptattr);
+
+LError0:
+ ptinfo2->Release();
+ pdisp->Release();
+ return hresult;
+}
+
+#endif /* } */
+
diff --git a/private/oleauto/src/dispatch/stddisp.h b/private/oleauto/src/dispatch/stddisp.h
new file mode 100644
index 000000000..d77a6f4c5
--- /dev/null
+++ b/private/oleauto/src/dispatch/stddisp.h
@@ -0,0 +1,325 @@
+/***
+*stddisp.h
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file declares the CStdDisp class. This 'standard' IDispatch
+* implementation that supports a single locale, and a single exposed
+* programmability interface (identified by IID_NULL), described by a
+* single TypeInfo.
+*
+*
+* Sample usage:
+*
+* class CMyObj : public IUnknown {
+* public:
+*
+* STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+* STDMETHOD(AddRef)(void);
+* STDMETHOD(Release)(void);
+*
+* <introduced methods described by a TypeInfo>
+*
+* private:
+* unsigned long m_refs;
+* IUnknown FAR* m_punkDisp;
+* };
+*
+* CMyObj::Create()
+* {
+* CMyObj FAR* pme;
+* ITypeInfo FAR* ptinfo;
+* IUnknown FAR* punkDisp;
+*
+* if((pme = new FAR CMyObj()) == NULL){
+* hresult = ResultFromScode(E_OUTOFMEMORY);
+* goto LError0;
+* }
+*
+* if((hresult = CreateDispTypeInfo(..., &ptinfo)) != NOERROR)
+* goto LError1;
+*
+* // create 'standard' IDispatch implementation, and initialize
+* // with this instances 'this' pointer, the desired locale, and
+* // the TypeInfo that describes the exposed interface.
+* //
+* if((hresult = CreateStdDispatch(
+* NULL, pme, LCID_USER_DEFAULT, ptinfo, &punkDisp)) != NOERROR)
+* return hresult;
+*
+* m_punkDisp = punkDisp;
+*
+* return pme;
+*
+* LError1:;
+* delete pme;
+*
+* LError0:;
+* return hresult;
+* }
+*
+* CMyObj::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+* {
+* if(riid == IID_IUnknown){
+* *ppv = this;
+* }else if(riid == IID_IDispatch){
+* return m_punkDisp->QueryInterface(riid, ppv);
+* }else
+* return ResultFromScode(E_NOINTERFACE);
+* return NOERROR;
+* }
+*
+* CMyObj::AddRef()
+* {
+* return ++m_refs;
+* }
+*
+* CMyObj::Release()
+* {
+* if(--m_refs == 0){
+* m_punkDisp->Release();
+* delete this;
+* return 0;
+* }
+* return m_refs;
+* }
+*
+*
+*Revision History:
+*
+* [00] 09-Feb-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+// forward declarations
+class FAR CStdDisp;
+
+
+STDAPI
+CreateStdDisp(
+ IUnknown FAR* punkOuter,
+ void FAR* pvThis,
+ ITypeInfo FAR* ptinfo,
+ IUnknown FAR* FAR* punkStdDisp);
+
+
+// "private" IUnknown implementation
+class FAR CStdDispUnkImpl : public IUnknown
+{
+public:
+ CStdDispUnkImpl(CStdDisp FAR* pstddisp);
+
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppvObj);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+private:
+ CStdDisp FAR* m_pstddisp;
+};
+
+
+class FAR CStdDisp : public IDispatch
+{
+public:
+ static HRESULT Create(
+ IUnknown FAR* punkOuter,
+ void FAR* pvThis,
+ ITypeInfo FAR* ptinfo,
+ IUnknown FAR* FAR* punkStdDisp);
+
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppvObj);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ STDMETHOD(GetTypeInfoCount)(unsigned int FAR* pctinfo);
+
+ STDMETHOD(GetTypeInfo)(
+ unsigned int itinfo,
+ LCID lcid,
+ ITypeInfo FAR* FAR* pptinfo);
+
+ STDMETHOD(GetIDsOfNames)(
+ REFIID riid,
+ OLECHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ LCID lcid,
+ DISPID FAR* rgdispid);
+
+ STDMETHOD(Invoke)(
+ DISPID dispidMember,
+ REFIID riid,
+ LCID lcid,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pdispparams,
+ VARIANT FAR* pvarResult,
+ EXCEPINFO FAR* pexcepinfo,
+ unsigned int FAR* puArgErr);
+
+ CStdDisp();
+
+ friend CStdDispUnkImpl;
+ CStdDispUnkImpl m_unk; // 'private' unknown
+
+private:
+
+ unsigned long m_refs;
+ IUnknown FAR* m_punk; // pointer to the controlling unknown
+
+ // 'this' ptr of the interface we are dispatching on
+ void FAR* m_this;
+
+ // typeinfo describing the interface we are dispatching on
+ ITypeInfo FAR* m_ptinfo;
+};
+
+
+#if OE_WIN32 && 0 /* { */
+
+// forward declarations
+class FAR CStdDispW;
+
+
+STDAPI
+CreateStdDispW(
+ IUnknown FAR* punkOuter,
+ void FAR* pvThis,
+ ITypeInfoW FAR* ptinfo,
+ IUnknown FAR* FAR* punkStdDispW);
+
+
+// "private" IUnknown implementation
+class FAR CStdDispWUnkImpl : public IUnknown
+{
+public:
+ CStdDispWUnkImpl(CStdDispW FAR* pstddisp);
+
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppvObj);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+private:
+ CStdDispW FAR* m_pstddisp;
+};
+
+
+class FAR CStdDispW : public IDispatchW
+{
+public:
+ static HRESULT Create(
+ IUnknown FAR* punkOuter,
+ void FAR* pvThis,
+ ITypeInfoW FAR* ptinfo,
+ IUnknown FAR* FAR* punkStdDispW);
+
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppvObj);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ STDMETHOD(GetTypeInfoCount)(unsigned int FAR* pctinfo);
+
+ STDMETHOD(GetTypeInfo)(
+ unsigned int itinfo,
+ LCID lcid,
+ ITypeInfoW FAR* FAR* pptinfo);
+
+ STDMETHOD(GetIDsOfNames)(
+ REFIID riid,
+ WCHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ LCID lcid,
+ DISPID FAR* rgdispid);
+
+ STDMETHOD(Invoke)(
+ DISPID dispidMember,
+ REFIID riid,
+ LCID lcid,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pdispparams,
+ VARIANT FAR* pvarResult,
+ WEXCEPINFO FAR* pexcepinfo,
+ unsigned int FAR* puArgErr);
+
+ CStdDispW();
+
+ friend CStdDispWUnkImpl;
+ CStdDispWUnkImpl m_unk; // 'private' unknown
+
+private:
+
+ unsigned long m_refs;
+ IUnknown FAR* m_punk; // pointer to the controlling unknown
+
+ // 'this' ptr of the interface we are dispatching on
+ void FAR* m_this;
+
+ // typeinfo describing the interface we are dispatching on
+ ITypeInfoW FAR* m_ptinfo;
+};
+
+
+// Forward Declaration
+class FAR CDualStdDisp;
+
+
+// "private" IUnknown implementation
+class FAR CDualStdDispUnkImpl : public IUnknown
+{
+public:
+ CDualStdDispUnkImpl(CDualStdDisp FAR* pstddisp);
+
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppvObj);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+private:
+ CDualStdDisp FAR* m_pstddisp;
+};
+
+
+class CDualStdDisp : public IUnknown {
+
+ public:
+
+ static HRESULT Create(
+ IUnknown FAR* punkOuter,
+ void FAR* pvThis,
+ ITypeInfo FAR* ptinfo,
+ IUnknown FAR* FAR* punkStdDisp);
+
+ static HRESULT Create(
+ IUnknown FAR* punkOuter,
+ void FAR* pvThis,
+ ITypeInfoW FAR* ptinfo,
+ IUnknown FAR* FAR* punkStdDispW);
+
+ // IUnknown Methods
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppvObj);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ friend CDualStdDispUnkImpl;
+ CDualStdDispUnkImpl m_unk; // 'private' unknown
+
+ protected:
+
+ CDualStdDisp();
+ virtual ~CDualStdDisp() {}
+
+ STDMETHOD(CreateUnicodeTable)(void);
+ STDMETHOD(CreateAnsiTable)(void);
+
+ private:
+
+ unsigned long m_refs;
+ IUnknown FAR* m_punk; // pointer to the controlling unknown
+ void FAR* m_this;
+
+ IUnknown FAR* m_pAnsiDispatch;
+ IUnknown FAR* m_pUnicodeDispatch;
+};
+
+#endif /* } */
diff --git a/private/oleauto/src/dispatch/string.c b/private/oleauto/src/dispatch/string.c
new file mode 100644
index 000000000..c207fd137
--- /dev/null
+++ b/private/oleauto/src/dispatch/string.c
@@ -0,0 +1,530 @@
+/***
+*string.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file contains the string comparrison routines for the
+* Ole2 NLS API. These routines support the implementation of
+* CompareStringA.
+*
+*
+*Revision History:
+*
+* [00] 08-30-93 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+ASSERTDATA
+
+#define HAVE_DW 0x01
+#define HAVE_CW 0x02
+#define HAVE_SW 0x04
+
+extern STRINFO FAR* g_pstrinfo;
+
+// Optimized version of CompareStringA -
+//
+// This version assumes,
+// - The locale has no compressions
+// - Both strings are zero terminated
+// - We are *not* ignoring symbols
+// - This locale does not have reversed diacritic weights
+//
+int
+ZeroTermNoIgnoreSym(
+ unsigned long dwFlags,
+ const char FAR* pch1,
+ const char FAR* pch2)
+{
+ BYTE ch;
+ int dw, cw, sw;
+ int fEnd, fRedo;
+ WORD wHave;
+ WORD w1, w2;
+ WORD wEx1, wEx2;
+ WORD FAR* prgw;
+ WORD aw1, aw2;
+ WORD dw1, dw2;
+ WORD cw1, cw2;
+ WORD sw1, sw2;
+ EXPANSION FAR* pexp;
+
+ ASSERT(g_pstrinfo->fRevDW == 0);
+ ASSERT(g_pstrinfo->prgdig == NULL);
+ ASSERT((dwFlags & NORM_IGNORESYMBOLS) == 0);
+
+ wHave = 0;
+
+ sw1 = 0;
+ sw2 = 0;
+
+ wEx1 = 0;
+ wEx2 = 0;
+
+ fEnd = 0;
+ fRedo = 0;
+
+ prgw = g_pstrinfo->prgwSort; // sort weight table
+
+ while(1){
+
+ // get the next weight from string #1
+ if(wEx1){ // we have the second weight of an expansion
+ w1 = wEx1;
+ wEx1 = 0;
+ }else{
+ if((ch = *pch1) == '\0'){
+ fEnd |= 0x1;
+ }else{
+ ++pch1;
+ w1 = prgw[(BYTE)ch];
+ }
+ }
+
+ // get the next weight from string #2
+ if(wEx2){ // we have the second weight of an expansion
+ w2 = wEx2;
+ wEx2 = 0;
+ }else{
+ if((ch = *pch2) == '\0'){
+ fEnd |= 0x2;
+ }else{
+ ++pch2;
+ w2 = prgw[(BYTE)ch];
+ }
+ }
+
+Lredo_chkend:;
+ if(fEnd){ // reached the end of one of our strings
+ if(fEnd & 0x1){
+ if(fEnd & 0x2) // reached end of both at the same time
+ goto Lend;
+ goto Lscan2;
+ }else{
+ ASSERT(fEnd&0x2);
+ goto Lscan1;
+ }
+ }
+
+ // Note: we can short circuit here if the entire weights are
+ // equal, because we know the locale has no compressions
+ //
+ if(w1 != w2){
+
+ aw1 = w1 & AWMASK;
+ aw2 = w2 & AWMASK;
+
+ // handle special cases for w1
+#if 0
+ if(aw1 >= AW_UNSORTABLE && aw1 <= AW_MAXSW)
+#else //0
+ if(aw1 == AW_UNSORTABLE || w1 & SPECIALBIT)
+#endif //0
+ {
+ sw1 = aw1;
+ fRedo |= 0x1;
+ }
+
+#if 0
+ if(aw2 >= AW_UNSORTABLE && aw2 <= AW_MAXSW)
+#else //0
+ if(aw2 == AW_UNSORTABLE || w2 & SPECIALBIT)
+#endif //0
+ {
+ sw2 = aw2;
+ fRedo |= 0x2;
+ }
+
+ if(fRedo){
+ if(fRedo & 0x1){
+ if((ch = *pch1) == '\0'){
+ fEnd |= 0x1;
+ }else{
+ ++pch1;
+ w1 = prgw[(BYTE)ch];
+ }
+ }
+ if(fRedo & 0x2){
+ if((ch = *pch2) == '\0'){
+ fEnd |= 0x2;
+ }else{
+ ++pch2;
+ w2 = prgw[(BYTE)ch];
+ }
+ }
+ if((wHave & HAVE_SW) == 0){
+ if(sw1 != sw2){
+ sw = (sw1 < sw2) ? 1 : 3;
+ wHave |= HAVE_SW;
+ }
+ sw1 = sw2 = 0;
+ }
+ fRedo = 0;
+ goto Lredo_chkend; // may have reached the end-of-str
+ }
+
+ ASSERT(aw1 != AW_DONTUSE && aw1 != AW_DIGRAPH);
+ if(aw1 == AW_EXPANSION){
+ pexp = &g_pstrinfo->prgexp[(w1 >> 8) & 0xFF];
+ w1 = pexp->w1;
+ wEx1 = pexp->w2;
+ aw1 = w1 & AWMASK;
+ }
+
+ ASSERT(aw2 != AW_DONTUSE && aw2 != AW_DIGRAPH);
+ if(aw2 == AW_EXPANSION){
+ pexp = &g_pstrinfo->prgexp[(w2 >> 8) & 0xFF];
+ w2 = pexp->w1;
+ wEx2 = pexp->w2;
+ aw2 = w2 & AWMASK;
+ }
+
+ if(aw1 != aw2)
+ return (aw1 < aw2) ? 1 : 3;
+
+ if((wHave & HAVE_DW) == 0){
+ dw1 = (w1 & DWMASK);
+ dw2 = (w2 & DWMASK);
+ if(dw1 != dw2){
+ dw = (dw1 < dw2) ? 1 : 3;
+ wHave |= HAVE_DW;
+ }
+ }
+
+ if((wHave & HAVE_CW) == 0){
+ cw1 = (w1 & CWMASK);
+ cw2 = (w2 & CWMASK);
+ if(cw1 != cw2){
+ cw = (cw1 < cw2) ? 1 : 3;
+ wHave |= HAVE_CW;
+ }
+ }
+ }
+ }
+
+
+#define IGNORE_WEIGHT(W) \
+ (((W) & AWMASK) == AW_UNSORTABLE)
+
+Lscan1:;
+ // Is there anything in the remainder of string #1 that we shouldn't ignore?
+ if(!IGNORE_WEIGHT(w1) || wEx1)
+ return 3;
+ while((ch = *pch1) != '\0'){
+ ++pch1;
+ w1 = prgw[(BYTE)ch];
+ if(!IGNORE_WEIGHT(w1))
+ return 3;
+ }
+ goto Lend;
+
+Lscan2:;
+ // Is there anything in the remainder of string #2 that we shouldn't ignore?
+ if(!IGNORE_WEIGHT(w2) || wEx2)
+ return 1;
+ while((ch = *pch2) != '\0'){
+ ++pch2;
+ w2 = prgw[(BYTE)ch];
+ if(!IGNORE_WEIGHT(w2))
+ return 1;
+ }
+ goto Lend;
+
+#undef IGNORE_WEIGHT
+
+Lend:;
+
+ // reached the end of both strings without a decision
+ if((wHave & HAVE_DW) != 0 && (dwFlags & NORM_IGNORENONSPACE) == 0)
+ return dw;
+
+ if((wHave & HAVE_CW) != 0 && (dwFlags & NORM_IGNORECASE) == 0)
+ return cw;
+
+ if((wHave & HAVE_SW) != 0)
+ return sw;
+
+ return 2; // they're the same
+}
+
+
+// Default - handles all cases
+int
+DefCompareStringA(
+ unsigned long dwFlags,
+ const char FAR* pch1, int cch1,
+ const char FAR* pch2, int cch2)
+{
+ int dw, cw, sw;
+ int fEnd, fRedo;
+ WORD wHave;
+ WORD FAR* prgw;
+ WORD wSymbolBit;
+ WORD w1, w2;
+ WORD wEx1, wEx2;
+ WORD aw1, aw2;
+ WORD dw1, dw2;
+ WORD cw1, cw2;
+ WORD sw1, sw2;
+ EXPANSION FAR* pexp;
+ DIGRAPH FAR* pdig, FAR* pdigEnd;
+ const char FAR* pchEnd1, FAR* pchEnd2;
+
+ ASSERT(cch1 >= 0 && cch2 >= 0); // lengths must be computed by caller
+
+ wHave = 0;
+
+ sw1 = 0;
+ sw2 = 0;
+
+ wEx1 = 0;
+ wEx2 = 0;
+
+ wSymbolBit = (dwFlags & NORM_IGNORESYMBOLS) ? SYMBOLBIT : 0;
+
+ fEnd = 0;
+ fRedo = 0;
+
+ pchEnd1 = &pch1[cch1];
+ pchEnd2 = &pch2[cch2];
+
+ prgw = g_pstrinfo->prgwSort; // sort weight table
+
+ while(1){
+
+ // get the next weight from string #1
+ if(wEx1){ // we have the second weight of an expansion
+ w1 = wEx1;
+ wEx1 = 0;
+ }else{
+ if(pch1 == pchEnd1){
+ fEnd |= 0x1;
+ }else{
+ w1 = prgw[(BYTE)*pch1++];
+ }
+ }
+
+ // get the next weight from string #2
+ if(wEx2){ // we have the second weight of an expansion
+ w2 = wEx2;
+ wEx2 = 0;
+ }else{
+ if(pch2 == pchEnd2){
+ fEnd |= 0x2;
+ }else{
+ w2 = prgw[(BYTE)*pch2++];
+ }
+ }
+
+Lredo_chkend:;
+ if(fEnd){ // reached the end of one of our strings
+ if(fEnd & 0x1){
+ if(fEnd & 0x2) // reached end of both at the same time
+ goto Lend;
+ goto Lscan2;
+ }else{
+ ASSERT(fEnd&0x2);
+ goto Lscan1;
+ }
+ }
+
+ //if(w1 != w2)
+ {
+
+ aw1 = w1 & AWMASK;
+ aw2 = w2 & AWMASK;
+
+ //if(aw1 != aw2)
+ {
+
+ // handle special cases for w1
+#if 0
+ if(aw1 >= AW_UNSORTABLE && aw1 <= AW_MAXSW)
+#else //0
+ if(aw1 == AW_UNSORTABLE || w1 & SPECIALBIT)
+#endif //0
+ {
+ if((w1 & wSymbolBit) == 0)
+ sw1 = aw1;
+ fRedo |= 0x1;
+ }else if(w1 & wSymbolBit){
+ fRedo |= 0x1;
+ }
+
+#if 0
+ if(aw2 >= AW_UNSORTABLE && aw2 <= AW_MAXSW)
+#else //0
+ if(aw2 == AW_UNSORTABLE || w2 & SPECIALBIT)
+#endif //0
+ {
+ if((w2 & wSymbolBit) == 0)
+ sw2 = aw2;
+ fRedo |= 0x2;
+ }else if(w2 & wSymbolBit){
+ fRedo |= 0x2;
+ }
+
+ if(fRedo){
+ if(fRedo & 0x1){
+ if(pch1 == pchEnd1){
+ fEnd |= 0x1;
+ }else{
+ w1 = prgw[(BYTE)*pch1++];
+ }
+ }
+ if(fRedo & 0x2){
+ if(pch2 == pchEnd2){
+ fEnd |= 0x2;
+ }else{
+ w2 = prgw[(BYTE)*pch2++];
+ }
+ }
+ if((wHave & HAVE_SW) == 0){
+ if(sw1 != sw2){
+ sw = (sw1 < sw2) ? 1 : 3;
+ wHave |= HAVE_SW;
+ }
+ sw1 = sw2 = 0;
+ }
+ fRedo = 0;
+ goto Lredo_chkend; // may have reached the end-of-str
+ }
+
+ switch(aw1){
+#ifdef _DEBUG
+ case AW_DONTUSE:
+ ASSERT(UNREACHED);
+ break;
+#endif
+ case AW_EXPANSION:
+ pexp = &g_pstrinfo->prgexp[(w1 >> 8) & 0xFF];
+ w1 = pexp->w1;
+ wEx1 = pexp->w2;
+ aw1 = w1 & AWMASK;
+ break;
+ case AW_DIGRAPH:
+ pdig = &g_pstrinfo->prgdig[(w1 >> 8) & 0xFF];
+ w1 = pdig->w; // if its not a digraph, we use will this
+ // it cant be a digraph if were at the end of the string
+ if(pch1 < pchEnd1){
+ BYTE chNext = *pch1;
+ pdigEnd = pdig + D_ENTRY(pdig);
+ for(++pdig; pdig <= pdigEnd; ++pdig){
+ if(D_CH(pdig) == chNext){
+ ++pch1; // consume the second character
+ w1 = pdig->w; // use the digraph weight
+ break;
+ }
+ }
+ }
+ aw1 = w1 & AWMASK;
+ break;
+ }
+
+ switch(aw2){
+#ifdef _DEBUG
+ case AW_DONTUSE:
+ ASSERT(UNREACHED);
+ break;
+#endif
+ case AW_EXPANSION:
+ pexp = &g_pstrinfo->prgexp[(w2 >> 8) & 0xFF];
+ w2 = pexp->w1;
+ wEx2 = pexp->w2;
+ aw2 = w2 & AWMASK;
+ break;
+ case AW_DIGRAPH:
+ pdig = &g_pstrinfo->prgdig[(w2 >> 8) & 0xFF];
+ w2 = pdig->w; // if its not a digraph, we use will this
+ // it cant be a digraph if were at the end of the string
+ if(pch2 < pchEnd2){
+ BYTE chNext = *pch2;
+ pdigEnd = pdig + D_ENTRY(pdig);
+ for(++pdig; pdig <= pdigEnd; ++pdig){
+ if(D_CH(pdig) == chNext){
+ ++pch2; // consume the second character
+ w2 = pdig->w; // use the digraph weight
+ break;
+ }
+ }
+ }
+ aw2 = w2 & AWMASK;
+ break;
+ }
+
+ if(aw1 != aw2)
+ return (aw1 < aw2) ? 1 : 3;
+ }
+
+ // If were in a reverse diacritic locale, then we
+ // remember the last DW difference we see, not the first.
+ if((wHave & HAVE_DW) == 0 || g_pstrinfo->fRevDW){
+ dw1 = (w1 & DWMASK);
+ dw2 = (w2 & DWMASK);
+ if(dw1 != dw2){
+ dw = (dw1 < dw2) ? 1 : 3;
+ wHave |= HAVE_DW;
+ }
+ }
+
+ if((wHave & HAVE_CW) == 0){
+ cw1 = (w1 & CWMASK);
+ cw2 = (w2 & CWMASK);
+ if(cw1 != cw2){
+ cw = (cw1 < cw2) ? 1 : 3;
+ wHave |= HAVE_CW;
+ }
+ }
+
+ } /* w1 != w2 */
+ }
+
+#define IGNORE_WEIGHT(W) \
+ (((W) & AWMASK) == AW_UNSORTABLE || ((W) & wSymbolBit))
+
+Lscan1:;
+ // Is there anything in the remainder of string #1 that we shouldn't ignore?
+ if(!IGNORE_WEIGHT(w1) || wEx1)
+ return 3;
+ while(pch1 < pchEnd1){
+ w1 = prgw[(BYTE)*pch1++];
+ if(!IGNORE_WEIGHT(w1))
+ return 3;
+ }
+ goto Lend;
+
+Lscan2:;
+ // Is there anything in the remainder of string #2 that we shouldn't ignore?
+ if(!IGNORE_WEIGHT(w2) || wEx2)
+ return 1;
+ while(pch2 < pchEnd2){
+ w2 = prgw[(BYTE)*pch2++];
+ if(!IGNORE_WEIGHT(w2))
+ return 1;
+ }
+ goto Lend;
+
+#undef IGNORE_WEIGHT
+
+Lend:;
+
+ // reached the end of both strings without a decision
+ if((wHave & HAVE_DW) != 0 && (dwFlags & NORM_IGNORENONSPACE) == 0)
+ return dw;
+
+ if((wHave & HAVE_CW) != 0 && (dwFlags & NORM_IGNORECASE) == 0)
+ return cw;
+
+ if((wHave & HAVE_SW) != 0 && (dwFlags & NORM_IGNORESYMBOLS) == 0)
+ return sw;
+
+ return 2; // they're the same
+}
+
diff --git a/private/oleauto/src/dispatch/tables.c b/private/oleauto/src/dispatch/tables.c
new file mode 100644
index 000000000..1276697f1
--- /dev/null
+++ b/private/oleauto/src/dispatch/tables.c
@@ -0,0 +1,95 @@
+/***
+*tables.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Thie file contains the tables that describe the marshaling information
+* for the various TypeInfo related structures.
+*
+*Revision History:
+*
+* [00] 08-Mar-93 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "dispmrsh.h"
+
+
+HRESULT TypedescReadOrWrite(IStream FAR*, BOOL, void FAR*);
+
+FIELDDESC NEAR g_rgfdescIdldesc[] = {
+ FIELDDAT(IDLDESC, FT_WORD, wIDLFlags, NULL)
+#if defined(WIN16)
+ // this field is always zero. We mis-type it here as a LONG instead of
+ // a BSTR for 16/32 interop
+ , FIELDDAT(IDLDESC, FT_LONG, bstrIDLInfo, NULL)
+#else
+ , FIELDDAT(IDLDESC, FT_LONG, dwReserved, NULL)
+#endif
+ , FIELDEND()
+};
+
+FIELDDESC NEAR g_rgfdescElemdesc[] = {
+ FIELDDAT(ELEMDESC, FT_SPECIAL, tdesc, TypedescReadOrWrite)
+ , FIELDDAT(ELEMDESC, FT_STRUCT, idldesc, g_rgfdescIdldesc)
+ , FIELDEND()
+};
+
+// Note: be careful with the ordering of the following table. I
+// moved the entry for 'idldescType' to the front of the table to
+// work around a C7/C8 compiler bug that was generating an incorrect
+// fixup with it was in the table in its position as declared in
+// the TYPEATTR struct.
+
+FIELDDESC NEAR g_rgfdescTypeattr[] = {
+ FIELDDAT(TYPEATTR, FT_STRUCT, idldescType, g_rgfdescIdldesc)
+ , FIELDDAT(TYPEATTR, FT_ENUM, typekind, NULL)
+ , FIELDDAT(TYPEATTR, FT_WORD, wMajorVerNum, NULL)
+ , FIELDDAT(TYPEATTR, FT_WORD, wMinorVerNum, NULL)
+ , FIELDDAT(TYPEATTR, FT_LONG, lcid, NULL)
+ , FIELDDAT(TYPEATTR, FT_WORD, cFuncs, NULL)
+ , FIELDDAT(TYPEATTR, FT_WORD, cVars, NULL)
+ , FIELDDAT(TYPEATTR, FT_WORD, cImplTypes, NULL)
+ , FIELDDAT(TYPEATTR, FT_MBYTE, guid, NULL)
+ , FIELDDAT(TYPEATTR, FT_WORD, wTypeFlags, NULL)
+ , FIELDDAT(TYPEATTR, FT_WORD, cbAlignment, NULL)
+ , FIELDDAT(TYPEATTR, FT_LONG, cbSizeInstance, NULL)
+ , FIELDDAT(TYPEATTR, FT_WORD, cbSizeVft, NULL)
+ , FIELDDAT(TYPEATTR, FT_LONG, memidConstructor,NULL)
+ , FIELDDAT(TYPEATTR, FT_LONG, memidDestructor, NULL)
+ , FIELDEND()
+
+ /* NOTE: tdescAlias is read by hand, if typekind == TKIND_ALIAS */
+};
+
+FIELDDESC NEAR g_rgfdescFuncdesc[] = {
+ FIELDDAT(FUNCDESC, FT_STRUCT, elemdescFunc, g_rgfdescElemdesc)
+ , FIELDDAT(FUNCDESC, FT_LONG, memid, NULL)
+ , FIELDDAT(FUNCDESC, FT_ENUM, funckind, NULL)
+ , FIELDDAT(FUNCDESC, FT_ENUM, invkind, NULL)
+ , FIELDDAT(FUNCDESC, FT_ENUM, callconv, NULL)
+ , FIELDDAT(FUNCDESC, FT_SHORT, cParams, NULL)
+ , FIELDDAT(FUNCDESC, FT_SHORT, cParamsOpt, NULL)
+ , FIELDDAT(FUNCDESC, FT_SHORT, oVft, NULL)
+ , FIELDDAT(FUNCDESC, FT_WORD, wFuncFlags, NULL)
+ , FIELDEND()
+
+ /* NOTE: lprgelemdescParams is read by hand */
+};
+
+FIELDDESC NEAR g_rgfdescVardesc[] = {
+ FIELDDAT(VARDESC, FT_LONG, memid, NULL)
+ , FIELDDAT(VARDESC, FT_ENUM, varkind, NULL)
+ , FIELDDAT(VARDESC, FT_STRUCT, elemdescVar, g_rgfdescElemdesc)
+ , FIELDDAT(VARDESC, FT_WORD, wVarFlags, NULL)
+ , FIELDEND()
+
+ /* NOTE: the VARDESC union is read by hand */
+};
+
+
diff --git a/private/oleauto/src/dispatch/tcprox.cpp b/private/oleauto/src/dispatch/tcprox.cpp
new file mode 100644
index 000000000..9007030d1
--- /dev/null
+++ b/private/oleauto/src/dispatch/tcprox.cpp
@@ -0,0 +1,440 @@
+/***
+*tcprox.cpp
+*
+* Copyright (C) 1992-94, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This module implements the ITypeComp proxy class.
+*
+*Revision History:
+*
+* [00] 13-Jun-94 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#ifndef WIN32
+#include <cobjps.h>
+#endif //!WIN32
+
+#include "dispmrsh.h"
+#include "tcps.h"
+#include "tips.h"
+
+ASSERTDATA
+
+
+CProxTypeComp::CProxTypeComp(IUnknown FAR* punkOuter)
+ : m_unk(this), m_proxy(this), m_tcomp(this)
+{
+ if(punkOuter == NULL)
+ punkOuter = &m_unk;
+ m_punkOuter = punkOuter;
+}
+
+IUnknown FAR*
+CProxTypeComp::Create(IUnknown FAR* punkOuter)
+{
+ CProxTypeComp FAR* pproxtcomp;
+
+ if((pproxtcomp = new FAR CProxTypeComp(punkOuter)) != NULL){
+ pproxtcomp->m_refs = 1;
+ return &pproxtcomp->m_unk;
+ }
+ return NULL;
+}
+
+
+//---------------------------------------------------------------------
+// ITypeComp proxy class' IUnknown implementation
+//---------------------------------------------------------------------
+
+CPTCompUnkImpl::CPTCompUnkImpl(CProxTypeComp FAR* pproxtcomp)
+{
+ m_pproxtcomp = pproxtcomp;
+}
+
+STDMETHODIMP
+CPTCompUnkImpl::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ *ppv = NULL;
+ if(IsEqualIID(riid, IID_IUnknown)){
+ *ppv = (void FAR*)&(m_pproxtcomp->m_unk);
+ }else
+ if(IsEqualIID(riid, IID_IPROXY)){
+ *ppv = (void FAR*)&(m_pproxtcomp->m_proxy);
+ }else
+ if(IsEqualIID(riid, IID_ITypeComp)){
+ *ppv = (void FAR*)&(m_pproxtcomp->m_tcomp);
+ }
+ if(*ppv == NULL)
+ return RESULT(E_NOINTERFACE);
+ ((IUnknown FAR*)*ppv)->AddRef();
+ return NOERROR;
+}
+
+STDMETHODIMP_(unsigned long)
+CPTCompUnkImpl::AddRef()
+{
+ return ++m_pproxtcomp->m_refs;
+}
+
+STDMETHODIMP_(unsigned long)
+CPTCompUnkImpl::Release()
+{
+ if(--m_pproxtcomp->m_refs==0){
+ delete m_pproxtcomp;
+ return 0;
+ }
+ return m_pproxtcomp->m_refs;
+}
+
+
+//---------------------------------------------------------------------
+// ITypeComp proxy class' IRpcProxy implementation
+//---------------------------------------------------------------------
+
+CPTCompProxImpl::CPTCompProxImpl(CProxTypeComp FAR* pproxtcomp)
+{
+ m_pproxtcomp = pproxtcomp;
+}
+
+CPTCompProxImpl::~CPTCompProxImpl()
+{
+ if(m_pproxtcomp->m_plrpc)
+ m_pproxtcomp->m_plrpc->Release();
+}
+
+STDMETHODIMP
+CPTCompProxImpl::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ return m_pproxtcomp->m_unk.QueryInterface(riid, ppv);
+}
+
+STDMETHODIMP_(unsigned long)
+CPTCompProxImpl::AddRef()
+{
+ return m_pproxtcomp->m_unk.AddRef();
+}
+
+STDMETHODIMP_(unsigned long)
+CPTCompProxImpl::Release()
+{
+ return m_pproxtcomp->m_unk.Release();
+}
+
+STDMETHODIMP
+CPTCompProxImpl::Connect(ICHANNEL FAR* plrpc)
+{
+ if(plrpc){
+ plrpc->AddRef();
+ m_pproxtcomp->m_plrpc = plrpc;
+ return m_pproxtcomp->m_tcomp.SysKind();
+ }
+ return RESULT(E_FAIL);
+}
+
+STDMETHODIMP_(void)
+CPTCompProxImpl::Disconnect()
+{
+ if(m_pproxtcomp->m_plrpc)
+ m_pproxtcomp->m_plrpc->Release();
+ m_pproxtcomp->m_plrpc = NULL;
+}
+
+
+//---------------------------------------------------------------------
+// ITypeComp proxy class' ITypeComp methods
+//---------------------------------------------------------------------
+
+CPTCompTypeCompImpl::CPTCompTypeCompImpl(CProxTypeComp FAR* pproxtcomp)
+{
+ m_pproxtcomp = pproxtcomp;
+ m_syskindStub = (SYSKIND)-1; // something invalid
+}
+
+STDMETHODIMP
+CPTCompTypeCompImpl::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ return m_pproxtcomp->m_punkOuter->QueryInterface(riid, ppv);
+}
+
+STDMETHODIMP_(unsigned long)
+CPTCompTypeCompImpl::AddRef()
+{
+ return m_pproxtcomp->m_punkOuter->AddRef();
+}
+
+STDMETHODIMP_(unsigned long)
+CPTCompTypeCompImpl::Release()
+{
+ return m_pproxtcomp->m_punkOuter->Release();
+}
+
+//
+// ITypeComp methods
+//
+
+/***
+*HRESULT CPTCompTypeCompImpl::Bind
+*Purpose:
+* Proxy implementation of ITypeComp::Bind
+*
+* Marshal out:
+* ULONG lHashVal
+* WORD wFlags
+* BSTR bstrName
+*
+* Marshal in:
+* HRESULT hresultRet
+* ULONG desckind
+* BINDPTR bindptr
+* if(desckind == DESCKIND_FUNCDESC || desckind == DESCKIND_VARDESC)
+* ITypeInfo* ptinfo
+*
+*Entry:
+* szName =
+* lHashVal =
+* wFlags =
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDMETHODIMP
+CPTCompTypeCompImpl::Bind(
+ OLECHAR FAR* szName,
+ unsigned long lHashVal,
+ unsigned short wFlags,
+ ITypeInfo FAR* FAR* pptinfo,
+ DESCKIND FAR* pdesckind,
+ BINDPTR FAR* pbindptr)
+{
+ BSTR bstr;
+ IStream FAR* pstm;
+ ICHANNEL FAR* plrpc;
+ VARDESC FAR* pvardesc;
+ FUNCDESC FAR* pfuncdesc;
+ unsigned long ulDesckind;
+ HRESULT hresult, hresultRet;
+
+#if ID_DEBUG
+ if(IsBadWritePtr(pptinfo, sizeof(*pptinfo)))
+ return RESULT(E_INVALIDARG);
+ if(IsBadWritePtr(pdesckind, sizeof(*pdesckind)))
+ return RESULT(E_INVALIDARG);
+ if(IsBadWritePtr(pbindptr, sizeof(*pbindptr)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ pstm = NULL;
+ bstr = NULL;
+ pvardesc = NULL;
+ pfuncdesc = NULL;
+
+ if((plrpc = m_pproxtcomp->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPECOMP_BIND, 256, IID_ITypeComp);
+
+ IfFailGo(PUT(pstm, lHashVal), LError1);
+ IfFailGo(PUT(pstm, wFlags), LError1);
+ IfFailGo(ErrSysAllocString(szName, &bstr), LError1);
+ IfFailGo(BstrWrite(pstm, bstr, m_syskindStub), LError1);
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError2;
+
+ IfFailGo(GET(pstm, ulDesckind), LError1);
+ *pdesckind = (DESCKIND)ulDesckind;
+
+ if(ulDesckind == DESCKIND_IMPLICITAPPOBJ)
+ ulDesckind = DESCKIND_VARDESC; // it looks like a VARDESC to us
+
+ switch(ulDesckind){
+ case DESCKIND_NONE:
+ break;
+
+ case DESCKIND_VARDESC:
+ if((pvardesc = new VARDESC) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LError1;
+ }
+ IfFailGo(VardescRead(pstm, pvardesc, m_syskindStub), LError1);
+ DispUnmarshalInterface(pstm, IID_ITypeInfo, (void FAR* FAR*)pptinfo);
+ pbindptr->lpvardesc = pvardesc;
+ pvardesc = NULL;
+ break;
+
+ case DESCKIND_FUNCDESC:
+ if((pfuncdesc = new FUNCDESC) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LError1;
+ }
+ IfFailGo(FuncdescRead(pstm, pfuncdesc, m_syskindStub), LError1);
+ DispUnmarshalInterface(pstm, IID_ITypeInfo, (void FAR* FAR*)pptinfo);
+ pbindptr->lpfuncdesc = pfuncdesc;
+ pfuncdesc = NULL;
+ break;
+
+ case DESCKIND_TYPECOMP:
+ *pptinfo = NULL;
+ IfFailGo(
+ DispUnmarshalInterface(pstm, IID_ITypeComp, (void FAR* FAR*)&pbindptr->lptcomp),
+ LError1);
+ break;
+
+ default:
+ ASSERT(UNREACHED);
+ }
+
+LError2:;
+ hresult = hresultRet;
+
+LError1:;
+ if(pvardesc != NULL)
+ DoReleaseVarDesc(pvardesc);
+ if(pfuncdesc != NULL)
+ DoReleaseFuncDesc(pfuncdesc);
+ SysFreeString(bstr);
+ if(pstm != NULL)
+ pstm->Release();
+ return hresult;
+}
+
+/***
+*HRESULT CPTCompTypeCompImpl::BindType
+*Purpose:
+* Proxy implementation of ITypeComp::BindType
+*
+* Marshal out:
+* ULONG lHashVal
+* OLECHAR* szName
+*
+* Marshal in:
+* HRESULT hresultRet
+* ITypeInfo *ptinfo
+* ITypeComp *ptcomp
+*
+*Entry:
+* szName =
+* lHashVal =
+*
+*Exit:
+* return value = HRESULT
+*
+* *pptinfo =
+* *pptcompReserved =
+*
+***********************************************************************/
+STDMETHODIMP
+CPTCompTypeCompImpl::BindType(
+ OLECHAR FAR* szName,
+ unsigned long lHashVal,
+ ITypeInfo FAR* FAR* pptinfo,
+ ITypeComp FAR* FAR* pptcompReserved)
+{
+ BSTR bstr;
+ IStream FAR* pstm;
+ ICHANNEL FAR* plrpc;
+ ITypeInfo FAR* ptinfo;
+ HRESULT hresult, hresultRet;
+
+#if ID_DEBUG
+ if(IsBadWritePtr(pptinfo, sizeof(*pptinfo)))
+ return RESULT(E_INVALIDARG);
+ if(IsBadWritePtr(pptcompReserved, sizeof(*pptcompReserved)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ pstm = NULL;
+ bstr = NULL;
+ ptinfo = NULL;
+ *pptcompReserved = NULL; // set reserved out parm to NULL
+
+ if((plrpc = m_pproxtcomp->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPECOMP_BINDTYPE, 256, IID_ITypeComp);
+
+ IfFailGo(PUT(pstm, lHashVal), LError1);
+ IfFailGo(ErrSysAllocString(szName, &bstr), LError1);
+ IfFailGo(BstrWrite(pstm, bstr, m_syskindStub), LError1);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError2;
+
+ IfFailGo(DispUnmarshalInterface(pstm, IID_ITypeInfo, (void FAR* FAR*)&ptinfo), LError1);
+
+ if(pptinfo != NULL){
+ if(ptinfo != NULL)
+ ptinfo->AddRef();
+ *pptinfo = ptinfo;
+ }
+
+LError2:;
+ hresult = hresultRet;
+
+LError1:;
+ if(ptinfo != NULL)
+ ptinfo->Release();
+ SysFreeString(bstr);
+ if(pstm != NULL)
+ pstm->Release();
+ return hresult;
+}
+
+/***
+*HRESULT CPTCompTypeCompImpl::SysKind
+*Purpose:
+* Exchange syskinds between proxy and stub.
+*
+* Marshal In:
+* ULONG syskindProxy
+*
+* Marshal Out:
+* ULONG syskindStub
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CPTCompTypeCompImpl::SysKind()
+{
+ HRESULT hresult;
+ IStream FAR* pstm;
+ ICHANNEL FAR* plrpc;
+ unsigned long syskind;
+
+ if((plrpc = m_pproxtcomp->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPECOMP_SYSKIND, 32, IID_ITypeComp);
+
+ syskind = (unsigned long)SYS_CURRENT;
+ IfFailGo(PUT(pstm, syskind), LError1);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(GET(pstm, syskind), LError1);
+ m_syskindStub = (SYSKIND)syskind;
+
+LError1:
+ pstm->Release();
+ return hresult;
+}
diff --git a/private/oleauto/src/dispatch/tcps.h b/private/oleauto/src/dispatch/tcps.h
new file mode 100644
index 000000000..20b35e6f7
--- /dev/null
+++ b/private/oleauto/src/dispatch/tcps.h
@@ -0,0 +1,196 @@
+/***
+*tcps.h - ITypeComp Proxy and Stub class definitions
+*
+* Copyright (C) 1992-94, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file describes the ITypeComp Proxy and Stub classes.
+*
+* CProxTypeComp -- the ITypeComp proxy class
+* CPTCompUnkImpl - CProxTypeComp implementation of IUnknown
+* CPTCompProxImpl - CProxTypeComp implementation of IRpcProxy
+* CPTCompTypeCompImpl - CProxTypeComp implementation of ITypeComp
+*
+* CStubTypeComp -- the ITypeComp stub class
+*
+*Revision History:
+*
+* [00] 13-Jun-94 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+
+// forward declarations
+class FAR CProxTypeComp;
+class FAR CStubTypeComp;
+
+
+// ITypeComp proxy class' IUnknown implementation
+class FAR CPTCompUnkImpl : public IUnknown
+{
+public:
+ CPTCompUnkImpl(CProxTypeComp FAR* pproxtcomp);
+
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+private:
+ CProxTypeComp FAR* m_pproxtcomp;
+};
+
+
+// ITypeComp proxy class' IRpcProxy implementation
+class FAR CPTCompProxImpl : public IPROXY
+{
+public:
+ CPTCompProxImpl(CProxTypeComp FAR* pproxtcomp);
+ ~CPTCompProxImpl();
+
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ STDMETHOD(Connect)(ICHANNEL FAR* plrpc);
+ STDMETHOD_(void, Disconnect)(void);
+
+private:
+ CProxTypeComp FAR* m_pproxtcomp;
+};
+
+
+// ITypeComp
+class FAR CPTCompTypeCompImpl : public ITypeComp
+{
+public:
+ CPTCompTypeCompImpl(CProxTypeComp FAR* pproxtcomp);
+
+ // IUnknown methods
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ // ITypeComp methods
+ STDMETHOD(Bind)(
+ OLECHAR FAR* szName,
+ unsigned long lHashVal,
+ unsigned short wflags,
+ ITypeInfo FAR* FAR* pptinfo,
+ DESCKIND FAR* pdesckind,
+ BINDPTR FAR* pbindptr);
+
+ STDMETHOD(BindType)(
+ OLECHAR FAR* szName,
+ unsigned long lHashVal,
+ ITypeInfo FAR* FAR* pptinfo,
+ ITypeComp FAR* FAR* pptcomp);
+
+ HRESULT SysKind(void);
+
+private:
+ SYSKIND m_syskindStub;
+ CProxTypeComp FAR* m_pproxtcomp;
+};
+
+// ITypeComp Proxy Class
+class FAR CProxTypeComp
+{
+public:
+ static IUnknown FAR* Create(IUnknown FAR* punkOuter);
+
+private:
+ CProxTypeComp(IUnknown FAR* punkOuter);
+
+ friend CPTCompUnkImpl;
+ friend CPTCompProxImpl;
+ friend CPTCompTypeCompImpl;
+
+ CPTCompUnkImpl m_unk;
+ CPTCompProxImpl m_proxy;
+ CPTCompTypeCompImpl m_tcomp;
+
+private:
+
+ unsigned long m_refs;
+ ICHANNEL FAR* m_plrpc;
+ IUnknown FAR* m_punkOuter;
+};
+
+// ITypeComp Stub Class
+//
+class FAR CStubTypeComp : public ISTUB
+{
+public:
+ static HRESULT Create(IUnknown FAR* punkServer, ISTUB FAR* FAR* ppstub);
+
+ // IUnknown methods
+ //
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ // IRpcStub methods
+ //
+#if (OE_WIN32 || defined(WOW))
+ STDMETHOD(Connect)(IUnknown FAR* pUnk);
+ STDMETHOD_(void, Disconnect)(void);
+ STDMETHOD(Invoke)(RPCOLEMESSAGE FAR* pRpcMsg,
+ IRpcChannelBuffer FAR* pRpcChannel);
+ STDMETHOD_(IRpcStubBuffer *, IsIIDSupported)(REFIID iid);
+ STDMETHOD_(ULONG, CountRefs)(void);
+ STDMETHOD(DebugServerQueryInterface)(void FAR* FAR* ppv);
+ STDMETHOD_(void, DebugServerRelease)(void FAR* pv);
+#else
+ STDMETHOD(Connect)(IUnknown FAR* punkObject);
+ STDMETHOD_(void, Disconnect)(void);
+ STDMETHOD(Invoke)(
+ REFIID riid,
+ int imeth,
+ IStream FAR* pstm,
+ unsigned long dwDestCtx,
+ void FAR* pvDestCtx);
+#if OE_MAC
+ STDMETHOD_(unsigned long, IsIIDSupported)(REFIID riid);
+#else
+ STDMETHOD_(BOOL, IsIIDSupported)(REFIID riid);
+#endif
+ STDMETHOD_(unsigned long, CountRefs)(void);
+#endif
+
+ // introduced methods
+ HRESULT Bind(void);
+ HRESULT BindType(void);
+
+ HRESULT SysKind(void);
+
+ // helpers
+ HRESULT MarshalResult(void);
+
+private:
+ CStubTypeComp();
+ ~CStubTypeComp();
+
+ unsigned long m_refs;
+ IUnknown FAR* m_punk;
+ ITypeComp FAR* m_ptcomp;
+ IStream FAR* m_pstm;
+ SYSKIND m_syskindProxy;
+};
+
+
+// ITypeComp method indices
+//
+enum IMETH_TYPECOMP {
+ IMETH_TYPECOMP_QUERYINTERFACE = 0,
+ IMETH_TYPECOMP_ADDREF,
+ IMETH_TYPECOMP_RELEASE,
+
+ IMETH_TYPECOMP_BIND,
+ IMETH_TYPECOMP_BINDTYPE,
+
+ IMETH_TYPECOMP_SYSKIND
+};
+
diff --git a/private/oleauto/src/dispatch/tcstub.cpp b/private/oleauto/src/dispatch/tcstub.cpp
new file mode 100644
index 000000000..0a1e07856
--- /dev/null
+++ b/private/oleauto/src/dispatch/tcstub.cpp
@@ -0,0 +1,496 @@
+/***
+*tcstub.cpp
+*
+* Copyright (C) 1994, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This module implements the ITypeComp stub class.
+*
+*Revision History:
+*
+* [00] 05-Apr-94 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#ifndef WIN32
+#include <cobjps.h>
+#endif //!WIN32
+
+#include "dispmrsh.h"
+#include "tcps.h"
+#include "tips.h"
+
+ASSERTDATA
+
+
+CStubTypeComp::CStubTypeComp()
+{
+ m_refs = 0;
+ m_pstm = NULL;
+ m_punk = NULL;
+ m_ptcomp = NULL;
+ m_syskindProxy = (SYSKIND)-1; // something invalid
+}
+
+CStubTypeComp::~CStubTypeComp()
+{
+ Disconnect();
+}
+
+HRESULT
+CStubTypeComp::Create(IUnknown FAR* punkServer, ISTUB FAR* FAR* ppstub)
+{
+ CStubTypeComp FAR* pstub;
+
+ if(pstub = new FAR CStubTypeComp()){
+ pstub->m_refs = 1;
+ *ppstub = pstub;
+ if (punkServer)
+ return pstub->Connect(punkServer);
+ return NOERROR;
+ }
+ return RESULT(E_OUTOFMEMORY);
+}
+
+
+//---------------------------------------------------------------------
+// ITypeComp stub class' IUnknown implementation
+//---------------------------------------------------------------------
+
+STDMETHODIMP
+CStubTypeComp::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ if(IsEqualIID(riid, IID_IUnknown)){
+ *ppv = this;
+ }else if(IsEqualIID(riid, IID_ISTUB)){
+ *ppv = this;
+ }else{
+ *ppv = NULL;
+ return RESULT(E_NOINTERFACE);
+ }
+ ++m_refs;
+ return NOERROR;
+}
+
+STDMETHODIMP_(unsigned long)
+CStubTypeComp::AddRef()
+{
+ return ++m_refs;
+}
+
+STDMETHODIMP_(unsigned long)
+CStubTypeComp::Release()
+{
+ if(--m_refs == 0){
+ delete this;
+ return 0;
+ }
+ return m_refs;
+}
+
+
+//---------------------------------------------------------------------
+// ITypeComp stub class' IRpcStub implementation
+//---------------------------------------------------------------------
+
+STDMETHODIMP
+CStubTypeComp::Connect(IUnknown FAR* punkObj)
+{
+#if (defined(WIN32) || defined(WOW))
+ ASSERT(m_punk == NULL && m_ptcomp == NULL);
+ //This will keep the server object alive until we disconnect.
+ IfFailRet(punkObj->QueryInterface(IID_ITypeComp, (void FAR* FAR*)&m_ptcomp));
+ punkObj->AddRef();
+ m_punk = punkObj;
+ return NOERROR;
+#else
+ if(m_punk)
+ return RESULT(E_FAIL); // call Disconnect first
+
+ if (punkObj) {
+ punkObj->AddRef();
+ m_punk = punkObj;
+ }
+ return NOERROR;
+#endif
+}
+
+STDMETHODIMP_(void)
+CStubTypeComp::Disconnect()
+{
+ if(m_punk){
+ m_punk->Release();
+ m_punk = NULL;
+ }
+ if(m_ptcomp){
+ m_ptcomp->Release();
+ m_ptcomp = NULL;
+ }
+}
+
+/***
+*PUBLIC HRESULT CStubTypeComp::Invoke
+*
+*Purpose:
+* Dispatch the method with the given index (imeth) on the given
+* interface, using the arguments serialized in the given stream.
+*
+* This function is the callee side of an LRPC call.
+*
+*Entry:
+* iid = the IID of the interface on which we are to make the call
+* imeth = the method index
+* pstm = the IStream containing the method's actuals
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDMETHODIMP
+CStubTypeComp::Invoke(
+#if (OE_WIN32 || defined(WOW))
+ RPCOLEMESSAGE *pMessage,
+ ICHANNEL *pRpcChannel)
+#else
+ REFIID riid,
+ int iMethod,
+ IStream FAR* pstm,
+ unsigned long dwDestCtx,
+ void FAR* pvDestCtx)
+#endif
+{
+ HRESULT hresult;
+
+#if (OE_WIN32 || defined(WOW))
+ IStream FAR* pstm;
+
+ if(!m_punk)
+ return RESULT(E_FAIL);
+
+ OPEN_STUB_STREAM(pstm, pRpcChannel, pMessage, IID_ITypeComp);
+
+#else
+ UNUSED(dwDestCtx);
+ UNUSED(pvDestCtx);
+
+ if(!IsEqualIID(riid, IID_ITypeComp))
+ return RESULT(E_NOINTERFACE);
+
+ if(!m_punk)
+ return RESULT(E_FAIL);
+
+ if(m_ptcomp == NULL)
+ IfFailRet(m_punk->QueryInterface(IID_ITypeComp, (void FAR* FAR*)&m_ptcomp));
+#endif
+
+
+ m_pstm = pstm;
+
+ switch(GET_IMETHOD(pMessage)){
+ case IMETH_TYPECOMP_BIND:
+ hresult = Bind();
+ break;
+ case IMETH_TYPECOMP_BINDTYPE:
+ hresult = BindType();
+ break;
+ case IMETH_TYPECOMP_SYSKIND:
+ hresult = SysKind();
+ break;
+ default:
+ hresult = RESULT(E_INVALIDARG);
+ break;
+ }
+
+ RESET_STREAM(pstm);
+ DELETE_STREAM(pstm);
+ m_pstm = NULL;
+ return hresult;
+}
+
+
+/***
+*PUBLIC HRESULT CStubTypeComp::IsIIDSupported(REFIID)
+*Purpose:
+* Answer if the given IID is supported by this stub.
+*
+*Entry:
+* iid = the IID to query for support
+*
+*Exit:
+* return value = BOOL. TRUE if IID is supported, FALSE otherwise.
+*
+***********************************************************************/
+#if OE_MAC
+STDMETHODIMP_(unsigned long)
+#elif (OE_WIN32 || defined(WOW))
+STDMETHODIMP_(IRpcStubBuffer *)
+#else
+STDMETHODIMP_(BOOL)
+#endif
+CStubTypeComp::IsIIDSupported(REFIID riid)
+{
+#if (OE_WIN32 || defined(WOW))
+ IRpcStubBuffer *pStub = 0;
+ if (IsEqualIID(riid, IID_ITypeComp)) {
+ AddRef();
+ pStub = (IRpcStubBuffer *) this;
+ }
+ return pStub;
+#else
+ // REVIEW: I don't understand this, but thats the way Ole does it...
+ if(m_punk == NULL)
+ return FALSE;
+
+ return(IsEqualIID(riid, IID_ITypeComp));
+#endif
+}
+
+/***
+*unsigned long CStubTypeComp::CountRefs
+*Purpose:
+* Return the count of references held by this stub.
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = unsigned long, the count of refs.
+*
+***********************************************************************/
+STDMETHODIMP_(unsigned long)
+CStubTypeComp::CountRefs()
+{
+ unsigned long refs;
+
+ refs = 0;
+
+ if(m_punk != NULL)
+ ++refs;
+
+ if(m_ptcomp != NULL)
+ ++refs;
+
+ return refs;
+}
+
+/***
+*PRIVATE HRESULT CStubTypeComp::Bind
+*Purpose:
+* The stub implementation of ITypeComp::Bind
+*
+*Entry:
+* None
+*
+* Marshal In:
+* ULONG lHashVal
+* WORD wFlags
+* BSTR bstrName
+*
+* Marshal Out:
+* HRESULT hresultRet
+* ULONG desckind
+* BINDPTR bindptr
+* if(desckind == DESCKIND_VARDESC || desckind == DESCKIND_FUNCDESC)
+* ITypeInfo *ptinfo;
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeComp::Bind()
+{
+ BSTR bstrName;
+ BINDPTR bindptr;
+ DESCKIND desckind;
+ ITypeInfo FAR* ptinfo;
+ unsigned short wFlags;
+ unsigned long lHashVal;
+ unsigned long ulDesckind;
+ HRESULT hresult, hresultRet;
+
+ ptinfo = NULL;
+ bstrName = NULL;
+ hresult = NOERROR;
+ desckind = DESCKIND_NONE;
+
+ IfFailGo(GET(m_pstm, lHashVal), LError1);
+ IfFailGo(GET(m_pstm, wFlags), LError1);
+ IfFailGo(BstrRead(m_pstm, &bstrName, m_syskindProxy), LError1);
+
+ hresultRet = m_ptcomp->Bind(bstrName,
+ lHashVal,
+ wFlags,
+ &ptinfo,
+ &desckind,
+ &bindptr);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(DispMarshalHresult(m_pstm, hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError1;
+
+ ulDesckind = (unsigned long)desckind;
+ IfFailGo(PUT(m_pstm, ulDesckind), LError1);
+
+ switch(desckind){
+ case DESCKIND_NONE:
+ break;
+ case DESCKIND_VARDESC:
+ case DESCKIND_IMPLICITAPPOBJ:
+ IfFailGo(VardescWrite(m_pstm, bindptr.lpvardesc, m_syskindProxy),LError1);
+ IfFailGo(DispMarshalInterface(m_pstm, IID_ITypeInfo, ptinfo), LError1);
+ break;
+ case DESCKIND_FUNCDESC:
+ IfFailGo(FuncdescWrite(m_pstm,bindptr.lpfuncdesc,m_syskindProxy),LError1);
+ IfFailGo(DispMarshalInterface(m_pstm, IID_ITypeInfo, ptinfo), LError1);
+ break;
+ case DESCKIND_TYPECOMP:
+ IfFailGo(
+ DispMarshalInterface(m_pstm, IID_ITypeComp, bindptr.lptcomp),
+ LError1);
+ break;
+ default:
+ ASSERT(UNREACHED);
+ hresult = RESULT(DISP_E_BADCALLEE); // REVIEW: error code?
+ goto LError1;
+ }
+
+ hresult = NOERROR;
+
+LError1:;
+ switch(desckind){
+ case DESCKIND_VARDESC:
+ case DESCKIND_IMPLICITAPPOBJ:
+ ASSERT(ptinfo != NULL);
+ ptinfo->ReleaseVarDesc(bindptr.lpvardesc);
+ break;
+ case DESCKIND_FUNCDESC:
+ ASSERT(ptinfo != NULL);
+ ptinfo->ReleaseFuncDesc(bindptr.lpfuncdesc);
+ break;
+ case DESCKIND_TYPECOMP:
+ bindptr.lptcomp->Release();
+ break;
+ }
+ if(ptinfo != NULL)
+ ptinfo->Release();
+ SysFreeString(bstrName);
+ return hresult;
+}
+
+/***
+*PRIVATE HRESULT CStubTypeComp::BindType
+*Purpose:
+* The stub implementation of ITypeComp::BindType
+*
+*Entry:
+* None
+*
+* Marshal In:
+* ULONG lHashVal
+* BSTR bstrName
+*
+* Marshal Out:
+* HRESULT hresultRet
+* ITypeInfo *ptinfo
+* ITypeComp *ptcomp
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeComp::BindType()
+{
+ BSTR bstrName;
+ ITypeInfo FAR* ptinfo;
+ ITypeComp FAR* ptcomp;
+ unsigned long lHashVal;
+ HRESULT hresult, hresultRet;
+
+ ptinfo = NULL;
+ bstrName = NULL;
+
+ IfFailGo(GET(m_pstm, lHashVal), LError1);
+ IfFailGo(BstrRead(m_pstm, &bstrName, m_syskindProxy), LError1);
+
+ // NOTE: ptcomp is unused (reserved for future use). The docs say
+ // to pass NULL, but thats not right, we must pass something
+ // because typelib.dll assigns NULL to it!
+ ptcomp = NULL;
+ hresultRet = m_ptcomp->BindType(bstrName, lHashVal, &ptinfo, &ptcomp);
+ ASSERT(ptcomp == NULL);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(DispMarshalHresult(m_pstm, hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError1;
+
+ hresult = DispMarshalInterface(m_pstm, IID_ITypeInfo, ptinfo);
+
+LError1:;
+ if(ptinfo != NULL)
+ ptinfo->Release();
+ SysFreeString(bstrName);
+ return hresult;
+}
+
+/***
+*HRESULT CStubTypeComp::SysKind
+*Purpose:
+* Exchange syskinds with the proxy were connected to.
+*
+* Marshal In:
+* ULONG syskindProxy
+*
+* Marshal Out:
+* ULONG syskindStub
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeComp::SysKind()
+{
+ unsigned long syskind;
+
+ IfFailRet(GET(m_pstm, syskind));
+ m_syskindProxy = (SYSKIND)syskind;
+ syskind = (unsigned long)SYS_CURRENT;
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailRet(PUT(m_pstm, syskind));
+
+ return NOERROR;
+}
+
+#if (OE_WIN32 || defined(WOW))
+
+STDMETHODIMP
+CStubTypeComp::DebugServerQueryInterface(void FAR* FAR* ppv)
+{
+ *ppv = m_ptcomp;
+ return S_OK;
+}
+
+
+STDMETHODIMP_(void)
+CStubTypeComp::DebugServerRelease(void FAR* ppv)
+{ }
+
+#endif
diff --git a/private/oleauto/src/dispatch/time-api.cpp b/private/oleauto/src/dispatch/time-api.cpp
new file mode 100644
index 000000000..9f7df6685
--- /dev/null
+++ b/private/oleauto/src/dispatch/time-api.cpp
@@ -0,0 +1,173 @@
+/***
+*time-api.cpp
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Variant (application) time conversion routines.
+*
+* DosDateTimeToVariantTime()
+* VariantTimeToDosDateTime()
+*
+*
+*Revision History:
+*
+* [00] 15-Dec-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+* Variant time format
+* -------------------
+* This is also know as application time because its the format many
+* applications use. It is also the BASIC serialized or packed time format.
+*
+* A Variant time is stored in an 8 byte real (double), whose range
+* of values represent the dates from January 1, 1753 and
+* December 31, 2078 inclusive, where 2.0 represents January 1, 1900.
+* Negative numbers represent the dates prior to December 30, 1899.
+*
+*
+* Dos date/time format
+* --------------------
+*
+* The Dos date and time are stored in two packed 16-bit words as follows:
+*
+* Dos Date,
+*
+* 15 9 8 5 4 0
+* +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
+* | year (7) | month (4) | day (5) |
+* +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
+*
+* Year 1980 = 0
+* month january = 1
+* day first = 1
+*
+*
+* Dos Time,
+*
+* 15 11 10 5 4 0
+* +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
+* | hour (5) | min (6) | sec (5) |
+* +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
+*
+* hour 0-23
+* min 0-59
+* sec 0-29 (in 2 second increments)
+*
+*
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+ASSERTDATA
+
+
+/***
+*PUBLIC HRESULT DosDateTimeToVariantTime(unsigned short, unsigned short, double*)
+*Purpose:
+* Convert the given Dos date/time to a VARIANT time.
+*
+*Entry:
+* wDosDate = Dos date word
+* wDosTime = Dos time word
+*
+*Exit:
+* return value = int, TRUE if successful, FALSE if not.
+*
+* *pvtime = VARIANT time
+*
+***********************************************************************/
+STDAPI_(int)
+DosDateTimeToVariantTime(
+ unsigned short wDosDate,
+ unsigned short wDosTime,
+ double FAR* pvtime)
+{
+ UDS uds;
+ VARIANT var;
+
+#ifdef _DEBUG
+ if(IsBadWritePtr(pvtime, sizeof(*pvtime)))
+ return FALSE;
+#endif
+
+ uds.Year = ((wDosDate >> 9) & 0x7f) + 1980;
+ uds.Month = ((wDosDate >> 5) & 0x0f);
+ uds.DayOfMonth = ((wDosDate >> 0) & 0x1f);
+
+ uds.Hour = (wDosTime >> 11) & 0x1f;
+ uds.Minute = (wDosTime >> 5) & 0x3f;
+ uds.Second = ((wDosTime >> 0) & 0x1f) * 2;
+
+ if(uds.Year < 0 || uds.Month < 0 || uds.DayOfMonth < 0)
+ return FALSE;
+ if(uds.Year > 2099 || uds.Month > 12 || uds.DayOfMonth > 31)
+ return FALSE;
+ if(uds.Hour < 0 || uds.Minute < 0 || uds.Second < 0)
+ return FALSE;
+ if(uds.Hour > 23 || uds.Minute > 59 || uds.Second > 59)
+ return FALSE;
+
+ V_VT(&var) = VT_EMPTY;
+
+ if(ErrPackDate(&uds, &var, FALSE, 0) != NOERROR)
+ return FALSE;
+
+ ASSERT(V_VT(&var) == VT_DATE);
+
+ *pvtime = V_R8(&var);
+
+ return TRUE;
+}
+
+
+/***
+*HRESULT VariantTimeToDosDateTime(double, unsigned short*, unsigned short)
+*Purpose:
+* Convert a VARIANT time to a Dos date and time words.
+*
+*Entry:
+* vtime = VARIANT TIME
+*
+*Exit:
+* return value = HRESULT
+*
+* *pwDosDate = Dos date word
+* *pwDosTime = Dos time word
+*
+***********************************************************************/
+STDAPI_(int)
+VariantTimeToDosDateTime(
+ double vtime,
+ unsigned short FAR* pwDosDate,
+ unsigned short FAR* pwDosTime)
+{
+ UDS uds;
+ VARIANT var;
+
+#ifdef _DEBUG
+ if(IsBadWritePtr(pwDosDate, sizeof(*pwDosDate)))
+ return FALSE;
+ if(IsBadWritePtr(pwDosTime, sizeof(*pwDosTime)))
+ return FALSE;
+#endif
+
+ V_VT(&var) = VT_R8;
+ V_R8(&var) = vtime;
+ if(ErrUnpackDate(&uds, &var) != NOERROR)
+ return FALSE;
+
+ if(uds.Year < 1980 || uds.Year > 2099)
+ return FALSE;
+
+ uds.Year -= 1980;
+ uds.Second /= 2;
+
+ *pwDosDate = (uds.Year << 9) + (uds.Month << 5) + uds.DayOfMonth;
+ *pwDosTime = (uds.Hour << 11) + (uds.Minute << 5) + uds.Second;
+
+ return TRUE;
+}
diff --git a/private/oleauto/src/dispatch/tiprox.cpp b/private/oleauto/src/dispatch/tiprox.cpp
new file mode 100644
index 000000000..59999a62c
--- /dev/null
+++ b/private/oleauto/src/dispatch/tiprox.cpp
@@ -0,0 +1,1627 @@
+/***
+*tiprox.cpp
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This module implements the ITypeInfo proxy class.
+*
+*Revision History:
+*
+* [00] 06-Dec-93 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#ifndef WIN32
+#include <cobjps.h>
+#endif //!WIN32
+
+#include "dispmrsh.h"
+#include "tips.h"
+
+
+CProxTypeInfo::CProxTypeInfo(IUnknown FAR* punkOuter)
+ : m_unk(this), m_proxy(this), m_tinfo(this)
+{
+ if(punkOuter == NULL)
+ punkOuter = &m_unk;
+ m_punkOuter = punkOuter;
+}
+
+IUnknown FAR*
+CProxTypeInfo::Create(IUnknown FAR* punkOuter)
+{
+ CProxTypeInfo FAR* pproxtinfo;
+
+ if((pproxtinfo = new FAR CProxTypeInfo(punkOuter)) != NULL){
+ pproxtinfo->m_refs = 1;
+ return &pproxtinfo->m_unk;
+ }
+ return NULL;
+}
+
+
+//---------------------------------------------------------------------
+// ITypeInfo proxy class' IUnknown implementation
+//---------------------------------------------------------------------
+
+CPTIUnkImpl::CPTIUnkImpl(CProxTypeInfo FAR* pproxtinfo)
+{
+ m_pproxtinfo = pproxtinfo;
+}
+
+STDMETHODIMP
+CPTIUnkImpl::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ if(IsEqualIID(riid, IID_IUnknown)){
+ *ppv = (void FAR*)&(m_pproxtinfo->m_unk);
+ AddRef();
+ return NOERROR;
+ }
+
+ if(IsEqualIID(riid, IID_IPROXY)){
+ *ppv = (void FAR*)&(m_pproxtinfo->m_proxy);
+ AddRef();
+ return NOERROR;
+ }
+
+ if(IsEqualIID(riid, IID_ITypeInfo)){
+ *ppv = (void FAR*)&(m_pproxtinfo->m_tinfo);
+ m_pproxtinfo->m_punkOuter->AddRef();
+ return NOERROR;
+ }
+
+ *ppv = NULL;
+ return RESULT(E_NOINTERFACE);
+}
+
+STDMETHODIMP_(unsigned long)
+CPTIUnkImpl::AddRef()
+{
+ return ++m_pproxtinfo->m_refs;
+}
+
+STDMETHODIMP_(unsigned long)
+CPTIUnkImpl::Release()
+{
+ if(--m_pproxtinfo->m_refs==0){
+ delete m_pproxtinfo;
+ return 0;
+ }
+ return m_pproxtinfo->m_refs;
+}
+
+
+//---------------------------------------------------------------------
+// ITypeInfo proxy class' IRpcProxy implementation
+//---------------------------------------------------------------------
+
+CPTIProxImpl::CPTIProxImpl(CProxTypeInfo FAR* pproxtinfo)
+{
+ m_pproxtinfo = pproxtinfo;
+}
+
+CPTIProxImpl::~CPTIProxImpl()
+{
+ if(m_pproxtinfo->m_plrpc)
+ m_pproxtinfo->m_plrpc->Release();
+}
+
+STDMETHODIMP
+CPTIProxImpl::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ return m_pproxtinfo->m_unk.QueryInterface(riid, ppv);
+}
+
+STDMETHODIMP_(unsigned long)
+CPTIProxImpl::AddRef()
+{
+ return m_pproxtinfo->m_unk.AddRef();
+}
+
+STDMETHODIMP_(unsigned long)
+CPTIProxImpl::Release()
+{
+ return m_pproxtinfo->m_unk.Release();
+}
+
+STDMETHODIMP
+CPTIProxImpl::Connect(ICHANNEL FAR* plrpc)
+{
+ if(plrpc){
+ plrpc->AddRef();
+ m_pproxtinfo->m_plrpc = plrpc;
+ return NOERROR;
+ }
+ return RESULT(E_FAIL);
+}
+
+STDMETHODIMP_(void)
+CPTIProxImpl::Disconnect()
+{
+ if(m_pproxtinfo->m_plrpc)
+ m_pproxtinfo->m_plrpc->Release();
+ m_pproxtinfo->m_plrpc = NULL;
+}
+
+
+//---------------------------------------------------------------------
+// ITypeInfo proxy class' ITypeInfo methods
+//---------------------------------------------------------------------
+
+CPTITypeInfoImpl::CPTITypeInfoImpl(CProxTypeInfo FAR* pproxtinfo)
+{
+ m_pproxtinfo = pproxtinfo;
+}
+
+STDMETHODIMP
+CPTITypeInfoImpl::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ return m_pproxtinfo->m_punkOuter->QueryInterface(riid, ppv);
+}
+
+STDMETHODIMP_(unsigned long)
+CPTITypeInfoImpl::AddRef()
+{
+ return m_pproxtinfo->m_punkOuter->AddRef();
+}
+
+STDMETHODIMP_(unsigned long)
+CPTITypeInfoImpl::Release()
+{
+ return m_pproxtinfo->m_punkOuter->Release();
+}
+
+/***
+*HRESULT CPTITypeInfoImpl::GetTypeAttr
+*Purpose:
+*
+* Out:
+* None
+*
+* In:
+* <HRESULT hresultRet>
+* <TYPEATTR typeattr>
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value = HRESULT
+*
+* UNDONE
+*
+***********************************************************************/
+STDMETHODIMP
+CPTITypeInfoImpl::GetTypeAttr(TYPEATTR FAR* FAR* pptypeattr)
+{
+ ICHANNEL FAR* plrpc;
+ IStream FAR* pstm;
+ TYPEATTR FAR* ptypeattr;
+ HRESULT hresult, hresultRet;
+ unsigned long _proxySysKind, _stubSysKind;
+
+ if((plrpc = m_pproxtinfo->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPEINFO_GETTYPEATTR, 256, IID_ITypeInfo);
+
+ _proxySysKind = (unsigned long) SYS_CURRENT;
+ IfFailGo(PUT(pstm, _proxySysKind), LError1);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError2;
+
+ IfFailGo(GET(pstm, _stubSysKind), LError1);
+
+ if((ptypeattr = new FAR TYPEATTR) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LError1;
+ }
+
+ IfFailGo(TypeattrRead(pstm, ptypeattr, (SYSKIND) _stubSysKind), LError1);
+
+ *pptypeattr = ptypeattr;
+
+LError2:;
+ hresult = hresultRet;
+
+LError1:;
+ pstm->Release();
+ return hresult;
+}
+
+
+/***
+*CPTITypeInfoImpl::GetTypeComp
+*Purpose:
+*
+* Out:
+* None
+*
+* In:
+* <HRESULT hresultRet>
+* <ITypeComp tcomp>
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value = HRESULT
+*
+* UNDONE
+*
+***********************************************************************/
+STDMETHODIMP
+CPTITypeInfoImpl::GetTypeComp(ITypeComp FAR* FAR* pptcomp)
+{
+ ICHANNEL FAR* plrpc;
+ IStream FAR* pstm;
+ HRESULT hresult, hresultRet;
+
+ if((plrpc = m_pproxtinfo->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPEINFO_GETTYPECOMP, 256, IID_ITypeInfo);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError2;
+
+ IfFailGo(
+ DispUnmarshalInterface(pstm, IID_ITypeComp, (void FAR* FAR*)pptcomp),
+ LError1);
+
+LError2:;
+ hresult = hresultRet;
+
+LError1:;
+ pstm->Release();
+ return hresult;
+}
+
+
+/***
+*CPTITypeInfoImpl::GetFuncDesc
+*Purpose:
+*
+* Out:
+* <unsigned int index>
+*
+* In:
+* <HRESULT hresultRet>
+* <FUNCDESC funcdesc>
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value = HRESULT
+*
+* UNDONE
+*
+***********************************************************************/
+STDMETHODIMP
+CPTITypeInfoImpl::GetFuncDesc(
+ unsigned int index,
+ FUNCDESC FAR* FAR* ppfuncdesc)
+{
+ ICHANNEL FAR* plrpc;
+ IStream FAR* pstm;
+ FUNCDESC FAR* pfuncdesc;
+ HRESULT hresult, hresultRet;
+ unsigned long _proxySysKind, _stubSysKind;
+ unsigned long _index;
+
+ if((plrpc = m_pproxtinfo->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPEINFO_GETFUNCDESC, 256, IID_ITypeInfo);
+
+
+ _proxySysKind = (unsigned long) SYS_CURRENT;
+ IfFailGo(PUT(pstm, _proxySysKind), LError1);
+
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ _index = index;
+ IfFailGo(PUT(pstm, _index), LError1);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError2;
+
+ IfFailGo(GET(pstm, _stubSysKind), LError1);
+
+ if((pfuncdesc = new FAR FUNCDESC) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LError1;
+ }
+
+ IfFailGo(FuncdescRead(pstm, pfuncdesc, (SYSKIND) _stubSysKind), LError1);
+
+ *ppfuncdesc = pfuncdesc;
+
+LError2:;
+ hresult = hresultRet;
+
+LError1:;
+ pstm->Release();
+ return hresult;
+}
+
+
+/***
+*CPTITypeInfoImpl::GetVarDesc
+*Purpose:
+*
+* Out:
+* <unsigned int index>
+*
+* In:
+* <HRESULT hresultRet>
+* <VARDESC vardesc>
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value = HRESULT
+*
+* UNDONE
+*
+***********************************************************************/
+STDMETHODIMP
+CPTITypeInfoImpl::GetVarDesc(
+ unsigned int index,
+ VARDESC FAR* FAR* ppvardesc)
+{
+ ICHANNEL FAR* plrpc;
+ IStream FAR* pstm;
+ VARDESC FAR* pvardesc;
+ HRESULT hresult, hresultRet;
+ unsigned long _proxySysKind, _stubSysKind;
+ unsigned long _index;
+
+ if((plrpc = m_pproxtinfo->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPEINFO_GETVARDESC, 256, IID_ITypeInfo);
+
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ _proxySysKind = (unsigned long) SYS_CURRENT;
+ IfFailGo(PUT(pstm, _proxySysKind), LError1);
+
+ _index = index;
+ IfFailGo(PUT(pstm, _index), LError1);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError2;
+
+ IfFailGo(GET(pstm, _stubSysKind), LError1);
+
+ if((pvardesc = new FAR VARDESC) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LError1;
+ }
+
+ IfFailGo(VardescRead(pstm, pvardesc, (SYSKIND) _stubSysKind), LError1);
+
+ *ppvardesc = pvardesc;
+
+LError2:;
+ hresult = hresultRet;
+
+LError1:;
+ pstm->Release();
+ return hresult;
+}
+
+
+/***
+*CPTITypeInfoImpl::GetNames
+*Purpose:
+*
+* Out:
+* <MEMBERID memid>
+* <unsigned int cMaxNames>
+*
+* In:
+* <HRESULT hresultRet>
+* <unsigned int cNames>
+* <BSTR bstrName>*
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value =
+*
+***********************************************************************/
+STDMETHODIMP
+CPTITypeInfoImpl::GetNames(
+ MEMBERID memid,
+ BSTR FAR* rgbstrNames,
+ unsigned int cMaxNames,
+ unsigned int FAR* pcNames)
+{
+ ICHANNEL FAR* plrpc;
+ IStream FAR* pstm;
+ HRESULT hresult, hresultRet;
+ unsigned int u, cNames;
+ unsigned long _cMaxNames, _cNames;
+ unsigned long _proxySysKind, _stubSysKind;
+
+#ifdef _DEBUG
+ if(IsBadWritePtr(rgbstrNames, sizeof(BSTR) * cMaxNames))
+ return RESULT(E_INVALIDARG);
+ if(IsBadWritePtr(pcNames, sizeof(*pcNames)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ if((plrpc = m_pproxtinfo->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPEINFO_GETNAMES, 512, IID_ITypeInfo);
+
+ _proxySysKind = (unsigned long) SYS_CURRENT;
+ IfFailGo(PUT(pstm, _proxySysKind), LError1);
+
+ IfFailGo(PUT(pstm, memid), LError1);
+
+ // unsigned int always marshal/unmarshal as long (4 bytes)
+ _cMaxNames = cMaxNames;
+ IfFailGo(PUT(pstm, _cMaxNames), LError1);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet)){
+ hresult = hresultRet;
+ goto LError1;
+ }
+
+ IfFailGo(GET(pstm, _stubSysKind), LError1);
+
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ IfFailGo(GET(pstm, _cNames), LError1);
+ cNames = (unsigned int) _cNames;
+
+ // init the array to simplify unwinding if there is an error
+ for(u = 0; u < cNames; ++u)
+ rgbstrNames[u] = NULL;
+
+ for(u = 0; u < cNames; ++u)
+ IfFailGo(BstrRead(pstm, &rgbstrNames[u], (SYSKIND) _stubSysKind), LError2);
+
+ *pcNames = cNames;
+
+ hresult = hresultRet;
+
+LError2:;
+ // unwind string allocations if we failed
+ if(HRESULT_FAILED(hresult)){
+ for(u = 0; u < cNames; ++u){
+ if(rgbstrNames[u] == NULL)
+ break;
+ SysFreeString(rgbstrNames[u]);
+ rgbstrNames[u] = NULL;
+ }
+ }
+
+LError1:;
+ pstm->Release();
+ return hresult;
+}
+
+/***
+*CPTITypeInfoImpl::GetRefTypeOfImplType
+*Purpose:
+*
+* Out:
+* <unsigned int index>
+*
+* In:
+* <HRESULT hresultRet>
+* <HREFTYPE hreftype>
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value = HRESULT
+*
+* UNDONE
+*
+***********************************************************************/
+STDMETHODIMP
+CPTITypeInfoImpl::GetRefTypeOfImplType(
+ unsigned int index,
+ HREFTYPE FAR* phreftype)
+{
+ ICHANNEL FAR* plrpc;
+ IStream FAR* pstm;
+ HREFTYPE hreftype;
+ HRESULT hresult, hresultRet;
+ unsigned long _index;
+
+ if((plrpc = m_pproxtinfo->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPEINFO_GETREFTYPEOFIMPLTYPE, 100, IID_ITypeInfo);
+
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ //
+ // NOTE: We have to sign extend the index so that any special
+ // values (which are negative) are expanded to 32 bits on Win16.
+ //
+ _index = (int)index;
+ IfFailGo(PUT(pstm, _index), LError1);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError2;
+
+ IfFailGo(GET(pstm, hreftype), LError1);
+
+ *phreftype = hreftype;
+
+LError2:;
+ hresult = hresultRet;
+
+LError1:;
+ pstm->Release();
+ return hresult;
+}
+
+
+/***
+*CPTITypeInfoImpl::GetImplTypeFlags
+*Purpose:
+*
+* Out:
+* <unsigned int index>
+*
+* In:
+* <HRESULT hresultRet>
+* <int impltypeflags>
+*
+*Entry:
+* index =
+*
+*Exit:
+* return value = HRESULT
+*
+* *pimpltypeflags =
+*
+***********************************************************************/
+STDMETHODIMP
+CPTITypeInfoImpl::GetImplTypeFlags(
+ unsigned int index,
+ int FAR* pimpltypeflags)
+{
+ ICHANNEL FAR* plrpc;
+ IStream FAR* pstm;
+ HRESULT hresult, hresultRet;
+ unsigned long _index;
+ unsigned long _impltypeflags;
+
+ if((plrpc = m_pproxtinfo->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPEINFO_GETIMPLTYPEFLAGS, 100, IID_ITypeInfo);
+
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ _index = index;
+ IfFailGo(PUT(pstm, _index), LError1);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError2;
+
+ IfFailGo(GET(pstm, _impltypeflags), LError1);
+ *pimpltypeflags = (unsigned int) _impltypeflags;
+
+LError2:;
+ hresult = hresultRet;
+
+LError1:;
+ pstm->Release();
+ return hresult;
+}
+
+/***
+*CPTITypeInfoImpl::GetIDsOfNames
+*Purpose:
+* UNDONE
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDMETHODIMP
+CPTITypeInfoImpl::GetIDsOfNames(
+ OLECHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ MEMBERID FAR* rgmemid)
+{
+ UNUSED(rgszNames);
+ UNUSED(cNames);
+ UNUSED(rgmemid);
+
+ // REVIEW: factor out and share support from dispprox
+ return RESULT(E_NOTIMPL);
+}
+
+STDMETHODIMP
+CPTITypeInfoImpl::Invoke(
+ void FAR* pvInstance,
+ MEMBERID memid,
+ unsigned short wFlags,
+ DISPPARAMS FAR *pdispparams,
+ VARIANT FAR *pvarResult,
+ EXCEPINFO FAR *pexcepinfo,
+ unsigned int FAR *puArgErr)
+{
+ UNUSED(pvInstance);
+ UNUSED(memid);
+ UNUSED(wFlags);
+ UNUSED(pdispparams);
+ UNUSED(pvarResult);
+ UNUSED(pexcepinfo);
+ UNUSED(puArgErr);
+
+ return RESULT(E_NOTIMPL);
+}
+
+
+/***
+*CPTITypeInfoImpl::GetDocumentation
+*Purpose:
+*
+* Out:
+* <MEMBERID memid>
+*
+* In:
+* <HRESULT hresultRet>
+* <unsigned long dwHelpContext>
+* <BSTR bstrName>
+* <BSTR bstrDocString>
+* <BSTR bstrHelpFile>
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value = HRESULT
+*
+* UNDONE
+*
+***********************************************************************/
+STDMETHODIMP
+CPTITypeInfoImpl::GetDocumentation(
+ MEMBERID memid,
+ BSTR FAR* pbstrName,
+ BSTR FAR* pbstrDocString,
+ unsigned long FAR* pdwHelpContext,
+ BSTR FAR* pbstrHelpFile)
+{
+ ICHANNEL FAR* plrpc;
+ IStream FAR* pstm;
+ unsigned long dwHelpContext;
+ HRESULT hresult, hresultRet;
+ BSTR bstrName, bstrDocString, bstrHelpFile;
+ unsigned long _proxySysKind, _stubSysKind;
+
+#ifdef _DEBUG
+ if(pdwHelpContext != NULL
+ && IsBadWritePtr(pdwHelpContext, sizeof(*pdwHelpContext)))
+ return RESULT(E_INVALIDARG);
+ if(pbstrName != NULL
+ && IsBadWritePtr(pbstrName, sizeof(*pbstrName)))
+ return RESULT(E_INVALIDARG);
+ if(pbstrDocString != NULL
+ && IsBadWritePtr(pbstrDocString, sizeof(*pbstrDocString)))
+ return RESULT(E_INVALIDARG);
+ if(pbstrHelpFile != NULL
+ && IsBadWritePtr(pbstrHelpFile, sizeof(*pbstrHelpFile)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ bstrName = NULL;
+ bstrDocString = NULL;
+ bstrHelpFile = NULL;
+
+ if((plrpc = m_pproxtinfo->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPEINFO_GETDOCUMENTATION, 512, IID_ITypeInfo);
+
+ _proxySysKind = (unsigned long) SYS_CURRENT;
+ IfFailGo(PUT(pstm, _proxySysKind), LError1);
+
+ IfFailGo(PUT(pstm, memid), LError1);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet)){
+ hresult = hresultRet;
+ goto LError1;
+ }
+
+ IfFailGo(GET(pstm, _stubSysKind), LError1);
+ IfFailGo(GET(pstm, dwHelpContext), LError1);
+ IfFailGo(BstrRead(pstm, &bstrName, (SYSKIND) _stubSysKind), LError1);
+ IfFailGo(BstrRead(pstm, &bstrDocString, (SYSKIND) _stubSysKind), LError2);
+ IfFailGo(BstrRead(pstm, &bstrHelpFile, (SYSKIND) _stubSysKind), LError3);
+
+ if(pdwHelpContext != NULL)
+ *pdwHelpContext = dwHelpContext;
+
+ if(pbstrName != NULL)
+ *pbstrName = bstrName;
+ else
+ SysFreeString(bstrName);
+
+ if(pbstrDocString != NULL)
+ *pbstrDocString = bstrDocString;
+ else
+ SysFreeString(bstrDocString);
+
+ if(pbstrHelpFile != NULL)
+ *pbstrHelpFile = bstrHelpFile;
+ else
+ SysFreeString(bstrHelpFile);
+
+ pstm->Release();
+
+ return hresultRet;
+
+LError3:;
+ SysFreeString(bstrDocString);
+
+LError2:;
+ SysFreeString(bstrName);
+
+LError1:;
+ pstm->Release();
+ return hresult;
+}
+
+/***
+*CPTITypeInfoImpl::GetDllEntry
+*Purpose:
+*
+* Out:
+* <MEMBERID memid>
+*
+* In:
+* <HRESULT hresultRet>
+* <unsigned short wOrdinal>
+* <BSTR bstrDllName>
+* <BSTR bstrName>
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value = HRESULT
+*
+* UNDONE
+*
+***********************************************************************/
+STDMETHODIMP
+CPTITypeInfoImpl::GetDllEntry(
+ MEMBERID memid,
+ INVOKEKIND invkind,
+ BSTR FAR* pbstrDllName,
+ BSTR FAR* pbstrName,
+ unsigned short FAR* pwOrdinal)
+{
+ ICHANNEL FAR* plrpc;
+ IStream FAR* pstm;
+ unsigned short wOrdinal;
+ HRESULT hresult, hresultRet;
+ unsigned long _proxySysKind, _stubSysKind;
+ unsigned long _invkind;
+ BSTR bstrTemp;
+
+ if((plrpc = m_pproxtinfo->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPEINFO_GETDLLENTRY, 256, IID_ITypeInfo);
+
+ _proxySysKind = (unsigned long) SYS_CURRENT;
+ IfFailGo(PUT(pstm, _proxySysKind), LError1);
+
+ IfFailGo(PUT(pstm, memid), LError1);
+
+ _invkind = (unsigned long) invkind;
+ IfFailGo(PUT(pstm, _invkind), LError1);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet)){
+ hresult = hresultRet;
+ goto LError1;
+ }
+ IfFailGo(GET(pstm, _stubSysKind), LError1);
+ IfFailGo(GET(pstm, wOrdinal), LError1);
+ IfFailGo(BstrRead(pstm, &bstrTemp, (SYSKIND) _stubSysKind), LError1);
+ if (pbstrDllName) {
+ *pbstrDllName = bstrTemp;
+ } else {
+ SysFreeString(bstrTemp); // toss it
+ }
+
+ IfFailGo(BstrRead(pstm, &bstrTemp, (SYSKIND) _stubSysKind), LError2);
+ if (pbstrName) {
+ *pbstrName = bstrTemp;
+ } else {
+ SysFreeString(bstrTemp); // toss it
+ }
+
+ if (pwOrdinal)
+ *pwOrdinal = wOrdinal;
+
+ pstm->Release();
+
+ return hresultRet;
+
+LError2:;
+ SysFreeString(*pbstrDllName);
+
+LError1:;
+ pstm->Release();
+ return hresult;
+}
+
+/***
+*CPTITypeInfoImpl::GetRefTypeInfo
+*Purpose:
+*
+* Out:
+* <HREFTYPE hreftype>
+*
+* In:
+* <HRESULT hresultRet>
+* <ITypeInfo itinfo>
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value = HRESULT
+*
+* UNDONE
+*
+***********************************************************************/
+STDMETHODIMP
+CPTITypeInfoImpl::GetRefTypeInfo(
+ HREFTYPE hreftype,
+ ITypeInfo FAR* FAR* pptinfo)
+{
+ ICHANNEL FAR* plrpc;
+ IStream FAR* pstm;
+ HRESULT hresult, hresultRet;
+
+ if((plrpc = m_pproxtinfo->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPEINFO_GETREFTYPEINFO, 256, IID_ITypeInfo);
+
+ IfFailGo(PUT(pstm, hreftype), LError1);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError2;
+
+ IfFailGo(
+ DispUnmarshalInterface(pstm, IID_ITypeInfo, (void FAR* FAR*)pptinfo),
+ LError1);
+
+LError2:;
+ hresult = hresultRet;
+
+LError1:;
+ pstm->Release();
+ return hresult;
+}
+
+STDMETHODIMP
+CPTITypeInfoImpl::AddressOfMember(
+ MEMBERID memid,
+ INVOKEKIND invkind,
+ void FAR* FAR* ppv)
+{
+ UNUSED(memid);
+ UNUSED(invkind);
+ UNUSED(ppv);
+
+ return RESULT(E_NOTIMPL);
+}
+
+/***
+*UNDONE
+*Purpose:
+* Proxy implementation of ITypeInfo::CreateInstance
+*
+* Marshal Out:
+* IID
+*
+* Marshal Back:
+* newly created interface ptr.
+*
+*Entry:
+* punkOuter = controlling unknown
+* riid = the requested private interface
+*
+*Exit:
+* return value = HRESULT
+*
+* *ppvObj = the new instance, if successful.
+*
+***********************************************************************/
+STDMETHODIMP
+CPTITypeInfoImpl::CreateInstance(IUnknown FAR* punkOuter,
+ REFIID riid,
+ void FAR* FAR* ppvObj)
+{
+ IStream FAR* pstm;
+ ICHANNEL FAR* plrpc;
+ HRESULT hresult, hresultRet;
+
+ if((plrpc = m_pproxtinfo->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ // Ole doesn't (currently) support cross process aggregation
+ if(punkOuter != NULL)
+ return RESULT(CLASS_E_NOAGGREGATION);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPEINFO_CREATEINSTANCE, 256, IID_ITypeInfo);
+
+ IfFailGo(pstm->Write((const void FAR*)&riid, sizeof(IID), NULL), Error);
+
+ INVOKE_CALL(plrpc, pstm, Error);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), Error);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto Error2;
+
+ IfFailGo(DispUnmarshalInterface(pstm, riid, ppvObj), Error);
+
+Error2:;
+ hresult = hresultRet;
+
+Error:;
+ pstm->Release();
+ return hresult;
+}
+
+STDMETHODIMP
+CPTITypeInfoImpl::GetMops(
+ MEMBERID memid,
+ BSTR FAR* pbstrMops)
+{
+ UNUSED(memid);
+
+ *pbstrMops = NULL; // real implementation just returns a null
+ // string, we can do the same.
+ return NOERROR;
+}
+
+/***
+*CPTITypeInfoImpl::GetContainingTypeLib
+*Purpose:
+*
+* Out:
+* None
+*
+* In:
+* <HRESULT hresultRet>
+* <unsigned int index>
+* <ITypeLib tlib>
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value = HRESULT
+*
+* UNDONE
+*
+***********************************************************************/
+STDMETHODIMP
+CPTITypeInfoImpl::GetContainingTypeLib(
+ ITypeLib FAR* FAR* pptlib,
+ unsigned int FAR* pindex)
+{
+ ICHANNEL FAR* plrpc;
+ unsigned int index;
+ IStream FAR* pstm;
+ HRESULT hresult, hresultRet;
+ unsigned long _index;
+
+ if((plrpc = m_pproxtinfo->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPEINFO_GETCONTAININGTYPELIB, 256, IID_ITypeInfo);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError2;
+
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ IfFailGo(GET(pstm, _index), LError1);
+ index = (unsigned int) _index;
+
+ IfFailGo(
+ DispUnmarshalInterface(pstm, IID_ITypeLib, (void FAR* FAR*)pptlib),
+ LError1);
+
+ *pindex = index;
+
+LError2:;
+ hresult = hresultRet;
+
+LError1:;
+ pstm->Release();
+ return hresult;
+}
+
+
+/***
+*PUBLIC HRESULT CPTITypeInfoImpl::ReleaseTypeAttr
+*Purpose:
+* Free the given TYPEATTR
+*
+*Entry:
+* ptypeattr = the TYPEATTR to free
+*
+*Exit:
+* None
+*
+***********************************************************************/
+STDMETHODIMP_(void)
+CPTITypeInfoImpl::ReleaseTypeAttr(TYPEATTR FAR* ptypeattr)
+{
+#if defined(WIN16)
+ SysFreeString(ptypeattr->idldescType.bstrIDLInfo);
+#endif
+ delete ptypeattr;
+}
+
+
+/***
+* DoReleaseDanglingTypeDesc
+*Purpose:
+* Release any typedescs that are 'dangling' off of the current one.
+*
+*Entry:
+* ptypedesc = TYPEDESC to release from.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+INTERNAL_(void)
+DoReleaseDanglingTypeDesc(TYPEDESC FAR* ptypedesc)
+{
+ TYPEDESC FAR* ptypedescPrev;
+ short iType = 0;
+
+ if (ptypedesc->vt == VT_SAFEARRAY
+ || ptypedesc->vt == VT_PTR
+ || ptypedesc->vt == VT_CARRAY) {
+
+ do {
+ if (ptypedesc->vt == VT_SAFEARRAY || ptypedesc->vt == VT_PTR) {
+ ptypedescPrev = ptypedesc;
+ ptypedesc = ptypedesc->lptdesc;
+ }
+ else {
+ if (ptypedesc->vt == VT_CARRAY) {
+ DoReleaseDanglingTypeDesc(&ptypedesc->lpadesc->tdescElem);
+ delete ptypedesc->lpadesc;
+ }
+
+ ptypedescPrev = ptypedesc;
+ ptypedesc = NULL;
+ }
+
+ if (iType++) {
+ delete ptypedescPrev;
+ }
+
+ } while (ptypedesc != NULL);
+ }
+}
+
+
+/***
+*PUBLIC HRESULT CPTITypeInfoImpl::ReleaseFuncDesc
+*Purpose:
+* Free the given FUNCDESC
+*
+*Entry:
+* pfuncdesc = the FUNCDESC to free
+*
+*Exit:
+* None
+*
+***********************************************************************/
+INTERNAL_(void)
+DoReleaseFuncDesc(FUNCDESC FAR* pfuncdesc)
+{
+ short iParam;
+
+#if defined(WIN16)
+ SysFreeString(pfuncdesc->elemdescFunc.idldesc.bstrIDLInfo);
+#endif
+
+ for(iParam = 0; iParam < pfuncdesc->cParams; ++iParam) {
+#if defined(WIN16)
+ SysFreeString(pfuncdesc->lprgelemdescParam[iParam].idldesc.bstrIDLInfo);
+#endif
+
+ DoReleaseDanglingTypeDesc(&pfuncdesc->lprgelemdescParam[iParam].tdesc);
+ }
+
+ delete pfuncdesc->lprgelemdescParam;
+
+ DoReleaseDanglingTypeDesc(&pfuncdesc->elemdescFunc.tdesc);
+ delete pfuncdesc;
+}
+
+
+STDMETHODIMP_(void)
+CPTITypeInfoImpl::ReleaseFuncDesc(FUNCDESC FAR* pfuncdesc)
+{
+ DoReleaseFuncDesc(pfuncdesc);
+}
+
+
+/***
+*PUBLIC HRESULT CPTITypeInfoImpl::ReleaseVarDesc
+*Purpose:
+* Free the given VARDESC
+*
+*Entry:
+* pvardesc = the VARDESC to free
+*
+*Exit:
+* None
+*
+***********************************************************************/
+INTERNAL_(void)
+DoReleaseVarDesc(VARDESC FAR* pvardesc)
+{
+ DoReleaseDanglingTypeDesc(&pvardesc->elemdescVar.tdesc);
+ delete pvardesc;
+}
+
+STDMETHODIMP_(void)
+CPTITypeInfoImpl::ReleaseVarDesc(VARDESC FAR* pvardesc)
+{
+ DoReleaseVarDesc(pvardesc);
+}
+
+
+//---------------------------------------------------------------------
+// introduced methods
+//---------------------------------------------------------------------
+
+HRESULT
+CPTITypeInfoImpl::GetStream(
+ int imeth,
+ unsigned long size,
+ IStream FAR* FAR* ppstm)
+{
+ return NOERROR;
+}
+
+
+/***
+*CPTITypeInfoImpl::LrpcCall
+*Purpose:
+* Execute the LRPC call on the given stream.
+*
+* This routine is a helper for the ITypeInfo proxy methods.
+*
+*Entry:
+* pstm = the stream to execute the call on
+*
+*Exit:
+* return value = HRESULT
+*
+* *phresultRet = the HRESULT of the remote method invocation
+*
+***********************************************************************/
+HRESULT
+CPTITypeInfoImpl::LrpcCall(IStream FAR* pstm, HRESULT FAR* phresultRet)
+{
+ return NOERROR;
+}
+
+
+//---------------------------------------------------------------------
+// utilities
+//---------------------------------------------------------------------
+
+/***
+*HRESULT TypedescRead
+*Purpose:
+* Read a TYPEDESC from the given stream into the caller
+* allocated struct.
+*
+*Entry:
+* pstm = the stream to read from
+* ptdesc = where to put the reconstituted TYPEDESC.
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+extern "C" HRESULT
+TypedescRead(IStream FAR* pstm, TYPEDESC FAR* ptdesc, SYSKIND sysKind)
+{
+ TYPEDESC FAR* ptdescPtr;
+ ARRAYDESC FAR* lpadesc;
+ unsigned short cDims;
+ HRESULT hresult;
+
+ IfFailRet(GET(pstm, ptdesc->vt));
+
+ switch(ptdesc->vt){
+ case VT_SAFEARRAY:
+ case VT_PTR:
+ if((ptdescPtr = new FAR TYPEDESC) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+ hresult = TypedescRead(pstm, ptdescPtr, sysKind);
+ if (hresult != NOERROR) {
+ delete ptdescPtr;
+ return hresult;
+ }
+ ptdesc->lptdesc = ptdescPtr;
+ break;
+
+ case VT_CARRAY:
+ IfFailRet(GET(pstm, cDims));
+ if ((lpadesc = (ARRAYDESC FAR*) new FAR char [sizeof(ARRAYDESC) + (cDims-1) * sizeof(SAFEARRAYBOUND)]) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+ lpadesc->cDims = cDims;
+ hresult = TypedescRead(pstm, &lpadesc->tdescElem, sysKind);
+ while (hresult == NOERROR && cDims > 0) {
+ cDims--;
+ hresult = GET(pstm, lpadesc->rgbounds[cDims].cElements);
+ if (hresult == NOERROR) {
+ hresult = GET(pstm, lpadesc->rgbounds[cDims].lLbound);
+ }
+ }
+ if (hresult != NOERROR) {
+ delete lpadesc;
+ return hresult;
+ }
+ ptdesc->lpadesc = lpadesc;
+ break;
+
+#if 0
+ case VT_FIXEDSTRING:
+ IfFailRet(GET(pstm, ptdesc->cbSize));
+ break;
+#endif
+
+ case VT_USERDEFINED:
+ IfFailRet(GET(pstm, ptdesc->hreftype));
+ break;
+ }
+
+ return NOERROR;
+}
+
+
+HRESULT
+TypedescWrite(IStream FAR* pstm, TYPEDESC FAR* ptdesc, SYSKIND sysKind)
+{
+ unsigned short cDims;
+
+ IfFailRet(PUT(pstm, ptdesc->vt));
+
+ switch(ptdesc->vt){
+ case VT_SAFEARRAY:
+ case VT_PTR:
+ IfFailRet(TypedescWrite(pstm, ptdesc->lptdesc, sysKind));
+ break;
+
+ case VT_CARRAY:
+ cDims = ptdesc->lpadesc->cDims;
+ IfFailRet(PUT(pstm, cDims));
+ IfFailRet(TypedescWrite(pstm, &ptdesc->lpadesc->tdescElem, sysKind));
+ while (cDims > 0) {
+ cDims--;
+ IfFailRet(PUT(pstm, ptdesc->lpadesc->rgbounds[cDims].cElements));
+ IfFailRet(PUT(pstm, ptdesc->lpadesc->rgbounds[cDims].lLbound));
+ }
+ break;
+
+#if 0
+ case VT_FIXEDSTRING:
+ IfFailRet(PUT(pstm, ptdesc->cbSize));
+ break;
+#endif
+
+ case VT_USERDEFINED:
+ IfFailRet(PUT(pstm, ptdesc->hreftype));
+ break;
+ }
+
+ return NOERROR;
+}
+
+
+extern "C" HRESULT
+TypedescReadOrWrite(IStream FAR* pstm, BOOL fRead, void FAR* pvStruct, SYSKIND sysKind)
+{
+ return
+ (fRead ? TypedescRead : TypedescWrite)(pstm, (TYPEDESC FAR*)pvStruct, sysKind);
+}
+
+
+extern "C" {
+extern FIELDDESC NEARDATA g_rgfdescIdldesc[];
+extern FIELDDESC NEARDATA g_rgfdescElemdesc[];
+extern FIELDDESC NEARDATA g_rgfdescTypeattr[];
+extern FIELDDESC NEARDATA g_rgfdescFuncdesc[];
+extern FIELDDESC NEARDATA g_rgfdescVardesc[];
+}
+
+
+/***
+*PRIVATE HRESULT TypeattrWrite
+*Purpose:
+* Write the given TYPEATTR into the given stream.
+*
+*Entry:
+* pstm = the stream to write into
+* ptypeattr = the typeattr to write
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+INTERNAL_(HRESULT)
+TypeattrWrite(IStream FAR* pstm, TYPEATTR FAR* ptypeattr, SYSKIND sysKind)
+{
+ IfFailRet(StructWrite(pstm, g_rgfdescTypeattr, ptypeattr, sysKind));
+
+ if(ptypeattr->typekind == TKIND_ALIAS){
+ IfFailRet(TypedescWrite(pstm, &ptypeattr->tdescAlias, sysKind));
+ }
+
+ return NOERROR;
+}
+
+
+/***
+*PRIVATE HRESULT TypeattrRead
+*Purpose:
+* Read a TYPEATTR from the given stream
+*
+*Entry:
+* pstm = the stream to read from
+* ptypeattr = the struct to read into
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+INTERNAL_(HRESULT)
+TypeattrRead(IStream FAR* pstm, TYPEATTR FAR* ptypeattr, SYSKIND sysKind)
+{
+ IfFailRet(StructRead(pstm, g_rgfdescTypeattr, ptypeattr, sysKind));
+
+ if(ptypeattr->typekind == TKIND_ALIAS){
+ IfFailRet(TypedescRead(pstm, &ptypeattr->tdescAlias, sysKind));
+ }
+ ptypeattr->dwReserved = 0; // init un-marshalled fields to 0
+ ptypeattr->lpstrSchema = NULL;
+
+ return NOERROR;
+}
+
+
+/***
+*PRIVATE HRESULT FuncdescWrite
+*Purpose:
+* Write the given FUNCDESC into the given stream.
+*
+*Entry:
+* pstm = the stream to write into
+* pfuncdesc = the FUNCDESC to write
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+INTERNAL_(HRESULT)
+FuncdescWrite(IStream FAR* pstm, FUNCDESC FAR* pfuncdesc, SYSKIND sysKind)
+{
+ IfFailRet(StructWrite(pstm, g_rgfdescFuncdesc, pfuncdesc, sysKind));
+
+ // write the lprgelemdescParam by hand
+
+ for(int i = 0; i < pfuncdesc->cParams; ++i){
+ IfFailRet(
+ StructWrite(
+ pstm, g_rgfdescElemdesc, &pfuncdesc->lprgelemdescParam[i], sysKind));
+ }
+
+ return NOERROR;
+}
+
+
+/***
+*PRIVATE HRESULT FuncdescRead
+*Purpose:
+* Read a FUNCDESC from the given stream.
+*
+*Entry:
+* pstm = the stream to read from
+*
+*Exit:
+* return value = HRESULT
+*
+* *ppfuncdesc = the reconstituted FUNCDESC
+*
+***********************************************************************/
+INTERNAL_(HRESULT)
+FuncdescRead(IStream FAR* pstm, FUNCDESC FAR* pfuncdesc, SYSKIND sysKind)
+{
+ HRESULT hresult;
+ ELEMDESC FAR* prgelemdescParam;
+
+ prgelemdescParam = NULL;
+
+ IfFailRet(StructRead(pstm, g_rgfdescFuncdesc, pfuncdesc, sysKind));
+
+ if(pfuncdesc->cParams > 0){
+
+ if((prgelemdescParam = new FAR ELEMDESC [pfuncdesc->cParams]) == NULL){
+ return RESULT(E_OUTOFMEMORY);
+ }
+
+ for(int i = 0; i < pfuncdesc->cParams; ++i){
+ IfFailGo(
+ StructRead(pstm, g_rgfdescElemdesc, &prgelemdescParam[i], sysKind),
+ LError0);
+ }
+ }
+
+ pfuncdesc->lprgelemdescParam = prgelemdescParam;
+
+ pfuncdesc->lprgscode = NULL; // init reserved fields to zero
+ pfuncdesc->cScodes = 0;
+
+ return NOERROR;
+
+LError0:
+ delete prgelemdescParam;
+
+ return hresult;
+}
+
+
+/***
+*PRIVATE HRESULT VardescWrite
+*Purpose:
+* Write the given VARDESC into the given stream.
+*
+*Entry:
+* pstm = the stream to write into
+* pvardesc = the VARDESC to write
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+INTERNAL_(HRESULT)
+VardescWrite(IStream FAR* pstm, VARDESC FAR* pvardesc, SYSKIND sysKind)
+{
+ IfFailRet(StructWrite(pstm, g_rgfdescVardesc, pvardesc, sysKind));
+
+ switch(pvardesc->varkind){
+ case VAR_CONST:
+ IfFailRet(VariantWrite(pstm, pvardesc->lpvarValue, sysKind));
+ break;
+
+ case VAR_PERINSTANCE:
+ case VAR_DISPATCH:
+ IfFailRet(PUT(pstm, pvardesc->oInst));
+ break;
+ }
+
+ return NOERROR;
+}
+
+
+/***
+*PRIVATE HRESULT VardescRead
+*Purpose:
+* Read a VARDESC from the given stream
+*
+*Entry:
+* pstm = the stream to read from
+*
+*Exit:
+* return value = HRESULT
+*
+* *ppvardesc = the reconstituted VARDESC
+*
+***********************************************************************/
+INTERNAL_(HRESULT)
+VardescRead(IStream FAR* pstm, VARDESC FAR* pvardesc, SYSKIND sysKind)
+{
+ HRESULT hresult;
+ VARIANT FAR* pvar;
+
+ IfFailRet(StructRead(pstm, g_rgfdescVardesc, pvardesc, sysKind));
+
+ switch(pvardesc->varkind){
+ case VAR_CONST:
+ if((pvar = new FAR VARIANT) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+ if((hresult = VariantRead(pstm, pvar, NULL, sysKind)) != NOERROR){
+ delete pvar;
+ return hresult;
+ }
+ pvardesc->lpvarValue = pvar;
+ break;
+
+ case VAR_PERINSTANCE:
+ case VAR_DISPATCH:
+ IfFailRet(GET(pstm, pvardesc->oInst));
+ break;
+ }
+ pvardesc->lpstrSchema = NULL; // reserved
+
+ return NOERROR;
+}
diff --git a/private/oleauto/src/dispatch/tips.h b/private/oleauto/src/dispatch/tips.h
new file mode 100644
index 000000000..0141a71ac
--- /dev/null
+++ b/private/oleauto/src/dispatch/tips.h
@@ -0,0 +1,297 @@
+/***
+*tips.h - ITypeInfo Proxy and Stub class definitions
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file describes the ITypeInfo Proxy and Stub classes.
+*
+* CProxTypeInfo -- the ITypeInfo proxy class
+* CPTIUnkImpl - CProxTypeInfo implementation of IUnknown
+* CPTIProxImpl - CProxTypeInfo implementation of IRpcProxy
+* CPTITypeInfoImpl - CProxTypeInfo implementation of ITypeInfo
+*
+* CStubTypeInfo -- the ITypeInfo stub class
+*
+*Revision History:
+*
+* [00] 05-Mar-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+#ifndef __tips_h__
+#define __tips_h__
+
+#pragma warning(4:4355)
+
+
+// forward declarations
+class FAR CProxTypeInfo;
+class FAR CStubTypeInfo;
+
+
+// ITypeInfo proxy class' IUnknown implementation
+class FAR CPTIUnkImpl : public IUnknown
+{
+public:
+ CPTIUnkImpl(CProxTypeInfo FAR* pproxtinfo);
+
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+private:
+ CProxTypeInfo FAR* m_pproxtinfo;
+};
+
+
+// ITypeInfo proxy class' IRpcProxy implementation
+class FAR CPTIProxImpl : public IPROXY
+{
+public:
+ CPTIProxImpl(CProxTypeInfo FAR* pproxtinfo);
+ ~CPTIProxImpl();
+
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ STDMETHOD(Connect)(ICHANNEL FAR* plrpc);
+ STDMETHOD_(void, Disconnect)(void);
+
+private:
+ CProxTypeInfo FAR* m_pproxtinfo;
+};
+
+
+// ITypeInfo
+class FAR CPTITypeInfoImpl : public ITypeInfo
+{
+public:
+ CPTITypeInfoImpl(CProxTypeInfo FAR* pproxtinfo);
+
+ // IUnknown methods
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ // ITypeInfo methods
+ STDMETHOD(GetTypeAttr)(TYPEATTR FAR* FAR* pptypeattr);
+
+ STDMETHOD(GetTypeComp)(ITypeComp FAR* FAR* pptcomp);
+
+ STDMETHOD(GetFuncDesc)(
+ unsigned int index, FUNCDESC FAR* FAR* ppfuncdesc);
+
+ STDMETHOD(GetVarDesc)(unsigned int index, VARDESC FAR* FAR* ppvardesc);
+
+ STDMETHOD(GetNames)(
+ MEMBERID memid,
+ BSTR FAR* rgbstrNames,
+ unsigned int cMaxNames,
+ unsigned int FAR* pcNames);
+
+ STDMETHOD(GetRefTypeOfImplType)(
+ unsigned int index, HREFTYPE FAR* phreftype);
+
+ STDMETHOD(GetImplTypeFlags)(
+ unsigned int index, int FAR* pimpltypeflags);
+
+ STDMETHOD(GetIDsOfNames)(
+ OLECHAR FAR* FAR* rgszNames, unsigned int cNames, MEMBERID FAR* rgmemid);
+
+ STDMETHOD(Invoke)(
+ void FAR* pvInstance,
+ MEMBERID memid,
+ unsigned short wFlags,
+ DISPPARAMS FAR *pdispparams,
+ VARIANT FAR *pvarResult,
+ EXCEPINFO FAR *pexcepinfo,
+ unsigned int FAR *puArgErr);
+
+ STDMETHOD(GetDocumentation)(
+ MEMBERID memid,
+ BSTR FAR* pbstrName,
+ BSTR FAR* pbstrDocString,
+ unsigned long FAR* pdwHelpContext,
+ BSTR FAR* pbstrHelpFile);
+
+ STDMETHOD(GetDllEntry)(
+ MEMBERID memid,
+ INVOKEKIND invkind,
+ BSTR FAR* pbstrDllName,
+ BSTR FAR* pbstrName,
+ unsigned short FAR* pwOrdinal);
+
+ STDMETHOD(GetRefTypeInfo)(
+ HREFTYPE hreftype, ITypeInfo FAR* FAR* pptinfo);
+
+ STDMETHOD(AddressOfMember)(
+ MEMBERID memid, INVOKEKIND invkind, void FAR* FAR* ppv);
+
+ STDMETHOD(CreateInstance)(IUnknown FAR* punkOuter,
+ REFIID riid,
+ void FAR* FAR* ppvObj);
+
+ STDMETHOD(GetMops)(MEMBERID memid, BSTR FAR* pbstrMops);
+
+ STDMETHOD(GetContainingTypeLib)(
+ ITypeLib FAR* FAR* pptlib, unsigned int FAR* pindex);
+
+ STDMETHOD_(void, ReleaseTypeAttr)(TYPEATTR FAR* ptypeattr);
+ STDMETHOD_(void, ReleaseFuncDesc)(FUNCDESC FAR* pfuncdesc);
+ STDMETHOD_(void, ReleaseVarDesc)(VARDESC FAR* pvardesc);
+
+ // introduced methods
+
+ HRESULT GetStream(int imeth, unsigned long size, IStream FAR* FAR* ppstm);
+ HRESULT LrpcCall(IStream FAR* pstm, HRESULT FAR* phresultRet);
+
+private:
+ CProxTypeInfo FAR* m_pproxtinfo;
+};
+
+// ITypeInfo Proxy Class
+class FAR CProxTypeInfo
+{
+public:
+ static IUnknown FAR* Create(IUnknown FAR* punkOuter);
+
+private:
+ CProxTypeInfo(IUnknown FAR* punkOuter);
+
+ friend CPTIUnkImpl;
+ friend CPTIProxImpl;
+ friend CPTITypeInfoImpl;
+
+ CPTIUnkImpl m_unk;
+ CPTIProxImpl m_proxy;
+ CPTITypeInfoImpl m_tinfo;
+
+private:
+
+ unsigned long m_refs;
+ ICHANNEL FAR* m_plrpc;
+ IUnknown FAR* m_punkOuter;
+};
+
+// ITypeInfo Stub Class
+//
+class FAR CStubTypeInfo : public ISTUB
+{
+public:
+ static HRESULT Create(IUnknown FAR* punkServer, ISTUB FAR* FAR* ppstub);
+
+ // IUnknown methods
+ //
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ // IRpcStub methods
+ //
+#if (OE_WIN32 || defined(WOW))
+ STDMETHOD(Connect)(IUnknown FAR* pUnk);
+ STDMETHOD_(void, Disconnect)(void);
+ STDMETHOD(Invoke)(RPCOLEMESSAGE FAR* pRpcMsg,
+ IRpcChannelBuffer FAR* pRpcChannel);
+ STDMETHOD_(IRpcStubBuffer *, IsIIDSupported)(REFIID iid);
+ STDMETHOD_(ULONG, CountRefs)(void);
+ STDMETHOD(DebugServerQueryInterface)(void FAR* FAR* ppv);
+ STDMETHOD_(void, DebugServerRelease)(void FAR* pv);
+#else
+ STDMETHOD(Connect)(IUnknown FAR* punkObject);
+ STDMETHOD_(void, Disconnect)(void);
+ STDMETHOD(Invoke)(
+ REFIID riid,
+ int imeth,
+ IStream FAR* pstm,
+ unsigned long dwDestCtx,
+ void FAR* pvDestCtx);
+#if OE_MAC
+ STDMETHOD_(unsigned long, IsIIDSupported)(REFIID riid);
+#else
+ STDMETHOD_(BOOL, IsIIDSupported)(REFIID riid);
+#endif
+ STDMETHOD_(unsigned long, CountRefs)(void);
+#endif
+
+ // introduced methods
+ //
+ HRESULT GetTypeAttr(void);
+ HRESULT GetTypeComp(void);
+ HRESULT GetFuncDesc(void);
+ HRESULT GetVarDesc(void);
+ HRESULT GetNames(void);
+ HRESULT GetRefTypeOfImplType(void);
+ HRESULT GetImplTypeFlags(void);
+ HRESULT GetIDsOfNames(void);
+ HRESULT GetDocumentation(void);
+ HRESULT GetDllEntry(void);
+ HRESULT GetRefTypeInfo(void);
+ HRESULT CreateInstance(void);
+ HRESULT GetContainingTypeLib(void);
+
+ // helpers
+ HRESULT MarshalResult(void);
+
+private:
+ CStubTypeInfo();
+ ~CStubTypeInfo();
+
+ unsigned long m_refs;
+ IUnknown FAR* m_punk;
+ ITypeInfo FAR* m_ptinfo;
+
+ IStream FAR* m_pstm;
+ HRESULT m_hresultRet;
+};
+
+
+// ITypeInfo method indices
+//
+enum IMETH_TYPEINFO {
+ IMETH_TYPEINFO_QUERYINTERFACE = 0,
+ IMETH_TYPEINFO_ADDREF,
+ IMETH_TYPEINFO_RELEASE,
+
+ IMETH_TYPEINFO_GETTYPEATTR,
+ IMETH_TYPEINFO_GETTYPECOMP,
+ IMETH_TYPEINFO_GETFUNCDESC,
+ IMETH_TYPEINFO_GETVARDESC,
+ IMETH_TYPEINFO_GETNAMES,
+ IMETH_TYPEINFO_GETREFTYPEOFIMPLTYPE,
+ IMETH_TYPEINFO_GETIMPLTYPEFLAGS,
+ IMETH_TYPEINFO_GETIDSOFNAMES,
+ IMETH_TYPEINFO_INVOKE,
+ IMETH_TYPEINFO_GETDOCUMENTATION,
+ IMETH_TYPEINFO_GETDLLENTRY,
+ IMETH_TYPEINFO_GETREFTYPEINFO,
+ IMETH_TYPEINFO_ADDRESSOFMEMBER,
+ IMETH_TYPEINFO_CREATEINSTANCE,
+ IMETH_TYPEINFO_GETMOPS,
+ IMETH_TYPEINFO_GETCONTAININGTYPELIB,
+
+ IMETH_TYPEINFO_RELEASETYPEATTR,
+ IMETH_TYPEINFO_RELEASEFUNCDESC,
+ IMETH_TYPEINFO_RELEASEVARDESC
+};
+
+
+INTERNAL_(void) DoReleaseVarDesc(VARDESC FAR* pvardesc);
+INTERNAL_(void) DoReleaseFuncDesc(FUNCDESC FAR* pvardesc);
+
+
+// TypeInfo marshaling utilities
+
+INTERNAL_(HRESULT) TypeattrRead(IStream FAR*, TYPEATTR FAR*, SYSKIND);
+INTERNAL_(HRESULT) FuncdescRead(IStream FAR*, FUNCDESC FAR*, SYSKIND);
+INTERNAL_(HRESULT) VardescRead(IStream FAR*, VARDESC FAR*, SYSKIND);
+
+INTERNAL_(HRESULT) TypeattrWrite(IStream FAR*, TYPEATTR FAR*, SYSKIND);
+INTERNAL_(HRESULT) FuncdescWrite(IStream FAR*, FUNCDESC FAR*, SYSKIND);
+INTERNAL_(HRESULT) VardescWrite(IStream FAR*, VARDESC FAR*, SYSKIND);
+
+#endif __tips_h__
diff --git a/private/oleauto/src/dispatch/tistub.cpp b/private/oleauto/src/dispatch/tistub.cpp
new file mode 100644
index 000000000..ab0d89bfd
--- /dev/null
+++ b/private/oleauto/src/dispatch/tistub.cpp
@@ -0,0 +1,1034 @@
+/***
+*tistub.cpp
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This module implements the ITypeInfo stub class.
+*
+*Revision History:
+*
+* [00] 05-Mar-93 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#ifndef WIN32
+#include <cobjps.h>
+#endif //!WIN32
+
+#include "dispmrsh.h"
+#include "tips.h"
+
+ASSERTDATA
+
+CStubTypeInfo::CStubTypeInfo()
+{
+ m_refs = 0;
+ m_pstm = NULL;
+ m_punk = NULL;
+ m_ptinfo = NULL;
+}
+
+CStubTypeInfo::~CStubTypeInfo()
+{
+ Disconnect();
+}
+
+HRESULT
+CStubTypeInfo::Create(IUnknown FAR* punkServer, ISTUB FAR* FAR* ppstub)
+{
+ CStubTypeInfo FAR* pstub;
+
+ if(pstub = new FAR CStubTypeInfo()){
+ pstub->m_refs = 1;
+ *ppstub = pstub;
+ if (punkServer)
+ return pstub->Connect(punkServer);
+ return NOERROR;
+ }
+ return RESULT(E_OUTOFMEMORY);
+}
+
+
+//---------------------------------------------------------------------
+// ITypeInfo stub class' IUnknown implementation
+//---------------------------------------------------------------------
+
+STDMETHODIMP
+CStubTypeInfo::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ if(IsEqualIID(riid, IID_IUnknown)){
+ *ppv = this;
+ }else if(IsEqualIID(riid, IID_ISTUB)){
+ *ppv = this;
+ }else{
+ *ppv = NULL;
+ return RESULT(E_NOINTERFACE);
+ }
+ ++m_refs;
+ return NOERROR;
+}
+
+STDMETHODIMP_(unsigned long)
+CStubTypeInfo::AddRef()
+{
+ return ++m_refs;
+}
+
+STDMETHODIMP_(unsigned long)
+CStubTypeInfo::Release()
+{
+ if(--m_refs == 0){
+ delete this;
+ return 0;
+ }
+ return m_refs;
+}
+
+
+//---------------------------------------------------------------------
+// ITypeInfo stub class' IRpcStub implementation
+//---------------------------------------------------------------------
+
+STDMETHODIMP
+CStubTypeInfo::Connect(IUnknown FAR* punkObj)
+{
+#if (defined(WIN32) || defined(WOW))
+ ASSERT(m_punk == NULL && m_ptinfo == NULL);
+ //This will keep the server object alive until we disconnect.
+ IfFailRet(punkObj->QueryInterface(IID_ITypeInfo, (void FAR* FAR*)&m_ptinfo));
+ punkObj->AddRef();
+ m_punk = punkObj;
+ return NOERROR;
+#else
+ if(m_punk)
+ return RESULT(E_FAIL); // call Disconnect first
+ if (punkObj) {
+ punkObj->AddRef();
+ m_punk = punkObj;
+ }
+ return NOERROR;
+#endif
+}
+
+STDMETHODIMP_(void)
+CStubTypeInfo::Disconnect()
+{
+ if(m_punk){
+ m_punk->Release();
+ m_punk = NULL;
+ }
+ if(m_ptinfo){
+ m_ptinfo->Release();
+ m_ptinfo = NULL;
+ }
+}
+
+/***
+*PUBLIC HRESULT CStubTypeInfo::Invoke
+*
+*Purpose:
+* Dispatch the method with the given index (imeth) on the given
+* interface, using the arguments serialized in the given stream.
+*
+* This function is the callee side of an LRPC call.
+*
+*Entry:
+* iid = the IID of the interface on which we are to make the call
+* imeth = the method index
+* pstm = the IStream containing the method's actuals
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDMETHODIMP
+CStubTypeInfo::Invoke(
+#if (OE_WIN32 || defined(WOW))
+ RPCOLEMESSAGE *pMessage,
+ ICHANNEL *pRpcChannel)
+{
+ HRESULT hresult;
+ IStream FAR* pstm;
+
+ if(!m_punk)
+ return RESULT(E_FAIL);
+
+ OPEN_STUB_STREAM(pstm, pRpcChannel, pMessage, IID_ITypeInfo);
+
+#else
+ REFIID riid,
+ int iMethod,
+ IStream FAR* pstm,
+ unsigned long dwDestCtx,
+ void FAR* pvDestCtx)
+{
+ HRESULT hresult;
+
+ UNUSED(dwDestCtx);
+ UNUSED(pvDestCtx);
+
+ if(!IsEqualIID(riid, IID_ITypeInfo))
+ return RESULT(E_NOINTERFACE);
+
+ if(!m_punk)
+ return RESULT(E_FAIL);
+
+ if(m_ptinfo == NULL)
+ IfFailRet(m_punk->QueryInterface(IID_ITypeInfo, (void FAR* FAR*)&m_ptinfo));
+#endif
+
+ m_pstm = pstm;
+
+ switch(GET_IMETHOD(pMessage)){
+ case IMETH_TYPEINFO_GETTYPEATTR:
+ hresult = GetTypeAttr();
+ break;
+
+ case IMETH_TYPEINFO_GETTYPECOMP:
+ hresult = GetTypeComp();
+ break;
+
+ case IMETH_TYPEINFO_GETFUNCDESC:
+ hresult = GetFuncDesc();
+ break;
+
+ case IMETH_TYPEINFO_GETVARDESC:
+ hresult = GetVarDesc();
+ break;
+
+ case IMETH_TYPEINFO_GETNAMES:
+ hresult = GetNames();
+ break;
+
+ case IMETH_TYPEINFO_GETREFTYPEOFIMPLTYPE:
+ hresult = GetRefTypeOfImplType();
+ break;
+
+ case IMETH_TYPEINFO_GETIMPLTYPEFLAGS:
+ hresult = GetImplTypeFlags();
+ break;
+
+ case IMETH_TYPEINFO_GETIDSOFNAMES:
+ hresult = GetIDsOfNames();
+ break;
+
+ case IMETH_TYPEINFO_GETDOCUMENTATION:
+ hresult = GetDocumentation();
+ break;
+
+ case IMETH_TYPEINFO_GETDLLENTRY:
+ hresult = GetDllEntry();
+ break;
+
+ case IMETH_TYPEINFO_GETREFTYPEINFO:
+ hresult = GetRefTypeInfo();
+ break;
+
+ case IMETH_TYPEINFO_CREATEINSTANCE:
+ hresult = CreateInstance();
+ break;
+
+ case IMETH_TYPEINFO_GETCONTAININGTYPELIB:
+ hresult = GetContainingTypeLib();
+ break;
+
+ case IMETH_TYPEINFO_GETMOPS:
+ hresult = RESULT(E_NOTIMPL);
+ break;
+
+ // we should never see the following,
+ case IMETH_TYPEINFO_INVOKE: // not remotable
+ case IMETH_TYPEINFO_ADDRESSOFMEMBER: // not remotable(?)
+ case IMETH_TYPEINFO_RELEASETYPEATTR: // handled in proxy
+ case IMETH_TYPEINFO_RELEASEFUNCDESC: // handled in proxy
+ case IMETH_TYPEINFO_RELEASEVARDESC: // handled in proxy
+ default:
+ hresult = RESULT(E_INVALIDARG);
+ break;
+ }
+
+ RESET_STREAM(pstm);
+
+ DELETE_STREAM(pstm);
+
+ m_pstm = NULL;
+
+ return hresult;
+}
+
+
+/***
+*PUBLIC HRESULT CStubTypeInfo::IsIIDSupported(REFIID)
+*Purpose:
+* Answer if the given IID is supported by this stub.
+*
+*Entry:
+* iid = the IID to query for support
+*
+*Exit:
+* return value = BOOL. TRUE if IID is supported, FALSE otherwise.
+*
+***********************************************************************/
+#if OE_MAC
+STDMETHODIMP_(unsigned long)
+#elif (OE_WIN32 || defined(WOW))
+STDMETHODIMP_(IRpcStubBuffer *)
+#else
+STDMETHODIMP_(BOOL)
+#endif
+CStubTypeInfo::IsIIDSupported(REFIID riid)
+{
+#if (OE_WIN32 || defined(WOW))
+ IRpcStubBuffer *pStub = 0;
+ if (IsEqualIID(riid, IID_ITypeInfo)) {
+ AddRef();
+ pStub = (IRpcStubBuffer *) this;
+ }
+ return pStub;
+#else
+ // REVIEW: I don't understand this, but thats the way Ole does it...
+ if(m_punk == NULL)
+ return FALSE;
+
+ return(IsEqualIID(riid, IID_ITypeInfo));
+#endif
+}
+
+/***
+*unsigned long CStubTypeInfo::CountRefs
+*Purpose:
+* Return the count of references held by this stub.
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = unsigned long, the count of refs.
+*
+***********************************************************************/
+STDMETHODIMP_(unsigned long)
+CStubTypeInfo::CountRefs()
+{
+ unsigned long refs;
+
+ refs = 0;
+
+ if(m_punk != NULL)
+ ++refs;
+
+ if(m_ptinfo != NULL)
+ ++refs;
+
+ return refs;
+}
+
+/***
+*HRESULT CStubTypeInfo::GetTypeAttr
+*Purpose:
+*
+* In:
+* None
+*
+* Out:
+* <HRESULT hresult>
+* <TYPEATTR tattr>
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeInfo::GetTypeAttr()
+{
+ HRESULT hresult;
+ TYPEATTR FAR* ptypeattr;
+ unsigned long _proxySysKind, _stubSysKind;
+
+ IfFailGo(GET(m_pstm, _proxySysKind), LError0);
+ REWIND_STREAM(m_pstm);
+
+ ptypeattr = NULL;
+ m_hresultRet = m_ptinfo->GetTypeAttr(&ptypeattr);
+
+ IfFailGo(DispMarshalHresult(m_pstm, m_hresultRet), LError0);
+
+ // if call failed, do bother marshaling "out" params
+ if(HRESULT_FAILED(m_hresultRet))
+ goto LError0;
+
+ _stubSysKind = (unsigned long) SYS_CURRENT;
+ IfFailGo(PUT(m_pstm, _stubSysKind), LError0);
+
+ hresult = TypeattrWrite(m_pstm, ptypeattr, (SYSKIND) _proxySysKind);
+
+LError0:;
+ if(ptypeattr != NULL)
+ m_ptinfo->ReleaseTypeAttr(ptypeattr);
+
+ return hresult;
+
+}
+
+
+/***
+*HRESULT CStubTypeInfo::GetTypeComp
+*Purpose:
+*
+* In:
+* None
+*
+* Out:
+* <HRESULT hresultRet>
+* <ITypeComp tcomp>
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeInfo::GetTypeComp()
+{
+ HRESULT hresult;
+ ITypeComp FAR* ptcomp;
+
+ ptcomp = NULL;
+ m_hresultRet = m_ptinfo->GetTypeComp(&ptcomp);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(DispMarshalHresult(m_pstm, m_hresultRet), LError0);
+
+ // if call failed, do bother marshaling "out" params
+ if(HRESULT_FAILED(m_hresultRet))
+ goto LError0;
+
+ hresult = DispMarshalInterface(m_pstm, IID_ITypeComp, ptcomp);
+
+LError0:;
+ if(ptcomp != NULL)
+ ptcomp->Release();
+
+ return hresult;
+}
+
+/***
+*HRESULT CStubTypeInfo::GetFuncDesc
+*Purpose:
+*
+* In:
+* <unsigned int index>
+*
+* Out:
+* <HRESULT hresult>
+* <FUNCDESC funcdesc>
+*
+*Entry:
+* None
+*
+*Exit:
+* return value =
+*
+***********************************************************************/
+HRESULT
+CStubTypeInfo::GetFuncDesc()
+{
+ unsigned int index;
+ HRESULT hresult;
+ FUNCDESC FAR* pfuncdesc;
+ unsigned long _proxySysKind, _stubSysKind;
+ unsigned long _index;
+
+ IfFailGo(GET(m_pstm, _proxySysKind), LError0);
+
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ IfFailGo(GET(m_pstm, _index), LError0);
+ index = (unsigned int) _index;
+
+ pfuncdesc = NULL;
+ m_hresultRet = m_ptinfo->GetFuncDesc(index, &pfuncdesc);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(MarshalResult(), LError0);
+
+ // if call failed, do bother marshaling "out" params
+ if(HRESULT_FAILED(m_hresultRet))
+ goto LError0;
+
+ _stubSysKind = (unsigned long) SYS_CURRENT;
+ IfFailGo(PUT(m_pstm, _stubSysKind), LError0);
+
+ hresult = FuncdescWrite(m_pstm, pfuncdesc, (SYSKIND) _proxySysKind);
+
+LError0:;
+ if(pfuncdesc != NULL)
+ m_ptinfo->ReleaseFuncDesc(pfuncdesc);
+
+ return hresult;
+}
+
+/***
+*HRESULT GetTypeInfoStub::GetVarDesc
+*Purpose:
+*
+* In:
+* <unsigned int index>
+*
+* Out:
+* <HRESULT hresult>
+* <VARDESC vardesc>
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeInfo::GetVarDesc()
+{
+ unsigned int index;
+ HRESULT hresult;
+ VARDESC FAR* pvardesc;
+ unsigned long _proxySysKind, _stubSysKind;
+ unsigned long _index;
+
+ IfFailGo(GET(m_pstm, _proxySysKind), LError0);
+
+ // unsigned int always marshal/unmarshal as long (4 bytes)
+ IfFailGo(GET(m_pstm, _index), LError0);
+ index = (unsigned int) _index;
+
+ pvardesc = NULL;
+ m_hresultRet = m_ptinfo->GetVarDesc(index, &pvardesc);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(MarshalResult(), LError1);
+
+ // if call failed, don't bother marshaling "out" params
+ if(HRESULT_FAILED(m_hresultRet))
+ goto LError1;
+
+ _stubSysKind = (unsigned long) SYS_CURRENT;
+ IfFailGo(PUT(m_pstm, _stubSysKind), LError1);
+
+ IfFailGo(VardescWrite(m_pstm, pvardesc, (SYSKIND) _proxySysKind), LError1);
+
+LError1:;
+ if(pvardesc != NULL)
+ m_ptinfo->ReleaseVarDesc(pvardesc);
+
+LError0:;
+ return hresult;
+}
+
+/***
+*HRESULT CStubTypeInfo::GetNames
+*Purpose:
+*
+* In:
+* <MEMBERID memid>
+* <unsigned int cMaxNames>
+*
+* Out:
+* <HRESULT hresultRet>
+* <unsigned int cNames>
+* <BSTR bstrName>*
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeInfo::GetNames()
+{
+ MEMBERID memid;
+ HRESULT hresult;
+ BSTR FAR* rgbstrNames;
+ unsigned int u, cNames, cMaxNames;
+ unsigned long _cNames, _cMaxNames;
+ unsigned long _proxySysKind, _stubSysKind;
+
+ IfFailGo(GET(m_pstm, _proxySysKind), LError0);
+
+ IfFailGo(GET(m_pstm, memid), LError0);
+
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ IfFailGo(GET(m_pstm, _cMaxNames), LError0);
+ cMaxNames = (unsigned int) _cMaxNames;
+
+ if((rgbstrNames = new FAR BSTR [cMaxNames]) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LError0;
+ }
+
+ cNames = 0;
+ // REVIEW: should we init rgbstrNames to null here, just to be safe?
+ m_hresultRet = m_ptinfo->GetNames(memid, rgbstrNames, cMaxNames, &cNames);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(MarshalResult(), LError1);
+
+ // if call failed, do bother marshaling "out" params
+ if(HRESULT_FAILED(m_hresultRet))
+ goto LError1;
+
+ _stubSysKind = (unsigned long) SYS_CURRENT;
+ IfFailGo(PUT(m_pstm, _stubSysKind), LError1);
+
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ _cNames = cNames;
+ IfFailGo(PUT(m_pstm, _cNames), LError1);
+
+ for(u = 0; u < cNames; ++u){
+ IfFailGo(BstrWrite(m_pstm, rgbstrNames[u], (SYSKIND) _proxySysKind), LError1);
+ }
+
+LError1:;
+ // assume no names were allocated unless the call succeeded
+ if(HRESULT_SUCCESS(m_hresultRet)){
+ for(u = 0; u < cNames; ++u)
+ SysFreeString(rgbstrNames[u]);
+ }
+ delete rgbstrNames;
+
+LError0:;
+ return hresult;
+}
+
+/***
+*HRESULT CStubTypeInfo::GetRefTypeOfImplType
+*Purpose:
+*
+* In:
+* <unsigned int index>
+*
+* Out:
+* <HRESULT hresultRet>
+* <HREFTYPE hreftype>
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeInfo::GetRefTypeOfImplType()
+{
+ unsigned int index;
+ HRESULT hresult;
+ HREFTYPE hreftype;
+ unsigned long _index;
+
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ IfFailGo(GET(m_pstm, _index), LError1);
+ index = (unsigned int) _index;
+
+ m_hresultRet = m_ptinfo->GetRefTypeOfImplType(index, &hreftype);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(MarshalResult(), LError1);
+
+ if(HRESULT_FAILED(m_hresultRet))
+ goto LError1;
+
+ hresult = PUT(m_pstm, hreftype);
+
+LError1:;
+ return hresult;
+}
+
+/***
+*HRESULT CStubTypeInfo::GetImplTypeFlags
+*Purpose:
+*
+* In:
+* <unsigned int index>
+*
+* Out:
+* <HRESULT hresultRet>
+* <int impltypeflags>
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeInfo::GetImplTypeFlags()
+{
+ unsigned int index;
+ HRESULT hresult;
+ int impltypeflags;
+ unsigned long _impltypeflags;
+ unsigned long _index;
+
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ IfFailGo(GET(m_pstm, _index), LError1);
+ index = (unsigned int) _index;
+
+ m_hresultRet = m_ptinfo->GetImplTypeFlags(index, &impltypeflags);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(MarshalResult(), LError1);
+
+ if(HRESULT_FAILED(m_hresultRet))
+ goto LError1;
+
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ _impltypeflags = impltypeflags;
+ hresult = PUT(m_pstm, _impltypeflags);
+
+LError1:;
+ return hresult;
+}
+
+HRESULT
+CStubTypeInfo::GetIDsOfNames()
+{
+ return RESULT(E_NOTIMPL);
+}
+
+/***
+*HRESULT CStubTypeInfo::GetDocumentation
+*Purpose:
+*
+* In:
+* <MEMBERID memid>
+*
+* Out:
+* <HRESULT hresultRet>
+* <unsigned long dwHelpContext>
+* <BSTR bstrName>
+* <BSTR bstrDocString>
+* <BSTR bstrHelpFile>
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeInfo::GetDocumentation()
+{
+ MEMBERID memid;
+ HRESULT hresult;
+ unsigned long dwHelpContext;
+ BSTR bstrName, bstrDocString, bstrHelpFile;
+ unsigned long _proxySysKind, _stubSysKind;
+
+ IfFailGo(GET(m_pstm, _proxySysKind), LError0);
+
+ IfFailGo(GET(m_pstm, memid), LError0);
+
+ bstrName = NULL;
+ bstrHelpFile = NULL;
+ bstrDocString = NULL;
+
+ m_hresultRet = m_ptinfo->GetDocumentation(
+ memid, &bstrName, &bstrDocString, &dwHelpContext, &bstrHelpFile);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(MarshalResult(), LError1);
+
+ // if call failed, dont marshal "out" params
+ if(HRESULT_FAILED(m_hresultRet))
+ goto LError1;
+
+ _stubSysKind = (unsigned long) SYS_CURRENT;
+ IfFailGo(PUT(m_pstm, _stubSysKind), LError1);
+
+ IfFailGo(PUT(m_pstm, dwHelpContext), LError1);
+ IfFailGo(BstrWrite(m_pstm, bstrName, (SYSKIND) _proxySysKind), LError1);
+ IfFailGo(BstrWrite(m_pstm, bstrDocString, (SYSKIND) _proxySysKind), LError1);
+ IfFailGo(BstrWrite(m_pstm, bstrHelpFile, (SYSKIND) _proxySysKind), LError1);
+
+ hresult = NOERROR;
+
+LError1:;
+ // assume none of these were allocated if the call failed
+ if(HRESULT_SUCCESS(m_hresultRet)){
+ SysFreeString(bstrName);
+ SysFreeString(bstrHelpFile);
+ SysFreeString(bstrDocString);
+ }
+
+LError0:;
+ return hresult;
+}
+
+/***
+*HRESULT CStubTypeInfo::GetDllEntry
+*Purpose:
+*
+* In:
+* <MEMBERID memid>
+*
+* Out:
+* <HRESULT hresultRet>
+* <unsigned short wOrdinal>
+* <BSTR bstrDllName>
+* <BSTR bstrName>
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeInfo::GetDllEntry()
+{
+ MEMBERID memid;
+ INVOKEKIND invkind;
+ HRESULT hresult;
+ unsigned short wOrdinal;
+ BSTR bstrName, bstrDllName;
+ unsigned long _proxySysKind, _stubSysKind;
+ unsigned long _invkind;
+
+ IfFailGo(GET(m_pstm, _proxySysKind), LError0);
+
+ IfFailGo(GET(m_pstm, memid), LError0);
+
+ IfFailGo(GET(m_pstm, _invkind), LError0);
+ invkind = (INVOKEKIND) _invkind;
+
+ bstrName = NULL;
+ bstrDllName = NULL;
+
+ m_hresultRet = m_ptinfo->GetDllEntry(
+ memid, invkind, &bstrDllName, &bstrName, &wOrdinal);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(MarshalResult(), LError1);
+
+ // if call failed, dont marshal "out" params
+ if(HRESULT_FAILED(m_hresultRet))
+ goto LError1;
+
+ _stubSysKind = (unsigned long) SYS_CURRENT;
+ IfFailGo(PUT(m_pstm, _stubSysKind), LError1);
+
+ IfFailGo(PUT(m_pstm, wOrdinal), LError1);
+ IfFailGo(BstrWrite(m_pstm, bstrDllName, (SYSKIND) _proxySysKind), LError1);
+ IfFailGo(BstrWrite(m_pstm, bstrName, (SYSKIND) _proxySysKind), LError1);
+
+ hresult = NOERROR;
+
+LError1:;
+ // assume none of these were allocated if the call failed
+ if(HRESULT_SUCCESS(m_hresultRet)){
+ SysFreeString(bstrName);
+ SysFreeString(bstrDllName);
+ }
+
+LError0:;
+ return hresult;
+}
+
+/***
+*HRESULT CStubTypeInfo::GetRefTypeInfo
+*Purpose:
+*
+* In:
+* <HREFTYPE hreftype>
+*
+* Out:
+* <HRESULT hresultRet>
+* <ITypeInfo itinfo>
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeInfo::GetRefTypeInfo()
+{
+ HREFTYPE hreftype;
+ HRESULT hresult;
+ ITypeInfo FAR* ptinfo;
+
+ IfFailGo(GET(m_pstm, hreftype), LError0);
+
+ ptinfo = NULL;
+ m_hresultRet = m_ptinfo->GetRefTypeInfo(hreftype, &ptinfo);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(MarshalResult(), LError1);
+
+ // if call failed, do bother marshaling "out" params
+ if(HRESULT_FAILED(m_hresultRet))
+ goto LError1;
+
+ hresult = DispMarshalInterface(m_pstm, IID_ITypeInfo, ptinfo);
+
+LError1:;
+ if(ptinfo != NULL)
+ ptinfo->Release();
+
+LError0:;
+ return hresult;
+}
+
+/***
+*HRESULT CStubTypeInfo::CreateInstance
+*Purpose:
+* Stub implementation of ITypeInfo::CreateInstance
+*
+* Marshal In:
+* IID
+*
+* Marshal Out:
+* newly create interface ptr.
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeInfo::CreateInstance()
+{
+ IID iid;
+ HRESULT hresult;
+ void FAR* pvObj;
+
+ IfFailGo(m_pstm->Read((void FAR*)&iid, sizeof(IID), NULL), Error);
+
+ m_hresultRet = m_ptinfo->CreateInstance(NULL, iid, &pvObj);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(MarshalResult(), Error);
+
+ // If call failed, don't marshal the out params
+ if(HRESULT_FAILED(m_hresultRet))
+ goto Error;
+
+ hresult = DispMarshalInterface(m_pstm, iid, (IUnknown FAR*)pvObj);
+
+ ((IUnknown FAR*)pvObj)->Release();
+
+Error:;
+ return hresult;
+}
+
+/***
+*HRESULT CStubTypeInfo::GetContainingTypeLib
+*Purpose:
+*
+* In:
+* None
+*
+* Out:
+* <HRESULT hresultRet>
+* <unsigned int index>
+* <ITypeLib tlib>
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeInfo::GetContainingTypeLib()
+{
+ unsigned int index;
+ HRESULT hresult;
+ ITypeLib FAR* ptlib;
+ unsigned long _index;
+
+ ptlib = NULL;
+ m_hresultRet = m_ptinfo->GetContainingTypeLib(&ptlib, &index);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(DispMarshalHresult(m_pstm, m_hresultRet), LError0);
+
+ // unsigned int alway marshal/unmarshal as long (4 bytes)
+ _index = index;
+ IfFailGo(PUT(m_pstm, _index), LError0);
+
+ hresult = DispMarshalInterface(m_pstm, IID_ITypeLib, ptlib);
+
+
+LError0:;
+ if(ptlib != NULL)
+ ptlib->Release();
+
+ return hresult;
+}
+
+
+//---------------------------------------------------------------------
+// helpers
+//---------------------------------------------------------------------
+
+// this is a helper for the TypeInfo stub methods, that all return
+// the called methods hresult as the first marshaled result.
+
+HRESULT
+CStubTypeInfo::MarshalResult()
+{
+ /*IfFailRet(Rewind(m_pstm));*/
+
+ return DispMarshalHresult(m_pstm, m_hresultRet);
+}
+
+
+
+#if (OE_WIN32 || defined(WOW))
+
+STDMETHODIMP
+CStubTypeInfo::DebugServerQueryInterface(void FAR* FAR* ppv)
+{
+ *ppv = m_ptinfo;
+ return S_OK;
+}
+
+
+STDMETHODIMP_(void)
+CStubTypeInfo::DebugServerRelease(void FAR* ppv)
+{
+
+}
+
+#endif
diff --git a/private/oleauto/src/dispatch/tiutil.cpp b/private/oleauto/src/dispatch/tiutil.cpp
new file mode 100644
index 000000000..a63c693ba
--- /dev/null
+++ b/private/oleauto/src/dispatch/tiutil.cpp
@@ -0,0 +1,99 @@
+/***
+*tiutil.cxx - TypeInfo/TypeLib Utilities
+*
+* Copyright (C) 1994, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file contains misc TypeInfo/TypeLib releated utilities.
+*
+*Documentation:
+*
+*Revision History:
+*
+* [00] 23-Jun-94 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+ASSERTDATA
+
+
+/***
+*PUBLIC HRESULT GetPrimaryInterface
+*Purpose:
+* Given a TypeInfo describing a Coclass, search for and return
+* type TypeInfo that describes that class' primary interface.
+*
+*Entry:
+* ptinfo = the TypeInfo of the base class.
+*
+*Exit:
+* return value = HRESULT
+*
+* *ptinfoPrimary = the TypeInfo of the primary interface, NULL
+* if the class does not have a primary interface.
+*
+***********************************************************************/
+INTERNAL_(HRESULT)
+GetPrimaryInterface(ITypeInfo *ptinfo, ITypeInfo **pptinfoPri)
+{
+ BOOL fIsDual;
+ TYPEKIND tkind;
+ HRESULT hresult;
+ HREFTYPE hreftype;
+ int impltypeflags;
+ TYPEATTR *ptattr;
+ unsigned int iImplType, cImplTypes;
+ ITypeInfo *ptinfoRef;
+
+ ptinfoRef = NULL;
+
+ IfFailGo(ptinfo->GetTypeAttr(&ptattr), Error);
+ cImplTypes = ptattr->cImplTypes;
+ tkind = ptattr->typekind;
+ ptinfo->ReleaseTypeAttr(ptattr);
+
+ if(tkind != TKIND_COCLASS)
+ return RESULT(E_INVALIDARG);
+
+ // Look for the interface marked [default] and not [source]
+ for(iImplType = 0; iImplType < cImplTypes; ++iImplType){
+ IfFailGo(ptinfo->GetImplTypeFlags(iImplType, &impltypeflags), Error);
+ if(IMPLTYPEFLAG_FDEFAULT
+ == (impltypeflags & (IMPLTYPEFLAG_FDEFAULT | IMPLTYPEFLAG_FSOURCE)))
+ {
+ // Found It!
+ IfFailGo(ptinfo->GetRefTypeOfImplType(iImplType, &hreftype), Error);
+ IfFailGo(ptinfo->GetRefTypeInfo(hreftype, &ptinfoRef), Error);
+
+ // If its dual, get the interface portion
+ IfFailGo(ptinfoRef->GetTypeAttr(&ptattr), Error);
+ fIsDual = (ptattr->wTypeFlags & TYPEFLAG_FDUAL)
+ && (ptattr->typekind == TKIND_DISPATCH);
+ ptinfoRef->ReleaseTypeAttr(ptattr);
+
+ if (fIsDual) {
+ IfFailGo(ptinfoRef->GetRefTypeOfImplType((UINT)-1, &hreftype), Error);
+ IfFailGo(ptinfoRef->GetRefTypeInfo(hreftype, pptinfoPri), Error);
+ ptinfoRef->Release();
+ }
+ else {
+ *pptinfoPri = ptinfoRef;
+ }
+
+ return NOERROR;
+ }
+ }
+ // NotFound
+ *pptinfoPri = NULL;
+ return NOERROR;
+
+Error:
+ if(ptinfoRef != NULL)
+ ptinfoRef->Release();
+ return hresult;
+}
+
diff --git a/private/oleauto/src/dispatch/tlprox.cpp b/private/oleauto/src/dispatch/tlprox.cpp
new file mode 100644
index 000000000..05d6d4938
--- /dev/null
+++ b/private/oleauto/src/dispatch/tlprox.cpp
@@ -0,0 +1,867 @@
+/***
+*tlprox.cpp
+*
+* Copyright (C) 1992-94, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This module implements the ITypeLib proxy class.
+*
+*Revision History:
+*
+* [00] 05-Apr-94 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#ifndef WIN32
+#include <cobjps.h>
+#endif //!WIN32
+
+#include "dispmrsh.h"
+#include "tlps.h"
+//#include "dispstrm.h"
+
+ASSERTDATA
+
+
+CProxTypeLib::CProxTypeLib(IUnknown FAR* punkOuter)
+ : m_unk(this), m_proxy(this), m_tlib(this)
+{
+ if(punkOuter == NULL)
+ punkOuter = &m_unk;
+ m_punkOuter = punkOuter;
+}
+
+IUnknown FAR*
+CProxTypeLib::Create(IUnknown FAR* punkOuter)
+{
+ CProxTypeLib FAR* pproxtinfo;
+
+ if((pproxtinfo = new FAR CProxTypeLib(punkOuter)) != NULL){
+ pproxtinfo->m_refs = 1;
+ return &pproxtinfo->m_unk;
+ }
+ return NULL;
+}
+
+
+//---------------------------------------------------------------------
+// ITypeLib proxy class' IUnknown implementation
+//---------------------------------------------------------------------
+
+CPTLibUnkImpl::CPTLibUnkImpl(CProxTypeLib FAR* pproxtlib)
+{
+ m_pproxtlib = pproxtlib;
+}
+
+STDMETHODIMP
+CPTLibUnkImpl::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ *ppv = NULL;
+ if(IsEqualIID(riid, IID_IUnknown)){
+ *ppv = (void FAR*)&(m_pproxtlib->m_unk);
+ }else
+ if(IsEqualIID(riid, IID_IPROXY)){
+ *ppv = (void FAR*)&(m_pproxtlib->m_proxy);
+ }else
+ if(IsEqualIID(riid, IID_ITypeLib)){
+ *ppv = (void FAR*)&(m_pproxtlib->m_tlib);
+ }
+ if(*ppv == NULL)
+ return RESULT(E_NOINTERFACE);
+ ((IUnknown FAR*)*ppv)->AddRef();
+ return NOERROR;
+}
+
+STDMETHODIMP_(unsigned long)
+CPTLibUnkImpl::AddRef()
+{
+ return ++m_pproxtlib->m_refs;
+}
+
+STDMETHODIMP_(unsigned long)
+CPTLibUnkImpl::Release()
+{
+ if(--m_pproxtlib->m_refs==0){
+ delete m_pproxtlib;
+ return 0;
+ }
+ return m_pproxtlib->m_refs;
+}
+
+
+//---------------------------------------------------------------------
+// ITypeLib proxy class' IRpcProxy implementation
+//---------------------------------------------------------------------
+
+CPTLibProxImpl::CPTLibProxImpl(CProxTypeLib FAR* pproxtlib)
+{
+ m_pproxtlib = pproxtlib;
+}
+
+CPTLibProxImpl::~CPTLibProxImpl()
+{
+ if(m_pproxtlib->m_plrpc)
+ m_pproxtlib->m_plrpc->Release();
+}
+
+STDMETHODIMP
+CPTLibProxImpl::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ return m_pproxtlib->m_unk.QueryInterface(riid, ppv);
+}
+
+STDMETHODIMP_(unsigned long)
+CPTLibProxImpl::AddRef()
+{
+ return m_pproxtlib->m_unk.AddRef();
+}
+
+STDMETHODIMP_(unsigned long)
+CPTLibProxImpl::Release()
+{
+ return m_pproxtlib->m_unk.Release();
+}
+
+STDMETHODIMP
+CPTLibProxImpl::Connect(ICHANNEL FAR* plrpc)
+{
+ if(plrpc){
+ plrpc->AddRef();
+ m_pproxtlib->m_plrpc = plrpc;
+ return m_pproxtlib->m_tlib.SysKind();
+ }
+ return RESULT(E_FAIL);
+}
+
+STDMETHODIMP_(void)
+CPTLibProxImpl::Disconnect()
+{
+ if(m_pproxtlib->m_plrpc)
+ m_pproxtlib->m_plrpc->Release();
+ m_pproxtlib->m_plrpc = NULL;
+}
+
+
+//---------------------------------------------------------------------
+// ITypeLib proxy class' ITypeLib methods
+//---------------------------------------------------------------------
+
+CPTLibTypeLibImpl::CPTLibTypeLibImpl(CProxTypeLib FAR* pproxtlib)
+{
+ m_pproxtlib = pproxtlib;
+ m_syskindStub = (SYSKIND)-1; // something invalid
+}
+
+STDMETHODIMP
+CPTLibTypeLibImpl::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ return m_pproxtlib->m_punkOuter->QueryInterface(riid, ppv);
+}
+
+STDMETHODIMP_(unsigned long)
+CPTLibTypeLibImpl::AddRef()
+{
+ return m_pproxtlib->m_punkOuter->AddRef();
+}
+
+STDMETHODIMP_(unsigned long)
+CPTLibTypeLibImpl::Release()
+{
+ return m_pproxtlib->m_punkOuter->Release();
+}
+
+//
+// ITypeLib methods
+//
+
+/***
+*unsigned int CPTLibTypeLibImpl::GetTypeInfoCount
+*Purpose:
+* The proxy implementation of ITypeLib::GetTypeInfoCount
+*
+* Marshal In:
+* None
+*
+* Marshal Out:
+* ULONG cTypeInfo
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT CPTLibTypeLibImpl::DoGetTypeInfoCount(unsigned int FAR* pcTinfo)
+{
+ HRESULT hresult;
+ IStream FAR* pstm;
+ ICHANNEL FAR* plrpc;
+ unsigned long ulCount;
+
+ if((plrpc = m_pproxtlib->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPELIB_GETTYPEINFOCOUNT, 256, IID_ITypeLib);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(GET(pstm, ulCount), LError1);
+
+ *pcTinfo = (unsigned int)ulCount;
+
+LError1:;
+ pstm->Release();
+ return hresult;
+}
+STDMETHODIMP_(unsigned int)
+CPTLibTypeLibImpl::GetTypeInfoCount(void)
+{
+ unsigned int cTinfo;
+ HRESULT hresult;
+
+ hresult = DoGetTypeInfoCount(&cTinfo);
+ if(HRESULT_FAILED(hresult))
+ return 0;
+ return cTinfo;
+}
+
+/***
+*HRESULT CPTLibTypeLibImpl::GetTypeInfo
+*Purpose:
+* The proxy implementation of ITypeLib::GetTypeInfo
+*
+*Entry:
+* index = the index of the the typeinfo were retrieving.
+*
+* Marshal In:
+* ULONG index
+*
+* Marshal Out:
+* HRESULT hresult
+* ITypeLib* ptlib
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDMETHODIMP
+CPTLibTypeLibImpl::GetTypeInfo(unsigned int index, ITypeInfo FAR* FAR* pptinfo)
+{
+ IStream FAR* pstm;
+ ICHANNEL FAR* plrpc;
+ unsigned long ulIndex;
+ HRESULT hresult, hresultRet;
+
+ if((plrpc = m_pproxtlib->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPELIB_GETTYPEINFO, 256, IID_ITypeLib);
+
+ ulIndex = (unsigned long)index;
+ IfFailGo(PUT(pstm, ulIndex), LError1);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError2;
+
+ IfFailGo(
+ DispUnmarshalInterface(pstm, IID_ITypeInfo, (void FAR* FAR*)pptinfo),
+ LError1);
+
+LError2:;
+ hresult = hresultRet;
+
+LError1:;
+ pstm->Release();
+ return hresult;
+}
+
+/***
+*HRESULT CPTLibTypeLibImpl::GetTypeInfoType
+*Purpose:
+* The proxy implementation of ITypeLib::GetTypeInfoType
+*
+* Marshal In:
+* ULONG index
+*
+* Marshal Out:
+* HRESULT hresult
+* ULONG tkind
+*
+*Entry:
+* index = the index of the typeinfo whose type were retrieving
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDMETHODIMP
+CPTLibTypeLibImpl::GetTypeInfoType(unsigned int index, TYPEKIND FAR* ptkind)
+{
+ TYPEKIND tkind;
+ unsigned long ulTkind;
+ IStream FAR* pstm;
+ ICHANNEL FAR* plrpc;
+ unsigned long ulIndex;
+ HRESULT hresult, hresultRet;
+
+ if((plrpc = m_pproxtlib->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPELIB_GETTYPEINFOTYPE, 256, IID_ITypeLib);
+
+ ulIndex = (unsigned long)index;
+ IfFailGo(PUT(pstm, ulIndex), LError1);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError2;
+
+ IfFailGo(GET(pstm, ulTkind), LError1);
+ tkind = (TYPEKIND)ulTkind;
+
+ *ptkind = tkind;
+
+LError2:;
+ hresult = hresultRet;
+
+LError1:;
+ pstm->Release();
+ return hresult;
+}
+
+/***
+*HRESULT CPTLibTypeLibImpl::GetTypeInfoOfGuid
+*Purpose:
+* The proxy implementation of ITypeLib::GetTypeInfoOfGuid
+*
+* Marshal In:
+* GUID guid
+*
+* Marshal Out:
+* HRESULT hresult
+* ITypeInfo* ptinfo
+*
+*Entry:
+* guid = the guid of the typeinfo to retrieve
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDMETHODIMP
+CPTLibTypeLibImpl::GetTypeInfoOfGuid(REFGUID guid, ITypeInfo FAR* FAR* pptinfo)
+{
+ IStream FAR* pstm;
+ ICHANNEL FAR* plrpc;
+ HRESULT hresult, hresultRet;
+
+ if((plrpc = m_pproxtlib->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPELIB_GETTYPEINFOOFGUID, 256,IID_ITypeLib);
+
+ // Write the guid
+ IfFailGo(pstm->Write((const void FAR*)&guid, sizeof(GUID), NULL), LError1);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError2;
+
+ IfFailGo(
+ DispUnmarshalInterface(pstm, IID_ITypeInfo, (void FAR* FAR*)pptinfo),
+ LError1);
+
+LError2:;
+ hresult = hresultRet;
+
+LError1:;
+ pstm->Release();
+ return hresult;
+}
+
+/***
+*HRESULT CPTLibTypeLibImpl::GetLibAttr
+*Purpose:
+* The proxy implementation of ITypeLib::GetLibAttr
+*
+* Marshal In:
+* None
+*
+* Marshal Out:
+* HRESULT hresult
+* TLIBATTR tlibattr
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDMETHODIMP
+CPTLibTypeLibImpl::GetLibAttr(TLIBATTR FAR* FAR* pptlibattr)
+{
+ IStream FAR* pstm;
+ ICHANNEL FAR* plrpc;
+ TLIBATTR FAR* ptlibattr;
+ HRESULT hresult, hresultRet;
+
+ if((plrpc = m_pproxtlib->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPELIB_GETLIBATTR, 256, IID_ITypeLib);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError2;
+
+ if((ptlibattr = new TLIBATTR) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LError1;
+ }
+
+ hresult = ReadLibAttr(pstm, ptlibattr);
+
+ if(HRESULT_FAILED(hresult)){
+ delete ptlibattr;
+ goto LError1;
+ }
+
+ *pptlibattr = ptlibattr;
+
+LError2:;
+ hresult = hresultRet;
+
+LError1:;
+ pstm->Release();
+ return hresult;
+}
+
+/***
+*HRESULT CPTLibTypeLibImpl::GetTypeComp
+*Purpose:
+* The proxy implementation of ITypeLib::GetTypeComp
+*
+*Entry:
+* None
+*
+* Marshal In:
+* None
+*
+* Marshal Out:
+* HRESULT hresult
+* ITypeComp *ptcomp
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDMETHODIMP
+CPTLibTypeLibImpl::GetTypeComp(ITypeComp FAR* FAR* pptcomp)
+{
+ IStream FAR* pstm;
+ ICHANNEL FAR* plrpc;
+ HRESULT hresult, hresultRet;
+
+ if((plrpc = m_pproxtlib->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPELIB_GETTYPECOMP, 256, IID_ITypeLib);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError2;
+
+ IfFailGo(
+ DispUnmarshalInterface(pstm, IID_ITypeComp, (void FAR* FAR*)pptcomp),
+ LError1);
+
+LError2:;
+ hresult = hresultRet;
+
+LError1:;
+ pstm->Release();
+ return hresult;
+}
+
+/***
+*HRESULT CPTLibTypeLibImpl::GetDocumentation
+*Purpose:
+*
+* Marshal In:
+* ULONG index
+* UCHAR fHelpContext
+* UCHAR fName
+* UCHAR fDocString
+* UCHAR fHelpFile
+
+* Marshal Out:
+* HRESULT hresult
+* if(fHelpContext) ULONG dwHelpContext
+* if(fName) BSTR bstrName
+* if(fDocString) BSTR bstrDocString
+* if(fHelpFile) BSTR bstrHelpFile
+*
+*Entry:
+* index = the index of the typeinfo to get the documentation for.
+*
+*Exit:
+* return value = HRESULT
+*
+* *pbstrName = the name of the typeinfo
+* *pbstrDocString = a doc string describing the typeinfo
+* *pdwHelpContext = a help context for the typeinfo
+* *pbstrHelpFile = path to the help file for the typeinfo
+*
+***********************************************************************/
+STDMETHODIMP
+CPTLibTypeLibImpl::GetDocumentation(
+ int index,
+ BSTR FAR* pbstrName,
+ BSTR FAR* pbstrDocString,
+ unsigned long FAR* pdwHelpContext,
+ BSTR FAR* pbstrHelpFile)
+{
+ IStream FAR* pstm;
+ ICHANNEL FAR* plrpc;
+ unsigned long ulIndex;
+ HRESULT hresult, hresultRet;
+ unsigned char fHelpContext, fName, fDocString, fHelpFile;
+
+ BSTR bstrName;
+ BSTR bstrDocString;
+ BSTR bstrHelpFile;
+ unsigned long dwHelpContext;
+
+ bstrName = NULL;
+ bstrDocString = NULL;
+ bstrHelpFile = NULL;
+
+ if((plrpc = m_pproxtlib->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPELIB_GETDOCUMENTATION, 256, IID_ITypeLib);
+
+ ulIndex = (unsigned long)index;
+ IfFailGo(PUT(pstm, ulIndex), LError1);
+
+ fHelpContext = (pdwHelpContext != NULL);
+ IfFailGo(PUT(pstm, fHelpContext), LError1);
+
+ fName = (pbstrName != NULL);
+ IfFailGo(PUT(pstm, fName), LError1);
+
+ fDocString = (pbstrDocString != NULL);
+ IfFailGo(PUT(pstm, fDocString), LError1);
+
+ fHelpFile = (pbstrHelpFile != NULL);
+ IfFailGo(PUT(pstm, fHelpFile), LError1);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+ if(HRESULT_FAILED(hresultRet))
+ goto LError2;
+
+ if(fHelpContext)
+ IfFailGo(GET(pstm, dwHelpContext), LError1);
+ if(fName)
+ IfFailGo(BstrRead(pstm, &bstrName, m_syskindStub), LError1);
+ if(fDocString)
+ IfFailGo(BstrRead(pstm, &bstrDocString, m_syskindStub), LError1);
+ if(fHelpFile)
+ IfFailGo(BstrRead(pstm, &bstrHelpFile, m_syskindStub), LError1);
+
+ // Success! assign the out params..
+ if(fHelpContext)
+ *pdwHelpContext = dwHelpContext;
+ if(fName)
+ *pbstrName = bstrName;
+ if(fDocString)
+ *pbstrDocString = bstrDocString;
+ if(fHelpFile)
+ *pbstrHelpFile = bstrHelpFile;
+
+LError2:;
+ hresult = hresultRet;
+
+LError1:;
+ if(HRESULT_FAILED(hresult)){
+ if(bstrName != NULL)
+ SysFreeString(bstrName);
+ if(bstrDocString != NULL)
+ SysFreeString(bstrDocString);
+ if(bstrHelpFile != NULL)
+ SysFreeString(bstrHelpFile);
+ }
+ pstm->Release();
+ return hresult;
+}
+
+/***
+*HRESULT CPTLibTypeLibImpl::IsName
+*Purpose:
+* The proxy implementation of ITypeLib::IsName
+*
+* Marshal In:
+* long lHashVal
+* BSTR name
+*
+* Marshal Out:
+* HRESULT hresult
+* long fName
+*
+*Entry:
+* szNameBuf = the name to check for
+* lHashVal = the hash value of the name where checking for
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDMETHODIMP
+CPTLibTypeLibImpl::IsName(
+ OLECHAR FAR* szNameBuf,
+ unsigned long lHashVal,
+ int FAR* pfName)
+{
+ BSTR bstr;
+ IStream FAR* pstm;
+ ICHANNEL FAR* plrpc;
+ unsigned long fName;
+ HRESULT hresult, hresultRet;
+
+ bstr = NULL;
+
+ if((plrpc = m_pproxtlib->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPELIB_ISNAME, 256, IID_ITypeLib);
+
+ IfFailGo(PUT(pstm, lHashVal), LError1);
+
+ IfFailGo(ErrSysAllocString(szNameBuf, &bstr), LError1);
+ IfFailGo(BstrWrite(pstm, bstr, m_syskindStub), LError1);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+ if(HRESULT_FAILED(hresultRet))
+ goto LError2;
+
+ IfFailGo(GET(pstm, fName), LError1);
+ *pfName = (int)fName;
+
+LError2:;
+ hresult = hresultRet;
+
+LError1:;
+ SysFreeString(bstr);
+ pstm->Release();
+ return hresult;
+}
+
+/***
+*HRESULT CPTLibTypeLibImpl::FindName
+*Purpose:
+* The proxy implementation of ITypeLib::FindName
+*
+* Marshal In:
+* ULONG cFound;
+* ULONG lHashVal
+* BSTR szNameBuf
+*
+* Marshal Out:
+* HRESULT hresult
+* ULONG cFound
+* MEMID[cFound] rgmemid
+* ITypeInfo[cFOund] rgptinfo
+*
+*Entry:
+* szNameBuf = the name to look for
+* lHashVal = the hash value of the name were looking for
+*
+*Exit:
+* return value = HRESULT
+*
+* rgptinfo = array populated with typeinfos where the name was found
+* rgmemid = array of memids indicating where on the corresponding
+* typeinfo the name was found.
+* *pcFound = the number of occurances that were found.
+*
+***********************************************************************/
+STDMETHODIMP
+CPTLibTypeLibImpl::FindName(
+ OLECHAR FAR* szNameBuf,
+ unsigned long lHashVal,
+ ITypeInfo FAR* FAR* rgptinfo,
+ MEMBERID FAR* rgmemid,
+ unsigned short FAR* pcFound)
+{
+ BSTR bstr;
+ IStream FAR* pstm;
+ ICHANNEL FAR* plrpc;
+ unsigned long i, cFound;
+ HRESULT hresult, hresultRet;
+
+ if((plrpc = m_pproxtlib->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPELIB_FINDNAME, 256, IID_ITypeLib);
+
+ bstr = NULL;
+ cFound = (unsigned long)*pcFound;
+ for(i = 0; i < cFound; ++i)
+ rgptinfo[i] = NULL;
+
+ IfFailGo(PUT(pstm, cFound), LError1);
+ IfFailGo(PUT(pstm, lHashVal), LError1);
+ IfFailGo(ErrSysAllocString(szNameBuf, &bstr), LError1);
+ IfFailGo(BstrWrite(pstm, bstr, m_syskindStub), LError1);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), LError1);
+ if(HRESULT_FAILED(hresultRet))
+ goto LError2;
+
+ IfFailGo(GET(pstm, cFound), LError1);
+ ASSERT(cFound <= (unsigned long)*pcFound);
+
+ IfFailGo(
+ pstm->Read(rgmemid, cFound * sizeof(MEMBERID), NULL),
+ LError1);
+
+ for(i = 0; i < cFound; ++i){
+ IfFailGo(
+ DispUnmarshalInterface(
+ pstm, IID_ITypeInfo, (void FAR* FAR*)&rgptinfo[i]),
+ LError1);
+ }
+ *pcFound = (unsigned short)cFound; // return count actually found
+
+LError2:;
+ hresult = hresultRet;
+LError1:;
+ if(HRESULT_FAILED(hresult)){
+ // cleanup if call failed.
+ for(i = 0; i < cFound; ++i){
+ if(rgptinfo[i] == NULL)
+ break;
+ rgptinfo[i]->Release();
+ rgptinfo[i] = NULL;
+ }
+ }
+ SysFreeString(bstr);
+ pstm->Release();
+ return hresult;
+}
+
+STDMETHODIMP_(void)
+CPTLibTypeLibImpl::ReleaseTLibAttr(TLIBATTR FAR* ptlibattr)
+{
+ if(ptlibattr != NULL)
+ delete ptlibattr;
+}
+
+/***
+*HRESULT CPTLibTypeLibImpl::SysKind
+*Purpose:
+* Exchange syskinds between proxy and stub.
+*
+* Marshal In:
+* ULONG syskindProxy
+*
+* Marshal Out:
+* ULONG syskindStub
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CPTLibTypeLibImpl::SysKind()
+{
+ HRESULT hresult;
+ IStream FAR* pstm;
+ ICHANNEL FAR* plrpc;
+ unsigned long syskind;
+
+ if((plrpc = m_pproxtlib->m_plrpc) == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ OPEN_STREAM(plrpc, pstm, IMETH_TYPELIB_SYSKIND, 32, IID_ITypeLib);
+
+ syskind = (unsigned long)SYS_CURRENT;
+ IfFailGo(PUT(pstm, syskind), LError1);
+
+ INVOKE_CALL(plrpc, pstm, LError1);
+
+ IfFailGo(GET(pstm, syskind), LError1);
+ m_syskindStub = (SYSKIND)syskind;
+
+LError1:
+ pstm->Release();
+ return hresult;
+}
+
+
+//---------------------------------------------------------------------
+// utilities
+//---------------------------------------------------------------------
+
+INTERNAL_(HRESULT)
+ReadLibAttr(IStream FAR* pstm, TLIBATTR FAR* ptlibattr)
+{
+ unsigned long syskind;
+
+ IfFailRet(GET(pstm, ptlibattr->guid));
+ IfFailRet(GET(pstm, ptlibattr->lcid));
+ IfFailRet(GET(pstm, syskind));
+ ptlibattr->syskind = (SYSKIND)syskind;
+ IfFailRet(GET(pstm, ptlibattr->wMajorVerNum));
+ IfFailRet(GET(pstm, ptlibattr->wMinorVerNum));
+ IfFailRet(GET(pstm, ptlibattr->wLibFlags));
+ return NOERROR;
+}
+
+INTERNAL_(HRESULT)
+WriteLibAttr(IStream FAR* pstm, TLIBATTR FAR* ptlibattr)
+{
+ unsigned long syskind;
+
+ IfFailRet(PUT(pstm, ptlibattr->guid));
+ IfFailRet(PUT(pstm, ptlibattr->lcid));
+ syskind = (unsigned long)ptlibattr->syskind;
+ IfFailRet(PUT(pstm, syskind));
+ IfFailRet(PUT(pstm, ptlibattr->wMajorVerNum));
+ IfFailRet(PUT(pstm, ptlibattr->wMinorVerNum));
+ IfFailRet(PUT(pstm, ptlibattr->wLibFlags));
+ return NOERROR;
+}
+
diff --git a/private/oleauto/src/dispatch/tlps.h b/private/oleauto/src/dispatch/tlps.h
new file mode 100644
index 000000000..3e8c90683
--- /dev/null
+++ b/private/oleauto/src/dispatch/tlps.h
@@ -0,0 +1,226 @@
+/***
+*tlps.h - ITypeLib Proxy and Stub class definitions
+*
+* Copyright (C) 1992-94, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file describes the ITypeLib Proxy and Stub classes.
+*
+* CProxTypeLib -- the ITypeLib proxy class
+* CPTLibUnkImpl - CProxTypeLib implementation of IUnknown
+* CPTLibProxImpl - CProxTypeLib implementation of IRpcProxy
+* CPTLibTypeLibImpl - CProxTypeLib implementation of ITypeLib
+*
+* CStubTypeLib -- the ITypeLib stub class
+*
+*Revision History:
+*
+* [00] 05-Apr-94 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+
+// forward declarations
+class FAR CProxTypeLib;
+class FAR CStubTypeLib;
+
+
+// ITypeLib proxy class' IUnknown implementation
+class FAR CPTLibUnkImpl : public IUnknown
+{
+public:
+ CPTLibUnkImpl(CProxTypeLib FAR* pproxtlib);
+
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+private:
+ CProxTypeLib FAR* m_pproxtlib;
+};
+
+
+// ITypeLib proxy class' IRpcProxy implementation
+class FAR CPTLibProxImpl : public IPROXY
+{
+public:
+ CPTLibProxImpl(CProxTypeLib FAR* pproxtlib);
+ ~CPTLibProxImpl();
+
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ STDMETHOD(Connect)(ICHANNEL FAR* plrpc);
+ STDMETHOD_(void, Disconnect)(void);
+
+private:
+ CProxTypeLib FAR* m_pproxtlib;
+};
+
+
+// ITypeLib
+class FAR CPTLibTypeLibImpl : public ITypeLib
+{
+public:
+ CPTLibTypeLibImpl(CProxTypeLib FAR* pproxtlib);
+
+ // IUnknown methods
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ // ITypeLib methods
+ STDMETHOD_(unsigned int, GetTypeInfoCount)(THIS);
+ STDMETHOD(GetTypeInfo)(unsigned int index, ITypeInfo FAR* FAR* pptinfo);
+ STDMETHOD(GetTypeInfoType)(unsigned int index, TYPEKIND FAR* ptypekind);
+ STDMETHOD(GetTypeInfoOfGuid)(REFGUID guid, ITypeInfo FAR* FAR* pptinfo);
+ STDMETHOD(GetLibAttr)(TLIBATTR FAR* FAR* pptlibattr);
+ STDMETHOD(GetTypeComp)(ITypeComp FAR* FAR* pptcomp);
+ STDMETHOD(GetDocumentation)(
+ int index,
+ BSTR FAR* pbstrName,
+ BSTR FAR* pbstrDocString,
+ unsigned long FAR* pdwHelpContext,
+ BSTR FAR* pbstrHelpFile);
+ STDMETHOD(IsName)(
+ OLECHAR FAR* szNameBuf,
+ unsigned long lHashVal,
+ int FAR* lpfName);
+ STDMETHOD(FindName)(
+ OLECHAR FAR* szNameBuf,
+ unsigned long lHashVal,
+ ITypeInfo FAR* FAR* rgptinfo,
+ MEMBERID FAR* rgmemid,
+ unsigned short FAR* pcFound);
+ STDMETHOD_(void, ReleaseTLibAttr)(TLIBATTR FAR* ptlibattr);
+
+ HRESULT SysKind(void);
+ HRESULT DoGetTypeInfoCount(unsigned int FAR* pcTinfo);
+
+private:
+ SYSKIND m_syskindStub;
+ CProxTypeLib FAR* m_pproxtlib;
+};
+
+// ITypeLib Proxy Class
+class FAR CProxTypeLib
+{
+public:
+ static IUnknown FAR* Create(IUnknown FAR* punkOuter);
+
+private:
+ CProxTypeLib(IUnknown FAR* punkOuter);
+
+ friend CPTLibUnkImpl;
+ friend CPTLibProxImpl;
+ friend CPTLibTypeLibImpl;
+
+ CPTLibUnkImpl m_unk;
+ CPTLibProxImpl m_proxy;
+ CPTLibTypeLibImpl m_tlib;
+
+private:
+
+ unsigned long m_refs;
+ ICHANNEL FAR* m_plrpc;
+ IUnknown FAR* m_punkOuter;
+};
+
+// ITypeLib Stub Class
+//
+class FAR CStubTypeLib : public ISTUB
+{
+public:
+ static HRESULT Create(IUnknown FAR* punkServer, ISTUB FAR* FAR* ppstub);
+
+ // IUnknown methods
+ //
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ // IRpcStub methods
+ //
+#if (OE_WIN32 || defined(WOW))
+ STDMETHOD(Connect)(IUnknown FAR* pUnk);
+ STDMETHOD_(void, Disconnect)(void);
+ STDMETHOD(Invoke)(RPCOLEMESSAGE FAR* pRpcMsg,
+ IRpcChannelBuffer FAR* pRpcChannel);
+ STDMETHOD_(IRpcStubBuffer *, IsIIDSupported)(REFIID iid);
+ STDMETHOD_(ULONG, CountRefs)(void);
+ STDMETHOD(DebugServerQueryInterface)(void FAR* FAR* ppv);
+ STDMETHOD_(void, DebugServerRelease)(void FAR* pv);
+#else
+ STDMETHOD(Connect)(IUnknown FAR* punkObject);
+ STDMETHOD_(void, Disconnect)(void);
+ STDMETHOD(Invoke)(
+ REFIID riid,
+ int imeth,
+ IStream FAR* pstm,
+ unsigned long dwDestCtx,
+ void FAR* pvDestCtx);
+#if OE_MAC
+ STDMETHOD_(unsigned long, IsIIDSupported)(REFIID riid);
+#else
+ STDMETHOD_(BOOL, IsIIDSupported)(REFIID riid);
+#endif
+ STDMETHOD_(unsigned long, CountRefs)(void);
+#endif
+
+ // introduced methods
+ HRESULT GetTypeInfoCount(void);
+ HRESULT GetTypeInfo(void);
+ HRESULT GetTypeInfoType(void);
+ HRESULT GetTypeInfoOfGuid(void);
+ HRESULT GetLibAttr(void);
+ HRESULT GetTypeComp(void);
+ HRESULT GetDocumentation(void);
+ HRESULT IsName(void);
+ HRESULT FindName(void);
+
+ HRESULT SysKind(void);
+
+ // helpers
+ HRESULT MarshalResult(void);
+
+private:
+ CStubTypeLib();
+ ~CStubTypeLib();
+
+ unsigned long m_refs;
+ IUnknown FAR* m_punk;
+ ITypeLib FAR* m_ptlib;
+ IStream FAR* m_pstm;
+ SYSKIND m_syskindProxy;
+};
+
+
+// ITypeLib method indices
+//
+enum IMETH_TYPELIB {
+ IMETH_TYPELIB_QUERYINTERFACE = 0,
+ IMETH_TYPELIB_ADDREF,
+ IMETH_TYPELIB_RELEASE,
+
+ IMETH_TYPELIB_GETTYPEINFOCOUNT,
+ IMETH_TYPELIB_GETTYPEINFO,
+ IMETH_TYPELIB_GETTYPEINFOTYPE,
+ IMETH_TYPELIB_GETTYPEINFOOFGUID,
+ IMETH_TYPELIB_GETLIBATTR,
+ IMETH_TYPELIB_GETTYPECOMP,
+ IMETH_TYPELIB_GETDOCUMENTATION,
+ IMETH_TYPELIB_ISNAME,
+ IMETH_TYPELIB_FINDNAME,
+ IMETH_TYPELIB_RELEASETLIBATTR,
+
+ IMETH_TYPELIB_SYSKIND
+};
+
+// TypeLib marshaling utilities
+INTERNAL_(HRESULT) ReadLibAttr(IStream FAR* pstm, TLIBATTR FAR* ptlibattr);
+INTERNAL_(HRESULT) WriteLibAttr(IStream FAR* pstm, TLIBATTR FAR* ptlibattr);
+
diff --git a/private/oleauto/src/dispatch/tlstub.cpp b/private/oleauto/src/dispatch/tlstub.cpp
new file mode 100644
index 000000000..ce16dbfcd
--- /dev/null
+++ b/private/oleauto/src/dispatch/tlstub.cpp
@@ -0,0 +1,846 @@
+/***
+*tlstub.cpp
+*
+* Copyright (C) 1994, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This module implements the ITypeLib stub class.
+*
+*Revision History:
+*
+* [00] 05-Apr-94 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#ifndef WIN32
+#include <cobjps.h>
+#endif //!WIN32
+
+#include "dispmrsh.h"
+#include "tlps.h"
+//#include "dispstrm.h"
+
+ASSERTDATA
+
+
+CStubTypeLib::CStubTypeLib()
+{
+ m_refs = 0;
+ m_pstm = NULL;
+ m_punk = NULL;
+ m_ptlib = NULL;
+ m_syskindProxy = (SYSKIND)-1; // something invalid
+}
+
+CStubTypeLib::~CStubTypeLib()
+{
+ Disconnect();
+}
+
+HRESULT
+CStubTypeLib::Create(IUnknown FAR* punkServer, ISTUB FAR* FAR* ppstub)
+{
+ CStubTypeLib FAR* pstub;
+
+ if(pstub = new FAR CStubTypeLib()){
+ pstub->m_refs = 1;
+ *ppstub = pstub;
+ if (punkServer)
+ return pstub->Connect(punkServer);
+ return NOERROR;
+ }
+ return RESULT(E_OUTOFMEMORY);
+}
+
+
+//---------------------------------------------------------------------
+// ITypeLib stub class' IUnknown implementation
+//---------------------------------------------------------------------
+
+STDMETHODIMP
+CStubTypeLib::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ if(IsEqualIID(riid, IID_IUnknown)){
+ *ppv = this;
+ }else if(IsEqualIID(riid, IID_ISTUB)){
+ *ppv = this;
+ }else{
+ *ppv = NULL;
+ return RESULT(E_NOINTERFACE);
+ }
+ ++m_refs;
+ return NOERROR;
+}
+
+STDMETHODIMP_(unsigned long)
+CStubTypeLib::AddRef()
+{
+ return ++m_refs;
+}
+
+STDMETHODIMP_(unsigned long)
+CStubTypeLib::Release()
+{
+ if(--m_refs == 0){
+ delete this;
+ return 0;
+ }
+ return m_refs;
+}
+
+
+//---------------------------------------------------------------------
+// ITypeLib stub class' IRpcStub implementation
+//---------------------------------------------------------------------
+
+STDMETHODIMP
+CStubTypeLib::Connect(IUnknown FAR* punkObj)
+{
+#if (defined(WIN32) || defined(WOW))
+ ASSERT(m_punk == NULL && m_ptlib == NULL);
+ //This will keep the server object alive until we disconnect.
+ IfFailRet(punkObj->QueryInterface(IID_ITypeLib, (void FAR* FAR*)&m_ptlib));
+ punkObj->AddRef();
+ m_punk = punkObj;
+ return NOERROR;
+#else
+ if(m_punk)
+ return RESULT(E_FAIL); // call Disconnect first
+
+ if (punkObj) {
+ punkObj->AddRef();
+ m_punk = punkObj;
+ }
+ return NOERROR;
+#endif
+}
+
+STDMETHODIMP_(void)
+CStubTypeLib::Disconnect()
+{
+ if(m_punk){
+ m_punk->Release();
+ m_punk = NULL;
+ }
+ if(m_ptlib){
+ m_ptlib->Release();
+ m_ptlib = NULL;
+ }
+}
+
+/***
+*PUBLIC HRESULT CStubTypeLib::Invoke
+*
+*Purpose:
+* Dispatch the method with the given index (imeth) on the given
+* interface, using the arguments serialized in the given stream.
+*
+* This function is the callee side of an LRPC call.
+*
+*Entry:
+* iid = the IID of the interface on which we are to make the call
+* imeth = the method index
+* pstm = the IStream containing the method's actuals
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDMETHODIMP
+CStubTypeLib::Invoke(
+#if (OE_WIN32 || defined(WOW))
+ RPCOLEMESSAGE *pMessage,
+ ICHANNEL *pRpcChannel)
+#else
+ REFIID riid,
+ int iMethod,
+ IStream FAR* pstm,
+ unsigned long dwDestCtx,
+ void FAR* pvDestCtx)
+#endif
+{
+ HRESULT hresult;
+
+#if (OE_WIN32 || defined(WOW))
+ IStream FAR* pstm;
+
+ if(!m_punk)
+ return RESULT(E_FAIL);
+
+ OPEN_STUB_STREAM(pstm, pRpcChannel, pMessage, IID_ITypeLib);
+
+#else
+ UNUSED(dwDestCtx);
+ UNUSED(pvDestCtx);
+
+ if(!IsEqualIID(riid, IID_ITypeLib))
+ return RESULT(E_NOINTERFACE);
+
+ if(!m_punk)
+ return RESULT(E_FAIL);
+
+ if(m_ptlib == NULL)
+ IfFailRet(m_punk->QueryInterface(IID_ITypeLib, (void FAR* FAR*)&m_ptlib));
+#endif
+
+
+ m_pstm = pstm;
+
+ switch(GET_IMETHOD(pMessage)){
+ case IMETH_TYPELIB_GETTYPEINFOCOUNT:
+ hresult = GetTypeInfoCount();
+ break;
+ case IMETH_TYPELIB_GETTYPEINFO:
+ hresult = GetTypeInfo();
+ break;
+ case IMETH_TYPELIB_GETTYPEINFOTYPE:
+ hresult = GetTypeInfoType();
+ break;
+ case IMETH_TYPELIB_GETTYPEINFOOFGUID:
+ hresult = GetTypeInfoOfGuid();
+ break;
+ case IMETH_TYPELIB_GETLIBATTR:
+ hresult = GetLibAttr();
+ break;
+ case IMETH_TYPELIB_GETTYPECOMP:
+ hresult = GetTypeComp();
+ break;
+ case IMETH_TYPELIB_GETDOCUMENTATION:
+ hresult = GetDocumentation();
+ break;
+ case IMETH_TYPELIB_ISNAME:
+ hresult = IsName();
+ break;
+ case IMETH_TYPELIB_FINDNAME:
+ hresult = FindName();
+ break;
+ case IMETH_TYPELIB_SYSKIND:
+ hresult = SysKind();
+ break;
+
+ case IMETH_TYPELIB_RELEASETLIBATTR: // should be handled by the proxy!
+ default:
+ hresult = RESULT(E_INVALIDARG);
+ break;
+ }
+
+ RESET_STREAM(pstm);
+ DELETE_STREAM(pstm);
+ m_pstm = NULL;
+ return hresult;
+}
+
+
+/***
+*PUBLIC HRESULT CStubTypeLib::IsIIDSupported(REFIID)
+*Purpose:
+* Answer if the given IID is supported by this stub.
+*
+*Entry:
+* iid = the IID to query for support
+*
+*Exit:
+* return value = BOOL. TRUE if IID is supported, FALSE otherwise.
+*
+***********************************************************************/
+#if OE_MAC
+STDMETHODIMP_(unsigned long)
+#elif (OE_WIN32 || defined(WOW))
+STDMETHODIMP_(IRpcStubBuffer *)
+#else
+STDMETHODIMP_(BOOL)
+#endif
+CStubTypeLib::IsIIDSupported(REFIID riid)
+{
+#if (OE_WIN32 || defined(WOW))
+ IRpcStubBuffer *pStub = 0;
+ if (IsEqualIID(riid, IID_ITypeLib)) {
+ AddRef();
+ pStub = (IRpcStubBuffer *) this;
+ }
+ return pStub;
+#else
+ // REVIEW: I don't understand this, but thats the way Ole does it...
+ if(m_punk == NULL)
+ return FALSE;
+
+ return(IsEqualIID(riid, IID_ITypeLib));
+#endif
+}
+
+/***
+*unsigned long CStubTypeLib::CountRefs
+*Purpose:
+* Return the count of references held by this stub.
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = unsigned long, the count of refs.
+*
+***********************************************************************/
+STDMETHODIMP_(unsigned long)
+CStubTypeLib::CountRefs()
+{
+ unsigned long refs;
+
+ refs = 0;
+
+ if(m_punk != NULL)
+ ++refs;
+
+ if(m_ptlib != NULL)
+ ++refs;
+
+ return refs;
+}
+
+/***
+*UNDONE
+*Purpose:
+*
+* Marshal In:
+* None.
+*
+* Marshal Out:
+* ULONG cTypeInfo
+*
+*Entry:
+* UNDONE
+*
+*Exit:
+* return value =
+*
+***********************************************************************/
+HRESULT
+CStubTypeLib::GetTypeInfoCount()
+{
+ unsigned long cTypeInfo;
+
+ cTypeInfo = (unsigned long)m_ptlib->GetTypeInfoCount();
+
+ REWIND_STREAM(m_pstm);
+
+ return PUT(m_pstm, cTypeInfo);
+}
+
+/***
+*HRESULT CStubTypeLib::GetTypeInfo
+*Purpose:
+* The stub implementation of ITypeLib::GetTypeInfo
+*
+* Marshal In:
+* ULONG index
+*
+* Marshal Out:
+* HRESULT hresult
+* ITypeInfo* ptinfo
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeLib::GetTypeInfo()
+{
+ int index;
+ unsigned long ulIndex;
+ ITypeInfo FAR* ptinfo;
+ HRESULT hresult, hresultRet;
+
+ hresult = NOERROR;
+ ptinfo = NULL;
+
+ IfFailGo(GET(m_pstm, ulIndex), LError1);
+ index = (int)ulIndex;
+
+ hresultRet = m_ptlib->GetTypeInfo(index, &ptinfo);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(DispMarshalHresult(m_pstm, hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError1;
+
+ IfFailGo(
+ DispMarshalInterface(m_pstm, IID_ITypeInfo, ptinfo),
+ LError1);
+
+LError1:;
+ if(ptinfo != NULL)
+ ptinfo->Release();
+ return hresult;
+}
+
+/***
+*HRESULT CStubTypeLib::GetTypeInfoType
+*Purpose:
+* The stub implementation of ITypeLib::GetTypeInfoType
+*
+* Marshal In:
+* ULONG index
+*
+* Marshal Out:
+* HRESULT hresult
+* ULONG tkind
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeLib::GetTypeInfoType()
+{
+ int index;
+ TYPEKIND tkind;
+ unsigned long ulTkind;
+ unsigned long ulIndex;
+ HRESULT hresult, hresultRet;
+
+ hresult = NOERROR;
+
+ IfFailGo(GET(m_pstm, ulIndex), LError1);
+ index = (int)ulIndex;
+
+ hresultRet = m_ptlib->GetTypeInfoType(index, &tkind);
+ ulTkind = (unsigned long)tkind;
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(DispMarshalHresult(m_pstm, hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError1;
+
+ IfFailGo(PUT(m_pstm, ulTkind), LError1);
+
+LError1:;
+ return hresult;
+}
+
+/***
+*HRESULT CStubTypeLib::GetTypeInfoOfGuid
+*Purpose:
+* The stub implementation of ITypeLib::GetTypeInfoOfGuid
+*
+* Marshal In:
+* GUID guid
+*
+* Marshal Out:
+* HRESULT hresult
+* ITypeInfo* ptinfo
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeLib::GetTypeInfoOfGuid()
+{
+ GUID guid;
+ ITypeInfo FAR* ptinfo;
+ HRESULT hresult, hresultRet;
+
+ hresult = NOERROR;
+ ptinfo = NULL;
+
+ IfFailGo(m_pstm->Read(&guid, sizeof(GUID), NULL), LError1);
+
+ hresultRet = m_ptlib->GetTypeInfoOfGuid(guid, &ptinfo);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(DispMarshalHresult(m_pstm, hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError1;
+
+ IfFailGo(
+ DispMarshalInterface(m_pstm, IID_ITypeInfo, ptinfo),
+ LError1);
+
+LError1:;
+ if(ptinfo != NULL)
+ ptinfo->Release();
+ return hresult;
+}
+
+/***
+*HRESULT CStubTypeLib::GetLibAttr
+*Purpose:
+* The stub implementation of ITypeLib::GetLibAttr
+*
+* Marshal In:
+* None
+*
+* Marshal Out:
+* HRESULT hresult
+* TLIBATTR tlibattr
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeLib::GetLibAttr()
+{
+ TLIBATTR FAR* ptlibattr;
+ HRESULT hresult, hresultRet;
+
+ hresult = NOERROR;
+ ptlibattr = NULL;
+
+ hresultRet = m_ptlib->GetLibAttr(&ptlibattr);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(DispMarshalHresult(m_pstm, hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError1;
+
+ IfFailGo(WriteLibAttr(m_pstm, ptlibattr), LError1);
+
+LError1:;
+ if(ptlibattr != NULL)
+ m_ptlib->ReleaseTLibAttr(ptlibattr);
+ return hresult;
+}
+
+/***
+*HRESULT CStubTypeLib::GetTypeComp
+*Purpose:
+* The stub implementation of ITypeLib::GetTypeComp
+*
+* Marshal In:
+* None
+*
+* Marshal Out:
+* HRESULT hresult
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeLib::GetTypeComp()
+{
+ ITypeComp FAR* ptcomp;
+ HRESULT hresult, hresultRet;
+
+ ptcomp = NULL;
+ hresult = NOERROR;
+
+ hresultRet = m_ptlib->GetTypeComp(&ptcomp);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(DispMarshalHresult(m_pstm, hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError1;
+
+ IfFailGo(
+ DispMarshalInterface(m_pstm, IID_ITypeComp, ptcomp),
+ LError1);
+
+LError1:;
+ if(ptcomp != NULL)
+ ptcomp->Release();
+ return hresult;
+}
+
+/***
+*HRESULT CStubTypeLib::GetDocumentation
+*Purpose:
+* The stub implementation of ITypeLib::GetDocumentation
+*
+* Marshal In:
+* ULONG index
+* UCHAR fHelpContext
+* UCHAR fName
+* UCHAR fDocString
+* UCHAR fHelpFile
+*
+* Marshal Out:
+* HRESULT hresult
+* if(fHelpContext) ULONG dwHelpContext
+* if(fName) BSTR bstrName
+* if(fDocString) BSTR bstrDocString
+* if(fHelpFile) BSTR bstrHelpFile
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeLib::GetDocumentation()
+{
+ int index;
+ unsigned long ulIndex;
+ HRESULT hresult, hresultRet;
+ BSTR bstrName, FAR* pbstrName;
+ BSTR bstrHelpFile, FAR* pbstrHelpFile;
+ BSTR bstrDocString, FAR* pbstrDocString;
+ unsigned long dwHelpContext, FAR* pdwHelpContext;
+ unsigned char fHelpContext, fName, fDocString, fHelpFile;
+
+ hresult = NOERROR;
+ bstrName = NULL;
+ bstrDocString = NULL;
+ bstrHelpFile = NULL;
+
+ IfFailGo(GET(m_pstm, ulIndex), LError1);
+ index = (int)ulIndex;
+ IfFailGo(GET(m_pstm, fHelpContext), LError1);
+ IfFailGo(GET(m_pstm, fName), LError1);
+ IfFailGo(GET(m_pstm, fDocString), LError1);
+ IfFailGo(GET(m_pstm, fHelpFile), LError1);
+
+ pdwHelpContext = fHelpContext ? &dwHelpContext : NULL;
+ pbstrName = fName ? &bstrName : NULL;
+ pbstrDocString = fDocString ? &bstrDocString : NULL;
+ pbstrHelpFile = fHelpFile ? &bstrHelpFile : NULL;
+
+ hresultRet = m_ptlib->GetDocumentation(
+ index, pbstrName, pbstrDocString, pdwHelpContext, pbstrHelpFile);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(DispMarshalHresult(m_pstm, hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError1;
+
+ if(fHelpContext)
+ IfFailGo(PUT(m_pstm, dwHelpContext), LError1);
+ if(fName)
+ IfFailGo(BstrWrite(m_pstm, bstrName, m_syskindProxy), LError1);
+ if(fDocString)
+ IfFailGo(BstrWrite(m_pstm, bstrDocString, m_syskindProxy), LError1);
+ if(fHelpFile)
+ IfFailGo(BstrWrite(m_pstm, bstrHelpFile, m_syskindProxy), LError1);
+
+LError1:;
+ SysFreeString(bstrName);
+ SysFreeString(bstrDocString);
+ SysFreeString(bstrHelpFile);
+
+ return hresult;
+}
+
+/***
+*HRESULT CStubTypeLib::IsName
+*Purpose:
+* The stub implementation of ITypeLib::IsName
+*
+* Marshal In:
+* ULONG lHashVal
+* BSTR bstrName
+*
+* Marshal Out:
+* HRESULT hresult
+* ULONG fName
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeLib::IsName()
+{
+ int fIsName;
+ BSTR bstrName;
+ unsigned long lHashVal;
+ unsigned long ulIsName;
+ HRESULT hresult, hresultRet;
+
+ hresult = NOERROR;
+ bstrName = NULL;
+
+ IfFailGo(GET(m_pstm, lHashVal), LError1);
+ IfFailGo(BstrRead(m_pstm, &bstrName, m_syskindProxy), LError1);
+
+ hresultRet = m_ptlib->IsName(bstrName, lHashVal, &fIsName);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(DispMarshalHresult(m_pstm, hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError1;
+
+ ulIsName = (unsigned long)fIsName;
+ IfFailGo(PUT(m_pstm, ulIsName), LError1);
+
+LError1:;
+ SysFreeString(bstrName);
+ return hresult;
+}
+
+/***
+*HRESULT CStubTypeLib::FindName
+*Purpose:
+* Stub implementation of ITypeLib::FindName.
+*
+* Marshal In:
+* ULONG cFound
+* ULONG lHashVal
+* BSTR bstrName
+*
+* Marshal Out:
+* HRESULT hresult
+* ULONG cFound
+* MEMID[cFound] rgmemid
+* ITypeInfo[cFound] rgptinfo
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeLib::FindName()
+{
+ BSTR bstrName;
+ MEMBERID FAR* rgmemid;
+ ITypeInfo FAR* FAR* rgptinfo;
+ unsigned short us, cFound;
+ HRESULT hresult, hresultRet;
+ unsigned long ul, ulFound, cFoundIn, lHashVal;
+
+ hresult = NOERROR;
+ bstrName = NULL;
+ rgmemid = NULL;
+ rgptinfo = NULL;
+ cFound = 0; // in case of error
+
+ IfFailGo(GET(m_pstm, cFoundIn), LError1);
+ cFound = (unsigned short)cFoundIn;
+ IfFailGo(GET(m_pstm, lHashVal), LError1);
+ IfFailGo(BstrRead(m_pstm, &bstrName, m_syskindProxy), LError1);
+
+ if((rgmemid = new FAR MEMBERID[cFound]) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LError1;
+ }
+
+ if((rgptinfo = new FAR ITypeInfo FAR* [cFound]) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto LError1;
+ }
+ //memset(rgptinfo, 0, cFound * sizeof(ITypeInfo FAR*));
+
+ hresultRet = m_ptlib->FindName(
+ bstrName, lHashVal, rgptinfo, rgmemid, &cFound);
+ ASSERT(cFound <= (unsigned short)cFoundIn);
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(DispMarshalHresult(m_pstm, hresultRet), LError1);
+
+ if(HRESULT_FAILED(hresultRet))
+ goto LError1;
+
+ ulFound = (unsigned long)cFound;
+ IfFailGo(PUT(m_pstm, ulFound), LError1);
+ IfFailGo(m_pstm->Write(rgmemid, sizeof(MEMBERID) * cFound, NULL), LError1);
+ for(us = 0; us < cFound; ++us){
+ IfFailGo(
+ DispMarshalInterface(m_pstm, IID_ITypeInfo, rgptinfo[us]),
+ LError1);
+ }
+
+LError1:;
+ if(rgmemid != NULL)
+ delete rgmemid;
+ if(rgptinfo != NULL){
+ for(ul = 0; ul < cFound; ++ul){
+ ASSERT(rgptinfo[ul] != NULL);
+ rgptinfo[ul]->Release();
+ }
+ delete rgptinfo;
+ }
+ SysFreeString(bstrName);
+ return hresult;
+}
+
+/***
+*HRESULT CStubTypeLib::SysKind
+*Purpose:
+* Exchange syskinds with the proxy were connected to.
+*
+* Marshal In:
+* ULONG syskindProxy
+*
+* Marshal Out:
+* ULONG syskindStub
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubTypeLib::SysKind()
+{
+ unsigned long syskind;
+
+ IfFailRet(GET(m_pstm, syskind));
+ m_syskindProxy = (SYSKIND)syskind;
+ syskind = (unsigned long)SYS_CURRENT;
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailRet(PUT(m_pstm, syskind));
+
+ return NOERROR;
+}
+
+#if (OE_WIN32 || defined(WOW))
+
+STDMETHODIMP
+CStubTypeLib::DebugServerQueryInterface(void FAR* FAR* ppv)
+{
+ *ppv = m_ptlib;
+ return S_OK;
+}
+
+
+STDMETHODIMP_(void)
+CStubTypeLib::DebugServerRelease(void FAR* ppv)
+{ }
+
+#endif
diff --git a/private/oleauto/src/dispatch/ups.cpp b/private/oleauto/src/dispatch/ups.cpp
new file mode 100644
index 000000000..f8afeb715
--- /dev/null
+++ b/private/oleauto/src/dispatch/ups.cpp
@@ -0,0 +1,1719 @@
+/***
+*ups.cpp
+*
+* Copyright (C) 1992-94, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This module implements the Universal Proxy and Stub classes.
+*
+*Revision History:
+*
+* [00] 21-Jun-94 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#if !OE_WIN32
+# include <cobjps.h>
+#endif
+#include "dispmrsh.h"
+#include "ups.h"
+#include "dispps.h"
+#include <stdarg.h>
+#include <stdlib.h>
+#if OE_WIN
+# include <shellapi.h>
+#endif
+
+ASSERTDATA
+
+// In all builds, we use the Ansi registry.
+#if !OE_WIN32
+# define StringFromGUID2A StringFromGUID2
+# define RegQueryValueA RegQueryValue
+# define RegOpenKeyA RegOpenKey
+# define RegEnumKeyA RegEnumKey
+#else
+STDAPI_(int) StringFromGUID2A(REFGUID rguid, char FAR* szGuid, long cbMax);
+#endif
+
+extern long g_cfnUnk;
+extern void FAR* FAR g_rgpfnUnk[];
+
+extern long g_cfnDisp;
+extern void FAR* FAR g_rgpfnDisp[];
+
+
+HRESULT
+VarVtOfTypeDesc(ITypeInfo FAR* ptinfo,
+ TYPEDESC FAR* ptdesc,
+ VARTYPE FAR* pvt,
+ GUID FAR* pguid);
+HRESULT
+VarVtOfUDT(ITypeInfo FAR* ptinfo,
+ TYPEDESC FAR* ptdesc,
+ VARTYPE FAR* pvt,
+ GUID FAR* pguid);
+
+HRESULT
+GetTypeInfoOfIID(REFIID riid, ITypeInfo FAR* FAR* pptinfo);
+
+#if OE_WIN16
+INTERNAL_(HRESULT)
+DoLoadTypeLib(const OLECHAR FAR* szFile, ITypeLib FAR* FAR* pptlib);
+#else
+# define DoLoadTypeLib LoadTypeLib
+#endif
+
+
+CProxUniv::CProxUniv(IUnknown FAR* punkOuter)
+{
+ // Verify that the vtable ptr for the interface pointer that
+ // we are remoting is at the address point of the proxy.
+ ASSERT(OA_FIELD_OFFSET(CProxUniv, m_pvtbl) == 0);
+
+ m_cRefs = 0;
+ m_plrpc = NULL;
+ if(punkOuter == NULL)
+ punkOuter = (IUnknown FAR*)&m_priv;
+ m_punkOuter = punkOuter;
+ m_syskindStub = (SYSKIND)-1; // something invalid
+ m_fIsDual = 0;
+ m_iid = IID_NULL;
+ m_cFuncs = 0;
+ m_rgMethInfo = NULL;
+}
+
+CProxUniv::~CProxUniv()
+{
+ if (m_rgMethInfo != NULL) {
+ for (UINT i=0; i<m_cFuncs; ++i) {
+ if (m_rgMethInfo[i].ptinfo) {
+ m_rgMethInfo[i].ptinfo->ReleaseFuncDesc(m_rgMethInfo[i].pfdesc);
+ m_rgMethInfo[i].ptinfo->Release();
+ }
+ }
+ delete m_rgMethInfo;
+ }
+}
+
+/***
+*PRIVATE HRESULT CanWeRemoteIt
+*Purpose:
+* Answer if the given typeinfo describes an interface that can
+* be remoted by the Universal marshaler.
+*
+* 1. Must be OA-compatable (ie, use only OA types)
+* 2. All methods must return HRESULTs
+* 3. All methods must be CDECL
+* 4. Must have fewer than 512 methods
+*
+*Entry:
+* ptinfo = the TypeInfo that describes the interface were going to remote.
+*
+*Exit:
+* *pcFuncs = the TOTAL # of functions in the inheritance heirarchy for this
+* typeinfo.
+* *pfIsDual = TRUE if this is a dispinterface portion of a dual interface
+* return value = HRESULT. NOERROR if it can be remoted.
+*
+***********************************************************************/
+HRESULT
+CanWeRemoteIt(ITypeInfo FAR* ptinfo, USHORT FAR* pcFuncs, BOOL FAR* pfIsDual)
+{
+ HRESULT hresult;
+ TYPEATTR FAR* ptattr;
+ BOOL fIsDual;
+ USHORT cFuncs;
+
+ ptattr = NULL;
+
+ IfFailGo(ptinfo->GetTypeAttr(&ptattr), Error);
+
+ // If either "dual" or "oleautomation" is specified, then we
+ // know that mktyplib verified that the interface consists entirely
+ // of Automation compatable types.
+ if((ptattr->wTypeFlags & (TYPEFLAG_FDUAL | TYPEFLAG_FOLEAUTOMATION)) == 0){
+ hresult = RESULT(E_FAIL);
+ goto Error;
+ }
+
+ fIsDual = ((ptattr->wTypeFlags & TYPEFLAG_FDUAL) != 0)
+ && (ptattr->typekind == TKIND_DISPATCH);
+ *pfIsDual = fIsDual;
+
+ // The dispinteface version of a dual interface has it's heirarchy
+ // "flattened", so ptattr->cFuncs is the correct # of functions.
+ cFuncs = ptattr->cFuncs; // assume dual interface
+
+ if (!fIsDual) {
+ // For non-dual intefaces, take the sizeof the VFT, and divide by 4
+ // to get total # of functions in inheritance heirarchy. This is
+ // exactly how cFuncs is computed in the DUAL case.
+ cFuncs = ptattr->cbSizeVft / sizeof(void FAR*);
+ }
+
+ if(cFuncs >= (unsigned short)g_cfnDisp){
+ hresult = RESULT(E_FAIL);
+ goto Error;
+ }
+
+ // CONSIDER: should check the calling convention and return type
+ // CONSIDER: of each method...
+
+ *pcFuncs = cFuncs;
+ hresult = NOERROR;
+
+Error:;
+ if(ptattr != NULL)
+ ptinfo->ReleaseTypeAttr(ptattr);
+ return hresult;
+}
+
+/***
+*PRIVATE HRESULT CProxUniv::Create
+*Purpose:
+* Create an instance of the Universal Proxy.
+*
+*Entry:
+* punkOuter = the controlling unknown
+* riid = the IID of the interface for which the instance will be a proxy
+*
+*Exit:
+* return value = HRESULT
+*
+* *pprox = the newly created instance, if successful.
+*
+***********************************************************************/
+HRESULT
+CProxUniv::Create(IUnknown FAR* punkOuter,
+ REFIID riid,
+ IUnknown FAR* FAR* ppunk)
+{
+ USHORT cFuncs;
+ HRESULT hresult;
+ CProxUniv FAR* pprox;
+ ITypeInfo FAR* ptinfo;
+ ITypeInfo FAR* ptinfoProxy;
+ BOOL fIsDual;
+ HREFTYPE hreftype;
+
+ pprox = NULL;
+ ptinfo = NULL;
+ ptinfoProxy = NULL;
+
+ // Lookup the LIBID for the given IID
+ IfFailGo(GetTypeInfoOfIID(riid, &ptinfo), Error);
+
+ IfFailGo(CanWeRemoteIt(ptinfo, &cFuncs, &fIsDual), Error);
+
+ if((pprox = new CProxUniv(punkOuter)) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto Error;
+ }
+ pprox->m_iid = riid;
+ pprox->m_cFuncs = cFuncs;
+ pprox->m_fIsDual = fIsDual;
+
+ if(fIsDual){
+ // get the dual interface typeinfo
+ IfFailGo(ptinfo->GetRefTypeOfImplType((UINT)-1, &hreftype), Error);
+ IfFailGo(ptinfo->GetRefTypeInfo(hreftype, &ptinfoProxy), Error);
+ pprox->m_pvtbl = g_rgpfnDisp;
+ }else{
+ // the typeinfo we've got is good enough
+ ptinfo->AddRef();
+ ptinfoProxy = ptinfo;
+ pprox->m_pvtbl = g_rgpfnUnk;
+ }
+
+ // allocate space for per-method data
+ if ((pprox->m_rgMethInfo = new METHINFO[cFuncs]) == NULL) {
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto Error;
+ }
+ memset(pprox->m_rgMethInfo, 0, sizeof(METHINFO)*cFuncs);
+
+ IfFailGo(pprox->CacheFuncDescs(ptinfoProxy), Error);
+
+ pprox->m_priv.AddRef();
+ *ppunk = (IUnknown FAR*)&pprox->m_priv;
+ pprox = NULL;
+
+ hresult = NOERROR;
+
+Error:;
+ if(ptinfo != NULL)
+ ptinfo->Release();
+ if(ptinfoProxy != NULL)
+ ptinfoProxy->Release();
+ if(pprox != NULL)
+ delete pprox;
+ return hresult;
+}
+
+
+HRESULT
+CProxUniv::CacheFuncDescs(ITypeInfo *ptinfo)
+{
+ HRESULT hresult;
+ unsigned int i, iFuncIndex;
+ FUNCDESC *pfdesc;
+ HREFTYPE hRefType;
+ ITypeInfo *ptinfoBase = NULL;
+ TYPEATTR FAR* ptattr = NULL;
+
+ IfFailGo(ptinfo->GetTypeAttr(&ptattr), Error);
+
+ // first walk any base type infos
+ if (ptattr->cImplTypes) {
+
+ // if this is IDispatch, stop recursing - IDispatch itself is not
+ // OA-compatible because of the 'unsigned int' parameters to
+ // GetTypeInfoCount() and others...
+ if (IsEqualIID(IID_IDispatch, ptattr->guid))
+ goto Error; // just return NOERROR
+
+ IfFailGo(ptinfo->GetRefTypeOfImplType(0, &hRefType), Error);
+ IfFailGo(ptinfo->GetRefTypeInfo(hRefType, &ptinfoBase), Error);
+ IfFailGo(CacheFuncDescs(ptinfoBase), Error);
+ } else {
+ // know that IUnknown is at the bottom of everybody
+ // optimization: don't need to cache it's funcdesc's
+
+ ASSERT(IsEqualIID(IID_IUnknown, ptattr->guid))
+
+ goto Error; // just return NOERROR
+ }
+
+ // get and cache funcdescs for each method
+ for (i=0; i<ptattr->cFuncs; ++i) {
+
+ // get the funcdesc
+ IfFailGo(ptinfo->GetFuncDesc(i, &pfdesc), Error);
+
+ // figure out which method we got, based on the vtable offset
+ iFuncIndex = pfdesc->oVft/sizeof(void FAR*);
+
+ // Make sure we haven't already seen this funcdesc
+ // CONSIDER: if a derived class overrides a function in a base class,
+ // CONSIDER: then the new pfdesc and ptinfo should NOT overwrite the
+ // CONSIDER: ones in m_rgMethInfo[] - they should simply be tossed.
+ // CONSIDER: The functions are written in from most derived class to
+ // CONSIDER: base class, so the function we really want to call is the
+ // CONSIDER: first one encountered.
+ ASSERT(m_rgMethInfo[iFuncIndex].pfdesc == NULL);
+
+ // cache the funcdesc
+ m_rgMethInfo[iFuncIndex].pfdesc = pfdesc;
+
+ // cache the typeinfo
+ ptinfo->AddRef();
+ m_rgMethInfo[iFuncIndex].ptinfo = ptinfo;
+
+#if defined(_X86_)
+
+ // Compute the size of the arguments which need to be cleaned up
+ IfFailGo(GetCbStackCleanupOfFuncDesc(pfdesc, ptinfo,
+ &m_rgMethInfo[iFuncIndex].cbStackCleanup), Error);
+
+#endif //defined(_X86_)
+
+ }
+
+Error:
+ if (ptattr)
+ ptinfo->ReleaseTypeAttr(ptattr);
+ if (ptinfoBase)
+ ptinfoBase->Release();
+ return hresult;
+}
+
+//---------------------------------------------------------------------
+// The Proxy Class' private IUnknown and IProxy implementations
+//---------------------------------------------------------------------
+
+/***
+*PRIVATE CProxUniv FAR* PProx
+*Purpose:
+* Returns a pointer to the containing CProxUniv instance.
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = CProxUniv*
+*
+***********************************************************************/
+inline CProxUniv FAR* CProxUniv::CPriv::PProx()
+{
+ CProxUniv FAR* pprox;
+
+ pprox = (CProxUniv FAR*)((unsigned char FAR*)this - OA_FIELD_OFFSET(CProxUniv, m_priv));
+
+ // Make sure we got where we expected. The following test works
+ // because all universal proxies have a pointer to the universal
+ // delegator at the address point of their instance.
+ ASSERT(*(void FAR* FAR*)pprox == g_rgpfnUnk
+ || *(void FAR* FAR*)pprox == g_rgpfnDisp);
+
+ return pprox;
+}
+
+STDMETHODIMP
+CProxUniv::CPriv::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ CProxUniv FAR* pprox;
+
+ if(riid == IID_IUnknown || riid == IID_IPROXY){
+ *ppv = this;
+ }else{
+ pprox = PProx();
+ if(riid == pprox->m_iid){
+ *ppv = pprox;
+ }else{
+ *ppv = NULL;
+ return RESULT(E_NOINTERFACE);
+ }
+ }
+ ((IUnknown FAR*)*ppv)->AddRef();
+ return NOERROR;
+}
+
+STDMETHODIMP_(unsigned long)
+CProxUniv::CPriv::AddRef()
+{
+ CProxUniv FAR* pprox = PProx();
+
+ return ++pprox->m_cRefs;
+}
+
+STDMETHODIMP_(unsigned long)
+CProxUniv::CPriv::Release()
+{
+ CProxUniv FAR* pprox = PProx();
+
+ if(--pprox->m_cRefs == 0){
+ delete pprox;
+ return 0;
+ }
+ return pprox->m_cRefs;
+}
+
+STDMETHODIMP
+CProxUniv::CPriv::Connect(ICHANNEL FAR* plrpc)
+{
+ CProxUniv FAR* pprox = PProx();
+
+ if(plrpc == NULL)
+ return RESULT(E_FAIL);
+
+ plrpc->AddRef();
+ pprox->m_plrpc = plrpc;
+ IfFailRet(pprox->PSInit());
+ return NOERROR;
+}
+
+STDMETHODIMP_(void)
+CProxUniv::CPriv::Disconnect(void)
+{
+ CProxUniv FAR* pprox = PProx();
+
+ if(pprox->m_plrpc != NULL)
+ pprox->m_plrpc->Release();
+ pprox->m_plrpc = NULL;
+ pprox->m_syskindStub = (SYSKIND)-1; // something invalid
+}
+
+/***
+*PRIVATE HRESULT CProxUniv::PSInit
+*Purpose:
+* Internal init routine that exchanges info between the proxy and
+* stub at connect time.
+*
+* Marshaled out:
+* ULONG syskindProxy
+* ULONG fIsDual
+* IID m_iid
+*
+* Marshaled in:
+* ULONG syskindStub
+*
+*Entry:
+* None
+*
+*Exit:
+* return value =
+*
+***********************************************************************/
+HRESULT
+CProxUniv::PSInit()
+{
+ HRESULT hresult;
+ IStream FAR* pstm;
+ unsigned long fIsDual;
+ unsigned long syskindStub;
+ unsigned long syskindProxy;
+
+ pstm = NULL;
+
+ ASSERT(m_plrpc != NULL);
+ OPEN_STREAM(m_plrpc, pstm, IMETH_UNIVERSAL_PSInit, 256, m_iid);
+
+ syskindProxy = SYS_CURRENT;
+ IfFailGo(PUT(pstm, syskindProxy), Error);
+
+ fIsDual = m_fIsDual;
+ IfFailGo(PUT(pstm, fIsDual), Error);
+
+ IfFailGo(PUT(pstm, m_iid), Error);
+
+ INVOKE_CALL(m_plrpc, pstm, Error);
+
+ IfFailGo(GET(pstm, syskindStub), Error);
+ m_syskindStub = (SYSKIND)syskindStub;
+
+ hresult = NOERROR;
+
+Error:;
+ if(pstm != NULL)
+ pstm->Release();
+ return hresult;
+}
+
+/***
+*HRESULT ProxyMethod
+*Purpose:
+* The Universal marshaler.
+*
+*Entry:
+* pprox = ptr to CProxUniv instance (ProxyMethod is called from native code)
+* iMeth = the method index
+* args = ptr to arg list
+*if defined(_X86_)
+* pcbStackCleanup = ptr to OUT parm: amount of stack to clean up after
+* the _stdcall
+*endif //defined(_X86_)
+*
+* Marshaled Out:
+* long cArgs
+* VARTYPE[] rgVt = array of argument types
+* VARIANT[] rgArgs = array of argument values
+*
+* Marhsaled In:
+* hresult hresultRet = return value
+* VARIANT[] rgArgsOut = out params
+* Rich Error state (if any)
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDAPI_(HRESULT)
+ProxyMethod(CProxUniv *pprox, int iMeth, va_list args
+#if defined(_X86_)
+ ,int *pcbStackCleanup
+#endif //defined(_X86_)
+ )
+{
+ GUID guid;
+ long cArgs;
+ long ccTemp;
+ int i, oVft;
+ IStream FAR* pstm;
+ VARIANTX FAR* pvarx;
+ TYPEDESC FAR* ptdesc;
+ FUNCDESC FAR* pfdesc;
+ HRESULT hresult, hresultRet;
+ VARTYPE FAR* prgvt, rgvt[16];
+ VARIANT FAR* prgvar, rgvar[16], FAR* pvar;
+
+ // We should never get called for QI, AddRef or Release
+ ASSERT(iMeth > 2);
+
+#if defined(_X86_)
+ // WARNING: *pcbStackCleanup must be set before *any* return! Otherwise,
+ // WARNING: the caller won't know how to clean its parameters on the
+ // WARNING: stack, so we'll crash on the return, because the Universal
+ // WARNING: Method was called using _stdcall (callee cleans up).
+
+ *pcbStackCleanup = pprox->m_rgMethInfo[iMeth].cbStackCleanup;
+#endif //defined(_X86_)
+
+ if(pprox->m_plrpc == NULL)
+ return RESULT(OLE_E_NOTRUNNING);
+
+ pstm = NULL;
+ prgvt = NULL;
+ prgvar = NULL;
+ pfdesc = NULL;
+ oVft = iMeth * sizeof(void FAR*);
+
+ OPEN_STREAM(pprox->m_plrpc, pstm, iMeth, 256, pprox->m_iid);
+
+ // Aquire the FUNCDESC that describe the method we're marshaling
+ pfdesc = pprox->m_rgMethInfo[iMeth].pfdesc;
+ if (pfdesc == NULL) {
+ ASSERT(FALSE); // the funcdesc should be non-NULL after Create() is done
+ hresult = RESULT(E_FAIL);
+ goto Error;
+ }
+
+ cArgs = (long)pfdesc->cParams;
+
+ if(cArgs == 0){
+ prgvt = NULL;
+ prgvar = NULL;
+ }else if(cArgs < DIM(rgvar)){
+ prgvt = rgvt;
+ prgvar = rgvar;
+ }else{
+ if((prgvt = new FAR VARTYPE[cArgs]) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto Error;
+ }
+ if((prgvar = new FAR VARIANT[cArgs]) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto Error;
+ }
+ }
+
+ // Build array of VARIANTs containing the arguments to be Marshaled
+ // and a corresponding array of argument types.
+
+ for(i = 0; i < cArgs; ++i){
+
+ pvar = &prgvar[i];
+
+ ptdesc = &pfdesc->lprgelemdescParam[i].tdesc;
+ IfFailGo(VarVtOfTypeDesc(pprox->m_rgMethInfo[iMeth].ptinfo,
+ ptdesc,
+ &V_VT(pvar),
+ &guid), Error);
+
+ switch(V_VT(pvar)){
+ case VT_INTERFACE:
+ prgvt[i] = VT_UNKNOWN;
+ goto StuffIID;
+ case VT_INTERFACE | VT_BYREF:
+ prgvt[i] = VT_UNKNOWN | VT_BYREF;
+StuffIID:;
+ pvarx = (VARIANTX FAR*)pvar;
+ if((pvarx->piid = new IID) == NULL){
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto Error;
+ }
+ *pvarx->piid = guid;
+ break;
+ default:
+ prgvt[i] = V_VT(pvar);
+ break;
+ }
+
+ switch(prgvt[i]){
+ case VT_UI1:
+ V_UI1(pvar) = va_arg(args, unsigned char);
+ break;
+ case VT_I2:
+ case VT_BOOL:
+ V_I2(pvar) = va_arg(args, short);
+ break;
+ case VT_I4:
+ case VT_ERROR:
+ V_I4(pvar) = va_arg(args, long);
+ break;
+ case VT_CY:
+ V_CY(pvar) = va_arg(args, CY);
+ break;
+ case VT_R4: // in C++, floats are passed as floats (I think...)
+ V_R4(pvar) = va_arg(args, float);
+ break;
+ case VT_R8:
+ case VT_DATE:
+ V_R8(pvar) = va_arg(args, double);
+ break;
+ case VT_VARIANT:
+ *pvar = va_arg(args, VARIANT);
+ break;
+ case VT_BSTR:
+ case VT_UNKNOWN:
+ case VT_DISPATCH:
+LPointer:;
+ V_BYREF(pvar) = va_arg(args, void FAR*);
+ break;
+ default:
+ if(prgvt[i] & (VT_BYREF|VT_ARRAY))
+ goto LPointer;
+ // FALLTHROUGH
+ case VT_NULL: // cant show up as arg type
+ case VT_EMPTY: // cant show up as arg type
+ ASSERT(UNREACHED);
+ hresult = RESULT(E_FAIL);
+ goto Error;
+ }
+ }
+
+ // Write the server function's calling convention (always marshal as long)
+ ccTemp = (long)pfdesc->callconv;
+ IfFailGo(PUT(pstm, ccTemp), Error);
+
+ // Write the argument count
+ IfFailGo(PUT(pstm, cArgs), Error);
+
+ // Marshal the array of argument types
+ if(cArgs > 0){
+ IfFailGo(pstm->Write(prgvt, cArgs*sizeof(VARTYPE), NULL), Error);
+
+ // Marshal the array of arguments
+ for(i = 0; i < cArgs; ++i)
+ IfFailGo(VariantWrite(pstm, &prgvar[i], pprox->m_syskindStub), Error);
+ }
+
+ INVOKE_CALL(pprox->m_plrpc, pstm, Error);
+
+ IfFailGo(DispUnmarshalHresult(pstm, &hresultRet), Error);
+
+ // Unmarshal the out params
+ for(i = 0; i < cArgs; ++i){
+ if(prgvt[i] & VT_BYREF)
+ IfFailGo(VariantReadType(pstm, &prgvar[i], pprox->m_syskindStub), Error);
+ }
+
+ // Unmarshal the Rich Error state (if any)
+ IfFailGo(UnmarshalErrorInfo(pstm, pprox->m_syskindStub), Error);
+
+ hresult = hresultRet;
+
+Error:;
+ if(prgvt != NULL && prgvt != rgvt)
+ delete prgvt;
+ if(prgvar != NULL){
+ VARIANTX FAR* pvarxEnd = (VARIANTX FAR*)&prgvar[cArgs];
+ for(pvarx = (VARIANTX FAR*)prgvar; pvarx < pvarxEnd; ++pvarx){
+ if((V_VT(pvarx) & ~VT_BYREF) == VT_INTERFACE){
+ if(pvarx->piid != NULL)
+ delete pvarx->piid;
+ }
+ }
+ if(prgvar != rgvar)
+ delete prgvar;
+ }
+ if(pstm != NULL)
+ pstm->Release();
+ return hresult;
+}
+
+//---------------------------------------------------------------------
+// Implementation of the Universal Marshaler Stub class
+//---------------------------------------------------------------------
+
+
+CStubUniv::CStubUniv()
+{
+ m_cRefs = 0;
+ m_pstm = NULL;
+ m_punk = NULL;
+ m_fIsDual = FALSE;
+ m_syskindProxy = (SYSKIND)-1; // something invalid
+ m_iid = IID_NULL;
+ m_punkCustom = NULL;
+}
+
+CStubUniv::~CStubUniv()
+{
+ Disconnect();
+}
+
+HRESULT
+CStubUniv::Create(IUnknown FAR* punkServer,
+ REFIID riid,
+ ISTUB FAR* FAR* ppstub)
+{
+ CStubUniv FAR* pstub;
+
+ if((pstub = new FAR CStubUniv()) == NULL)
+ return RESULT(E_OUTOFMEMORY);
+ pstub->AddRef();
+ pstub->m_iid = riid;
+ if (punkServer)
+ pstub->Connect(punkServer);
+ *ppstub = pstub;
+ return NOERROR;
+}
+
+STDMETHODIMP
+CStubUniv::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ if(IsEqualIID(riid, IID_IUnknown)){
+ *ppv = this;
+ }else if(IsEqualIID(riid, IID_ISTUB)){
+ *ppv = this;
+ }else{
+ *ppv = NULL;
+ return RESULT(E_NOINTERFACE);
+ }
+ ++m_cRefs;
+ return NOERROR;
+}
+
+STDMETHODIMP_(unsigned long)
+CStubUniv::AddRef()
+{
+ return ++m_cRefs;
+}
+
+STDMETHODIMP_(unsigned long)
+CStubUniv::Release()
+{
+ if(--m_cRefs == 0){
+ delete this;
+ return 0;
+ }
+ return m_cRefs;
+}
+
+//---------------------------------------------------------------------
+// Universal Stub class' IRpcStub implementation
+//---------------------------------------------------------------------
+
+STDMETHODIMP
+CStubUniv::Connect(IUnknown FAR* punkObj)
+{
+#if (defined(WIN32) || defined(WOW))
+ ASSERT(m_punk == NULL && m_punkCustom == NULL);
+ IfFailRet(punkObj->QueryInterface(m_iid, (void FAR* FAR*)&m_punkCustom));
+ punkObj->AddRef();
+ m_punk = punkObj;
+ return NOERROR;
+#else
+ if(m_punk)
+ return RESULT(E_FAIL); // call Disconnect first
+
+ if (punkObj) {
+ punkObj->AddRef();
+ m_punk = punkObj;
+ }
+ return NOERROR;
+#endif
+}
+
+STDMETHODIMP_(void)
+CStubUniv::Disconnect()
+{
+ if(m_punk){
+ m_punk->Release();
+ m_punk = NULL;
+ }
+ if(m_punkCustom){
+ m_punkCustom->Release();
+ m_punkCustom = NULL;
+ }
+}
+
+/***
+*PUBLIC HRESULT CStubUniv::Invoke
+*
+*Purpose:
+* Dispatch the method with the given index (imeth) on the given
+* interface, using the arguments serialized in the given stream.
+*
+* This function is the callee side of an LRPC call.
+*
+*Entry:
+* iid = the IID of the interface on which we are to make the call
+* imeth = the method index
+* pstm = the IStream containing the method's actuals
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+STDMETHODIMP
+CStubUniv::Invoke(
+#if (OE_WIN32 || defined(WOW))
+ RPCOLEMESSAGE *pmessage,
+ ICHANNEL *pchannel)
+#else
+ REFIID riid,
+ int iMethod,
+ IStream FAR* pstm,
+ unsigned long dwDestCtx,
+ void FAR* pvDestCtx)
+#endif
+{
+ int iMeth;
+ HRESULT hresult;
+
+#if (OE_WIN32 || defined(WOW))
+ IStream FAR* pstm;
+
+ OPEN_STUB_STREAM(pstm, pchannel, pmessage, m_iid);
+
+ iMeth = pmessage->iMethod;
+#else
+ UNUSED(dwDestCtx);
+ UNUSED(pvDestCtx);
+
+ iMeth = iMethod;
+ ASSERT(riid == m_iid);
+#endif
+
+ if(m_punk == NULL)
+ return RESULT(E_FAIL);
+
+ m_pstm = pstm;
+
+ if(m_punkCustom == NULL)
+ IfFailRet(m_punk->QueryInterface(m_iid, (void FAR* FAR*)&m_punkCustom));
+
+ switch(iMeth){
+ case IMETH_UNIVERSAL_GetTypeInfoCount:
+ if(!m_fIsDual)
+ goto LMethod;
+ hresult = StubGetTypeInfoCount((IDispatch FAR*)m_punkCustom, pstm);
+ break;
+
+ case IMETH_UNIVERSAL_GetTypeInfo:
+ if(!m_fIsDual)
+ goto LMethod;
+ hresult = StubGetTypeInfo((IDispatch FAR*)m_punkCustom, pstm);
+ break;
+
+ case IMETH_UNIVERSAL_GetIDsOfNames:
+ if(!m_fIsDual)
+ goto LMethod;
+ hresult = StubGetIDsOfNames((IDispatch FAR*)m_punkCustom, pstm);
+ break;
+
+ case IMETH_UNIVERSAL_Invoke:
+ if(!m_fIsDual)
+ goto LMethod;
+ hresult = StubInvoke((IDispatch FAR*)m_punkCustom, pstm);
+ break;
+
+ case IMETH_UNIVERSAL_PSInit:
+ hresult = PSInit();
+ break;
+
+ default:
+ if(iMeth <= IMETH_UNIVERSAL_Release || iMeth >= g_cfnDisp){
+ hresult = RESULT(E_INVALIDARG);
+ break;
+ }
+LMethod:;
+ hresult = DispatchMethod(iMeth);
+ break;
+ }
+
+ RESET_STREAM(pstm);
+ DELETE_STREAM(pstm);
+ m_pstm = NULL;
+ return hresult;
+}
+
+
+/***
+*PUBLIC HRESULT CStubUniv::IsIIDSupported(REFIID)
+*Purpose:
+* Answer if the given IID is supported by this stub.
+*
+*Entry:
+* iid = the IID to query for support
+*
+*Exit:
+* return value = BOOL. TRUE if IID is supported, FALSE otherwise.
+*
+***********************************************************************/
+#if (OE_WIN32 || defined(WOW))
+STDMETHODIMP_(IRpcStubBuffer *)
+#else
+STDMETHODIMP_(OLEBOOL)
+#endif
+CStubUniv::IsIIDSupported(REFIID riid)
+{
+#if (OE_WIN32 || defined(WOW))
+ IRpcStubBuffer *prpcsbuf = 0;
+ if (IsEqualIID(riid, m_iid)){
+ AddRef();
+ prpcsbuf = (IRpcStubBuffer*)this;
+ }
+ return prpcsbuf;
+#else
+ // REVIEW: I don't understand this, but thats the way Ole does it...
+ if(m_punk == NULL)
+ return FALSE;
+ return(IsEqualIID(riid, m_iid));
+#endif
+}
+
+/***
+*unsigned long CStubUniv::CountRefs
+*Purpose:
+* Return the count of references held by this stub.
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = unsigned long, the count of refs.
+*
+***********************************************************************/
+STDMETHODIMP_(unsigned long)
+CStubUniv::CountRefs()
+{
+ unsigned long refs;
+
+ refs = 0;
+ if(m_punk != NULL)
+ ++refs;
+ if(m_punkCustom != NULL)
+ ++refs;
+ return refs;
+}
+
+#if (OE_WIN32 || defined(WOW))
+
+STDMETHODIMP
+CStubUniv::DebugServerQueryInterface(void FAR* FAR* ppv)
+{
+ *ppv = m_punkCustom;
+ return S_OK;
+}
+
+
+STDMETHODIMP_(void)
+CStubUniv::DebugServerRelease(void FAR* ppv)
+{ }
+
+#endif
+
+
+/***
+*HRESULT CStubUniv::PSInit
+*Purpose:
+* Exchange info between proxy and stub at connect time.
+*
+* Marshaled out:
+* ULONG syskindProxy
+* ULONG fIsDual
+* IID m_iid
+*
+* Marshaled in:
+* ULONG syskindStub
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT
+CStubUniv::PSInit()
+{
+ HRESULT hresult;
+ unsigned long fIsDual;
+ unsigned long syskindStub;
+ unsigned long syskindProxy;
+
+ IfFailGo(GET(m_pstm, syskindProxy), Error);
+ m_syskindProxy = (SYSKIND)syskindProxy;
+
+ IfFailGo(GET(m_pstm, fIsDual), Error);
+ m_fIsDual = (BOOL)fIsDual;
+
+ IfFailGo(GET(m_pstm, m_iid), Error);
+
+ REWIND_STREAM(m_pstm);
+
+ syskindStub = SYS_CURRENT;
+ IfFailGo(PUT(m_pstm, syskindStub), Error);
+
+ hresult = NOERROR;
+
+Error:;
+ return hresult;
+}
+
+/***
+*PRIVATE HRESULT CStubUniv::DispatchMethod
+*Purpose:
+* Dispatch a vtable method based on the contents of the current stream.
+*
+* Marshaled In:
+* long cArgs
+* VARTYPE[] rgVt = array of argument types
+* VARIANT[] rgArgs = array of argument values
+*
+* Marhsaled Out:
+* hresult hresultRet = return value
+* VARIANT[] rgArgsOut = out params
+* Rich Error State (if any)
+*
+*
+*Entry:
+* iMeth = the index of the method to invoke.
+*
+*Exit:
+* return value =
+*
+***********************************************************************/
+HRESULT
+CStubUniv::DispatchMethod(int iMeth)
+{
+ int i;
+ long cArgs;
+ long cc; // really a CALLCONV, but don't marshal ints!
+ HRESULT hresult, hresultRet;
+ VARTYPE rgvt[16], FAR* prgvt;
+ VARIANT rgvar[16], FAR* prgvar;
+ VARIANT rgvarRef[16], FAR* prgvarRef;
+ VARIANT FAR* rgpvar[16], FAR* FAR* prgpvar;
+ VARIANT varRet;
+
+ // NOTE: do not go to "Error" until prgvt, prgvar, prgvarRef, and prgpvar
+ // are all initialized.
+
+ IfFailRet(GET(m_pstm, cc));
+ IfFailRet(GET(m_pstm, cArgs));
+
+ if(cArgs == 0){
+ prgvt = NULL;
+ prgvar = NULL;
+ prgvarRef = NULL;
+ prgpvar = NULL;
+ }else if(cArgs < DIM(rgvar)){
+ prgvt = rgvt;
+ prgvar = rgvar;
+ memset(prgvar, 0, (int)cArgs * sizeof(VARIANT));
+ prgvarRef = rgvarRef;
+ memset(prgvarRef, 0, (int)cArgs * sizeof(VARIANT));
+ prgpvar = rgpvar;
+ }else{
+
+ // init in case of error
+ prgvt = NULL;
+ prgvar = NULL;
+ prgvarRef = NULL;
+ prgpvar = NULL;
+
+ if((prgvt = new FAR VARTYPE[cArgs]) == NULL)
+ goto ErrorOOM;
+ if((prgvar = new FAR VARIANT[cArgs]) == NULL)
+ goto ErrorOOM;
+ memset(prgvar, 0, (int)cArgs * sizeof(VARIANT));
+ if((prgvarRef = new FAR VARIANT[cArgs]) == NULL)
+ goto ErrorOOM;
+ memset(prgvarRef, 0, (int)cArgs * sizeof(VARIANT));
+ if((prgpvar = new FAR VARIANT FAR*[cArgs]) == NULL)
+ goto ErrorOOM;
+ }
+
+ if(cArgs > 0){
+ IfFailGo(m_pstm->Read(prgvt, cArgs * sizeof(VARTYPE), NULL), Error);
+ for(i = 0; i < cArgs; ++i){
+ IfFailGo(VariantRead(m_pstm,
+ &prgvar[i],
+ &rgvarRef[i],
+ m_syskindProxy),
+ Error);
+ prgpvar[i] = &prgvar[i];
+ }
+ }
+
+ hresult = DoInvokeMethod(m_punkCustom,
+ iMeth * sizeof(void FAR*),
+ (CALLCONV)cc,
+ VT_ERROR,
+ (unsigned int)cArgs,
+ prgvt,
+ prgpvar,
+ &varRet);
+
+ if(HRESULT_FAILED(hresult)){
+ hresultRet = hresult;
+ }else{
+ ASSERT(V_VT(&varRet) = VT_ERROR);
+ hresultRet = (HRESULT)V_ERROR(&varRet);
+ }
+
+ REWIND_STREAM(m_pstm);
+
+ IfFailGo(DispMarshalHresult(m_pstm, hresultRet), Error);
+
+ // Marshal back the Out params
+ for(i = 0; i < cArgs; ++i){
+ if(prgvt[i] & VT_BYREF)
+ IfFailGo(VariantWrite(m_pstm, &prgvar[i], m_syskindProxy), Error);
+ }
+
+ // Marshal the Rich Error state (if any)
+ IfFailGo(MarshalErrorInfo(m_pstm, m_syskindProxy), Error);
+
+ hresult = NOERROR;
+
+Error:;
+
+ VARIANT FAR* pvar, FAR* pvarEnd;
+
+ if(prgpvar != NULL && prgpvar != rgpvar)
+ delete prgpvar;
+
+ if(prgvarRef != NULL){
+ pvarEnd = &prgvarRef[cArgs];
+ for(pvar = prgvarRef; pvar < pvarEnd; ++pvar)
+ if(V_VT(pvar) != VT_EMPTY)
+ VariantClear(pvar);
+ if(prgvarRef != rgvarRef)
+ delete prgvarRef;
+ }
+ if(prgvar != NULL){
+ pvarEnd = &prgvar[cArgs];
+ for(pvar = prgvar; pvar < pvarEnd; ++pvar)
+ VariantClear(pvar);
+ if(prgvar != rgvar)
+ delete prgvar;
+ }
+ if(prgvt != NULL && prgvt != rgvt)
+ delete prgvt;
+ return hresult;
+
+ErrorOOM:
+ hresult = RESULT(E_OUTOFMEMORY);
+ goto Error;
+}
+
+
+//---------------------------------------------------------------------
+// Utilities
+//---------------------------------------------------------------------
+
+HRESULT
+VarVtOfIface(ITypeInfo FAR* ptinfo,
+ TYPEATTR FAR* ptattr,
+ VARTYPE FAR* pvt,
+ GUID FAR* pguid)
+{
+ HRESULT hresult;
+
+ switch(ptattr->typekind){
+ case TKIND_DISPATCH:
+ if ((ptattr->wTypeFlags & TYPEFLAG_FDUAL) == 0) {
+ // regular (non-dual) dispinterface is just VT_DISPATCH.
+ *pvt = VT_DISPATCH;
+ // don't have to set up *pguid, since not VT_INTERFACE
+ break;
+ }
+ // The interface typeinfo version of a dual interface has the same
+ // same guid as the dispinterface portion does, hence we can just use
+ // the dispinterface guid here.
+ /* FALLTHROUGH */
+
+ case TKIND_INTERFACE:
+ *pvt = VT_INTERFACE;
+ *pguid = ptattr->guid;
+ break;
+
+ default:
+ ASSERT(UNREACHED);
+ hresult = RESULT(DISP_E_BADVARTYPE);
+ goto Error;
+ }
+
+ hresult = NOERROR;
+
+Error:;
+ return hresult;
+}
+
+HRESULT
+VarVtOfUDT(ITypeInfo FAR* ptinfo,
+ TYPEDESC FAR* ptdesc,
+ VARTYPE FAR* pvt,
+ GUID FAR* pguid)
+{
+ HRESULT hresult;
+ TYPEATTR FAR* ptattrRef;
+ ITypeInfo FAR* ptinfoRef;
+
+ ASSERT(ptdesc->vt == VT_USERDEFINED);
+
+ ptinfoRef = NULL;
+ ptattrRef = NULL;
+
+ IfFailGo(ptinfo->GetRefTypeInfo(ptdesc->hreftype, &ptinfoRef), Error);
+ IfFailGo(ptinfoRef->GetTypeAttr(&ptattrRef), Error);
+
+ switch (ptattrRef->typekind) {
+ case TKIND_ENUM:
+#if HP_16BIT
+ *pvt = VT_I2;
+#else
+ *pvt = VT_I4;
+#endif
+ hresult = NOERROR;
+ break;
+
+ case TKIND_ALIAS:
+ hresult = VarVtOfTypeDesc(ptinfoRef,
+ &ptattrRef->tdescAlias,
+ pvt,
+ pguid);
+ break;
+
+ case TKIND_DISPATCH:
+ case TKIND_INTERFACE:
+ hresult = VarVtOfIface(ptinfoRef, ptattrRef, pvt, pguid);
+ break;
+
+ case TKIND_COCLASS:
+ { TYPEATTR FAR* ptattrPri;
+ ITypeInfo FAR* ptinfoPri;
+
+ if((hresult = GetPrimaryInterface(ptinfoRef, &ptinfoPri)) == NOERROR){
+ if((hresult = ptinfoPri->GetTypeAttr(&ptattrPri)) == NOERROR){
+ hresult = VarVtOfIface(ptinfoPri, ptattrPri, pvt, pguid);
+ ptinfoPri->ReleaseTypeAttr(ptattrPri);
+ }
+ ptinfoPri->Release();
+ }
+ }
+ break;
+
+ default:
+ IfFailGo(RESULT(DISP_E_BADVARTYPE), Error);
+ break;
+ }
+
+Error:;
+ if(ptinfoRef != NULL){
+ if(ptattrRef != NULL)
+ ptinfoRef->ReleaseTypeAttr(ptattrRef);
+ ptinfoRef->Release();
+ }
+ return hresult;
+}
+
+/***
+*PRIVATE HRESULT VarVtOfTypeDesc
+*Purpose:
+* Convert the given typeinfo TYPEDESC into a VARTYPE that can be
+* represented in a VARIANT. For some this is a 1:1 mapping, for
+* others we convert to a (possibly machine dependent, eg VT_INT->VT_I2)
+* base type, and others we cant represent in a VARIANT.
+*
+*Entry:
+* ptinfo =
+* ptdesc = * to the typedesc to convert
+* pvt =
+* pguid =
+*
+*Exit:
+* return value = HRESULT
+*
+* *pvt = a VARTYPE that may be stored in a VARIANT.
+* *pguid = a guid for a custom interface.
+*
+*
+* Following is a summary of how types are represented in typeinfo.
+* Note the difference between the apparent levels of indirection
+* between IDispatch* / DispFoo*, and DualFoo*.
+*
+* I2 => VT_I2
+* I2* => VT_PTR - VT_I2
+*
+* IDispatch * => VT_DISPATCH
+* IDispatch ** => VT_PTR - VT_DISPATCH
+* DispFoo * => VT_DISPATCH
+* DispFoo ** => VT_PTR - VT_DISPATCH
+* DualFoo * => VT_PTR - VT_INTERFACE (DispIID)
+* DualFoo ** => VT_PTR - VT_PTR - VT_INTERFACE (DispIID)
+* IFoo * => VT_PTR - VT_INTERFACE (IID)
+* IFoo ** => VT_PTR - VT_PTR - VT_INTERFACE (IID)
+*
+***********************************************************************/
+HRESULT
+VarVtOfTypeDesc(ITypeInfo FAR* ptinfo,
+ TYPEDESC FAR* ptdesc,
+ VARTYPE FAR* pvt,
+ GUID FAR* pguid)
+{
+ VARTYPE vt;
+ HRESULT hresult;
+
+ if(ptdesc->vt < VT_VMAX || ptdesc->vt == VT_UI1){
+ // all types from VT_EMPTY (0) up to & including VT_UNKNOWN
+ *pvt = ptdesc->vt; // are dispatchable
+ return NOERROR;
+ }
+
+ hresult = NOERROR;
+
+ switch (ptdesc->vt) {
+ case VT_INT:
+#if OE_WIN16
+ *pvt = VT_I2;
+#else
+ *pvt = VT_I4;
+#endif
+ break;
+
+ // REVIEW: do we need to do hresult-mapping for 16/32 interop here?
+ case VT_HRESULT:
+ *pvt = VT_ERROR;
+ break;
+
+ case VT_VOID:
+ *pvt = VT_EMPTY;
+ break;
+
+ case VT_USERDEFINED:
+ hresult = VarVtOfUDT(ptinfo, ptdesc, pvt, pguid);
+ break;
+
+ case VT_PTR:
+ // Special case: only an interface may have 2 levels of VT_PTR, or
+ // a dispinterface** (which is represented by VT_PTR-VT_PTR-VT_USERDEFINED-TKIND_DISPATCH
+ if(ptdesc->lptdesc->vt == VT_PTR && ptdesc->lptdesc->lptdesc->vt == VT_USERDEFINED){
+ hresult = VarVtOfUDT(ptinfo, ptdesc->lptdesc->lptdesc, &vt, pguid);
+ if(hresult == NOERROR){
+ if (vt == VT_INTERFACE)
+ *pvt = (VT_BYREF | VT_INTERFACE);
+ else if (vt == VT_DISPATCH)
+ *pvt = (VT_BYREF | VT_DISPATCH);
+ else
+ hresult = RESULT(DISP_E_BADVARTYPE);
+ break;
+ }
+ }
+
+ // Special case: VT_PTR-VT_USERDEFINED-TKIND_DISPATCH is VT_DISPATCH is
+ // a dispinterface* (VT_DISPATCH)
+ if (ptdesc->lptdesc->vt == VT_USERDEFINED) {
+ hresult = VarVtOfUDT(ptinfo, ptdesc->lptdesc, &vt, pguid);
+ if (hresult == NOERROR && vt == VT_DISPATCH) {
+ *pvt = VT_DISPATCH;
+ break;
+ }
+ }
+
+ hresult = VarVtOfTypeDesc(ptinfo, ptdesc->lptdesc, &vt, pguid);
+ if(hresult == NOERROR){
+ if(vt & VT_BYREF){
+ // ByRef can only be applied once
+ hresult = RESULT(DISP_E_BADVARTYPE);
+ break;
+ }
+ // Note: a VT_PTR->VT_INTERFACE gets folded into just a
+ // VT_INTERFACE in a variant
+ *pvt = (vt == VT_INTERFACE) ? VT_INTERFACE : (vt | VT_BYREF);
+ }
+ break;
+
+ case VT_SAFEARRAY:
+ hresult = VarVtOfTypeDesc(ptinfo, ptdesc->lptdesc, &vt, pguid);
+ if(hresult == NOERROR){
+ if(vt & (VT_BYREF | VT_ARRAY)){
+ // error if nested array or array of pointers
+ hresult = RESULT(DISP_E_BADVARTYPE);
+ break;
+ }
+ *pvt = (vt | VT_ARRAY);
+ }
+ break;
+
+ default:
+ ASSERT(UNREACHED);
+ hresult = RESULT(DISP_E_BADVARTYPE);
+ break;
+ }
+
+ return hresult;
+}
+
+/***
+*PRIVATE HRESULT SzLibIdOfIID
+*Purpose:
+* Return the string for of the LibId registered typelib that contains
+* the definition of the interface with the given IID.
+*
+*Entry:
+* riid = the IID to find the LibId of.
+* cbLibId = size of the passed in LibId buffer
+*
+*Exit:
+* return value = HRESULT
+*
+* rgchLibId = string form of the typelib's LibId.
+*
+***********************************************************************/
+HRESULT
+SzLibIdOfIID(REFIID riid, char FAR* rgchLibId, long cbLibId)
+{
+ char szKey[10+CCH_SZGUID0+8+1];
+
+ strcpy(szKey, "Interface\\");
+ StringFromGUID2A(riid, &szKey[10], CCH_SZGUID0);
+ strcat(szKey, "\\TypeLib");
+
+ if(RegQueryValueA(HKEY_CLASSES_ROOT,
+ szKey, rgchLibId, &cbLibId) != ERROR_SUCCESS)
+ return RESULT(TYPE_E_LIBNOTREGISTERED);
+ return NOERROR;
+}
+
+// Is the given string a valid stringized LCID?
+BOOL
+FIsLCID(char FAR* szLcid)
+{
+ int len;
+ LCID lcid;
+ char rgch[32];
+ char FAR* pchEnd;
+
+ len = strlen(szLcid);
+ lcid = (LCID)strtoul(szLcid, &pchEnd, 16);
+ // if converting to LCID consumed all characters..
+ if(pchEnd == &szLcid[len]){
+ // and its a number the system claims to know about...
+ if(GetLocaleInfoA(lcid,
+ LOCALE_NOUSEROVERRIDE | LOCALE_ILANGUAGE,
+ rgch, DIM(rgch)) > 0)
+ {
+ // then assume its a valid stringized LCID
+ return TRUE;
+ }
+ }
+ return FALSE;
+}
+
+/***
+*PRIVATE HRESULT GetTypeInfoOfIID
+*Purpose:
+* Return the typeinfo that describes the interface named by the
+* given IID.
+*
+*Entry:
+* riid = the IID of the interface for which were loading the typeinfo
+*
+*Exit:
+* return value = HRESULT
+*
+* *ptinfo = type typeinfo of the interface named by riid, if successful.
+*
+***********************************************************************/
+HRESULT
+GetTypeInfoOfIID(REFIID riid, ITypeInfo FAR* FAR* pptinfo)
+{
+#define CCH_SZTYPELIB0 (7+1) // Typelib\0
+#define CCH_SZVERS0 (5+1+5+1) // wMaj.wMin\0
+#define CCH_SZLANG0 (4+1) // 0409\0
+#define CCH_SZPLATFORM0 (5+1) // win16\0
+#define CCH_SZKEY0 \
+ CCH_SZTYPELIB0+CCH_SZGUID0+CCH_SZVERS0+CCH_SZLANG0+CCH_SZPLATFORM0
+
+ int i;
+ long cb;
+ HRESULT hresult;
+ char FAR* pchEnd;
+ char szKey[CCH_SZKEY0+1];
+ char rgchVer[CCH_SZVERS0+1]; // wMaj.wMin\0
+ char rgchBest[CCH_SZVERS0+1];
+ ITypeLib FAR* ptlib;
+ ITypeInfo FAR* ptinfo;
+ WORD wMajBest, wMinBest, wMaj, wMin;
+ HKEY hkRoot, hkGuid, hkVers, hkLang, hkPlatform;
+ OLECHAR FAR* pszTypeLib;
+ char rgchTypeLib[256];
+#if OE_WIN32
+ WCHAR rgwchTypeLib[256];
+#endif
+
+ ptlib = NULL;
+ hkRoot = HKEY_CLASSES_ROOT;
+ hkGuid = HKEY_CLASSES_ROOT;
+ hkVers = HKEY_CLASSES_ROOT;
+ hkLang = HKEY_CLASSES_ROOT;
+ hkPlatform = HKEY_CLASSES_ROOT;
+
+ // Hold open the root key for efficiency
+ if(RegOpenKeyA(HKEY_CLASSES_ROOT, NULL, &hkRoot) != ERROR_SUCCESS)
+ return RESULT(REGDB_E_READREGDB);
+
+ // Find the LibId of TypeLib containing the definition of the given IID
+ strcpy(szKey, "TypeLib\\");
+ IfFailRet(SzLibIdOfIID(riid, &szKey[8], CCH_SZGUID0+1));
+
+ if(RegOpenKeyA(HKEY_CLASSES_ROOT, szKey, &hkGuid) != ERROR_SUCCESS)
+ return RESULT(TYPE_E_LIBNOTREGISTERED);
+
+ // Find the highest version number for the registered type lib
+ rgchBest[0] = '\0';
+ wMajBest = wMinBest = 0;
+ for(i = 0;
+ RegEnumKeyA(hkGuid, i, rgchVer, DIM(rgchVer)) == ERROR_SUCCESS;
+ ++i)
+ {
+ wMaj = (WORD)strtoul(rgchVer, &pchEnd, 16);
+ // ignore the version if its format isnt #.#
+ if(*pchEnd != '.')
+ continue;
+ wMin = (WORD)strtoul(pchEnd+1, NULL, 16);
+ if(wMaj > wMajBest || (wMaj == wMajBest && wMin > wMinBest)){
+ wMajBest = wMaj;
+ wMinBest = wMin;
+ strcpy(rgchBest, rgchVer);
+ }
+ }
+
+ // Open the key for the highest version number
+ if(RegOpenKeyA(hkGuid, rgchBest, &hkVers) != ERROR_SUCCESS)
+ goto ErrorNotReg;
+
+ // Grab the fist language subkey under the version
+ // Need to possibly skip over FLAGS and HELPDIR subkeys
+ for(i=0;; ++i){
+ if(RegEnumKeyA(hkVers, i, szKey, 16) != ERROR_SUCCESS)
+ goto ErrorNotReg;
+ if(FIsLCID(szKey))
+ break;
+ }
+ if(RegOpenKeyA(hkVers, szKey, &hkLang) != ERROR_SUCCESS)
+ goto ErrorNotReg;
+
+ // Grab the first platform subkey under the language
+ // we can do this because none of the info we use to construct the
+ // proxy is platform-specific. For example, we ignore calling
+ // convention on the proxy side of things. It's irrelevent.
+ if(RegEnumKeyA(hkLang, 0, szKey, CCH_SZPLATFORM0) != ERROR_SUCCESS)
+ goto ErrorNotReg;
+ if(RegOpenKeyA(hkLang, szKey, &hkPlatform) != ERROR_SUCCESS)
+ goto ErrorNotReg;
+
+ cb = DIM(rgchTypeLib);
+ if(RegQueryValueA(hkPlatform, NULL, rgchTypeLib, &cb) != ERROR_SUCCESS)
+ goto ErrorNotReg;
+
+#if OE_WIN32
+ cb = DIM(rgchTypeLib);
+ MultiByteToWideChar(CP_ACP,
+ MB_PRECOMPOSED,
+ rgchTypeLib,
+ cb,
+ rgwchTypeLib,
+ cb);
+ pszTypeLib = rgwchTypeLib;
+#else
+ pszTypeLib = rgchTypeLib;
+#endif
+
+ // Load the typelib we worked so hard to find
+ IfFailGo(DoLoadTypeLib(pszTypeLib, &ptlib), Error);
+
+ // Extract the typeinfo that describes the interface
+ IfFailGo(ptlib->GetTypeInfoOfGuid(riid, &ptinfo), Error);
+
+ *pptinfo = ptinfo;
+ hresult = NOERROR;
+ // FALLTHROUGH...
+
+Error:;
+ if(ptlib != NULL)
+ ptlib->Release();
+ if(hkPlatform != HKEY_CLASSES_ROOT)
+ RegCloseKey(hkPlatform);
+ if(hkLang != HKEY_CLASSES_ROOT)
+ RegCloseKey(hkLang);
+ if(hkVers != HKEY_CLASSES_ROOT)
+ RegCloseKey(hkVers);
+ if(hkGuid != HKEY_CLASSES_ROOT)
+ RegCloseKey(hkGuid);
+ RegCloseKey(hkRoot);
+ return hresult;
+
+ErrorNotReg:;
+ hresult = RESULT(TYPE_E_LIBNOTREGISTERED);
+ goto Error;
+}
+
+
+#if defined(_X86_)
+/***
+*int GetCbStackCleanupOfFuncDesc
+*Purpose:
+* For _stdcall on x86 Win32, the Universal Method must clean up its parameters.
+* This function computes the number of bytes of stack which must be
+* cleaned up.
+*
+*
+*Entry:
+* pfdesc = FUNCDESC describing the function and its parameter types
+* ptinfo = ITypeInfo describing the object interface
+*
+*Exit:
+* return value = HRESULT
+*
+* *pcbStackCleanup = number of bytes of stack to clean up, if successful
+*
+***********************************************************************/
+HRESULT
+GetCbStackCleanupOfFuncDesc(FUNCDESC FAR* pfdesc,
+ ITypeInfo FAR* ptinfo,
+ int FAR* pcbStackCleanup)
+{
+ int i;
+ TYPEDESC FAR* ptdesc;
+ VARIANT var, FAR* pvar;
+ VARTYPE vt;
+ HRESULT hresult;
+ GUID guid;
+
+ // We have to ignore the calling convention in the typelib, and assume
+ // that the proxy is being called with the STDCALL calling convention.
+ // The typelib is from the server, so the calling convention in the
+ // typelib is only useful on the stub side of things.
+
+ pvar = &var;
+
+ *pcbStackCleanup = 4; // account for the 'this' pointer
+ // since we know we are returning a hresult (or void?) then we know
+ // there's not a hidden parm for a structure return.
+
+ for(i = 0; i < pfdesc->cParams; ++i){
+
+ ptdesc = &pfdesc->lprgelemdescParam[i].tdesc;
+ IfFailGo(VarVtOfTypeDesc(ptinfo,
+ ptdesc,
+ &V_VT(pvar),
+ &guid), Error);
+
+ vt = V_VT(pvar);
+ switch(vt){
+ case VT_CY:
+ case VT_R8:
+ case VT_DATE:
+ *pcbStackCleanup+=8;
+ break;
+ case VT_VARIANT:
+ *pcbStackCleanup+=sizeof(VARIANT);
+ break;
+ case VT_NULL: // cant show up as arg type
+ case VT_EMPTY: // cant show up as arg type
+ ASSERT(UNREACHED);
+ hresult = RESULT(E_FAIL);
+ goto Error;
+ default:
+ *pcbStackCleanup+=4;
+ break;
+ } // switch(vt)
+ } // for()
+
+ hresult = NOERROR;
+
+Error:
+ return hresult;
+}
+#endif //defined(_X86_)
diff --git a/private/oleauto/src/dispatch/ups.h b/private/oleauto/src/dispatch/ups.h
new file mode 100644
index 000000000..8069d2ae7
--- /dev/null
+++ b/private/oleauto/src/dispatch/ups.h
@@ -0,0 +1,170 @@
+/***
+*ups.h - The Universal Proxy/Stub class definitions
+*
+* Copyright (C) 1992-94, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file describes the TypeInfo-driven, Universal Proxy Stub classes
+*
+* CProxUniv -- The Universal Proxy class
+* CStubUniv -- The Universal Stub class
+*
+*Revision History:
+*
+* [00] 21-Jun-94 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+
+// forward declarations
+class FAR CProxUniv;
+class FAR CStubUniv;
+
+// METHINFO
+//
+// Data stored for each method
+//
+typedef struct {
+ FUNCDESC *pfdesc; // funcdesc corresponding to this vtable entry
+ ITypeInfo *ptinfo;
+#if defined(_X86_)
+ int cbStackCleanup; // #bytes of args to clean up for _stdcall
+#endif //defined(_X86_)
+} METHINFO;
+
+
+#if defined(_X86_)
+HRESULT GetCbStackCleanupOfFuncDesc(FUNCDESC FAR* pfdesc,
+ ITypeInfo FAR* ptinfo,
+ int FAR* pcbStackCleanup);
+#endif //defined(_X86_)
+extern "C" STDAPI_(HRESULT) ProxyMethod(CProxUniv *pprox,
+ int iMeth,
+ va_list args
+#if defined(_X86_)
+ , int *pcbStackCleanup
+#endif //defined(_X86_)
+ );
+
+// CProxUniv - 'prox'
+//
+// The Universal proxy class
+//
+class FAR CProxUniv
+{
+ void *m_pvtbl;
+
+public:
+
+static HRESULT Create(IUnknown FAR* punkOuter,
+ REFIID riid,
+ IUnknown FAR* FAR* pprox);
+
+ CProxUniv(IUnknown FAR* punkOuter);
+ ~CProxUniv();
+
+ class FAR CPriv : public IPROXY
+ {
+ public:
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ STDMETHOD(Connect)(ICHANNEL FAR* plrpc);
+ STDMETHOD_(void, Disconnect)(void);
+
+ inline CProxUniv FAR* PProx();
+ };
+ friend CPriv;
+ CPriv m_priv;
+
+ HRESULT PSInit(void);
+ HRESULT CacheFuncDescs(ITypeInfo *ptinfo);
+
+ unsigned long m_cRefs;
+ ICHANNEL FAR* m_plrpc;
+ IUnknown FAR* m_punkOuter;
+ SYSKIND m_syskindStub;
+
+ BOOL m_fIsDual; // Is this a dual interface?
+ IID m_iid; // the IID for which this instance is a proxy
+ USHORT m_cFuncs; // count of functions on the custom interface
+ METHINFO FAR* m_rgMethInfo;// array parallel to the vtable with data
+ // specific to each method
+};
+
+
+// CStubUniv - 'stub'
+//
+// The Universal stub class.
+//
+class FAR CStubUniv : public ISTUB
+{
+public:
+
+static HRESULT Create(IUnknown FAR* punkServer,
+ REFIID riid,
+ ISTUB FAR* FAR* ppstub);
+
+ // IUnknown methods
+ //
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(unsigned long, AddRef)(void);
+ STDMETHOD_(unsigned long, Release)(void);
+
+ // IRpcStub methods
+ //
+#if (OE_WIN32 || defined(WOW))
+ STDMETHOD(Connect)(IUnknown FAR* pUnk);
+ STDMETHOD_(void, Disconnect)(void);
+ STDMETHOD(Invoke)(RPCOLEMESSAGE FAR* pRpcMsg,
+ IRpcChannelBuffer FAR* pRpcChannel);
+ STDMETHOD_(IRpcStubBuffer*, IsIIDSupported)(REFIID riid);
+ STDMETHOD_(ULONG, CountRefs)(void);
+ STDMETHOD(DebugServerQueryInterface)(void FAR* FAR* ppv);
+ STDMETHOD_(void, DebugServerRelease)(void FAR* pv);
+#else
+ STDMETHOD(Connect)(IUnknown FAR* punkObject);
+ STDMETHOD_(void, Disconnect)(void);
+ STDMETHOD(Invoke)(REFIID riid,
+ int imeth,
+ IStream FAR* pstm,
+ unsigned long dwDestCtx,
+ void FAR* pvDestCtx);
+ STDMETHOD_(OLEBOOL, IsIIDSupported)(REFIID riid);
+ STDMETHOD_(unsigned long, CountRefs)(void);
+#endif
+
+ HRESULT PSInit(void);
+ HRESULT DispatchMethod(int iMeth);
+
+private:
+ CStubUniv();
+ ~CStubUniv();
+
+ unsigned long m_cRefs;
+ IUnknown FAR* m_punk;
+ IStream FAR* m_pstm;
+ SYSKIND m_syskindProxy;
+ BOOL m_fIsDual; // Is this a dual interface?
+ IID m_iid; // the IID of the custom interface
+ IUnknown FAR* m_punkCustom;
+};
+
+
+enum IMETH_UNIVERSAL {
+ IMETH_UNIVERSAL_QueryInterface = 0,
+ IMETH_UNIVERSAL_AddRef,
+ IMETH_UNIVERSAL_Release,
+
+ IMETH_UNIVERSAL_GetTypeInfoCount,
+ IMETH_UNIVERSAL_GetTypeInfo,
+ IMETH_UNIVERSAL_GetIDsOfNames,
+ IMETH_UNIVERSAL_Invoke,
+
+ IMETH_UNIVERSAL_PSInit = 32000 // something much larger than the
+ // max possible vtable index
+};
diff --git a/private/oleauto/src/dispatch/uvft.cpp b/private/oleauto/src/dispatch/uvft.cpp
new file mode 100644
index 000000000..8d49bb3de
--- /dev/null
+++ b/private/oleauto/src/dispatch/uvft.cpp
@@ -0,0 +1,396 @@
+/***
+*uvft.cpp
+*
+* Copyright (C) 1992-94, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This module implements the Universal Proxy class' Universal
+* Delegator. This is the mondo shared vtable, that delagates
+* all vtable calls to a central marshaling routine. Also known
+* as the Universal Vtable (uvft).
+*
+*Revision History:
+*
+* [00] 22-Jun-94 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#ifndef WIN32
+# include <cobjps.h>
+#endif
+#include "dispmrsh.h"
+#include "ups.h"
+#include "dispps.h"
+#include <stdarg.h>
+
+ASSERTDATA
+
+HRESULT STDMETHODCALLTYPE
+UnivQueryInterface(CProxUniv *pthis, REFIID riid, void FAR* FAR* ppv)
+{
+ return pthis->m_punkOuter->QueryInterface(riid, ppv);
+}
+
+unsigned long STDMETHODCALLTYPE
+UnivAddRef(CProxUniv *pthis)
+{
+ return pthis->m_punkOuter->AddRef();
+}
+
+unsigned long STDMETHODCALLTYPE
+UnivRelease(CProxUniv *pthis)
+{
+ return pthis->m_punkOuter->Release();
+}
+
+HRESULT STDMETHODCALLTYPE
+UnivGetTypeInfoCount(CProxUniv *pprox, unsigned int FAR* pctinfo)
+{
+ return ProxyGetTypeInfoCount(pprox->m_plrpc,
+ pprox->m_syskindStub,
+ pctinfo);
+}
+
+HRESULT STDMETHODCALLTYPE
+UnivGetTypeInfo(CProxUniv *pprox,
+ unsigned int itinfo,
+ LCID lcid,
+ ITypeInfo FAR* FAR* pptinfo)
+{
+ return ProxyGetTypeInfo(pprox->m_plrpc,
+ pprox->m_syskindStub,
+ itinfo,
+ lcid,
+ pptinfo);
+}
+
+HRESULT STDMETHODCALLTYPE
+UnivGetIDsOfNames(CProxUniv *pprox,
+ REFIID riid,
+ OLECHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ LCID lcid,
+ DISPID FAR* rgdispid)
+{
+ return ProxyGetIDsOfNames(pprox->m_plrpc,
+ pprox->m_syskindStub,
+ riid,
+ rgszNames,
+ cNames,
+ lcid,
+ rgdispid);
+}
+
+HRESULT STDMETHODCALLTYPE
+UnivInvoke(CProxUniv *pprox,
+ DISPID dispidMember,
+ REFIID riid,
+ LCID lcid,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pdispparams,
+ VARIANT FAR* pvarResult,
+ EXCEPINFO FAR* pexcepinfo,
+ unsigned int FAR* puArgErr)
+{
+ return ProxyInvoke(pprox->m_plrpc,
+ pprox->m_syskindStub,
+ dispidMember,
+ riid,
+ lcid,
+ wFlags,
+ pdispparams,
+ pvarResult,
+ pexcepinfo,
+ puArgErr);
+}
+
+
+#if defined(_X86_)
+
+// UM ## X() is native code in win32\i386\invoke.asm
+// WARNING: If the number of MDEFs changes, the WHILE... macro in invoke.asm
+// WARNING: must be changed to match
+#define MDEF(X) extern "C" UM ## X (void);
+
+#else //!defined(_X86_)
+
+#define MDEF(X) \
+ HRESULT CDECLMETHODCALLTYPE \
+ UM ## X (CProxUniv FAR* pprox, ...) { \
+ va_list args; \
+ va_start(args, pprox); \
+ return ProxyMethod(pprox, X, args); \
+ }
+
+#endif //!defined(_X86_)
+
+ MDEF(3) MDEF(4)
+MDEF(5) MDEF(6) MDEF(7) MDEF(8) MDEF(9)
+
+MDEF(10) MDEF(11) MDEF(12) MDEF(13) MDEF(14)
+MDEF(15) MDEF(16) MDEF(17) MDEF(18) MDEF(19)
+MDEF(20) MDEF(21) MDEF(22) MDEF(23) MDEF(24)
+MDEF(25) MDEF(26) MDEF(27) MDEF(28) MDEF(29)
+MDEF(30) MDEF(31) MDEF(32) MDEF(33) MDEF(34)
+MDEF(35) MDEF(36) MDEF(37) MDEF(38) MDEF(39)
+MDEF(40) MDEF(41) MDEF(42) MDEF(43) MDEF(44)
+MDEF(45) MDEF(46) MDEF(47) MDEF(48) MDEF(49)
+MDEF(50) MDEF(51) MDEF(52) MDEF(53) MDEF(54)
+MDEF(55) MDEF(56) MDEF(57) MDEF(58) MDEF(59)
+MDEF(60) MDEF(61) MDEF(62) MDEF(63) MDEF(64)
+MDEF(65) MDEF(66) MDEF(67) MDEF(68) MDEF(69)
+MDEF(70) MDEF(71) MDEF(72) MDEF(73) MDEF(74)
+MDEF(75) MDEF(76) MDEF(77) MDEF(78) MDEF(79)
+MDEF(80) MDEF(81) MDEF(82) MDEF(83) MDEF(84)
+MDEF(85) MDEF(86) MDEF(87) MDEF(88) MDEF(89)
+MDEF(90) MDEF(91) MDEF(92) MDEF(93) MDEF(94)
+MDEF(95) MDEF(96) MDEF(97) MDEF(98) MDEF(99)
+
+MDEF(100) MDEF(101) MDEF(102) MDEF(103) MDEF(104)
+MDEF(105) MDEF(106) MDEF(107) MDEF(108) MDEF(109)
+MDEF(110) MDEF(111) MDEF(112) MDEF(113) MDEF(114)
+MDEF(115) MDEF(116) MDEF(117) MDEF(118) MDEF(119)
+MDEF(120) MDEF(121) MDEF(122) MDEF(123) MDEF(124)
+MDEF(125) MDEF(126) MDEF(127) MDEF(128) MDEF(129)
+MDEF(130) MDEF(131) MDEF(132) MDEF(133) MDEF(134)
+MDEF(135) MDEF(136) MDEF(137) MDEF(138) MDEF(139)
+MDEF(140) MDEF(141) MDEF(142) MDEF(143) MDEF(144)
+MDEF(145) MDEF(146) MDEF(147) MDEF(148) MDEF(149)
+MDEF(150) MDEF(151) MDEF(152) MDEF(153) MDEF(154)
+MDEF(155) MDEF(156) MDEF(157) MDEF(158) MDEF(159)
+MDEF(160) MDEF(161) MDEF(162) MDEF(163) MDEF(164)
+MDEF(165) MDEF(166) MDEF(167) MDEF(168) MDEF(169)
+MDEF(170) MDEF(171) MDEF(172) MDEF(173) MDEF(174)
+MDEF(175) MDEF(176) MDEF(177) MDEF(178) MDEF(179)
+MDEF(180) MDEF(181) MDEF(182) MDEF(183) MDEF(184)
+MDEF(185) MDEF(186) MDEF(187) MDEF(188) MDEF(189)
+MDEF(190) MDEF(191) MDEF(192) MDEF(193) MDEF(194)
+MDEF(195) MDEF(196) MDEF(197) MDEF(198) MDEF(199)
+
+MDEF(200) MDEF(201) MDEF(202) MDEF(203) MDEF(204)
+MDEF(205) MDEF(206) MDEF(207) MDEF(208) MDEF(209)
+MDEF(210) MDEF(211) MDEF(212) MDEF(213) MDEF(214)
+MDEF(215) MDEF(216) MDEF(217) MDEF(218) MDEF(219)
+MDEF(220) MDEF(221) MDEF(222) MDEF(223) MDEF(224)
+MDEF(225) MDEF(226) MDEF(227) MDEF(228) MDEF(229)
+MDEF(230) MDEF(231) MDEF(232) MDEF(233) MDEF(234)
+MDEF(235) MDEF(236) MDEF(237) MDEF(238) MDEF(239)
+MDEF(240) MDEF(241) MDEF(242) MDEF(243) MDEF(244)
+MDEF(245) MDEF(246) MDEF(247) MDEF(248) MDEF(249)
+MDEF(250) MDEF(251) MDEF(252) MDEF(253) MDEF(254)
+MDEF(255) MDEF(256) MDEF(257) MDEF(258) MDEF(259)
+MDEF(260) MDEF(261) MDEF(262) MDEF(263) MDEF(264)
+MDEF(265) MDEF(266) MDEF(267) MDEF(268) MDEF(269)
+MDEF(270) MDEF(271) MDEF(272) MDEF(273) MDEF(274)
+MDEF(275) MDEF(276) MDEF(277) MDEF(278) MDEF(279)
+MDEF(280) MDEF(281) MDEF(282) MDEF(283) MDEF(284)
+MDEF(285) MDEF(286) MDEF(287) MDEF(288) MDEF(289)
+MDEF(290) MDEF(291) MDEF(292) MDEF(293) MDEF(294)
+MDEF(295) MDEF(296) MDEF(297) MDEF(298) MDEF(299)
+
+MDEF(300) MDEF(301) MDEF(302) MDEF(303) MDEF(304)
+MDEF(305) MDEF(306) MDEF(307) MDEF(308) MDEF(309)
+MDEF(310) MDEF(311) MDEF(312) MDEF(313) MDEF(314)
+MDEF(315) MDEF(316) MDEF(317) MDEF(318) MDEF(319)
+MDEF(320) MDEF(321) MDEF(322) MDEF(323) MDEF(324)
+MDEF(325) MDEF(326) MDEF(327) MDEF(328) MDEF(329)
+MDEF(330) MDEF(331) MDEF(332) MDEF(333) MDEF(334)
+MDEF(335) MDEF(336) MDEF(337) MDEF(338) MDEF(339)
+MDEF(340) MDEF(341) MDEF(342) MDEF(343) MDEF(344)
+MDEF(345) MDEF(346) MDEF(347) MDEF(348) MDEF(349)
+MDEF(350) MDEF(351) MDEF(352) MDEF(353) MDEF(354)
+MDEF(355) MDEF(356) MDEF(357) MDEF(358) MDEF(359)
+MDEF(360) MDEF(361) MDEF(362) MDEF(363) MDEF(364)
+MDEF(365) MDEF(366) MDEF(367) MDEF(368) MDEF(369)
+MDEF(370) MDEF(371) MDEF(372) MDEF(373) MDEF(374)
+MDEF(375) MDEF(376) MDEF(377) MDEF(378) MDEF(379)
+MDEF(380) MDEF(381) MDEF(382) MDEF(383) MDEF(384)
+MDEF(385) MDEF(386) MDEF(387) MDEF(388) MDEF(389)
+MDEF(390) MDEF(391) MDEF(392) MDEF(393) MDEF(394)
+MDEF(395) MDEF(396) MDEF(397) MDEF(398) MDEF(399)
+
+MDEF(400) MDEF(401) MDEF(402) MDEF(403) MDEF(404)
+MDEF(405) MDEF(406) MDEF(407) MDEF(408) MDEF(409)
+MDEF(410) MDEF(411) MDEF(412) MDEF(413) MDEF(414)
+MDEF(415) MDEF(416) MDEF(417) MDEF(418) MDEF(419)
+MDEF(420) MDEF(421) MDEF(422) MDEF(423) MDEF(424)
+MDEF(425) MDEF(426) MDEF(427) MDEF(428) MDEF(429)
+MDEF(430) MDEF(431) MDEF(432) MDEF(433) MDEF(434)
+MDEF(435) MDEF(436) MDEF(437) MDEF(438) MDEF(439)
+MDEF(440) MDEF(441) MDEF(442) MDEF(443) MDEF(444)
+MDEF(445) MDEF(446) MDEF(447) MDEF(448) MDEF(449)
+MDEF(450) MDEF(451) MDEF(452) MDEF(453) MDEF(454)
+MDEF(455) MDEF(456) MDEF(457) MDEF(458) MDEF(459)
+MDEF(460) MDEF(461) MDEF(462) MDEF(463) MDEF(464)
+MDEF(465) MDEF(466) MDEF(467) MDEF(468) MDEF(469)
+MDEF(470) MDEF(471) MDEF(472) MDEF(473) MDEF(474)
+MDEF(475) MDEF(476) MDEF(477) MDEF(478) MDEF(479)
+MDEF(480) MDEF(481) MDEF(482) MDEF(483) MDEF(484)
+MDEF(485) MDEF(486) MDEF(487) MDEF(488) MDEF(489)
+MDEF(490) MDEF(491) MDEF(492) MDEF(493) MDEF(494)
+MDEF(495) MDEF(496) MDEF(497) MDEF(498) MDEF(499)
+
+MDEF(500) MDEF(501) MDEF(502) MDEF(503) MDEF(504)
+MDEF(505) MDEF(506) MDEF(507) MDEF(508) MDEF(509)
+MDEF(510) MDEF(511) MDEF(512)
+
+
+#define MSET10(X) \
+ UM ## X ## 0, \
+ UM ## X ## 1, \
+ UM ## X ## 2, \
+ UM ## X ## 3, \
+ UM ## X ## 4, \
+ UM ## X ## 5, \
+ UM ## X ## 6, \
+ UM ## X ## 7, \
+ UM ## X ## 8, \
+ UM ## X ## 9,
+
+// A universal delegator for a custom interface that derives from
+// IUnknown (and *not* IDispatch).
+//
+void FAR* g_rgpfnUnk[] =
+{
+ UnivQueryInterface,
+ UnivAddRef,
+ UnivRelease,
+ UM3,
+ UM4,
+ UM5,
+ UM6,
+ UM7,
+ UM8,
+ UM9,
+ MSET10(1)
+ MSET10(2)
+ MSET10(3)
+ MSET10(4)
+ MSET10(5)
+ MSET10(6)
+ MSET10(7)
+ MSET10(8)
+ MSET10(9)
+ MSET10(10)
+ MSET10(11)
+ MSET10(12)
+ MSET10(13)
+ MSET10(14)
+ MSET10(15)
+ MSET10(16)
+ MSET10(17)
+ MSET10(18)
+ MSET10(19)
+ MSET10(20)
+ MSET10(21)
+ MSET10(22)
+ MSET10(23)
+ MSET10(24)
+ MSET10(25)
+ MSET10(26)
+ MSET10(27)
+ MSET10(28)
+ MSET10(29)
+ MSET10(30)
+ MSET10(31)
+ MSET10(32)
+ MSET10(33)
+ MSET10(34)
+ MSET10(35)
+ MSET10(36)
+ MSET10(37)
+ MSET10(38)
+ MSET10(39)
+ MSET10(40)
+ MSET10(41)
+ MSET10(42)
+ MSET10(43)
+ MSET10(44)
+ MSET10(45)
+ MSET10(46)
+ MSET10(47)
+ MSET10(48)
+ MSET10(49)
+ MSET10(50)
+ UM510,
+ UM511,
+ UM512
+};
+
+// A universal delegator for a custom interface that derives from
+// IDispatch.
+//
+void FAR* g_rgpfnDisp[] =
+{
+ UnivQueryInterface,
+ UnivAddRef,
+ UnivRelease,
+ UnivGetTypeInfoCount,
+ UnivGetTypeInfo,
+ UnivGetIDsOfNames,
+ UnivInvoke,
+ UM7,
+ UM8,
+ UM9,
+ MSET10(1)
+ MSET10(2)
+ MSET10(3)
+ MSET10(4)
+ MSET10(5)
+ MSET10(6)
+ MSET10(7)
+ MSET10(8)
+ MSET10(9)
+ MSET10(10)
+ MSET10(11)
+ MSET10(12)
+ MSET10(13)
+ MSET10(14)
+ MSET10(15)
+ MSET10(16)
+ MSET10(17)
+ MSET10(18)
+ MSET10(19)
+ MSET10(20)
+ MSET10(21)
+ MSET10(22)
+ MSET10(23)
+ MSET10(24)
+ MSET10(25)
+ MSET10(26)
+ MSET10(27)
+ MSET10(28)
+ MSET10(29)
+ MSET10(30)
+ MSET10(31)
+ MSET10(32)
+ MSET10(33)
+ MSET10(34)
+ MSET10(35)
+ MSET10(36)
+ MSET10(37)
+ MSET10(38)
+ MSET10(39)
+ MSET10(40)
+ MSET10(41)
+ MSET10(42)
+ MSET10(43)
+ MSET10(44)
+ MSET10(45)
+ MSET10(46)
+ MSET10(47)
+ MSET10(48)
+ MSET10(49)
+ MSET10(50)
+ UM510,
+ UM511,
+ UM512
+};
+
+
+long g_cfnUnk = DIM(g_rgpfnUnk);
+long g_cfnDisp = DIM(g_rgpfnDisp);
diff --git a/private/oleauto/src/dispatch/validate.cpp b/private/oleauto/src/dispatch/validate.cpp
new file mode 100644
index 000000000..1e7765560
--- /dev/null
+++ b/private/oleauto/src/dispatch/validate.cpp
@@ -0,0 +1,291 @@
+/***
+*validate.cpp - parameter validate support routines
+*
+* Copyright (C) 1992 - 1993, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This module contains paramater validation support utilities.
+*
+*
+*Revision History:
+*
+* [00] 19-Jan-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#ifdef _DEBUG /* { */
+
+/***
+*PUBLIC int FIsBadReadPtr
+*Purpose:
+* Answer if the given address is not readable for the given range.
+*
+*Entry:
+* pv = the address to check
+* cb = the range to check
+*
+*Exit:
+* return value = int
+*
+***********************************************************************/
+INTERNAL_(int)
+FIsBadReadPtr(const void *pv, unsigned int cb)
+{
+#if OE_WIN
+ return IsBadReadPtr(pv, cb);
+#else
+ // CONSIDER: should be a more comprehensive check for this on the mac.
+ return pv == NULL;
+#endif
+}
+
+/***
+*PUBLIC int FIsBadWritePtr
+*Purpose:
+* Answer if the given address is not writeable anywhere on the given range
+*
+*Entry:
+* pv = the address to check
+* cb = the range of bytes to check
+*
+*Exit:
+* return value = int
+*
+***********************************************************************/
+INTERNAL_(int)
+FIsBadWritePtr(void *pv, unsigned int cb)
+{
+#if OE_WIN
+ return IsBadWritePtr(pv, cb);
+#else
+ // CONSIDER: should be a more comprehensive check for this on the mac.
+ return pv == NULL;
+#endif
+}
+
+/***
+*PUBLIC int FIsBadCodePtr
+*Purpose:
+* Answer if the given address is not executable.
+*
+*Entry:
+* pv = the address to check
+*
+*Exit:
+* return value = int
+*
+***********************************************************************/
+INTERNAL_(int)
+FIsBadCodePtr(void *pv)
+{
+#if OE_WIN
+ return IsBadCodePtr((FARPROC)pv);
+#else
+ // CONSIDER: should be a more comprehensive check for this on the mac.
+ return pv == NULL;
+#endif
+}
+
+/***
+*PUBLIC int FIsBadStringPtr
+*Purpose:
+* Answer if the given address is not a valid string.
+*
+*Entry:
+* pv = the address of the string.
+* cchMax = the maximum length of the string.
+*
+*Exit:
+* return value = int
+*
+***********************************************************************/
+INTERNAL_(int)
+FIsBadStringPtr(OLECHAR FAR*pv, unsigned int cchMax)
+{
+#if OE_WIN16
+ return IsBadStringPtr(pv, cchMax);
+#elif OE_WIN32
+#if _X86_
+ if (g_fChicago) {
+ return IsBadStringPtrA((char *)pv, (cchMax == -1) ? BYTELEN(pv) : cchMax*2);
+ }
+#endif //_X86_
+ return IsBadStringPtrW(pv, cchMax);
+#else
+ // CONSIDER: should be a more comprehensive check for this on the mac.
+ return pv == NULL;
+#endif
+}
+
+/***
+*PUBLIC int FIsBadInterface
+*Purpose:
+* Answer if the given address is not a valid interface with the
+* given number of methods.
+*
+*Entry:
+* pv = the address of the interface
+* cMethods = the count of methods on the interface
+*
+*Exit:
+* return value = int
+*
+***********************************************************************/
+INTERNAL_(int)
+FIsBadInterface(void *pv, unsigned int cMethods)
+{
+struct vtable {
+ void (*rgpfn[1])();
+};
+struct iface {
+ vtable *pvft;
+};
+
+ unsigned int i;
+ vtable *pvft;
+ iface *piface = (struct iface*)pv;
+
+ // verify that the instance is readable
+ if(FIsBadReadPtr(piface, sizeof(void*)))
+ return TRUE;
+ // verify that the vtable is readable
+ pvft = piface->pvft;
+ if(FIsBadReadPtr(pvft, sizeof(void(*)()) * cMethods))
+ return TRUE;
+ // verify that the vtable is fully populated with function pointers
+ for(i = 0; i < cMethods; ++i){
+ if(FIsBadCodePtr(pvft->rgpfn[i]))
+ return TRUE;
+ }
+ return FALSE;
+}
+
+/***
+*int IsBadDispParams(DISPPARAMS*)
+*
+*Purpose:
+* Check for a bad DISPPARAMS structure.
+*
+*Entry:
+* pdispparams = pointer to a DISPPARAMS structure.
+*
+*Exit:
+* return value = int. TRUE if bad, FALSE if not.
+*
+***********************************************************************/
+INTERNAL_(int)
+IsBadDispParams(DISPPARAMS FAR* pdispparams)
+{
+ int fBad;
+
+ if(IsBadReadPtr(pdispparams, sizeof(*pdispparams)))
+ return TRUE;
+
+ // check the rgvarg array, if there is supposed to be one.
+ //
+ if(pdispparams->cArgs > 0){
+ fBad = IsBadReadPtr(
+ pdispparams->rgvarg,
+ pdispparams->cArgs * sizeof(pdispparams->rgvarg[0]));
+ if(fBad)
+ return TRUE;
+ }
+
+ // check the rgdispid array, if there is supposed to be one.
+ //
+ if(pdispparams->cNamedArgs > 0){
+ fBad = IsBadReadPtr(
+ pdispparams->rgdispidNamedArgs,
+ pdispparams->cNamedArgs * sizeof(pdispparams->rgdispidNamedArgs[0]));
+ if(fBad)
+ return TRUE;
+ }
+
+ return FALSE;
+}
+
+
+/***
+*PRIVATE int IsBadReadSA(SAFEARRAY*)
+*Purpose:
+* Validate the given safe array descriptor.
+*
+*Entry:
+* psa = the SafeArray descriptor to validate
+*
+*Exit:
+* return value = int. FALSE if its Ok, TRUE if its Bad.
+*
+***********************************************************************/
+INTERNAL_(int)
+IsBadReadSA(SAFEARRAY FAR* psa)
+{
+ if(IsBadReadPtr(psa, sizeof(*psa)))
+ return TRUE;
+
+ if(IsBadReadPtr(psa->rgsabound, psa->cDims * sizeof(SAFEARRAYBOUND)))
+ return TRUE;
+
+ return FALSE;
+}
+
+/***
+*PRIVATE int IsBadWriteSA(SAFEARRAY*)
+*Purpose:
+* Validate the given safe array descriptor.
+*
+*Entry:
+* psa = the SafeArray descriptor to validate
+*
+*Exit:
+* return value = int. FALSE if its Ok, TRUE if its Bad.
+*
+***********************************************************************/
+INTERNAL_(int)
+IsBadWriteSA(SAFEARRAY FAR* psa)
+{
+ if(IsBadWritePtr(psa, sizeof(*psa)))
+ return TRUE;
+
+ if(IsBadWritePtr(psa->rgsabound, psa->cDims * sizeof(SAFEARRAYBOUND)))
+ return TRUE;
+
+ return FALSE;
+}
+
+
+#ifdef _MAC /* { */
+
+// REVIEW: need to find a more complete way to do pointer validation
+// on the mac...
+
+EXTERN_C INTERNAL_(int)
+IsBadReadPtr(const void FAR* lp, unsigned int cb)
+{
+ UNUSED(cb);
+ return (lp == NULL);
+}
+
+EXTERN_C INTERNAL_(int)
+IsBadWritePtr(void FAR* lp, unsigned int cb)
+{
+ UNUSED(cb);
+ return (lp == NULL);
+}
+
+EXTERN_C INTERNAL_(int)
+IsBadStringPtr(const OLECHAR FAR* lpsz, unsigned int cchMax)
+{
+ UNUSED(cchMax);
+ return (lpsz == NULL);
+}
+
+#endif /* } */
+
+#endif /* } */
+
diff --git a/private/oleauto/src/dispatch/variant.cpp b/private/oleauto/src/dispatch/variant.cpp
new file mode 100644
index 000000000..4613a4a30
--- /dev/null
+++ b/private/oleauto/src/dispatch/variant.cpp
@@ -0,0 +1,1168 @@
+/*****************************************************************************
+*
+* Copyright (C) 1991-1993, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* File:
+*
+* variant.cpp
+*
+* Purpose:
+*
+* This file exports the following VARIANT API functions:
+*
+* VariantInit()
+* VariantClear()
+* VariantCopy()
+* VariantCopyInd()
+* VariantChangeType()
+* VariantChangeTypeEx()
+*
+* and defines the following private functions:
+*
+* IsLegalVartype()
+* ExtractValueProperty()
+* VariantChangeTypeInternal()
+*
+* Revision History:
+*
+* [00] 17-May-93 tomteng: merge disputil.cpp, rtglue.cpp, oleconv.c
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+ASSERTDATA
+
+/* For the Mac, code-segments must be pre-declared */
+#if OE_MAC
+#pragma code_seg("_TEXT")
+#pragma code_seg()
+#endif //OE_MAC
+
+PRIVATE_(HRESULT)
+ExtractValueProperty(IDispatch FAR* pdisp, LCID lcid, VARIANT FAR* pvarResult);
+
+
+/***
+*PUBLIC void VariantInit(VARIANT*)
+*Purpose:
+* Initialize the given VARIANT to VT_EMPTY.
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = void
+*
+* pvarg = pointer to initialized VARIANT
+*
+***********************************************************************/
+#if !OE_WIN32
+#pragma code_seg("_TEXT")
+#endif
+STDAPI_(void)
+VariantInit(VARIANT FAR* pvarg)
+{
+ V_VT(pvarg) = VT_EMPTY;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC HRESULT VariantClear(VARIANTARG FAR*)
+*Purpose:
+* Set the variant to nothing, releaseing any string or object
+* reference owned by that variant.
+*
+*Entry:
+* pvarg = the VARIANTARG to set to VT_EMPTY
+*
+*Exit:
+* return value = HRESULT
+* NOERROR
+* E_INVALIDARG
+* DISP_E_BADVARTYPE
+* DISP_E_ARRAYISLOCKED
+*
+*Note:
+* We dont release or clear anything thats ByRef. These aren't
+* owned by the variant, but by what the variant points at.
+*
+***********************************************************************/
+#if !OE_WIN32
+#pragma code_seg("_TEXT")
+#endif
+STDAPI
+VariantClear(VARIANTARG FAR* pvarg)
+{
+ VARTYPE vt;
+
+#ifdef _DEBUG
+ if(IsBadWritePtr(pvarg, sizeof(*pvarg)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ vt = V_VT(pvarg);
+
+ // Handle special-case internal type
+ if((vt & ~VT_BYREF) == VT_INTERFACE){
+ VARIANTX FAR* pvarx = (VARIANTX FAR*)pvarg;
+ if(pvarx->piid != NULL)
+ delete pvarx->piid;
+ }else{
+
+ IfFailRet(IsLegalVartype(vt));
+ }
+
+ switch(vt){
+ case VT_BSTR:
+ SysFreeString(V_BSTR(pvarg));
+ break;
+
+ case VT_UNKNOWN:
+ case VT_INTERFACE:
+ if(V_UNKNOWN(pvarg) != NULL)
+ V_UNKNOWN(pvarg)->Release();
+ break;
+
+ case VT_DISPATCH:
+ if(V_DISPATCH(pvarg) != NULL)
+ V_DISPATCH(pvarg)->Release();
+ break;
+
+ default:
+ if(V_ISARRAY(pvarg)){
+ if(!V_ISBYREF(pvarg)){
+ IfFailRet(SafeArrayDestroy(V_ARRAY(pvarg)));
+ }
+ }
+ break;
+ }
+
+#ifdef _DEBUG
+ MEMSET(pvarg, -1, sizeof(*pvarg));
+#endif
+
+ V_VT(pvarg) = VT_EMPTY;
+ return NOERROR;
+}
+#pragma code_seg()
+
+/***
+*PUBLIC HRESULT VariantCopy(VARIANTARG FAR*, VARIANTARG FAR*)
+*Purpose:
+* Copy the source VARIANTARG to the destination VARIANTARG.
+*
+*Entry:
+* pvargSrc = the source VARIANTARG
+*
+*Exit:
+* return value = HRESULT
+* NOERROR
+* E_INVALIDARG
+* E_OUTOFMEMORY
+* DISP_E_BADVARTYPE
+* DISP_E_ARRAYISLOCKED
+*
+* pvargDest = pointer to a copy of the soruce VARIANTARG
+*
+***********************************************************************/
+#if !OE_WIN32
+#pragma code_seg("_TEXT")
+#endif
+STDAPI
+VariantCopy(VARIANTARG FAR* pvargDest, VARIANTARG FAR* pvargSrc)
+{
+ BSTR bstr;
+
+#ifdef _DEBUG
+ if(IsBadReadPtr(pvargSrc, sizeof(*pvargSrc)))
+ return RESULT(E_INVALIDARG);
+ if(IsBadWritePtr(pvargDest, sizeof(*pvargDest)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+#if 0 /* yes: we allow literal copying of byrefs. */
+ // REVIEW: should we allow literal copying of ByRefs?
+ if(V_ISBYREF(pvargSrc))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ IfFailRet(IsLegalVartype(V_VT(pvargSrc)));
+
+ if(pvargDest == pvargSrc)
+ return NOERROR;
+
+ // free up strings or objects pvargDest is currently referencing.
+
+ IfFailRet(VariantClear(pvargDest));
+
+ if((V_VT(pvargSrc) & (VT_ARRAY | VT_BYREF)) == VT_ARRAY){
+
+ IfFailRet(SafeArrayCopy(V_ARRAY(pvargSrc), &V_ARRAY(pvargDest)));
+ V_VT(pvargDest) = V_VT(pvargSrc);
+
+ }else{
+
+ MEMCPY(pvargDest, pvargSrc, sizeof(VARIANTARG));
+
+ switch(V_VT(pvargSrc)){
+ case VT_BSTR:
+ bstr = V_BSTR(pvargSrc);
+ IfFailRet(ErrStringCopy(bstr, &V_BSTR(pvargDest)));
+ break;
+
+ case VT_UNKNOWN:
+ if(V_UNKNOWN(pvargDest) != NULL)
+ V_UNKNOWN(pvargDest)->AddRef();
+ break;
+
+ case VT_DISPATCH:
+ if(V_DISPATCH(pvargDest) != NULL)
+ V_DISPATCH(pvargDest)->AddRef();
+ break;
+
+ }
+ }
+
+ return NOERROR;
+}
+#pragma code_seg()
+
+/***
+*PUBLIC HRESULT VariantCopyInd(VARIANTARG*, VARIANTARG*)
+*Purpose:
+* Copy a VARIANTARG from the given source to dest, and indirect
+* the source if its a VT_BYREF.
+*
+*Entry:
+* pvargSrc = the VARIANTARG to copy and possibly indirect.
+*
+*Exit:
+* return value = HRESULT
+* NOERROR
+* E_INVALIDARG
+* E_OUTOFMEMORY
+* DISP_E_BADVARTYPE
+* DISP_E_ARRAYISLOCKED
+*
+* pvargDest = the indirected copy
+*
+***********************************************************************/
+#if !OE_WIN32
+#pragma code_seg("_TEXT")
+#endif
+STDAPI
+VariantCopyInd(VARIANTARG FAR* pvargDest, VARIANTARG FAR* pvargSrc)
+{
+ BSTR bstr;
+ VARTYPE vtTo;
+
+#ifdef _DEBUG
+ if(IsBadWritePtr(pvargSrc, sizeof(*pvargSrc)))
+ return RESULT(E_INVALIDARG);
+ if(IsBadWritePtr(pvargDest, sizeof(*pvargDest)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ // if the source is not ByRef, then this just maps to a
+ // simple VariantCopy.
+ //
+ if(!V_ISBYREF(pvargSrc)){
+ // just do the simple copy.
+ return VariantCopy(pvargDest, pvargSrc);
+ }
+
+ if(pvargDest != pvargSrc)
+ IfFailRet(VariantClear(pvargDest));
+
+ vtTo = V_VT(pvargSrc) & ~VT_BYREF;
+
+ switch(vtTo){
+ case VT_VARIANT:
+ // NOTE: we only allow one level of variants, with or without the ByRef.
+ if(V_VT(V_VARIANTREF(pvargSrc)) == (VT_BYREF | VT_VARIANT))
+ return RESULT(E_INVALIDARG);
+ IfFailRet(VariantCopyInd(pvargDest, V_VARIANTREF(pvargSrc)));
+ return NOERROR;
+
+#if VBA2
+ case VT_UI1:
+ V_UI1(pvargDest) = *V_UI1REF(pvargSrc);
+ break;
+#endif //VBA2
+
+ case VT_I2:
+ case VT_BOOL:
+ V_I2(pvargDest) = *V_I2REF(pvargSrc);
+ break;
+
+ case VT_I4:
+ case VT_ERROR:
+ V_I4(pvargDest) = *V_I4REF(pvargSrc);
+ break;
+
+ case VT_R4:
+ V_R4(pvargDest) = *V_R4REF(pvargSrc);
+ break;
+
+ case VT_R8:
+ case VT_DATE:
+ V_R8(pvargDest) = *V_R8REF(pvargSrc);
+ break;
+
+ case VT_CY:
+ V_CY(pvargDest) = *V_CYREF(pvargSrc);
+ break;
+
+ case VT_UNKNOWN:
+ V_UNKNOWN(pvargDest) = *V_UNKNOWNREF(pvargSrc);
+ if(V_UNKNOWN(pvargDest) != NULL)
+ V_UNKNOWN(pvargDest)->AddRef();
+ break;
+
+ case VT_DISPATCH:
+ V_DISPATCH(pvargDest) = *V_DISPATCHREF(pvargSrc);
+ if(V_DISPATCH(pvargDest) != NULL)
+ V_DISPATCH(pvargDest)->AddRef();
+ break;
+
+ case VT_BSTR:
+ bstr = *V_BSTRREF(pvargSrc);
+ IfFailRet(ErrStringCopy(bstr, &V_BSTR(pvargDest)));
+ break;
+
+ default:
+ if(vtTo & VT_ARRAY){
+ IfFailRet(SafeArrayCopy(*V_ARRAYREF(pvargSrc), &V_ARRAY(pvargDest)));
+ break;
+ }
+ return RESULT(E_INVALIDARG);
+ }
+
+ V_VT(pvargDest) = vtTo;
+
+ return NOERROR;
+}
+#pragma code_seg()
+
+/***
+*PUBLIC HRESULT VariantChangeType
+*Purpose:
+* This function changes the data type of a VARIANTARG to the given vt.
+* If the variant in initailly BYREF, it is converted to a VARIANT that
+* is not BYREF.
+*
+*Entry:
+* pargSrc = points to VARIANTARG to be converted.
+* vt = desired type of variant.
+*
+*Exit:
+* return value = HRESULT
+* NOERROR
+* E_INVALIDARG
+* E_OUTOFMEMORY
+* RESULT(DISP_E_OVERFLOW)
+* DISP_E_BADVARTYPE
+* DISP_E_TYPEMISMATCH
+*
+* *pargDest = contains the converted value.
+*
+***********************************************************************/
+
+STDAPI
+VariantChangeType(
+ VARIANTARG FAR* pvargDest,
+ VARIANTARG FAR* pvargSrc,
+ unsigned short wFlags,
+ VARTYPE vt)
+{
+ return VariantChangeTypeEx(pvargDest, pvargSrc, LOCALE_USER_DEFAULT, wFlags, vt);
+}
+
+
+STDAPI
+VariantChangeTypeEx(
+ VARIANTARG FAR* pvargDest,
+ VARIANTARG FAR* pvargSrc,
+ LCID lcid,
+ unsigned short wFlags,
+ VARTYPE vt)
+{
+
+static char NEARDATA
+g_fCoerceObjByExtractingValue[] = {
+ FALSE // VT_EMPTY
+ , FALSE // VT_NULL
+ , TRUE // VT_I2
+ , TRUE // VT_I4
+ , TRUE // VT_R4
+ , TRUE // VT_R8
+ , TRUE // VT_CY
+ , TRUE // VT_DATE
+ , TRUE // VT_BSTR
+ , FALSE // VT_DISPATCH
+ , TRUE // VT_ERROR
+ , TRUE // VT_BOOL
+ , FALSE // VT_VARIANT -- this is n/a really
+ , FALSE // VT_UNKNOWN
+ , FALSE // unused
+ , FALSE // unused
+ , TRUE // VT_I1
+ , TRUE // VT_UI1
+};
+
+ VARIANT varTmp;
+ HRESULT hresult;
+
+
+#ifdef _DEBUG
+ if(IsBadReadPtr(pvargSrc, sizeof(*pvargSrc)))
+ return RESULT(E_INVALIDARG);
+ if(IsBadWritePtr(pvargDest, sizeof(*pvargDest)))
+ return RESULT(E_INVALIDARG);
+#endif
+
+ // make sure both the source and target VARTYPEs are legal.
+ //
+ IfFailRet(IsLegalVartype(vt));
+ IfFailRet(IsLegalVartype(V_VT(pvargSrc)));
+
+ // we cant convert to or from VT_ARRAY
+ //
+ if(V_VT(pvargSrc) & VT_ARRAY)
+ return RESULT(DISP_E_TYPEMISMATCH);
+
+ // cant convert to array or byref.
+ //
+ if(vt & (VT_BYREF|VT_ARRAY|VT_RESERVED))
+ return RESULT(DISP_E_TYPEMISMATCH);
+
+ // if the source *and* target VARTYPE are the same, then there is
+ // no coersion to be done - we either copy, or do nothing at all.
+ //
+ if(vt == V_VT(pvargSrc)){
+ if(pvargDest == pvargSrc)
+ return NOERROR;
+ return VariantCopy(pvargDest, pvargSrc);
+ }
+
+ // Now we know some coersion must take place.
+
+ // Special case the handling of VT_DISPATCH - A IDispatch object is
+ // coerced to a base type by extracting its "value" property, and
+ // coercing that to the specfied target type.
+ //
+#ifdef _DEBUG
+ ASSERT(vt < DIM(g_fCoerceObjByExtractingValue));
+#endif
+
+ if ((V_VT(pvargSrc)&~VT_BYREF) == VT_DISPATCH
+ && g_fCoerceObjByExtractingValue[vt] == TRUE)
+ {
+ if(wFlags & VARIANT_NOVALUEPROP)
+ return RESULT(DISP_E_TYPEMISMATCH);
+
+ IDispatch FAR* pdisp =
+ V_ISBYREF(pvargSrc) ? *V_DISPATCHREF(pvargSrc) : V_DISPATCH(pvargSrc);
+
+ if(pdisp == NULL)
+ return RESULT(DISP_E_TYPEMISMATCH);
+
+ pdisp->AddRef();
+
+ V_VT(&varTmp) = VT_EMPTY;
+ hresult = ExtractValueProperty(pdisp, lcid, &varTmp);
+
+ pdisp->Release();
+
+ // if there was an error extracting the value property, then
+ // we simply report a type-mismatch.
+ //
+ if(hresult != NOERROR)
+ return RESULT(DISP_E_TYPEMISMATCH);
+
+ }else{
+
+ // otherwise just copy and coerce - this is a bit tricky because
+ // we want to make sure we leave the state of the params untouched
+ // if the corsion fails.
+
+ V_VT(&varTmp) = VT_EMPTY;
+
+ IfFailRet(VariantCopyInd(&varTmp, pvargSrc));
+
+ }
+
+ IfFailGo(VariantChangeTypeInternal(&varTmp, lcid, vt), LError0);
+
+ IfFailGo(VariantClear(pvargDest), LError0);
+
+ MEMCPY(pvargDest, &varTmp, sizeof(VARIANT));
+
+ return NOERROR;
+
+LError0:;
+ VariantClear(&varTmp);
+
+ return hresult;
+}
+
+
+
+static char rgfByVal[] = {
+ TRUE // VT_EMPTY
+ , TRUE // VT_NULL
+ , TRUE // VT_I2
+ , TRUE // VT_I4
+ , TRUE // VT_R4
+ , TRUE // VT_R8
+ , TRUE // VT_CY
+ , TRUE // VT_DATE
+ , TRUE // VT_BSTR
+ , TRUE // VT_DISPATCH
+ , TRUE // VT_ERROR
+ , TRUE // VT_BOOL
+ , FALSE // VT_VARIANT
+ , TRUE // VT_UNKNOWN
+#if 0 // we never index this far
+ , FALSE // unused
+ , FALSE // unused
+ , TRUE // VT_I1
+ , TRUE // VT_UI1
+#endif //0
+};
+
+static char rgfByRef[] =
+{
+ FALSE // VT_BYREF | VT_EMPTY
+ , FALSE // VT_BYREF | VT_NULL
+ , TRUE // VT_BYREF | VT_I2
+ , TRUE // VT_BYREF | VT_I4
+ , TRUE // VT_BYREF | VT_R4
+ , TRUE // VT_BYREF | VT_R8
+ , TRUE // VT_BYREF | VT_CY
+ , TRUE // VT_BYREF | VT_DATE
+ , TRUE // VT_BYREF | VT_BSTR
+ , TRUE // VT_BYREF | VT_DISPATCH
+ , TRUE // VT_BYREF | VT_ERROR
+ , TRUE // VT_BYREF | VT_BOOL
+ , TRUE // VT_BYREF | VT_VARIANT
+ , TRUE // VT_BYREF | VT_UNKNOWN
+#if 0 // we never index this far
+ , FALSE // VT_BYREF | unused
+ , FALSE // VT_BYREF | unused
+ , TRUE // VT_BYREF | VT_I1
+ , TRUE // VT_BYREF | VT_UI1
+#endif //0
+};
+
+
+/***
+*LOCAL HRESULT IsLegalVartype(VARTYPE)
+*Purpose:
+* Determines if the given vt is a legal VARTYPE.
+*
+*Entry:
+* vt = VARTYPE to check
+*
+*Exit:
+* return value = HRESULT
+* NOERROR
+* DISP_E_BADVARTYPE
+*
+***********************************************************************/
+#if !OE_WIN32
+#pragma code_seg("_TEXT")
+#endif
+INTERNAL_(HRESULT)
+IsLegalVartype(VARTYPE vt)
+{
+
+ // NOTE: legality is now the same for Array and ByRef, so optimize
+ if(vt & (VT_BYREF | VT_ARRAY)){
+ vt &= ~(VT_BYREF | VT_ARRAY);
+
+ if(vt < VT_VMAX && rgfByRef[vt] == TRUE)
+ return NOERROR;
+
+ }else{
+
+ if(vt < VT_VMAX && rgfByVal[vt] == TRUE)
+ return NOERROR;
+
+ }
+
+#if VBA2
+ if(vt == VT_UI1)
+ return NOERROR;
+#endif //VBA2
+
+ return RESULT(DISP_E_BADVARTYPE);
+}
+#pragma code_seg()
+
+
+/***
+*LOCAL STDAPI ExtractValueProperty(IDispatch*, LCID, VARIANT*)
+*Purpose:
+* Extract the value property from the given IDispatch*, and return
+* in the given variant.
+*
+*Entry:
+* pdisp = the IDispatch* to extract the value property from
+*
+*Exit:
+* return value = HRESULT
+*
+* *pvarResult = a VARIANT containing the contents of the "value" property
+*
+* Note: this routine assumes that pvarResult is properly initialized
+* to VT_EMPTY.
+*
+***********************************************************************/
+PRIVATE_(HRESULT)
+ExtractValueProperty(IDispatch FAR* pdisp, LCID lcid, VARIANT FAR* pvarResult)
+{
+ DISPPARAMS dispparams;
+
+ ASSERT(V_VT(pvarResult) == VT_EMPTY);
+
+ dispparams.cArgs = 0;
+ dispparams.rgvarg = NULL;
+ dispparams.cNamedArgs = 0;
+ dispparams.rgdispidNamedArgs = NULL;
+ return pdisp->Invoke(
+ DISPID_VALUE,
+ IID_NULL,
+ lcid,
+ DISPATCH_PROPERTYGET,
+ &dispparams, pvarResult, NULL, NULL);
+}
+
+
+
+/***
+*PRIVATE HRESULT VariantChangeTypeInternal(VARIANT*, LCID, VARTYPE)
+*Purpose:
+* In place variant coercion
+*
+*Entry:
+* pvar = the VARIANT to coerce
+* vt = the target type of the coersion
+*
+*Exit:
+* return value = HRESULT
+*
+* *lpvar = the coerced VARIANT
+*
+***********************************************************************/
+INTERNAL_(HRESULT)
+VariantChangeTypeInternal(VARIANT FAR* pvar, LCID lcid, VARTYPE vt)
+{
+ VARTYPE vtFrom;
+ HRESULT hresult;
+ void FAR* pvFrom;
+
+ vtFrom = V_VT(pvar);
+
+ // should never be called with either Array or ByRef bits set
+ ASSERT((vtFrom & (VT_ARRAY | VT_BYREF)) == 0);
+
+#ifdef _DEBUG
+ if(vtFrom == VT_BOOL && V_BOOL(pvar) != 0 && V_BOOL(pvar) != -1)
+ return RESULT(E_INVALIDARG);
+#endif
+
+ // Nothing to do, return success
+ if(vtFrom == vt)
+ return NOERROR;
+
+ // cant coerce to or from VT_ERROR
+ if(vtFrom == VT_ERROR || vt == VT_ERROR)
+ return RESULT(DISP_E_TYPEMISMATCH);
+
+ // Coercion of NULL type is invalid
+ if(vtFrom == VT_NULL)
+ return RESULT(DISP_E_TYPEMISMATCH);
+
+ // save pointer to possible resources that may need to be
+ // free'd if the coersion is successful.
+ pvFrom = V_BYREF(pvar);
+
+ hresult = NOERROR;
+
+ switch(vt){
+ case VT_NULL:
+ case VT_EMPTY:
+ break;
+
+#if VBA2
+ case VT_UI1:
+ switch(vtFrom){
+ case VT_EMPTY:
+ V_I2(pvar) = 0;
+ break;
+
+ case VT_I2:
+ hresult = VarUI1FromI2(V_I2(pvar), &V_UI1(pvar));
+ break;
+
+ case VT_I4:
+ hresult = VarUI1FromI4(V_I4(pvar), &V_UI1(pvar));
+ break;
+
+ case VT_R4:
+ hresult = VarUI1FromR4(V_R4(pvar), &V_UI1(pvar));
+ break;
+
+ case VT_R8:
+ case VT_DATE:
+ hresult = VarUI1FromR8(V_R8(pvar), &V_UI1(pvar));
+ break;
+
+ case VT_CY:
+ hresult = VarUI1FromCy(V_CY(pvar), &V_UI1(pvar));
+ break;
+
+ case VT_BOOL:
+ hresult = VarUI1FromBool(V_BOOL(pvar), &V_UI1(pvar));
+ break;
+
+ case VT_BSTR:
+ hresult = VarUI1FromStr(V_BSTR(pvar), lcid, NULL, &V_UI1(pvar));
+ break;
+
+ case VT_UNKNOWN:
+ case VT_DISPATCH:
+ hresult = RESULT(DISP_E_TYPEMISMATCH);
+ break;
+
+ default:
+ hresult = RESULT(E_INVALIDARG);
+ break;
+ }
+ break;
+#endif //VBA2
+
+ case VT_I2:
+ switch(vtFrom){
+ case VT_EMPTY:
+ V_I2(pvar) = 0;
+ break;
+
+#if VBA2
+ case VT_UI1:
+ hresult = VarI2FromUI1(V_UI1(pvar), &V_I2(pvar));
+ break;
+#endif //VBA2
+
+ case VT_I4:
+ hresult = VarI2FromI4(V_I4(pvar), &V_I2(pvar));
+ break;
+
+ case VT_R4:
+ hresult = VarI2FromR4(V_R4(pvar), &V_I2(pvar));
+ break;
+
+ case VT_R8:
+ case VT_DATE:
+ hresult = VarI2FromR8(V_R8(pvar), &V_I2(pvar));
+ break;
+
+ case VT_CY:
+ hresult = VarI2FromCy(V_CY(pvar), &V_I2(pvar));
+ break;
+
+ case VT_BOOL:
+ break;
+
+ case VT_BSTR:
+ hresult = VarI2FromStr(V_BSTR(pvar), lcid, NULL, &V_I2(pvar));
+ break;
+
+ case VT_UNKNOWN:
+ case VT_DISPATCH:
+ hresult = RESULT(DISP_E_TYPEMISMATCH);
+ break;
+
+ default:
+ hresult = RESULT(E_INVALIDARG);
+ break;
+ }
+ break;
+
+ case VT_I4:
+ switch(vtFrom){
+ case VT_EMPTY:
+ V_I4(pvar) = 0L;
+ break;
+
+#if VBA2
+ case VT_UI1:
+ hresult = VarI4FromUI1(V_UI1(pvar), &V_I4(pvar));
+ break;
+#endif //VBA2
+
+ case VT_I2:
+ case VT_BOOL:
+ V_I4(pvar) = (long)V_I2(pvar);
+ break;
+
+ case VT_R4:
+ hresult = VarI4FromR4(V_R4(pvar), &V_I4(pvar));
+ break;
+
+ case VT_R8:
+ case VT_DATE:
+ hresult = VarI4FromR8(V_R8(pvar), &V_I4(pvar));
+ break;
+
+ case VT_CY:
+ hresult = VarI4FromCy(V_CY(pvar), &V_I4(pvar));
+ break;
+
+ case VT_BSTR:
+ hresult = VarI4FromStr(V_BSTR(pvar), lcid, NULL, &V_I4(pvar));
+ break;
+
+ case VT_UNKNOWN:
+ case VT_DISPATCH:
+ hresult = RESULT(DISP_E_TYPEMISMATCH);
+ break;
+
+ default:
+ hresult = RESULT(E_INVALIDARG);
+ break;
+ }
+ break;
+
+ case VT_R4:
+ switch(vtFrom){
+ case VT_EMPTY:
+ V_R4(pvar) = (float)0.0;
+ break;
+
+#if VBA2
+ case VT_UI1:
+ hresult = VarR4FromUI1(V_UI1(pvar), &V_R4(pvar));
+ break;
+#endif //VBA2
+
+ case VT_I2:
+ case VT_BOOL:
+ V_R4(pvar) = (float)V_I2(pvar);
+ break;
+
+ case VT_I4:
+ V_R4(pvar) = (float)V_I4(pvar);
+ break;
+
+ case VT_R8:
+ case VT_DATE:
+ hresult = VarR4FromR8(V_R8(pvar), &V_R4(pvar));
+ break;
+
+ case VT_CY:
+ hresult = VarR4FromCy(V_CY(pvar), &V_R4(pvar));
+ break;
+
+ case VT_BSTR:
+ hresult = VarR4FromStr(V_BSTR(pvar), lcid, NULL, &V_R4(pvar));
+ break;
+
+ case VT_UNKNOWN:
+ case VT_DISPATCH:
+ hresult = RESULT(DISP_E_TYPEMISMATCH);
+ break;
+
+ default:
+ hresult = RESULT(E_INVALIDARG);
+ break;
+ }
+ break;
+
+ case VT_R8:
+ switch(vtFrom){
+ case VT_EMPTY:
+ V_R8(pvar) = 0.0;
+ break;
+
+#if VBA2
+ case VT_UI1:
+ hresult = VarR8FromUI1(V_UI1(pvar), &V_R8(pvar));
+ break;
+#endif //VBA2
+
+ case VT_BOOL:
+ case VT_I2:
+ V_R8(pvar) = (double)V_I2(pvar);
+ break;
+
+ case VT_I4:
+ V_R8(pvar) = (double)V_I4(pvar);
+ break;
+
+ case VT_R4:
+ V_R8(pvar) = (double)V_R4(pvar);
+ break;
+
+ case VT_DATE:
+ break;
+
+ case VT_CY:
+ hresult = VarR8FromCy(V_CY(pvar), &V_R8(pvar));
+ break;
+
+ case VT_BSTR:
+ hresult = VarR8FromStr(V_BSTR(pvar), lcid, NULL, &V_R8(pvar));
+ break;
+
+ case VT_UNKNOWN:
+ case VT_DISPATCH:
+ hresult = RESULT(DISP_E_TYPEMISMATCH);
+ break;
+
+ default:
+ hresult = RESULT(E_INVALIDARG);
+ break;
+ }
+ break;
+
+ case VT_CY:
+ switch(vtFrom){
+ case VT_EMPTY:
+ V_CY(pvar).Hi = V_CY(pvar).Lo = 0L;
+ break;
+
+#if VBA2
+ case VT_UI1:
+ hresult = VarCyFromUI1(V_UI1(pvar), &V_CY(pvar));
+ break;
+#endif //VBA2
+
+ case VT_I2:
+ case VT_BOOL:
+ hresult = VarCyFromI2(V_I2(pvar), &V_CY(pvar));
+ break;
+
+ case VT_I4:
+ hresult = VarCyFromI4(V_I4(pvar), &V_CY(pvar));
+ break;
+
+ case VT_R4:
+ hresult = VarCyFromR4(V_R4(pvar), &V_CY(pvar));
+ break;
+
+ case VT_R8:
+ case VT_DATE:
+ hresult = VarCyFromR8(V_R8(pvar), &V_CY(pvar));
+ break;
+
+ case VT_BSTR:
+ hresult = VarCyFromStr(V_BSTR(pvar), lcid, NULL, &V_CY(pvar));
+ break;
+
+ case VT_UNKNOWN:
+ case VT_DISPATCH:
+ hresult = RESULT(DISP_E_TYPEMISMATCH);
+ break;
+
+ default:
+ hresult = RESULT(E_INVALIDARG);
+ break;
+ }
+ break;
+
+ case VT_DATE:
+ switch(vtFrom){
+ case VT_EMPTY:
+ V_DATE(pvar) = 0.0;
+ break;
+
+#if VBA2
+ case VT_UI1:
+ V_DATE(pvar) = (DATE)V_UI1(pvar);
+ hresult = IsValidDate(V_DATE(pvar));
+ break;
+#endif //VBA2
+
+ case VT_I2:
+ case VT_BOOL:
+ V_DATE(pvar) = (DATE)V_I2(pvar);
+ hresult = IsValidDate(V_DATE(pvar));
+ break;
+
+ case VT_I4:
+ V_DATE(pvar) = (DATE)V_I4(pvar);
+ hresult = IsValidDate(V_DATE(pvar));
+ break;
+
+ case VT_R4:
+ V_DATE(pvar) = (DATE)V_R4(pvar);
+ hresult = IsValidDate(V_DATE(pvar));
+ break;
+
+ case VT_R8:
+ hresult = IsValidDate(V_DATE(pvar));
+ break;
+
+ case VT_CY:
+ hresult = VarDateFromCy(V_CY(pvar), &V_DATE(pvar));
+ break;
+
+ case VT_BSTR:
+ hresult = VarDateFromStr(V_BSTR(pvar), lcid, NULL, &V_DATE(pvar));
+ break;
+
+ case VT_UNKNOWN:
+ case VT_DISPATCH:
+ hresult = RESULT(DISP_E_TYPEMISMATCH);
+ break;
+
+ default:
+ hresult = RESULT(E_INVALIDARG);
+ break;
+ }
+ break;
+
+ case VT_BSTR:
+ switch(vtFrom){
+ case VT_EMPTY:
+ hresult = ErrSysAllocString(OASTR(""), &V_BSTR(pvar));
+ break;
+
+#if VBA2
+ case VT_UI1:
+ hresult = VarBstrFromUI1(V_UI1(pvar), lcid, NULL, &V_BSTR(pvar));
+ break;
+#endif //VBA2
+
+ case VT_I2:
+ case VT_BOOL:
+ hresult = VarBstrFromI2(V_I2(pvar), lcid, NULL, &V_BSTR(pvar));
+ break;
+
+ case VT_I4:
+ hresult = VarBstrFromI4(V_I4(pvar), lcid, NULL, &V_BSTR(pvar));
+ break;
+
+ case VT_R4:
+ hresult = VarBstrFromR4(V_R4(pvar), lcid, NULL, &V_BSTR(pvar));
+ break;
+
+ case VT_DATE:
+ hresult = VarBstrFromDate(V_DATE(pvar), lcid, NULL, &V_BSTR(pvar));
+ break;
+
+ case VT_R8:
+ hresult = VarBstrFromR8(V_R8(pvar), lcid, NULL, &V_BSTR(pvar));
+ break;
+
+ case VT_CY:
+ hresult = VarBstrFromCy(V_CY(pvar), lcid, NULL, &V_BSTR(pvar));
+ break;
+
+ case VT_UNKNOWN:
+ case VT_DISPATCH:
+ hresult = RESULT(DISP_E_TYPEMISMATCH);
+ break;
+
+ default:
+ hresult = RESULT(E_INVALIDARG);
+ break;
+ }
+ break;
+
+ case VT_BOOL:
+ switch(vtFrom){
+ case VT_EMPTY:
+ V_I2(pvar) = 0;
+ break;
+
+#if VBA2
+ case VT_UI1:
+ V_BOOL(pvar) = (V_UI1(pvar) != 0) ? -1 : 0;
+ break;
+#endif //VBA2
+
+ case VT_I2:
+ V_BOOL(pvar) = (V_I2(pvar) != 0) ? -1 : 0;
+ break;
+
+ case VT_I4:
+ V_BOOL(pvar) = (V_I4(pvar) != 0) ? -1 : 0;
+ break;
+
+ case VT_R4:
+ V_BOOL(pvar) = (V_R4(pvar) != (float)0.0) ? -1 : 0;
+ break;
+
+ case VT_R8:
+ case VT_DATE:
+ V_BOOL(pvar) = (V_R8(pvar) != 0.0) ? -1 : 0;
+ break;
+
+ case VT_CY:
+ hresult = VarBoolFromCy(V_CY(pvar), &V_BOOL(pvar));
+ break;
+
+ case VT_BSTR:
+ hresult = VarBoolFromStr(V_BSTR(pvar), lcid, NULL, &V_BOOL(pvar));
+ break;
+
+ case VT_UNKNOWN:
+ case VT_DISPATCH:
+ hresult = RESULT(DISP_E_TYPEMISMATCH);
+ break;
+
+ default:
+ hresult = RESULT(E_INVALIDARG);
+ break;
+ }
+ break;
+
+ case VT_UNKNOWN:
+ case VT_DISPATCH:
+ if (vtFrom == VT_UNKNOWN || vtFrom == VT_DISPATCH)
+ {
+ if (V_UNKNOWN(pvar) != NULL) {
+ if (vt == VT_UNKNOWN)
+ hresult = V_UNKNOWN(pvar)->QueryInterface(
+ IID_IUnknown,
+ (void FAR* FAR*) &V_UNKNOWN(pvar));
+ else if (vt == VT_DISPATCH)
+ hresult = V_UNKNOWN(pvar)->QueryInterface(
+ IID_IDispatch,
+ (void FAR* FAR*) &V_DISPATCH(pvar));
+ }
+ } else
+ hresult = RESULT(DISP_E_TYPEMISMATCH);
+ break;
+
+ default:
+ hresult = RESULT(E_INVALIDARG);
+ break;
+ }
+
+ // if the conversion succeeds, set the new variant type
+ if(hresult == NOERROR){
+
+ V_VT(pvar) = vt;
+
+ // free up resources VARIANT was holding before the coersion
+ switch(vtFrom){
+ case VT_BSTR:
+ SysFreeString((BSTR)pvFrom);
+ break;
+ case VT_UNKNOWN:
+ case VT_DISPATCH:
+ if (pvFrom != NULL) {
+ ((IUnknown FAR*)pvFrom)->Release();
+ }
+ break;
+ }
+ }
+ return hresult;
+}
diff --git a/private/oleauto/src/dispatch/win16/0401.c b/private/oleauto/src/dispatch/win16/0401.c
new file mode 100644
index 000000000..d4ccb930e
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0401.c
@@ -0,0 +1,714 @@
+/****************************************************************************
+* 0401.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Arabic - Saudi Arabia
+*
+* LCID = 0x0401
+*
+* CodePage = 1256
+*
+* Generated: Thu Dec 01 18:26:52 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+WORD NLSALLOC(0401) rgwSort_0401[256] = {
+ 0x0000, 0xc008, 0xc009, 0xc00a, 0xc00b, 0xc00c, 0xc00d, 0xc00e
+ , 0xc00f, 0x403b, 0x403c, 0x403d, 0x403e, 0x403f, 0xc010, 0xc011
+ , 0xc012, 0xc013, 0xc014, 0xc015, 0xc016, 0xc017, 0xc018, 0xc019
+ , 0xc01a, 0xc01b, 0xc01c, 0xc01d, 0xc01e, 0xc01f, 0xc020, 0xc021
+ , 0x4039, 0x4041, 0x4042, 0x4043, 0x4044, 0x4045, 0x4046, 0xc02d
+ , 0x4047, 0x4048, 0x4049, 0x406b, 0x404a, 0xc02e, 0x404b, 0x404c
+ , 0x0085, 0x0089, 0x008a, 0x008b, 0x008c, 0x008d, 0x008e, 0x008f
+ , 0x0090, 0x0091, 0x404d, 0x404e, 0x406c, 0x406d, 0x406e, 0x404f
+ , 0x4050, 0x1892, 0x1893, 0x1894, 0x1895, 0x1896, 0x1897, 0x1898
+ , 0x1899, 0x189a, 0x189b, 0x189c, 0x189d, 0x189e, 0x189f, 0x18a0
+ , 0x18a1, 0x18a2, 0x18a3, 0x18a4, 0x18a5, 0x18a7, 0x18a8, 0x18a9
+ , 0x18aa, 0x18ab, 0x18ac, 0x4051, 0x4052, 0x4053, 0x4054, 0x4055
+ , 0x4056, 0x0092, 0x0093, 0x0094, 0x0095, 0x0096, 0x0097, 0x0098
+ , 0x0099, 0x009a, 0x009b, 0x009c, 0x009d, 0x009e, 0x009f, 0x00a0
+ , 0x00a1, 0x00a2, 0x00a3, 0x00a4, 0x00a5, 0x00a7, 0x00a8, 0x00a9
+ , 0x00aa, 0x00ab, 0x00ac, 0x4057, 0x4058, 0x4059, 0x405a, 0xc022
+ , 0xc023, 0xc024, 0x4065, 0x0197, 0x4068, 0x4083, 0x4080, 0x4081
+ , 0x4154, 0x4084, 0xc025, 0x4069, 0x0005, 0xc026, 0xc027, 0xc028
+ , 0xc029, 0x4063, 0x4064, 0x4066, 0x4067, 0x4082, 0xc030, 0xc031
+ , 0xc02a, 0x18a6, 0xc02b, 0x406a, 0x0105, 0x4040, 0x0000, 0xc02c
+ , 0x403a, 0x4060, 0x4074, 0x4075, 0x4076, 0x4077, 0x405b, 0x4078
+ , 0x405c, 0x4079, 0x08ca, 0x4070, 0x407a, 0xc02f, 0x407b, 0x405d
+ , 0x407c, 0x406f, 0x108a, 0x108b, 0x405e, 0x407d, 0x407e, 0x407f
+ , 0x405f, 0x1089, 0x4061, 0x4071, 0x0086, 0x0087, 0x0088, 0x4062
+ , 0x08cb, 0x00ad, 0x0205, 0x01ad, 0x02ad, 0x03ad, 0x04ad, 0x00ae
+ , 0x00af, 0x00b0, 0x00b0, 0x00b1, 0x00b2, 0x00b3, 0x00b4, 0x00b5
+ , 0x00b6, 0x00b7, 0x00b8, 0x00b9, 0x00ba, 0x00bb, 0x00bc, 0x4072
+ , 0x00bd, 0x00be, 0x00bf, 0x00c0, 0x0000, 0x00c1, 0x00c2, 0x00c3
+ , 0x0192, 0x00c4, 0x0292, 0x00c5, 0x00c6, 0x00c7, 0x00c8, 0x0194
+ , 0x0296, 0x0196, 0x0396, 0x0496, 0x00c9, 0x01c9, 0x019a, 0x029a
+ , 0xc032, 0xc033, 0xc034, 0xc035, 0x01a0, 0xc036, 0xc037, 0x4073
+ , 0x4007, 0x01a7, 0xc038, 0x02a7, 0x03a7, 0x0000, 0x0000, 0x08cc
+};
+
+EXPANSION NLSALLOC(0401) rgexp_0401[3] = {
+ { 0x18a0, 0x1896 }
+ , { 0x00a0, 0x0096 }
+ , { 0x00ad, 0x00ae }
+};
+
+WORD NLSALLOC(0401) rgwCType12_0401[256] = {
+ 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x9068, 0x0028, 0x0028, 0x0028, 0x0028, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0xa048, 0xb010, 0xb010, 0x5010, 0x5010, 0x5010, 0x1010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0x5010, 0x7010, 0x5010, 0x4010, 0x4010
+ , 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084
+ , 0x3084, 0x3084, 0x7010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010, 0x0020
+ , 0x0020, 0x0020, 0xb010, 0x1112, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x5010, 0x0020, 0xb010, 0x1101, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x0020, 0xb010, 0x0020, 0xb010, 0x1102, 0xb010, 0xb010, 0x0020
+ , 0xa048, 0x2010, 0x5010, 0x5010, 0x5010, 0x5010, 0xb010, 0xb010
+ , 0xb010, 0xb010, 0x0000, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x5010, 0x5010, 0x3014, 0x3014, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x3014, 0x2010, 0xb010, 0xb010, 0xb010, 0xb010, 0x2010
+ , 0x0000, 0x2100, 0x2100, 0x2100, 0x2100, 0x2100, 0x2100, 0x2100
+ , 0x2100, 0x2100, 0x2100, 0x2100, 0x2100, 0x2100, 0x2100, 0x2100
+ , 0x2100, 0x2100, 0x2100, 0x2100, 0x2100, 0x2100, 0x2100, 0xb010
+ , 0x2100, 0x2100, 0x2100, 0x2100, 0x2010, 0x2100, 0x2100, 0x2100
+ , 0x1102, 0x2100, 0x1102, 0x2100, 0x2100, 0x2100, 0x2100, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x2100, 0x2100, 0x1102, 0x1102
+ , 0x2010, 0x2010, 0x2010, 0x2010, 0x1102, 0x2010, 0x2010, 0xb010
+ , 0x2010, 0x1102, 0x2010, 0x1102, 0x1102, 0x1010, 0x2010, 0x0000
+};
+
+WORD NLSALLOC(0401) rgwCType3_0401[256] = {
+ 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0008, 0x0008, 0x0008, 0x0008, 0x0008, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0048, 0x0048, 0x0448, 0x0048, 0x0448, 0x0048, 0x0048, 0x0440
+ , 0x0048, 0x0048, 0x0048, 0x0048, 0x0048, 0x0440, 0x0048, 0x0448
+ , 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040
+ , 0x0040, 0x0040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0048, 0x0048
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0448, 0x0048, 0x0448, 0x0448
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0000
+ , 0x0000, 0x0000, 0x0008, 0x8000, 0x0008, 0x0008, 0x0008, 0x0008
+ , 0x0001, 0x0008, 0x0000, 0x0008, 0x8000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0088, 0x0088, 0x0088, 0x0088, 0x0008, 0x0400, 0x0400
+ , 0x0000, 0x0000, 0x0000, 0x0008, 0x8000, 0x0008, 0x0000, 0x0000
+ , 0x0008, 0x0008, 0x0048, 0x0048, 0x0008, 0x0048, 0x0048, 0x0008
+ , 0x0408, 0x0008, 0x0000, 0x0008, 0x0048, 0x0408, 0x0008, 0x0448
+ , 0x0008, 0x0008, 0x0000, 0x0000, 0x0408, 0x0008, 0x0008, 0x0008
+ , 0x0408, 0x0000, 0x0008, 0x0008, 0x0000, 0x0000, 0x0000, 0x0008
+ , 0x0000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000
+ , 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000
+ , 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x0008
+ , 0x8000, 0x8000, 0x8000, 0x8000, 0x0601, 0x8000, 0x8000, 0x8000
+ , 0x8003, 0x8000, 0x8003, 0x8000, 0x8000, 0x8000, 0x8000, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8000, 0x8003, 0x8003
+ , 0x0001, 0x0001, 0x0001, 0x0001, 0x8003, 0x0001, 0x0001, 0x0008
+ , 0x0001, 0x8003, 0x0001, 0x8003, 0x8003, 0x0000, 0x0000, 0x0000
+};
+
+BYTE NLSALLOC(0401) rgbUCase_0401[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x9a, 0x9b, 0x8c, 0x9d, 0x9e, 0x9f
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
+};
+
+BYTE NLSALLOC(0401) rgbLCase_0401[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x8a, 0x8b, 0x9c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
+};
+
+static BYTE NLSALLOC(0401) rgbILANGUAGE[] = { /* "0401" */
+ 0x30, 0x34, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(0401) rgbSLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVLANGNAME[] = { /* "ARA" */
+ 0x41, 0x52, 0x41
+};
+
+static BYTE NLSALLOC(0401) rgbSNATIVELANGNAME[] = { /* "\x0627\x0644\x0639\x0631\x0628\x064a\x0629" */
+ 0xc7, 0xe1, 0xda, 0xd1, 0xc8, 0xed, 0xc9
+};
+
+static BYTE NLSALLOC(0401) rgbICOUNTRY[] = { /* "966" */
+ 0x39, 0x36, 0x36
+};
+
+static BYTE NLSALLOC(0401) rgbSCOUNTRY[] = { /* "Saudi Arabia" */
+ 0x53, 0x61, 0x75, 0x64, 0x69, 0x20, 0x41, 0x72
+ , 0x61, 0x62, 0x69, 0x61
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVCTRYNAME[] = { /* "SAU" */
+ 0x53, 0x41, 0x55
+};
+
+static BYTE NLSALLOC(0401) rgbSNATIVECTRYNAME[] = { /* "\x0627\x0644\x0645\x0645\x0644\x0643\x0629 \x0627\x0644\x0639\x0631\x0628\x064a\x0629 \x0627\x0644\x0633\x0639\x0648\x062f\x064a\x0629" */
+ 0xc7, 0xe1, 0xe3, 0xe3, 0xe1, 0xdf, 0xc9, 0x20
+ , 0xc7, 0xe1, 0xda, 0xd1, 0xc8, 0xed, 0xc9, 0x20
+ , 0xc7, 0xe1, 0xd3, 0xda, 0xe6, 0xcf, 0xed, 0xc9
+};
+
+static BYTE NLSALLOC(0401) rgbIDEFAULTLANGUAGE[] = { /* "0401" */
+ 0x30, 0x34, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(0401) rgbIDEFAULTCOUNTRY[] = { /* "966" */
+ 0x39, 0x36, 0x36
+};
+
+static BYTE NLSALLOC(0401) rgbIDEFAULTCODEPAGE[] = { /* "708" */
+ 0x37, 0x30, 0x38
+};
+
+static BYTE NLSALLOC(0401) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0401) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0401) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0401) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0401) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0401) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0401) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0401) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0401) rgbSCURRENCY[] = { /* "\x0631.\x0633.\x200f" */
+ 0xd1, 0x2e, 0xd3, 0x2e, 0xfe
+};
+
+static BYTE NLSALLOC(0401) rgbSINTLSYMBOL[] = { /* "SAR" */
+ 0x53, 0x41, 0x52
+};
+
+static BYTE NLSALLOC(0401) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0401) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0401) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0401) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0401) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0401) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0401) rgbINEGCURR[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0401) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(0401) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0401) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0401) rgbSLONGDATE[] = { /* "dd/MM/yyyy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0401) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0401) rgbILDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0401) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0401) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0401) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0401) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0401) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0401) rgbS1159[] = { /* "\x0635" */
+ 0xd5
+};
+
+static BYTE NLSALLOC(0401) rgbS2359[] = { /* "\x0645" */
+ 0xe3
+};
+
+static BYTE NLSALLOC(0401) rgbSDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(0401) rgbSDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(0401) rgbSDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(0401) rgbSDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(0401) rgbSDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(0401) rgbSDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(0401) rgbSDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(0401) rgbSMONTHNAME1[] = { /* "\x0645\x062d\x0631\x0645" */
+ 0xe3, 0xcd, 0xd1, 0xe3
+};
+
+static BYTE NLSALLOC(0401) rgbSMONTHNAME2[] = { /* "\x0633\x0641\x0631" */
+ 0xd3, 0xdd, 0xd1
+};
+
+static BYTE NLSALLOC(0401) rgbSMONTHNAME3[] = { /* "\x0631\x0628\x064a\x0639 \x0623\x0648\x0644" */
+ 0xd1, 0xc8, 0xed, 0xda, 0x20, 0xc3, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(0401) rgbSMONTHNAME4[] = { /* "\x0631\x0628\x064a\x0639 \x062b\x0627\x0646\x064a" */
+ 0xd1, 0xc8, 0xed, 0xda, 0x20, 0xcb, 0xc7, 0xe4
+ , 0xed
+};
+
+static BYTE NLSALLOC(0401) rgbSMONTHNAME5[] = { /* "\x062c\x0645\x0627\x062f\x0649 \x0623\x0648\x0644" */
+ 0xcc, 0xe3, 0xc7, 0xcf, 0xec, 0x20, 0xc3, 0xe6
+ , 0xe1
+};
+
+static BYTE NLSALLOC(0401) rgbSMONTHNAME6[] = { /* "\x062c\x0645\x0627\x062f\x0649 \x062b\x0627\x0646\x064a" */
+ 0xcc, 0xe3, 0xc7, 0xcf, 0xec, 0x20, 0xcb, 0xc7
+ , 0xe4, 0xed
+};
+
+static BYTE NLSALLOC(0401) rgbSMONTHNAME7[] = { /* "\x0631\x062c\x0628" */
+ 0xd1, 0xcc, 0xc8
+};
+
+static BYTE NLSALLOC(0401) rgbSMONTHNAME8[] = { /* "\x0634\x0639\x0628\x0627\x0646" */
+ 0xd4, 0xda, 0xc8, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(0401) rgbSMONTHNAME9[] = { /* "\x0631\x0645\x0636\x0627\x0646" */
+ 0xd1, 0xe3, 0xd6, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(0401) rgbSMONTHNAME10[] = { /* "\x0634\x0648\x0627\x0644" */
+ 0xd4, 0xe6, 0xc7, 0xe1
+};
+
+static BYTE NLSALLOC(0401) rgbSMONTHNAME11[] = { /* "\x0630\x0648 \x0627\x0644\x0642\x0639\x062f\x0629" */
+ 0xd0, 0xe6, 0x20, 0xc7, 0xe1, 0xde, 0xda, 0xcf
+ , 0xc9
+};
+
+static BYTE NLSALLOC(0401) rgbSMONTHNAME12[] = { /* "\x0630\x0648 \x0627\x0644\x062d\x062c\x0629" */
+ 0xd0, 0xe6, 0x20, 0xc7, 0xe1, 0xcd, 0xcc, 0xc9
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVMONTHNAME1[] = { /* "\x0645\x062d\x0631\x0645" */
+ 0xe3, 0xcd, 0xd1, 0xe3
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVMONTHNAME2[] = { /* "\x0633\x0641\x0631" */
+ 0xd3, 0xdd, 0xd1
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVMONTHNAME3[] = { /* "\x0631\x0628\x064a\x0639 \x0623\x0648\x0644" */
+ 0xd1, 0xc8, 0xed, 0xda, 0x20, 0xc3, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVMONTHNAME4[] = { /* "\x0631\x0628\x064a\x0639 \x062b\x0627\x0646\x064a" */
+ 0xd1, 0xc8, 0xed, 0xda, 0x20, 0xcb, 0xc7, 0xe4
+ , 0xed
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVMONTHNAME5[] = { /* "\x062c\x0645\x0627\x062f\x0649 \x0623\x0648\x0644" */
+ 0xcc, 0xe3, 0xc7, 0xcf, 0xec, 0x20, 0xc3, 0xe6
+ , 0xe1
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVMONTHNAME6[] = { /* "\x062c\x0645\x0627\x062f\x0649 \x062b\x0627\x0646\x064a" */
+ 0xcc, 0xe3, 0xc7, 0xcf, 0xec, 0x20, 0xcb, 0xc7
+ , 0xe4, 0xed
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVMONTHNAME7[] = { /* "\x0631\x062c\x0628" */
+ 0xd1, 0xcc, 0xc8
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVMONTHNAME8[] = { /* "\x0634\x0639\x0628\x0627\x0646" */
+ 0xd4, 0xda, 0xc8, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVMONTHNAME9[] = { /* "\x0631\x0645\x0636\x0627\x0646" */
+ 0xd1, 0xe3, 0xd6, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVMONTHNAME10[] = { /* "\x0634\x0648\x0627\x0644" */
+ 0xd4, 0xe6, 0xc7, 0xe1
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVMONTHNAME11[] = { /* "\x0630\x0648 \x0627\x0644\x0642\x0639\x062f\x0629" */
+ 0xd0, 0xe6, 0x20, 0xc7, 0xe1, 0xde, 0xda, 0xcf
+ , 0xc9
+};
+
+static BYTE NLSALLOC(0401) rgbSABBREVMONTHNAME12[] = { /* "\x0630\x0648 \x0627\x0644\x062d\x062c\x0629" */
+ 0xd0, 0xe6, 0x20, 0xc7, 0xe1, 0xcd, 0xcc, 0xc9
+};
+
+static BYTE NLSALLOC(0401) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0401) rgbIPOSSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0401) rgbINEGSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0401) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0401) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0401) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0401) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0401) rgbSENGCOUNTRY[] = { /* "Saudi Arabia" */
+ 0x53, 0x61, 0x75, 0x64, 0x69, 0x20, 0x41, 0x72
+ , 0x61, 0x62, 0x69, 0x61
+};
+
+static BYTE NLSALLOC(0401) rgbSENGLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(0401) rgbIFIRSTDAYOFWEEK[] = { /* "5" */
+ 0x35
+};
+
+static BYTE NLSALLOC(0401) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0401) rgbIDEFAULTANSICODEPAGE[] = { /* "1256" */
+ 0x31, 0x32, 0x35, 0x36
+};
+
+static BYTE NLSALLOC(0401) rgbINEGNUMBER[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0401) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0401) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0401) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0401) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0401) g_rglcinfo0401[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 12, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 24, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 5, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 10, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 1, rgbS1159 }
+ , { 1, rgbS2359 }
+ , { 5, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 7, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 8, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 5, rgbSABBREVDAYNAME1 }
+ , { 5, rgbSABBREVDAYNAME2 }
+ , { 7, rgbSABBREVDAYNAME3 }
+ , { 8, rgbSABBREVDAYNAME4 }
+ , { 8, rgbSABBREVDAYNAME5 }
+ , { 6, rgbSABBREVDAYNAME6 }
+ , { 6, rgbSABBREVDAYNAME7 }
+ , { 4, rgbSMONTHNAME1 }
+ , { 3, rgbSMONTHNAME2 }
+ , { 8, rgbSMONTHNAME3 }
+ , { 9, rgbSMONTHNAME4 }
+ , { 9, rgbSMONTHNAME5 }
+ , { 10, rgbSMONTHNAME6 }
+ , { 3, rgbSMONTHNAME7 }
+ , { 5, rgbSMONTHNAME8 }
+ , { 5, rgbSMONTHNAME9 }
+ , { 4, rgbSMONTHNAME10 }
+ , { 9, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 4, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 8, rgbSABBREVMONTHNAME3 }
+ , { 9, rgbSABBREVMONTHNAME4 }
+ , { 9, rgbSABBREVMONTHNAME5 }
+ , { 10, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 5, rgbSABBREVMONTHNAME8 }
+ , { 5, rgbSABBREVMONTHNAME9 }
+ , { 4, rgbSABBREVMONTHNAME10 }
+ , { 9, rgbSABBREVMONTHNAME11 }
+ , { 8, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 12, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0401) g_strinfo0401 = {
+ rgbUCase_0401
+ , rgbLCase_0401
+ , rgwCType12_0401
+ , rgwCType3_0401
+ , rgwSort_0401
+ , rgexp_0401
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0403.c b/private/oleauto/src/dispatch/win16/0403.c
new file mode 100644
index 000000000..575db1fe7
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0403.c
@@ -0,0 +1,531 @@
+/****************************************************************************
+* 0403.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Catalan - Spain
+*
+* LCID = 0x0403
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:34:41 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0409[256]; // from 0409:English - United States
+extern EXPANSION rgexp_0409[7];
+extern WORD rgwCType12_0409[256];
+extern WORD rgwCType3_0409[256];
+extern BYTE rgbUCase_0409[256];
+extern BYTE rgbLCase_0409[256];
+
+static BYTE NLSALLOC(0403) rgbILANGUAGE[] = { /* "0403" */
+ 0x30, 0x34, 0x30, 0x33
+};
+
+static BYTE NLSALLOC(0403) rgbSLANGUAGE[] = { /* "Catalan" */
+ 0x43, 0x61, 0x74, 0x61, 0x6c, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVLANGNAME[] = { /* "CAT" */
+ 0x43, 0x41, 0x54
+};
+
+static BYTE NLSALLOC(0403) rgbSNATIVELANGNAME[] = { /* "Català" */
+ 0x43, 0x61, 0x74, 0x61, 0x6c, 0xe0
+};
+
+static BYTE NLSALLOC(0403) rgbICOUNTRY[] = { /* "34" */
+ 0x33, 0x34
+};
+
+static BYTE NLSALLOC(0403) rgbSCOUNTRY[] = { /* "Spain" */
+ 0x53, 0x70, 0x61, 0x69, 0x6e
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVCTRYNAME[] = { /* "ESP" */
+ 0x45, 0x53, 0x50
+};
+
+static BYTE NLSALLOC(0403) rgbSNATIVECTRYNAME[] = { /* "Espanya" */
+ 0x45, 0x73, 0x70, 0x61, 0x6e, 0x79, 0x61
+};
+
+static BYTE NLSALLOC(0403) rgbIDEFAULTLANGUAGE[] = { /* "040a" */
+ 0x30, 0x34, 0x30, 0x61
+};
+
+static BYTE NLSALLOC(0403) rgbIDEFAULTCOUNTRY[] = { /* "34" */
+ 0x33, 0x34
+};
+
+static BYTE NLSALLOC(0403) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0403) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0403) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0403) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0403) rgbSTHOUSAND[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0403) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0403) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0403) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0403) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0403) rgbSCURRENCY[] = { /* "PTA" */
+ 0x50, 0x54, 0x41
+};
+
+static BYTE NLSALLOC(0403) rgbSINTLSYMBOL[] = { /* "ESP" */
+ 0x45, 0x53, 0x50
+};
+
+static BYTE NLSALLOC(0403) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0403) rgbSMONTHOUSANDSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0403) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0403) rgbICURRDIGITS[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0403) rgbIINTLCURRDIGITS[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0403) rgbICURRENCY[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0403) rgbINEGCURR[] = { /* "8" */
+ 0x38
+};
+
+static BYTE NLSALLOC(0403) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(0403) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0403) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0403) rgbSLONGDATE[] = { /* "dddd, d' / 'MMMM' / 'yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x2c, 0x20, 0x64, 0x27
+ , 0x20, 0x2f, 0x20, 0x27, 0x4d, 0x4d, 0x4d, 0x4d
+ , 0x27, 0x20, 0x2f, 0x20, 0x27, 0x79, 0x79, 0x79
+ , 0x79
+};
+
+static BYTE NLSALLOC(0403) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0403) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0403) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0403) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0403) rgbITLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0403) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0403) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0403) rgbS1159[] = { /* "0x0000" */
+ 0x30, 0x78, 0x30, 0x30, 0x30, 0x30
+};
+
+static BYTE NLSALLOC(0403) rgbS2359[] = { /* "0x0000" */
+ 0x30, 0x78, 0x30, 0x30, 0x30, 0x30
+};
+
+static BYTE NLSALLOC(0403) rgbSDAYNAME1[] = { /* "dilluns" */
+ 0x64, 0x69, 0x6c, 0x6c, 0x75, 0x6e, 0x73
+};
+
+static BYTE NLSALLOC(0403) rgbSDAYNAME2[] = { /* "dimarts" */
+ 0x64, 0x69, 0x6d, 0x61, 0x72, 0x74, 0x73
+};
+
+static BYTE NLSALLOC(0403) rgbSDAYNAME3[] = { /* "dimecres" */
+ 0x64, 0x69, 0x6d, 0x65, 0x63, 0x72, 0x65, 0x73
+};
+
+static BYTE NLSALLOC(0403) rgbSDAYNAME4[] = { /* "dijous" */
+ 0x64, 0x69, 0x6a, 0x6f, 0x75, 0x73
+};
+
+static BYTE NLSALLOC(0403) rgbSDAYNAME5[] = { /* "divendres" */
+ 0x64, 0x69, 0x76, 0x65, 0x6e, 0x64, 0x72, 0x65
+ , 0x73
+};
+
+static BYTE NLSALLOC(0403) rgbSDAYNAME6[] = { /* "dissabte" */
+ 0x64, 0x69, 0x73, 0x73, 0x61, 0x62, 0x74, 0x65
+};
+
+static BYTE NLSALLOC(0403) rgbSDAYNAME7[] = { /* "diumenge" */
+ 0x64, 0x69, 0x75, 0x6d, 0x65, 0x6e, 0x67, 0x65
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVDAYNAME1[] = { /* "dl." */
+ 0x64, 0x6c, 0x2e
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVDAYNAME2[] = { /* "dt." */
+ 0x64, 0x74, 0x2e
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVDAYNAME3[] = { /* "dc." */
+ 0x64, 0x63, 0x2e
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVDAYNAME4[] = { /* "dj." */
+ 0x64, 0x6a, 0x2e
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVDAYNAME5[] = { /* "dv." */
+ 0x64, 0x76, 0x2e
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVDAYNAME6[] = { /* "ds." */
+ 0x64, 0x73, 0x2e
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVDAYNAME7[] = { /* "dg." */
+ 0x64, 0x67, 0x2e
+};
+
+static BYTE NLSALLOC(0403) rgbSMONTHNAME1[] = { /* "gener" */
+ 0x67, 0x65, 0x6e, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0403) rgbSMONTHNAME2[] = { /* "febrer" */
+ 0x66, 0x65, 0x62, 0x72, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0403) rgbSMONTHNAME3[] = { /* "març" */
+ 0x6d, 0x61, 0x72, 0xe7
+};
+
+static BYTE NLSALLOC(0403) rgbSMONTHNAME4[] = { /* "abril" */
+ 0x61, 0x62, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(0403) rgbSMONTHNAME5[] = { /* "maig" */
+ 0x6d, 0x61, 0x69, 0x67
+};
+
+static BYTE NLSALLOC(0403) rgbSMONTHNAME6[] = { /* "juny" */
+ 0x6a, 0x75, 0x6e, 0x79
+};
+
+static BYTE NLSALLOC(0403) rgbSMONTHNAME7[] = { /* "juliol" */
+ 0x6a, 0x75, 0x6c, 0x69, 0x6f, 0x6c
+};
+
+static BYTE NLSALLOC(0403) rgbSMONTHNAME8[] = { /* "agost" */
+ 0x61, 0x67, 0x6f, 0x73, 0x74
+};
+
+static BYTE NLSALLOC(0403) rgbSMONTHNAME9[] = { /* "setembre" */
+ 0x73, 0x65, 0x74, 0x65, 0x6d, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(0403) rgbSMONTHNAME10[] = { /* "octubre" */
+ 0x6f, 0x63, 0x74, 0x75, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(0403) rgbSMONTHNAME11[] = { /* "novembre" */
+ 0x6e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(0403) rgbSMONTHNAME12[] = { /* "desembre" */
+ 0x64, 0x65, 0x73, 0x65, 0x6d, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVMONTHNAME1[] = { /* "gen." */
+ 0x67, 0x65, 0x6e, 0x2e
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVMONTHNAME2[] = { /* "feb." */
+ 0x66, 0x65, 0x62, 0x2e
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVMONTHNAME3[] = { /* "març" */
+ 0x6d, 0x61, 0x72, 0xe7
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVMONTHNAME4[] = { /* "abr." */
+ 0x61, 0x62, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVMONTHNAME5[] = { /* "maig" */
+ 0x6d, 0x61, 0x69, 0x67
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVMONTHNAME6[] = { /* "juny" */
+ 0x6a, 0x75, 0x6e, 0x79
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVMONTHNAME7[] = { /* "jul." */
+ 0x6a, 0x75, 0x6c, 0x2e
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVMONTHNAME8[] = { /* "ag." */
+ 0x61, 0x67, 0x2e
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVMONTHNAME9[] = { /* "set." */
+ 0x73, 0x65, 0x74, 0x2e
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVMONTHNAME10[] = { /* "oct." */
+ 0x6f, 0x63, 0x74, 0x2e
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVMONTHNAME11[] = { /* "nov." */
+ 0x6e, 0x6f, 0x76, 0x2e
+};
+
+static BYTE NLSALLOC(0403) rgbSABBREVMONTHNAME12[] = { /* "des." */
+ 0x64, 0x65, 0x73, 0x2e
+};
+
+static BYTE NLSALLOC(0403) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0403) rgbIPOSSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0403) rgbINEGSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0403) rgbIPOSSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0403) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0403) rgbINEGSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0403) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0403) rgbSENGCOUNTRY[] = { /* "Spain" */
+ 0x53, 0x70, 0x61, 0x69, 0x6e
+};
+
+static BYTE NLSALLOC(0403) rgbSENGLANGUAGE[] = { /* "Catalan" */
+ 0x43, 0x61, 0x74, 0x61, 0x6c, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0403) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0403) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0403) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0403) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0403) rgbSTIMEFORMAT[] = { /* "HH:mm:ss" */
+ 0x48, 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0403) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0403) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0403) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0403) g_rglcinfo0403[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 7, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 6, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 5, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 7, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 3, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 25, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 6, rgbS1159 }
+ , { 6, rgbS2359 }
+ , { 7, rgbSDAYNAME1 }
+ , { 7, rgbSDAYNAME2 }
+ , { 8, rgbSDAYNAME3 }
+ , { 6, rgbSDAYNAME4 }
+ , { 9, rgbSDAYNAME5 }
+ , { 8, rgbSDAYNAME6 }
+ , { 8, rgbSDAYNAME7 }
+ , { 3, rgbSABBREVDAYNAME1 }
+ , { 3, rgbSABBREVDAYNAME2 }
+ , { 3, rgbSABBREVDAYNAME3 }
+ , { 3, rgbSABBREVDAYNAME4 }
+ , { 3, rgbSABBREVDAYNAME5 }
+ , { 3, rgbSABBREVDAYNAME6 }
+ , { 3, rgbSABBREVDAYNAME7 }
+ , { 5, rgbSMONTHNAME1 }
+ , { 6, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 4, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 6, rgbSMONTHNAME7 }
+ , { 5, rgbSMONTHNAME8 }
+ , { 8, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 4, rgbSABBREVMONTHNAME1 }
+ , { 4, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 4, rgbSABBREVMONTHNAME4 }
+ , { 4, rgbSABBREVMONTHNAME5 }
+ , { 4, rgbSABBREVMONTHNAME6 }
+ , { 4, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 4, rgbSABBREVMONTHNAME9 }
+ , { 4, rgbSABBREVMONTHNAME10 }
+ , { 4, rgbSABBREVMONTHNAME11 }
+ , { 4, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 5, rgbSENGCOUNTRY }
+ , { 7, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 8, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0403) g_strinfo0403 = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0404.c b/private/oleauto/src/dispatch/win16/0404.c
new file mode 100644
index 000000000..a722b893a
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0404.c
@@ -0,0 +1,1036 @@
+/***
+*0404.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+*
+* China, Chinese Traditional
+*
+* LCID = 0x0404
+*
+*
+*Generated: 9/22/93 - by hand from lcid_cht.txt
+*
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+#include "nlsdbcs.h"
+
+
+#if 1
+static SORTWEIGHT NLSALLOC(0404) rgsortweight[] = {
+ { 0x0000, 0x0200, 0x00, 0x00 }
+ , { 0x0020, 0x0220, 0x00, 0x02 }
+ , { 0x0030, 0x0930, 0x00, 0x02 }
+ , { 0x003A, 0x023A, 0x00, 0x02 }
+ , { 0x0041, 0x0A41, 0x02, 0x02 }
+ , { 0x005B, 0x025B, 0x00, 0x02 }
+ , { 0x0061, 0x0A41, 0x00, 0x02 }
+ , { 0x007B, 0x027B, 0x00, 0x02 }
+ , { 0x007F, 0x021F, 0x00, 0xFF }
+ , { 0x8140, 0x0C40, 0x00, 0x00 }
+ , { 0xA140, 0x0220, 0x01, 0x02 }
+ , { 0xA141, 0x022C, 0x01, 0x02 }
+ , { 0xA142, 0x0303, 0x00, 0x00 }
+ , { 0xA144, 0x022E, 0x01, 0x02 }
+ , { 0xA145, 0x0306, 0x00, 0x00 }
+ , { 0xA146, 0x023B, 0x01, 0x02 }
+ , { 0xA147, 0x023A, 0x01, 0x02 }
+ , { 0xA148, 0x023F, 0x01, 0x02 }
+ , { 0xA149, 0x0221, 0x01, 0x02 }
+ , { 0xA14A, 0x030B, 0x00, 0x00 }
+ , { 0xA155, 0x027C, 0x01, 0x02 }
+ , { 0xA156, 0x0317, 0x00, 0x00 }
+ , { 0xA15D, 0x0228, 0x01, 0x02 }
+ , { 0xA15E, 0x0229, 0x01, 0x02 }
+ , { 0xA15F, 0x0320, 0x00, 0x00 }
+ , { 0xA161, 0x027B, 0x01, 0x02 }
+ , { 0xA162, 0x027D, 0x01, 0x02 }
+ , { 0xA163, 0x0324, 0x00, 0x00 }
+ , { 0xA165, 0x025B, 0x01, 0x02 }
+ , { 0xA166, 0x025D, 0x01, 0x02 }
+ , { 0xA167, 0x0328, 0x00, 0x00 }
+ , { 0xA173, 0x025E, 0x01, 0x02 }
+ , { 0xA174, 0x0335, 0x00, 0x00 }
+ , { 0xA1A5, 0x0260, 0x01, 0x02 }
+ , { 0xA1A6, 0x0227, 0x01, 0x02 }
+ , { 0xA1A7, 0x0368, 0x00, 0x00 }
+ , { 0xA1A8, 0x0222, 0x01, 0x02 }
+ , { 0xA1A9, 0x036A, 0x00, 0x00 }
+ , { 0xA1AD, 0x0223, 0x01, 0x02 }
+ , { 0xA1AE, 0x0226, 0x01, 0x02 }
+ , { 0xA1AF, 0x022A, 0x01, 0x02 }
+ , { 0xA1B0, 0x0371, 0x00, 0x00 }
+ , { 0xA1C5, 0x025F, 0x01, 0x02 }
+ , { 0xA1C6, 0x0387, 0x00, 0x00 }
+ , { 0xA1CF, 0x022B, 0x01, 0x02 }
+ , { 0xA1D0, 0x022D, 0x01, 0x02 }
+ , { 0xA1D1, 0x0392, 0x00, 0x00 }
+ , { 0xA1D5, 0x023C, 0x01, 0x02 }
+ , { 0xA1D6, 0x023E, 0x01, 0x02 }
+ , { 0xA1D7, 0x023D, 0x01, 0x02 }
+ , { 0xA1D8, 0x0399, 0x00, 0x00 }
+ , { 0xA1E3, 0x027E, 0x01, 0x02 }
+ , { 0xA1E4, 0x03A5, 0x00, 0x00 }
+ , { 0xA1FE, 0x022F, 0x01, 0x02 }
+ , { 0xA240, 0x025C, 0x01, 0x02 }
+ , { 0xA241, 0x0402, 0x00, 0x00 }
+ , { 0xA243, 0x0224, 0x01, 0x02 }
+ , { 0xA244, 0x0405, 0x00, 0x00 }
+ , { 0xA248, 0x0225, 0x01, 0x02 }
+ , { 0xA249, 0x0240, 0x01, 0x02 }
+ , { 0xA24A, 0x040B, 0x00, 0x00 }
+ , { 0xA259, 0x4B02, 0x00, 0x00 }
+ , { 0xA25A, 0x5202, 0x00, 0x00 }
+ , { 0xA25B, 0x5D02, 0x00, 0x00 }
+ , { 0xA25D, 0x6F02, 0x00, 0x00 }
+ , { 0xA25E, 0x8902, 0x00, 0x00 }
+ , { 0xA25F, 0x6F03, 0x00, 0x00 }
+ , { 0xA260, 0x4402, 0x00, 0x00 }
+ , { 0xA261, 0x8002, 0x00, 0x00 }
+ , { 0xA262, 0x0422, 0x00, 0x00 }
+ , { 0xA2AF, 0x0930, 0x01, 0x02 }
+ , { 0xA2B9, 0x0471, 0x00, 0x00 }
+ , { 0xA2CF, 0x0A41, 0x03, 0x02 }
+ , { 0xA2E9, 0x0A41, 0x01, 0x02 }
+ , { 0xA340, 0x0A57, 0x03, 0x02 }
+ , { 0xA344, 0x0544, 0x00, 0x00 }
+ , { 0xA440, 0x3140, 0x00, 0x00 }
+ , { 0xA442, 0x3242, 0x00, 0x00 }
+ , { 0xA454, 0x3454, 0x00, 0x00 }
+ , { 0xA4A1, 0x36A1, 0x00, 0x00 }
+ , { 0xA4FE, 0x38FE, 0x00, 0x00 }
+ , { 0xA5E0, 0x3BE0, 0x00, 0x00 }
+ , { 0xA6EA, 0x3FEA, 0x00, 0x00 }
+ , { 0xA8C3, 0x44C3, 0x00, 0x00 }
+ , { 0xAB45, 0x4B45, 0x00, 0x00 }
+ , { 0xADBC, 0x52BC, 0x00, 0x00 }
+ , { 0xB0AE, 0x5DAE, 0x00, 0x00 }
+ , { 0xB3C3, 0x66C3, 0x00, 0x00 }
+ , { 0xB6C3, 0x6FC3, 0x00, 0x00 }
+ , { 0xB9AC, 0x78AC, 0x00, 0x00 }
+ , { 0xBBF5, 0x80F5, 0x00, 0x00 }
+ , { 0xBEA7, 0x89A7, 0x00, 0x00 }
+ , { 0xC075, 0x9175, 0x00, 0x00 }
+ , { 0xC24F, 0x984F, 0x00, 0x00 }
+ , { 0xC35F, 0x9D5F, 0x00, 0x00 }
+ , { 0xC455, 0xA255, 0x00, 0x00 }
+ , { 0xC4D7, 0xA6D7, 0x00, 0x00 }
+ , { 0xC56B, 0xAA6B, 0x00, 0x00 }
+ , { 0xC5C8, 0xADC8, 0x00, 0x00 }
+ , { 0xC5F1, 0xB0F1, 0x00, 0x00 }
+ , { 0xC655, 0xB355, 0x00, 0x00 }
+ , { 0xC665, 0xB665, 0x00, 0x00 }
+ , { 0xC66C, 0xB86C, 0x00, 0x00 }
+ , { 0xC676, 0xBA76, 0x00, 0x00 }
+ , { 0xC679, 0xBC79, 0x00, 0x00 }
+ , { 0xC67D, 0xBE7D, 0x00, 0x00 }
+ , { 0xC67E, 0xC17E, 0x00, 0x00 }
+ , { 0xC6A1, 0x06A1, 0x00, 0x00 }
+ , { 0xC940, 0x3340, 0x00, 0x00 }
+ , { 0xC945, 0x3545, 0x00, 0x00 }
+ , { 0xC94D, 0x374D, 0x00, 0x00 }
+ , { 0xC963, 0x3A63, 0x00, 0x00 }
+ , { 0xC9AB, 0x3DAB, 0x00, 0x00 }
+ , { 0xCA5A, 0x425A, 0x00, 0x00 }
+ , { 0xCBB1, 0x48B1, 0x00, 0x00 }
+ , { 0xCDDD, 0x4EDD, 0x00, 0x00 }
+ , { 0xD0C8, 0x58C8, 0x00, 0x00 }
+ , { 0xD44B, 0x614B, 0x00, 0x00 }
+ , { 0xD851, 0x6A51, 0x00, 0x00 }
+ , { 0xDCB1, 0x73B1, 0x00, 0x00 }
+ , { 0xE0F0, 0x7BF0, 0x00, 0x00 }
+ , { 0xE4E6, 0x84E6, 0x00, 0x00 }
+ , { 0xE8F4, 0x8CF4, 0x00, 0x00 }
+ , { 0xECB9, 0x94B9, 0x00, 0x00 }
+ , { 0xEFB7, 0x9AB7, 0x00, 0x00 }
+ , { 0xF1EB, 0x9FEB, 0x00, 0x00 }
+ , { 0xF3FD, 0xA3FD, 0x00, 0x00 }
+ , { 0xF5C0, 0xA8C0, 0x00, 0x00 }
+ , { 0xF6D6, 0xABD6, 0x00, 0x00 }
+ , { 0xF7D0, 0xAED0, 0x00, 0x00 }
+ , { 0xF8A5, 0xB2A5, 0x00, 0x00 }
+ , { 0xF8EE, 0xB4EE, 0x00, 0x00 }
+ , { 0xF96B, 0xB76B, 0x00, 0x00 }
+ , { 0xF9A2, 0xB9A2, 0x00, 0x00 }
+ , { 0xF9BA, 0xBBBA, 0x00, 0x00 }
+ , { 0xF9C6, 0xC3C6, 0x00, 0x00 }
+ , { 0xF9C7, 0xBDC7, 0x00, 0x00 }
+ , { 0xF9CC, 0xBFCC, 0x00, 0x00 }
+ , { 0xF9D0, 0xC0D0, 0x00, 0x00 }
+ , { 0xF9D1, 0xC2D1, 0x00, 0x00 }
+ , { 0xF9D2, 0xC4D2, 0x00, 0x00 }
+ , { 0xF9D3, 0xC5D3, 0x00, 0x00 }
+ , { 0xF9D4, 0xC6D4, 0x00, 0x00 }
+ , { 0xF9D5, 0xC7D5, 0x00, 0x00 }
+ , { 0xFA40, 0x2C40, 0x00, 0x00 }
+};
+static MAPTABLE NLSALLOC(0404) rgmaptable[] = {
+ { 0x0220, 0x0001, 0x0020, 0xA140, 0x0020, 0xA140 }
+ , { 0x0221, 0x0001, 0x0021, 0xA149, 0x0021, 0xA149 }
+ , { 0x0222, 0x0001, 0x0022, 0xA1A8, 0x0022, 0xA1A8 }
+ , { 0x0223, 0x0001, 0x0023, 0xA1AD, 0x0023, 0xA1AD }
+ , { 0x0224, 0x0001, 0x0024, 0xA243, 0x0024, 0xA243 }
+ , { 0x0225, 0x0001, 0x0025, 0xA248, 0x0025, 0xA248 }
+ , { 0x0226, 0x0001, 0x0026, 0xA1AE, 0x0026, 0xA1AE }
+ , { 0x0227, 0x0001, 0x0027, 0xA1A6, 0x0027, 0xA1A6 }
+ , { 0x0228, 0x0002, 0x0028, 0xA15D, 0x0028, 0xA15D }
+ , { 0x022A, 0x0001, 0x002A, 0xA1AF, 0x002A, 0xA1AF }
+ , { 0x022B, 0x0001, 0x002B, 0xA1CF, 0x002B, 0xA1CF }
+ , { 0x022C, 0x0001, 0x002C, 0xA141, 0x002C, 0xA141 }
+ , { 0x022D, 0x0001, 0x002D, 0xA1D0, 0x002D, 0xA1D0 }
+ , { 0x022E, 0x0001, 0x002E, 0xA144, 0x002E, 0xA144 }
+ , { 0x022F, 0x0001, 0x002F, 0xA1FE, 0x002F, 0xA1FE }
+ , { 0x023A, 0x0001, 0x003A, 0xA147, 0x003A, 0xA147 }
+ , { 0x023B, 0x0001, 0x003B, 0xA146, 0x003B, 0xA146 }
+ , { 0x023C, 0x0001, 0x003C, 0xA1D5, 0x003C, 0xA1D5 }
+ , { 0x023D, 0x0001, 0x003D, 0xA1D7, 0x003D, 0xA1D7 }
+ , { 0x023E, 0x0001, 0x003E, 0xA1D6, 0x003E, 0xA1D6 }
+ , { 0x023F, 0x0001, 0x003F, 0xA148, 0x003F, 0xA148 }
+ , { 0x0240, 0x0001, 0x0040, 0xA249, 0x0040, 0xA249 }
+ , { 0x025B, 0x0001, 0x005B, 0xA165, 0x005B, 0xA165 }
+ , { 0x025C, 0x0001, 0x005C, 0xA240, 0x005C, 0xA240 }
+ , { 0x025D, 0x0001, 0x005D, 0xA166, 0x005D, 0xA166 }
+ , { 0x025E, 0x0001, 0x005E, 0xA173, 0x005E, 0xA173 }
+ , { 0x025F, 0x0001, 0x005F, 0xA1C5, 0x005F, 0xA1C5 }
+ , { 0x0260, 0x0001, 0x0060, 0xA1A5, 0x0060, 0xA1A5 }
+ , { 0x027B, 0x0001, 0x007B, 0xA161, 0x007B, 0xA161 }
+ , { 0x027C, 0x0001, 0x007C, 0xA155, 0x007C, 0xA155 }
+ , { 0x027D, 0x0001, 0x007D, 0xA162, 0x007D, 0xA162 }
+ , { 0x027E, 0x0001, 0x007E, 0xA1E3, 0x007E, 0xA1E3 }
+ , { 0x0930, 0x000A, 0x0030, 0xA2AF, 0x0030, 0xA2AF }
+ , { 0x0A41, 0x0016, 0x0041, 0xA2CF, 0x0061, 0xA2E9 }
+ , { 0x0A57, 0x0004, 0x0057, 0xA2E5, 0x0077, 0xA340 }
+};
+static TYPETABLE NLSALLOC(0404) rgtypetable[] = {
+ { 0x0000, 0x0020, 0x00, 0x00 }
+ , { 0x0009, 0x0068, 0x09, 0x00 }
+ , { 0x000A, 0x0028, 0x00, 0x00 }
+ , { 0x000E, 0x0020, 0x00, 0x00 }
+ , { 0x0020, 0x0048, 0x0A, 0x00 }
+ , { 0x0021, 0x0010, 0x0B, 0x08 }
+ , { 0x0024, 0x0010, 0x05, 0x08 }
+ , { 0x0026, 0x0010, 0x01, 0x08 }
+ , { 0x002B, 0x0010, 0x05, 0x08 }
+ , { 0x002C, 0x0010, 0x07, 0x08 }
+ , { 0x002D, 0x0010, 0x05, 0x08 }
+ , { 0x002E, 0x0010, 0x03, 0x08 }
+ , { 0x0030, 0x0084, 0x03, 0x00 }
+ , { 0x003A, 0x0010, 0x07, 0x08 }
+ , { 0x003B, 0x0010, 0x0B, 0x08 }
+ , { 0x0040, 0x0010, 0x01, 0x08 }
+ , { 0x0041, 0x0181, 0x01, 0x00 }
+ , { 0x0047, 0x0101, 0x01, 0x00 }
+ , { 0x005B, 0x0010, 0x0B, 0x08 }
+ , { 0x0061, 0x0182, 0x01, 0x00 }
+ , { 0x0067, 0x0102, 0x01, 0x00 }
+ , { 0x007B, 0x0010, 0x0B, 0x08 }
+ , { 0x007F, 0x0020, 0x00, 0x00 }
+ , { 0x0080, 0x0000, 0x00, 0x00 }
+ , { 0x8140, 0x0100, 0x01, 0x00 }
+ , { 0xA140, 0x0048, 0x0A, 0x00 }
+ , { 0xA141, 0x0010, 0x07, 0x08 }
+ , { 0xA142, 0x0010, 0x0B, 0x08 }
+ , { 0xA155, 0x0000, 0x0B, 0x08 }
+ , { 0xA2AF, 0x0084, 0x03, 0x00 }
+ , { 0xA2B9, 0x0000, 0x0B, 0x08 }
+ , { 0xA2CF, 0x0181, 0x01, 0x00 }
+ , { 0xA2D5, 0x0101, 0x01, 0x00 }
+ , { 0xA2E9, 0x0182, 0x01, 0x00 }
+ , { 0xA2EF, 0x0102, 0x01, 0x00 }
+ , { 0xA344, 0x0181, 0x01, 0x00 }
+ , { 0xA346, 0x0000, 0x0B, 0x08 }
+ , { 0xA440, 0x0100, 0x01, 0x00 }
+ , { 0xC6A1, 0x0000, 0x0B, 0x08 }
+ , { 0xC940, 0x0100, 0x01, 0x00 }
+};
+#else
+static unsigned char NLSALLOC(0404) rgsortweight[] = {
+ 0x00, 0x00, 0x00, 0x02, 0x00, 0x00
+ , 0x20, 0x00, 0x20, 0x02, 0x00, 0x02
+ , 0x30, 0x00, 0x30, 0x09, 0x00, 0x02
+ , 0x3A, 0x00, 0x3A, 0x02, 0x00, 0x02
+ , 0x41, 0x00, 0x41, 0x0a, 0x00, 0x02
+ , 0x5B, 0x00, 0x5B, 0x02, 0x00, 0x02
+ , 0x61, 0x00, 0x41, 0x0a, 0x02, 0x02
+ , 0x7B, 0x00, 0x7B, 0x02, 0x00, 0x02
+ , 0x7F, 0x00, 0x1F, 0x02, 0x00, 0xFF
+ , 0x40, 0x81, 0x40, 0x0C, 0x00, 0x00
+ , 0x40, 0xA1, 0x20, 0x02, 0x01, 0x02
+ , 0x41, 0xA1, 0x2C, 0x02, 0x01, 0x02
+ , 0x42, 0xA1, 0x03, 0x03, 0x00, 0x00
+ , 0x44, 0xA1, 0x2E, 0x02, 0x01, 0x02
+ , 0X45, 0xA1, 0x06, 0x03, 0x00, 0x00
+ , 0x46, 0xA1, 0x3B, 0x02, 0x01, 0x02
+ , 0x47, 0xA1, 0x3A, 0x02, 0x01, 0x02
+ , 0x48, 0xA1, 0x3F, 0x02, 0x01, 0x02
+ , 0x49, 0xA1, 0x21, 0x02, 0x01, 0x02
+ , 0X4A, 0xA1, 0x0B, 0x03, 0x00, 0x00
+ , 0x55, 0xA1, 0x7C, 0x02, 0x01, 0x02
+ , 0X56, 0xA1, 0x17, 0x03, 0x00, 0x00
+ , 0x5D, 0xA1, 0x28, 0x02, 0x01, 0x02
+ , 0x5E, 0xA1, 0x29, 0x02, 0x01, 0x02
+ , 0X5F, 0xA1, 0x20, 0x03, 0x00, 0x00
+ , 0x61, 0xA1, 0x7B, 0x02, 0x01, 0x02
+ , 0x62, 0xA1, 0x7D, 0x02, 0x01, 0x02
+ , 0X63, 0xA1, 0x24, 0x03, 0x00, 0x00
+ , 0x65, 0xA1, 0x5B, 0x02, 0x01, 0x02
+ , 0x66, 0xA1, 0x5D, 0x02, 0x01, 0x02
+ , 0X67, 0xA1, 0x28, 0x03, 0x00, 0x00
+ , 0x73, 0xA1, 0x5E, 0x02, 0x01, 0x02
+ , 0X74, 0xA1, 0x35, 0x03, 0x00, 0x00
+ , 0xA5, 0xA1, 0x60, 0x02, 0x01, 0x02
+ , 0xA6, 0xA1, 0x27, 0x02, 0x01, 0x02
+ , 0XA7, 0xA1, 0x68, 0x03, 0x00, 0x00
+ , 0xA8, 0xA1, 0x22, 0x02, 0x01, 0x02
+ , 0XA9, 0xA1, 0x6A, 0x03, 0x00, 0x00
+ , 0xAD, 0xA1, 0x23, 0x02, 0x01, 0x02
+ , 0xAE, 0xA1, 0x26, 0x02, 0x01, 0x02
+ , 0xAF, 0xA1, 0x2A, 0x02, 0x01, 0x02
+ , 0XB0, 0xA1, 0x71, 0x03, 0x00, 0x00
+ , 0xC5, 0xA1, 0x5F, 0x02, 0x01, 0x02
+ , 0XC6, 0xA1, 0x87, 0x03, 0x00, 0x00
+ , 0xCF, 0xA1, 0x2B, 0x02, 0x01, 0x02
+ , 0xD0, 0xA1, 0x2D, 0x02, 0x01, 0x02
+ , 0XD1, 0xA1, 0x92, 0x03, 0x00, 0x00
+ , 0xD5, 0xA1, 0x3C, 0x02, 0x01, 0x02
+ , 0xD6, 0xA1, 0x3E, 0x02, 0x01, 0x02
+ , 0xD7, 0xA1, 0x3D, 0x02, 0x01, 0x02
+ , 0XD8, 0xA1, 0x99, 0x03, 0x00, 0x00
+ , 0xE3, 0xA1, 0x7E, 0x02, 0x01, 0x02
+ , 0XE4, 0xA1, 0xA5, 0x03, 0x00, 0x00
+ , 0xFE, 0xA1, 0x2F, 0x02, 0x01, 0x02
+ , 0x40, 0xA2, 0x5C, 0x02, 0x01, 0x02
+ , 0X41, 0xA2, 0x02, 0x04, 0x00, 0x00
+ , 0x43, 0xA2, 0x24, 0x02, 0x01, 0x02
+ , 0X44, 0xA2, 0x05, 0x04, 0x00, 0x00
+ , 0x48, 0xA2, 0x25, 0x02, 0x01, 0x02
+ , 0x49, 0xA2, 0x40, 0x02, 0x01, 0x02
+ , 0x4A, 0xA2, 0x0B, 0x04, 0x00, 0x00
+ , 0x59, 0xA2, 0x02, 0x4B, 0x00, 0x00
+ , 0x5A, 0xA2, 0x02, 0x52, 0x00, 0x00
+ , 0x5B, 0xA2, 0x02, 0x5D, 0x00, 0x00
+ , 0x5D, 0xA2, 0x02, 0x6F, 0x00, 0x00
+ , 0x5E, 0xA2, 0x02, 0x89, 0x00, 0x00
+ , 0x5F, 0xA2, 0x03, 0x6F, 0x00, 0x00
+ , 0x60, 0xA2, 0x02, 0x44, 0x00, 0x00
+ , 0x61, 0xA2, 0x02, 0x80, 0x00, 0x00
+ , 0x62, 0xA2, 0x22, 0x04, 0x00, 0x00
+ , 0xAF, 0xA2, 0x30, 0x09, 0x01, 0x02
+ , 0xB9, 0xA2, 0x71, 0x04, 0x00, 0x00
+ , 0xCF, 0xA2, 0x41, 0x0A, 0x01, 0x02
+ , 0xE9, 0xA2, 0x41, 0x0A, 0x03, 0x02
+ , 0x40, 0xA3, 0x57, 0x0A, 0x03, 0x02
+ , 0x44, 0xA3, 0x44, 0x05, 0x00, 0x00
+ , 0x40, 0xA4, 0x40, 0x31, 0x00, 0x00
+ , 0x42, 0xA4, 0x42, 0x32, 0x00, 0x00
+ , 0x54, 0xA4, 0x54, 0x34, 0x00, 0x00
+ , 0xA1, 0xA4, 0xA1, 0x36, 0x00, 0x00
+ , 0xFE, 0xA4, 0xFE, 0x38, 0x00, 0x00
+ , 0xE0, 0xA5, 0xE0, 0x3B, 0x00, 0x00
+ , 0xEA, 0xA6, 0xEA, 0x3F, 0x00, 0x00
+ , 0xC3, 0xA8, 0xC3, 0x44, 0x00, 0x00
+ , 0x45, 0xAB, 0x45, 0x4B, 0x00, 0x00
+ , 0xBC, 0xAD, 0xBC, 0x52, 0x00, 0x00
+ , 0xAE, 0xB0, 0xAE, 0x5D, 0x00, 0x00
+ , 0xC3, 0xB3, 0xC3, 0x66, 0x00, 0x00
+ , 0xC3, 0xB6, 0xC3, 0x6F, 0x00, 0x00
+ , 0xAC, 0xB9, 0xAC, 0x78, 0x00, 0x00
+ , 0xF5, 0xBB, 0xF5, 0x80, 0x00, 0x00
+ , 0xA7, 0xBE, 0xA7, 0x89, 0x00, 0x00
+ , 0x75, 0xC0, 0x75, 0x91, 0x00, 0x00
+ , 0x4F, 0xC2, 0x4F, 0x98, 0x00, 0x00
+ , 0x5F, 0xC3, 0x5F, 0x9D, 0x00, 0x00
+ , 0x55, 0xC4, 0x55, 0xA2, 0x00, 0x00
+ , 0xD7, 0xC4, 0xD7, 0xA6, 0x00, 0x00
+ , 0x6B, 0xC5, 0x6B, 0xAA, 0x00, 0x00
+ , 0xC8, 0xC5, 0xC8, 0xAD, 0x00, 0x00
+ , 0xF1, 0xC5, 0xF1, 0xB0, 0x00, 0x00
+ , 0x55, 0xC6, 0x55, 0xB3, 0x00, 0x00
+ , 0x65, 0xC6, 0x65, 0xB6, 0x00, 0x00
+ , 0x6C, 0xC6, 0x6C, 0xB8, 0x00, 0x00
+ , 0x76, 0xC6, 0x76, 0xBA, 0x00, 0x00
+ , 0x79, 0xC6, 0x79, 0xBC, 0x00, 0x00
+ , 0x7D, 0xC6, 0x7D, 0xBE, 0x00, 0x00
+ , 0x7E, 0xC6, 0x7E, 0xC1, 0x00, 0x00
+ , 0xA1, 0xC6, 0xA1, 0x06, 0x00, 0x00
+ , 0x40, 0xC9, 0x40, 0x33, 0x00, 0x00
+ , 0x45, 0xC9, 0x45, 0x35, 0x00, 0x00
+ , 0x4D, 0xC9, 0x4D, 0x37, 0x00, 0x00
+ , 0x63, 0xC9, 0x63, 0x3A, 0x00, 0x00
+ , 0xAB, 0xC9, 0xAB, 0x3D, 0x00, 0x00
+ , 0x5A, 0xCA, 0x5A, 0x42, 0x00, 0x00
+ , 0xB1, 0xCB, 0xB1, 0x48, 0x00, 0x00
+ , 0xDD, 0xCD, 0xDD, 0x4E, 0x00, 0x00
+ , 0xC8, 0xD0, 0xC8, 0x58, 0x00, 0x00
+ , 0x4B, 0xD4, 0x4B, 0x61, 0x00, 0x00
+ , 0x51, 0xD8, 0x51, 0x6A, 0x00, 0x00
+ , 0xB1, 0xDC, 0xB1, 0x73, 0x00, 0x00
+ , 0xF0, 0xE0, 0xF0, 0x7B, 0x00, 0x00
+ , 0xE6, 0xE4, 0xE6, 0x84, 0x00, 0x00
+ , 0xF4, 0xE8, 0xF4, 0x8C, 0x00, 0x00
+ , 0xB9, 0xEC, 0xB9, 0x94, 0x00, 0x00
+ , 0xB7, 0xEF, 0xB7, 0x9A, 0x00, 0x00
+ , 0xEB, 0xF1, 0xEB, 0x9F, 0x00, 0x00
+ , 0xFD, 0xF3, 0xFD, 0xA3, 0x00, 0x00
+ , 0xC0, 0xF5, 0xC0, 0xA8, 0x00, 0x00
+ , 0xD6, 0xF6, 0xD6, 0xAB, 0x00, 0x00
+ , 0xD0, 0xF7, 0xD0, 0xAE, 0x00, 0x00
+ , 0xA5, 0xF8, 0xA5, 0xB2, 0x00, 0x00
+ , 0xEE, 0xF8, 0xEE, 0xB4, 0x00, 0x00
+ , 0x6B, 0xF9, 0x6B, 0xB7, 0x00, 0x00
+ , 0xA2, 0xF9, 0xA2, 0xB9, 0x00, 0x00
+ , 0xBA, 0xF9, 0xBA, 0xBB, 0x00, 0x00
+ , 0xC6, 0xF9, 0xC6, 0xC3, 0x00, 0x00
+ , 0xC7, 0xF9, 0xC7, 0xBD, 0x00, 0x00
+ , 0xCC, 0xF9, 0xCC, 0xBF, 0x00, 0x00
+ , 0xD0, 0xF9, 0xD0, 0xC0, 0x00, 0x00
+ , 0xD1, 0xF9, 0xD1, 0xC2, 0x00, 0x00
+ , 0xD2, 0xF9, 0xD2, 0xC4, 0x00, 0x00
+ , 0xD3, 0xF9, 0xD3, 0xC5, 0x00, 0x00
+ , 0xD4, 0xF9, 0xD4, 0xC6, 0x00, 0x00
+ , 0xD5, 0xF9, 0xD5, 0xC7, 0x00, 0x00
+ , 0x40, 0xFA, 0x40, 0x2C, 0x00, 0x00
+};
+
+static unsigned char NLSALLOC(0404) rgmaptable[] = {
+ 0x20, 0x02, 0x01, 0x00, 0x20, 0x00
+ , 0x40, 0xA1, 0x20, 0x00, 0x40, 0xA1
+ , 0x21, 0x02, 0x01, 0x00, 0x21, 0x00
+ , 0x49, 0xA1, 0x21, 0x00, 0x49, 0xA1
+ , 0x22, 0x02, 0x01, 0x00, 0x22, 0x00
+ , 0xA8, 0xA1, 0x22, 0x00, 0xA8, 0xA1
+ , 0x23, 0x02, 0x01, 0x00, 0x23, 0x00
+ , 0xAD, 0xA1, 0x23, 0x00, 0xAD, 0xA1
+ , 0x24, 0x02, 0x01, 0x00, 0x24, 0x00
+ , 0x43, 0xA2, 0x24, 0x00, 0x43, 0xA2
+ , 0x25, 0x02, 0x01, 0x00, 0x25, 0x00
+ , 0x48, 0xA2, 0x25, 0x00, 0x48, 0xA2
+ , 0x26, 0x02, 0x01, 0x00, 0x26, 0x00
+ , 0xAE, 0xA1, 0x26, 0x00, 0xAE, 0xA1
+ , 0x27, 0x02, 0x01, 0x00, 0x27, 0x00
+ , 0xA6, 0xA1, 0x27, 0x00, 0xA6, 0xA1
+ , 0x28, 0x02, 0x02, 0x00, 0x28, 0x00
+ , 0x5D, 0xA1, 0x28, 0x00, 0x5D, 0xA1
+ , 0x2A, 0x02, 0x01, 0x00, 0x2A, 0x00
+ , 0xAF, 0xA1, 0x2A, 0x00, 0xAF, 0xA1
+ , 0x2B, 0x02, 0x01, 0x00, 0x2B, 0x00
+ , 0xCF, 0xA1, 0x2B, 0x00, 0xCF, 0xA1
+ , 0x2C, 0x02, 0x01, 0x00, 0x2C, 0x00
+ , 0x41, 0xA1, 0x2C, 0x00, 0x41, 0xA1
+ , 0x2D, 0x02, 0x01, 0x00, 0x2D, 0x00
+ , 0xD0, 0xA1, 0x2D, 0x00, 0xD0, 0xA1
+ , 0x2E, 0x02, 0x01, 0x00, 0x2E, 0x00
+ , 0x44, 0xA1, 0x2E, 0x00, 0x44, 0xA1
+ , 0x2F, 0x02, 0x01, 0x00, 0x2F, 0x00
+ , 0xFE, 0xA1, 0x2F, 0x00, 0xFE, 0xA1
+ , 0x3A, 0x02, 0x01, 0x00, 0x3A, 0x00
+ , 0x47, 0xA1, 0x3A, 0x00, 0x47, 0xA1
+ , 0x3B, 0x02, 0x01, 0x00, 0x3B, 0x00
+ , 0x46, 0xA1, 0x3B, 0x00, 0x46, 0xA1
+ , 0x3C, 0x02, 0x01, 0x00, 0x3C, 0x00
+ , 0xD5, 0xA1, 0x3C, 0x00, 0xD5, 0xA1
+ , 0x3D, 0x02, 0x01, 0x00, 0x3D, 0x00
+ , 0xD7, 0xA1, 0x3D, 0x00, 0xD7, 0xA1
+ , 0x3E, 0x02, 0x01, 0x00, 0x3E, 0x00
+ , 0xD6, 0xA1, 0x3E, 0x00, 0xD6, 0xA1
+ , 0x3F, 0x02, 0x01, 0x00, 0x3F, 0x00
+ , 0x48, 0xA1, 0x3F, 0x00, 0x48, 0xA1
+ , 0x40, 0x02, 0x01, 0x00, 0x40, 0x00
+ , 0x49, 0xA2, 0x40, 0x00, 0x49, 0xA2
+ , 0x5B, 0x02, 0x01, 0x00, 0x5B, 0x00
+ , 0x65, 0xA1, 0x5B, 0x00, 0x65, 0xA1
+ , 0x5C, 0x02, 0x01, 0x00, 0x5C, 0x00
+ , 0x40, 0xA2, 0x5C, 0x00, 0x40, 0xA2
+ , 0x5D, 0x02, 0x01, 0x00, 0x5D, 0x00
+ , 0x66, 0xA1, 0x5D, 0x00, 0x66, 0xA1
+ , 0x5E, 0x02, 0x01, 0x00, 0x5E, 0x00
+ , 0x73, 0xA1, 0x5E, 0x00, 0x73, 0xA1
+ , 0x5F, 0x02, 0x01, 0x00, 0x5F, 0x00
+ , 0xC5, 0xA1, 0x5F, 0x00, 0xC5, 0xA1
+ , 0x60, 0x02, 0x01, 0x00, 0x60, 0x00
+ , 0xA5, 0xA1, 0x60, 0x00, 0xA5, 0xA1
+ , 0x7B, 0x02, 0x01, 0x00, 0x7B, 0x00
+ , 0x61, 0xA1, 0x7B, 0x00, 0x61, 0xA1
+ , 0x7C, 0x02, 0x01, 0x00, 0x7C, 0x00
+ , 0x55, 0xA1, 0x7C, 0x00, 0x55, 0xA1
+ , 0x7D, 0x02, 0x01, 0x00, 0x7D, 0x00
+ , 0x62, 0xA1, 0x7D, 0x00, 0x62, 0xA1
+ , 0x7E, 0x02, 0x01, 0x00, 0x7E, 0x00
+ , 0xE3, 0xA1, 0x7E, 0x00, 0xE3, 0xA1
+ , 0x30, 0x09, 0x0A, 0x00, 0x30, 0x00
+ , 0xAF, 0xA2, 0x30, 0x00, 0xAF, 0xA2
+ , 0x41, 0x0A, 0x16, 0x00, 0x41, 0x00
+ , 0xCF, 0xA2, 0x61, 0x00, 0xE9, 0xA2
+ , 0x57, 0x0A, 0x04, 0x00, 0x57, 0x00
+ , 0xE5, 0xA2, 0x77, 0x00, 0x40, 0xA3
+};
+
+static unsigned char NLSALLOC(0404) rgtypetable[] = {
+ 0x00, 0x00, 0x20, 0x00, 0x00, 0x00
+ , 0x09, 0x00, 0x68, 0x00, 0x09, 0x00
+ , 0x0A, 0x00, 0x28, 0x00, 0x00, 0x00
+ , 0x0E, 0x00, 0x20, 0x00, 0x00, 0x00
+ , 0x20, 0x00, 0x48, 0x00, 0x0A, 0x00
+ , 0x21, 0x00, 0x10, 0x00, 0x0B, 0x08
+ , 0x24, 0x00, 0x10, 0x00, 0x05, 0x08
+ , 0x26, 0x00, 0x10, 0x00, 0x01, 0x08
+ , 0x2B, 0x00, 0x10, 0x00, 0x05, 0x08
+ , 0x2C, 0x00, 0x10, 0x00, 0x07, 0x08
+ , 0x2D, 0x00, 0x10, 0x00, 0x05, 0x08
+ , 0x2E, 0x00, 0x10, 0x00, 0x03, 0x08
+ , 0x30, 0x00, 0x84, 0x00, 0x03, 0x00
+ , 0x3A, 0x00, 0x10, 0x00, 0x07, 0x08
+ , 0x3B, 0x00, 0x10, 0x00, 0x0B, 0x08
+ , 0x40, 0x00, 0x10, 0x00, 0x01, 0x08
+ , 0x41, 0x00, 0x81, 0x01, 0x01, 0x00
+ , 0x47, 0x00, 0x01, 0x01, 0x01, 0x00
+ , 0x5B, 0x00, 0x10, 0x00, 0x0B, 0x08
+ , 0x61, 0x00, 0x82, 0x01, 0x01, 0x00
+ , 0x67, 0x00, 0x02, 0x01, 0x01, 0x00
+ , 0x7B, 0x00, 0x10, 0x00, 0x0B, 0x08
+ , 0x7F, 0x00, 0x20, 0x00, 0x00, 0x00
+ , 0x80, 0x00, 0x00, 0x00, 0x00, 0x00
+ , 0x40, 0x81, 0x00, 0x01, 0x01, 0x00
+ , 0x40, 0xA1, 0x48, 0x00, 0x0A, 0x00
+ , 0x41, 0xA1, 0x10, 0x00, 0x07, 0x08
+ , 0x42, 0xA1, 0x10, 0x00, 0x0B, 0x08
+ , 0x55, 0xA1, 0x00, 0x00, 0x0B, 0x08
+ , 0xAF, 0xA2, 0x84, 0x00, 0x03, 0x00
+ , 0xB9, 0xA2, 0x00, 0x00, 0x0B, 0x08
+ , 0xCF, 0xA2, 0x81, 0x01, 0x01, 0x00
+ , 0xD5, 0xA2, 0x01, 0x01, 0x01, 0x00
+ , 0xE9, 0xA2, 0x82, 0x01, 0x01, 0x00
+ , 0xEF, 0xA2, 0x02, 0x01, 0x01, 0x00
+ , 0x44, 0xA3, 0x81, 0x01, 0x01, 0x00
+ , 0x46, 0xA3, 0x00, 0x00, 0x0B, 0x08
+ , 0x40, 0xA4, 0x00, 0x01, 0x01, 0x00
+ , 0xA1, 0xC6, 0x00, 0x00, 0x0B, 0x08
+ , 0x40, 0xC9, 0x00, 0x01, 0x01, 0x00
+};
+#endif
+
+static unsigned char NLSALLOC(0404) rgbSENGCOUNTRY[] = {
+ 'T', 'a', 'i', 'w', 'a', 'n'
+};
+
+static unsigned char NLSALLOC(0404) rgbSENGLANGUAGE[] = {
+ 'C', 'h', 'i', 'n', 'e', 's', 'e'
+};
+
+#if defined(VBA2) //hand-edited this locale info based on daytona [bassam]
+static BYTE NLSALLOC(0404) rgbIFIRSTDAYOFWEEK[] = { /* "6" */
+ 0x36
+};
+
+static BYTE NLSALLOC(0404) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0404) rgbIDEFAULTANSICODEPAGE[] = { /* "950" */
+ 0x39, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0404) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0404) rgbSTIMEFORMAT[] = { /* "tt h:mm:ss" */
+ 0x74, 0x74, 0x20, 0x68, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0404) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0404) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0404) rgbIOPTIONALCALENDAR[] = { /* "2" */
+ 0x32
+};
+#endif
+
+
+
+static unsigned char NLSALLOC(0404) rgbILANGUAGE[] = {
+ '0', '4', '0', '4'
+};
+
+static unsigned char NLSALLOC(0404) rgbSLANGUAGE[] = {
+ 0xa4, 0xa4, 0xa4, 0xe5, '(', 'C', 'h', 'i', 'n', 'e', 's', 'e', ' ', 'T', 'r', 'a', 'd', 'i', 't', 'i', 'o', 'n', 'a', 'l', ')'
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVLANGNAME[] = {
+ 'C', 'H', 'T'
+};
+
+static unsigned char NLSALLOC(0404) rgbSNATIVELANGNAME[] = {
+ 0xa4, 0xa4, 0xa4, 0xe5
+};
+
+static unsigned char NLSALLOC(0404) rgbICOUNTRY[] = {
+ '8', '8', '6'
+};
+
+static unsigned char NLSALLOC(0404) rgbSCOUNTRY[] = {
+ 0xa4, 0xa4, 0xb5, 0xd8, 0xa5, 0xc1, 0xb0, 0xea,
+ '(', 'T', 'a', 'i', 'w', 'a', 'n', ')'
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVCTRYNAME[] = {
+ 'T', 'W', 'N'
+};
+
+static unsigned char NLSALLOC(0404) rgbSNATIVECTRYNAME[] = {
+ 0xa4, 0xa4, 0xb5, 0xd8, 0xa5, 0xc1, 0xb0, 0xea
+};
+
+static unsigned char NLSALLOC(0404) rgbIDEFAULTLANGUAGE[] = {
+ '0', '4', '0', '4'
+};
+
+static unsigned char NLSALLOC(0404) rgbIDEFAULTCOUNTRY[] = {
+ '8', '8', '6'
+};
+
+static unsigned char NLSALLOC(0404) rgbIDEFAULTCODEPAGE[] = {
+ '9', '5', '0'
+};
+
+static unsigned char NLSALLOC(0404) rgbSLIST[] = {
+ ','
+};
+
+static unsigned char NLSALLOC(0404) rgbIMEASURE[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0404) rgbSDECIMAL[] = {
+ '.'
+};
+
+static unsigned char NLSALLOC(0404) rgbSTHOUSAND[] = {
+ ','
+};
+
+static unsigned char NLSALLOC(0404) rgbSGROUPING[] = {
+ '3', ';', '0'
+};
+
+static unsigned char NLSALLOC(0404) rgbIDIGITS[] = {
+ '2'
+};
+
+static unsigned char NLSALLOC(0404) rgbILZERO[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0404) rgbSNATIVEDIGITS[] = {
+ '0', '1', '2', '3', '4', '5', '6', '7', '8', '9'
+};
+
+static unsigned char NLSALLOC(0404) rgbSCURRENCY[] = {
+ 'N', 'T', '$'
+};
+
+static unsigned char NLSALLOC(0404) rgbSINTLSYMBOL[] = {
+ 'T', 'W', 'D'
+};
+
+static unsigned char NLSALLOC(0404) rgbSMONDECIMALSEP[] = {
+ '.'
+};
+
+static unsigned char NLSALLOC(0404) rgbSMONTHOUSANDSEP[] = {
+ ','
+};
+
+static unsigned char NLSALLOC(0404) rgbSMONGROUPING[] = {
+ '3', ';', '0'
+};
+
+static unsigned char NLSALLOC(0404) rgbICURRDIGITS[] = {
+ '2'
+};
+
+static unsigned char NLSALLOC(0404) rgbIINTLCURRDIGITS[] = {
+ '2'
+};
+
+static unsigned char NLSALLOC(0404) rgbICURRENCY[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0404) rgbINEGCURR[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0404) rgbSDATE[] = {
+ '/'
+};
+
+static unsigned char NLSALLOC(0404) rgbSTIME[] = {
+ ':'
+};
+
+static unsigned char NLSALLOC(0404) rgbSSHORTDATE[] = {
+ 'y', 'y', 'y', 'y', '/', 'M', '/', 'd'
+};
+
+static unsigned char NLSALLOC(0404) rgbSLONGDATE[] = {
+ 'd', 'd', 'd', 'd', ' ',
+ 'y', 'y', 'y', 'y', ' ',
+ 'M', 'M', ' ',
+ 'd', 'd'
+};
+
+static unsigned char NLSALLOC(0404) rgbIDATE[] = {
+ '2'
+};
+
+static unsigned char NLSALLOC(0404) rgbILDATE[] = {
+ '2'
+};
+
+static unsigned char NLSALLOC(0404) rgbITIME[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0404) rgbICENTURY[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0404) rgbITLZERO[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0404) rgbIDAYLZERO[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0404) rgbIMONLZERO[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0404) rgbS1159[] = {
+ 0xa4, 0x57, 0xa4, 0xc8
+};
+
+static unsigned char NLSALLOC(0404) rgbS2359[] = {
+ 0xa4, 0x55, 0xa4, 0xc8
+};
+
+static unsigned char NLSALLOC(0404) rgbSDAYNAME1[] = {
+ 0xac, 0x50, 0xb4, 0xc1, 0xa4, 0x40
+};
+
+static unsigned char NLSALLOC(0404) rgbSDAYNAME2[] = {
+ 0xac, 0x50, 0xb4, 0xc1, 0xa4, 0x47
+};
+
+static unsigned char NLSALLOC(0404) rgbSDAYNAME3[] = {
+ 0xac, 0x50, 0xb4, 0xc1, 0xa4, 0x54
+};
+
+static unsigned char NLSALLOC(0404) rgbSDAYNAME4[] = {
+ 0xac, 0x50, 0xb4, 0xc1, 0xa5, 0x7c
+};
+
+static unsigned char NLSALLOC(0404) rgbSDAYNAME5[] = {
+ 0xac, 0x50, 0xb4, 0xc1, 0xa4, 0xad
+};
+
+static unsigned char NLSALLOC(0404) rgbSDAYNAME6[] = {
+ 0xac, 0x50, 0xb4, 0xc1, 0xa4, 0xbb
+};
+
+static unsigned char NLSALLOC(0404) rgbSDAYNAME7[] = {
+ 0xac, 0x50, 0xb4, 0xc1, 0xa4, 0xe9
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVDAYNAME1[] = {
+ 0xac, 0x50, 0xb4, 0xc1, 0xa4, 0x40
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVDAYNAME2[] = {
+ 0xac, 0x50, 0xb4, 0xc1, 0xa4, 0x47
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVDAYNAME3[] = {
+ 0xac, 0x50, 0xb4, 0xc1, 0xa4, 0x54
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVDAYNAME4[] = {
+ 0xac, 0x50, 0xb4, 0xc1, 0xa5, 0x7c
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVDAYNAME5[] = {
+ 0xac, 0x50, 0xb4, 0xc1, 0xa4, 0xad
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVDAYNAME6[] = {
+ 0xac, 0x50, 0xb4, 0xc1, 0xa4, 0xbb
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVDAYNAME7[] = {
+ 0xac, 0x50, 0xb4, 0xc1, 0xa4, 0xe9
+};
+
+static unsigned char NLSALLOC(0404) rgbSMONTHNAME1[] = {
+ 0xa4, 0x40, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSMONTHNAME2[] = {
+ 0xa4, 0x47, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSMONTHNAME3[] = {
+ 0xa4, 0x54, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSMONTHNAME4[] = {
+ 0xa5, 0x7c, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSMONTHNAME5[] = {
+ 0xa4, 0xad, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSMONTHNAME6[] = {
+ 0xa4, 0xbb, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSMONTHNAME7[] = {
+ 0xa4, 0x43, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSMONTHNAME8[] = {
+ 0xa4, 0x4b, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSMONTHNAME9[] = {
+ 0xa4, 0x45, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSMONTHNAME10[] = {
+ 0xa4, 0x51, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSMONTHNAME11[] = {
+ 0xa4, 0x51, 0xa4, 0x40, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSMONTHNAME12[] = {
+ 0xa4, 0x51, 0xa4, 0x47, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVMONTHNAME1[] = {
+ 0xa4, 0x40, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVMONTHNAME2[] = {
+ 0xa4, 0x47, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVMONTHNAME3[] = {
+ 0xa4, 0x54, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVMONTHNAME4[] = {
+ 0xa5, 0x7c, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVMONTHNAME5[] = {
+ 0xa4, 0xad, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVMONTHNAME6[] = {
+ 0xa4, 0xbb, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVMONTHNAME7[] = {
+ 0xa4, 0x43, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVMONTHNAME8[] = {
+ 0xa4, 0x4b, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVMONTHNAME9[] = {
+ 0xa4, 0x45, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVMONTHNAME10[] = {
+ 0xa4, 0x51, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVMONTHNAME11[] = {
+ 0xa4, 0x51, 0xa4, 0x40, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSABBREVMONTHNAME12[] = {
+ 0xa4, 0x51, 0xa4, 0x47, 0xa4, 0xeb
+};
+
+static unsigned char NLSALLOC(0404) rgbSNEGATIVESIGN[] = {
+ '-'
+};
+
+static unsigned char NLSALLOC(0404) rgbIPOSSIGNPOSN[] = {
+ '3'
+};
+
+static unsigned char NLSALLOC(0404) rgbINEGSIGNPOSN[] = {
+ '3'
+};
+
+static unsigned char NLSALLOC(0404) rgbIPOSSYMPRECEDES[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0404) rgbIPOSSEPBYSPACE[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0404) rgbINEGSYMPRECEDES[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0404) rgbINEGSEPBYSPACE[] = {
+ '0'
+};
+
+#define LCINFODAT(X) { DIM(X), (X) }
+LCINFO NLSALLOC(0404) g_rglcinfo0404[] = {
+ { 0, NULL}
+ , LCINFODAT(rgbILANGUAGE)
+ , LCINFODAT(rgbSLANGUAGE)
+ , LCINFODAT(rgbSABBREVLANGNAME)
+ , LCINFODAT(rgbSNATIVELANGNAME)
+ , LCINFODAT(rgbICOUNTRY)
+ , LCINFODAT(rgbSCOUNTRY)
+ , LCINFODAT(rgbSABBREVCTRYNAME)
+ , LCINFODAT(rgbSNATIVECTRYNAME)
+ , LCINFODAT(rgbIDEFAULTLANGUAGE)
+ , LCINFODAT(rgbIDEFAULTCOUNTRY)
+ , LCINFODAT(rgbIDEFAULTCODEPAGE)
+ , LCINFODAT(rgbSLIST)
+ , LCINFODAT(rgbIMEASURE)
+ , LCINFODAT(rgbSDECIMAL)
+ , LCINFODAT(rgbSTHOUSAND)
+ , LCINFODAT(rgbSGROUPING)
+ , LCINFODAT(rgbIDIGITS)
+ , LCINFODAT(rgbILZERO)
+ , LCINFODAT(rgbSNATIVEDIGITS)
+ , LCINFODAT(rgbSCURRENCY)
+ , LCINFODAT(rgbSINTLSYMBOL)
+ , LCINFODAT(rgbSMONDECIMALSEP)
+ , LCINFODAT(rgbSMONTHOUSANDSEP)
+ , LCINFODAT(rgbSMONGROUPING)
+ , LCINFODAT(rgbICURRDIGITS)
+ , LCINFODAT(rgbIINTLCURRDIGITS)
+ , LCINFODAT(rgbICURRENCY)
+ , LCINFODAT(rgbINEGCURR)
+ , LCINFODAT(rgbSDATE)
+ , LCINFODAT(rgbSTIME)
+ , LCINFODAT(rgbSSHORTDATE)
+ , LCINFODAT(rgbSLONGDATE)
+ , LCINFODAT(rgbIDATE)
+ , LCINFODAT(rgbILDATE)
+ , LCINFODAT(rgbITIME)
+ , LCINFODAT(rgbICENTURY)
+ , LCINFODAT(rgbITLZERO)
+ , LCINFODAT(rgbIDAYLZERO)
+ , LCINFODAT(rgbIMONLZERO)
+ , LCINFODAT(rgbS1159)
+ , LCINFODAT(rgbS2359)
+ , LCINFODAT(rgbSDAYNAME1)
+ , LCINFODAT(rgbSDAYNAME2)
+ , LCINFODAT(rgbSDAYNAME3)
+ , LCINFODAT(rgbSDAYNAME4)
+ , LCINFODAT(rgbSDAYNAME5)
+ , LCINFODAT(rgbSDAYNAME6)
+ , LCINFODAT(rgbSDAYNAME7)
+ , LCINFODAT(rgbSABBREVDAYNAME1)
+ , LCINFODAT(rgbSABBREVDAYNAME2)
+ , LCINFODAT(rgbSABBREVDAYNAME3)
+ , LCINFODAT(rgbSABBREVDAYNAME4)
+ , LCINFODAT(rgbSABBREVDAYNAME5)
+ , LCINFODAT(rgbSABBREVDAYNAME6)
+ , LCINFODAT(rgbSABBREVDAYNAME7)
+ , LCINFODAT(rgbSMONTHNAME1)
+ , LCINFODAT(rgbSMONTHNAME2)
+ , LCINFODAT(rgbSMONTHNAME3)
+ , LCINFODAT(rgbSMONTHNAME4)
+ , LCINFODAT(rgbSMONTHNAME5)
+ , LCINFODAT(rgbSMONTHNAME6)
+ , LCINFODAT(rgbSMONTHNAME7)
+ , LCINFODAT(rgbSMONTHNAME8)
+ , LCINFODAT(rgbSMONTHNAME9)
+ , LCINFODAT(rgbSMONTHNAME10)
+ , LCINFODAT(rgbSMONTHNAME11)
+ , LCINFODAT(rgbSMONTHNAME12)
+ , LCINFODAT(rgbSABBREVMONTHNAME1)
+ , LCINFODAT(rgbSABBREVMONTHNAME2)
+ , LCINFODAT(rgbSABBREVMONTHNAME3)
+ , LCINFODAT(rgbSABBREVMONTHNAME4)
+ , LCINFODAT(rgbSABBREVMONTHNAME5)
+ , LCINFODAT(rgbSABBREVMONTHNAME6)
+ , LCINFODAT(rgbSABBREVMONTHNAME7)
+ , LCINFODAT(rgbSABBREVMONTHNAME8)
+ , LCINFODAT(rgbSABBREVMONTHNAME9)
+ , LCINFODAT(rgbSABBREVMONTHNAME10)
+ , LCINFODAT(rgbSABBREVMONTHNAME11)
+ , LCINFODAT(rgbSABBREVMONTHNAME12)
+ , { 0, NULL }
+ , LCINFODAT(rgbSNEGATIVESIGN)
+ , LCINFODAT(rgbIPOSSIGNPOSN)
+ , LCINFODAT(rgbINEGSIGNPOSN)
+ , LCINFODAT(rgbIPOSSYMPRECEDES)
+ , LCINFODAT(rgbIPOSSEPBYSPACE)
+ , LCINFODAT(rgbINEGSYMPRECEDES)
+ , LCINFODAT(rgbINEGSEPBYSPACE)
+ , LCINFODAT(rgbSENGCOUNTRY)
+ , LCINFODAT(rgbSENGLANGUAGE)
+#if defined(VBA2)
+ , LCINFODAT(rgbIFIRSTDAYOFWEEK)
+ , LCINFODAT(rgbIFIRSTWEEKOFYEAR)
+ , LCINFODAT(rgbIDEFAULTANSICODEPAGE)
+ , LCINFODAT(rgbINEGNUMBER)
+ , LCINFODAT(rgbSTIMEFORMAT)
+ , LCINFODAT(rgbITIMEMARKPOSN)
+ , LCINFODAT(rgbICALENDARTYPE)
+ , LCINFODAT(rgbIOPTIONALCALENDAR)
+ , { 0, NULL }
+ , { 0, NULL }
+#endif
+
+};
+#undef LCINFODAT
+
+
+#if 1
+STRINFO_KTP NLSALLOC(0404) g_strinfo0404 = {
+ rgsortweight
+ , rgmaptable
+ , rgtypetable
+ , DIM(rgsortweight)
+ , DIM(rgmaptable)
+ , DIM(rgtypetable)
+};
+#else
+STRINFO_KTP NLSALLOC(0404) g_strinfo0404 = {
+ (SORTWEIGHT FAR*) rgsortweight
+ , (MAPTABLE FAR*) rgmaptable
+ , (TYPETABLE FAR*) rgtypetable
+ , DIM(rgsortweight)
+ , DIM(rgmaptable)
+ , DIM(rgtypetable)
+};
+#endif
diff --git a/private/oleauto/src/dispatch/win16/0405.c b/private/oleauto/src/dispatch/win16/0405.c
new file mode 100644
index 000000000..4cdb8f69d
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0405.c
@@ -0,0 +1,711 @@
+/****************************************************************************
+* 0405.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Czech - Czech Republic
+*
+* LCID = 0x0405
+*
+* CodePage = 1250
+*
+* Generated: Thu Dec 01 18:04:22 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+WORD NLSALLOC(0405) rgwSort_0405[256] = {
+ 0x0000, 0xc007, 0xc008, 0xc009, 0xc00a, 0xc00b, 0xc00c, 0xc00d
+ , 0xc00e, 0x402f, 0x4030, 0x4031, 0x4032, 0x4033, 0xc00f, 0xc010
+ , 0xc011, 0xc012, 0xc013, 0xc014, 0xc015, 0xc016, 0xc017, 0xc018
+ , 0xc019, 0xc01a, 0xc01b, 0xc01c, 0xc01d, 0xc01e, 0xc01f, 0xc020
+ , 0x402d, 0x4034, 0x4035, 0x4036, 0x4037, 0x4038, 0x4039, 0xc028
+ , 0x403a, 0x403b, 0x403c, 0x405e, 0x403d, 0xc029, 0x403e, 0x403f
+ , 0x0075, 0x0076, 0x0077, 0x0078, 0x0079, 0x007a, 0x007b, 0x007c
+ , 0x007d, 0x007e, 0x4040, 0x4041, 0x405f, 0x4060, 0x4061, 0x4042
+ , 0x4043, 0x087f, 0x0880, 0x0006, 0x0883, 0x0884, 0x0885, 0x0886
+ , 0x0887, 0x0889, 0x088a, 0x088b, 0x088c, 0x088d, 0x088e, 0x088f
+ , 0x0890, 0x0891, 0x0892, 0x0894, 0x0896, 0x0898, 0x0899, 0x089a
+ , 0x089b, 0x089c, 0x089d, 0x4044, 0x4045, 0x4046, 0x4047, 0x4048
+ , 0x4049, 0x007f, 0x0080, 0x0306, 0x0083, 0x0084, 0x0085, 0x0086
+ , 0x0087, 0x0089, 0x008a, 0x008b, 0x008c, 0x008d, 0x008e, 0x008f
+ , 0x0090, 0x0091, 0x0092, 0x0094, 0x0096, 0x0098, 0x0099, 0x009a
+ , 0x009b, 0x009c, 0x009d, 0x404a, 0x404b, 0x404c, 0x404d, 0xc021
+ , 0xc022, 0xc023, 0x4058, 0xc024, 0x405b, 0x4073, 0x4070, 0x4071
+ , 0xc025, 0x4074, 0x0895, 0x405c, 0x0894, 0x0996, 0x089e, 0x0a9d
+ , 0xc026, 0x4056, 0x4057, 0x4059, 0x405a, 0x4072, 0xc02b, 0xc02c
+ , 0xc027, 0x0897, 0x0095, 0x405d, 0x0094, 0x0196, 0x009e, 0x029d
+ , 0x402e, 0x4052, 0x4152, 0x0b8c, 0x4067, 0x0d7f, 0x404e, 0x4068
+ , 0x404f, 0x4069, 0x0994, 0x4063, 0x406a, 0xc02a, 0x406b, 0x099d
+ , 0x406c, 0x4062, 0x4054, 0x038c, 0x4050, 0x406d, 0x406e, 0x406f
+ , 0x4051, 0x057f, 0x0194, 0x4064, 0x0a8c, 0x4055, 0x028c, 0x019d
+ , 0x0992, 0x0a7f, 0x0b7f, 0x0c7f, 0x097f, 0x098c, 0x0981, 0x0a81
+ , 0x0882, 0x0a84, 0x0c84, 0x0984, 0x0b84, 0x0989, 0x0a89, 0x0983
+ , 0x0a83, 0x098e, 0x0a8e, 0x0a8f, 0x0b8f, 0x0c8f, 0x098f, 0x4065
+ , 0x0893, 0x0b98, 0x0a98, 0x0c98, 0x0998, 0x099c, 0x0a96, 0x0005
+ , 0x0192, 0x027f, 0x037f, 0x047f, 0x017f, 0x018c, 0x0181, 0x0281
+ , 0x0082, 0x0284, 0x0484, 0x0184, 0x0384, 0x0189, 0x0289, 0x0183
+ , 0x0283, 0x018e, 0x028e, 0x028f, 0x038f, 0x048f, 0x018f, 0x4066
+ , 0x0093, 0x0398, 0x0298, 0x0498, 0x0198, 0x019c, 0x0296, 0x4053
+};
+
+DIGRAPH NLSALLOC(0405) rgdig_0405[5] = {
+ { 0x0881, 0x02 }
+ , { 0x1088, 0x48 }
+ , { 0x0888, 0x68 }
+ , { 0x0081, 0x02 }
+ , { 0x0088, 0x68 }
+};
+
+EXPANSION NLSALLOC(0405) rgexp_0405[1] = {
+ { 0x0094, 0x0094 }
+};
+
+WORD NLSALLOC(0405) rgwCType12_0405[256] = {
+ 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x9068, 0x0028, 0x0028, 0x0028, 0x0028, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0xa048, 0xb010, 0xb010, 0x5010, 0x5010, 0x5010, 0x1010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0x5010, 0x7010, 0x5010, 0x4010, 0x4010
+ , 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084
+ , 0x3084, 0x3084, 0x7010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010, 0x0020
+ , 0x0020, 0x0020, 0xb010, 0x0020, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x0020, 0x5010, 0x1101, 0xb010, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x0020, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x0020, 0xb010, 0x1102, 0xb010, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0xa048, 0x1010, 0x1010, 0x1101, 0x5010, 0x1101, 0xb010, 0xb010
+ , 0xb010, 0xb010, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0x1101
+ , 0x5010, 0x5010, 0x1010, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x1102, 0x1102, 0xb010, 0x1101, 0x1010, 0x1102, 0x1102
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0xb010
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0xb010
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1010
+};
+
+WORD NLSALLOC(0405) rgwCType3_0405[256] = {
+ 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0008, 0x0008, 0x0008, 0x0008, 0x0008, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0048, 0x0048, 0x0448, 0x0048, 0x0448, 0x0048, 0x0048, 0x0440
+ , 0x0048, 0x0048, 0x0048, 0x0048, 0x0048, 0x0440, 0x0048, 0x0448
+ , 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040
+ , 0x0040, 0x0040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0048, 0x0048
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0448, 0x0048, 0x0448, 0x0448
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0000
+ , 0x0000, 0x0000, 0x0008, 0x0000, 0x0008, 0x0008, 0x0008, 0x0008
+ , 0x0000, 0x0008, 0x8003, 0x0008, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x0000, 0x0088, 0x0088, 0x0088, 0x0088, 0x0008, 0x0400, 0x0400
+ , 0x0000, 0x0000, 0x8003, 0x0008, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x0008, 0x0401, 0x0408, 0x8003, 0x0008, 0x8003, 0x0048, 0x0008
+ , 0x0408, 0x0008, 0x8003, 0x0008, 0x0048, 0x0408, 0x0008, 0x8003
+ , 0x0008, 0x0008, 0x0408, 0x8003, 0x0408, 0x0008, 0x0008, 0x0008
+ , 0x0408, 0x8003, 0x8003, 0x0008, 0x8003, 0x0408, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0408
+};
+
+BYTE NLSALLOC(0405) rgbUCase_0405[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x8a, 0x9b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xa3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xa5, 0xaa, 0xbb, 0xbc, 0xbd, 0xbc, 0xaf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xf7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xff
+};
+
+BYTE NLSALLOC(0405) rgbLCase_0405[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x9a, 0x8b, 0x9c, 0x9d, 0x9e, 0x9f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f
+ , 0xa0, 0xa1, 0xa2, 0xb3, 0xa4, 0xb9, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xba, 0xab, 0xac, 0xad, 0xae, 0xbf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbe, 0xbd, 0xbe, 0xbf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xd7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xdf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
+};
+
+static BYTE NLSALLOC(0405) rgbILANGUAGE[] = { /* "0405" */
+ 0x30, 0x34, 0x30, 0x35
+};
+
+static BYTE NLSALLOC(0405) rgbSLANGUAGE[] = { /* "Czech" */
+ 0x43, 0x7a, 0x65, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVLANGNAME[] = { /* "CSY" */
+ 0x43, 0x53, 0x59
+};
+
+static BYTE NLSALLOC(0405) rgbSNATIVELANGNAME[] = { /* "\x010de\x0161tina" */
+ 0xe8, 0x65, 0x9a, 0x74, 0x69, 0x6e, 0x61
+};
+
+static BYTE NLSALLOC(0405) rgbICOUNTRY[] = { /* "42" */
+ 0x34, 0x32
+};
+
+static BYTE NLSALLOC(0405) rgbSCOUNTRY[] = { /* "Czech Republic" */
+ 0x43, 0x7a, 0x65, 0x63, 0x68, 0x20, 0x52, 0x65
+ , 0x70, 0x75, 0x62, 0x6c, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVCTRYNAME[] = { /* "CZE" */
+ 0x43, 0x5a, 0x45
+};
+
+static BYTE NLSALLOC(0405) rgbSNATIVECTRYNAME[] = { /* "\x010cesk\x00e1\x0020republika" */
+ 0xc8, 0x65, 0x73, 0x6b, 0xe1, 0x20, 0x72, 0x65
+ , 0x70, 0x75, 0x62, 0x6c, 0x69, 0x6b, 0x61
+};
+
+static BYTE NLSALLOC(0405) rgbIDEFAULTLANGUAGE[] = { /* "0405" */
+ 0x30, 0x34, 0x30, 0x35
+};
+
+static BYTE NLSALLOC(0405) rgbIDEFAULTCOUNTRY[] = { /* "42" */
+ 0x34, 0x32
+};
+
+static BYTE NLSALLOC(0405) rgbIDEFAULTCODEPAGE[] = { /* "852" */
+ 0x38, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0405) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0405) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0405) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0405) rgbSTHOUSAND[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(0405) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0405) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0405) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0405) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0405) rgbSCURRENCY[] = { /* "K\x010d" */
+ 0x4b, 0xe8
+};
+
+static BYTE NLSALLOC(0405) rgbSINTLSYMBOL[] = { /* "CZK" */
+ 0x43, 0x5a, 0x4b
+};
+
+static BYTE NLSALLOC(0405) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0405) rgbSMONTHOUSANDSEP[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(0405) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0405) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0405) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0405) rgbICURRENCY[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0405) rgbINEGCURR[] = { /* "8" */
+ 0x38
+};
+
+static BYTE NLSALLOC(0405) rgbSDATE[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0405) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0405) rgbSSHORTDATE[] = { /* "d.M.yyyy" */
+ 0x64, 0x2e, 0x4d, 0x2e, 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0405) rgbSLONGDATE[] = { /* "d. MMMM yyyy" */
+ 0x64, 0x2e, 0x20, 0x4d, 0x4d, 0x4d, 0x4d, 0x20
+ , 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0405) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0405) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0405) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0405) rgbICENTURY[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0405) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0405) rgbIDAYLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0405) rgbIMONLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0405) rgbS1159[] = { /* "dop." */
+ 0x64, 0x6f, 0x70, 0x2e
+};
+
+static BYTE NLSALLOC(0405) rgbS2359[] = { /* "odp." */
+ 0x6f, 0x64, 0x70, 0x2e
+};
+
+static BYTE NLSALLOC(0405) rgbSDAYNAME1[] = { /* "pond\x011blí" */
+ 0x70, 0x6f, 0x6e, 0x64, 0xec, 0x6c, 0xed
+};
+
+static BYTE NLSALLOC(0405) rgbSDAYNAME2[] = { /* "\x00fater\x00fd" */
+ 0xfa, 0x74, 0x65, 0x72, 0xfd
+};
+
+static BYTE NLSALLOC(0405) rgbSDAYNAME3[] = { /* "st\x0159eda" */
+ 0x73, 0x74, 0xf8, 0x65, 0x64, 0x61
+};
+
+static BYTE NLSALLOC(0405) rgbSDAYNAME4[] = { /* "\x010dtvrtek" */
+ 0xe8, 0x74, 0x76, 0x72, 0x74, 0x65, 0x6b
+};
+
+static BYTE NLSALLOC(0405) rgbSDAYNAME5[] = { /* "pátek" */
+ 0x70, 0xe1, 0x74, 0x65, 0x6b
+};
+
+static BYTE NLSALLOC(0405) rgbSDAYNAME6[] = { /* "sobota" */
+ 0x73, 0x6f, 0x62, 0x6f, 0x74, 0x61
+};
+
+static BYTE NLSALLOC(0405) rgbSDAYNAME7[] = { /* "ned\x011ble" */
+ 0x6e, 0x65, 0x64, 0xec, 0x6c, 0x65
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVDAYNAME1[] = { /* "po" */
+ 0x70, 0x6f
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVDAYNAME2[] = { /* "út" */
+ 0xfa, 0x74
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVDAYNAME3[] = { /* "st" */
+ 0x73, 0x74
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVDAYNAME4[] = { /* "\x010dt" */
+ 0xe8, 0x74
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVDAYNAME5[] = { /* "pá" */
+ 0x70, 0xe1
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVDAYNAME6[] = { /* "so" */
+ 0x73, 0x6f
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVDAYNAME7[] = { /* "ne" */
+ 0x6e, 0x65
+};
+
+static BYTE NLSALLOC(0405) rgbSMONTHNAME1[] = { /* "leden" */
+ 0x6c, 0x65, 0x64, 0x65, 0x6e
+};
+
+static BYTE NLSALLOC(0405) rgbSMONTHNAME2[] = { /* "únor" */
+ 0xfa, 0x6e, 0x6f, 0x72
+};
+
+static BYTE NLSALLOC(0405) rgbSMONTHNAME3[] = { /* "b\x0159ezen" */
+ 0x62, 0xf8, 0x65, 0x7a, 0x65, 0x6e
+};
+
+static BYTE NLSALLOC(0405) rgbSMONTHNAME4[] = { /* "duben" */
+ 0x64, 0x75, 0x62, 0x65, 0x6e
+};
+
+static BYTE NLSALLOC(0405) rgbSMONTHNAME5[] = { /* "kv\x011bten" */
+ 0x6b, 0x76, 0xec, 0x74, 0x65, 0x6e
+};
+
+static BYTE NLSALLOC(0405) rgbSMONTHNAME6[] = { /* "\x010derven" */
+ 0xe8, 0x65, 0x72, 0x76, 0x65, 0x6e
+};
+
+static BYTE NLSALLOC(0405) rgbSMONTHNAME7[] = { /* "\x010dervenec" */
+ 0xe8, 0x65, 0x72, 0x76, 0x65, 0x6e, 0x65, 0x63
+};
+
+static BYTE NLSALLOC(0405) rgbSMONTHNAME8[] = { /* "srpen" */
+ 0x73, 0x72, 0x70, 0x65, 0x6e
+};
+
+static BYTE NLSALLOC(0405) rgbSMONTHNAME9[] = { /* "z\x00e1\x0159\x00ed" */
+ 0x7a, 0xe1, 0xf8, 0xed
+};
+
+static BYTE NLSALLOC(0405) rgbSMONTHNAME10[] = { /* "\x0159\x00edjen" */
+ 0xf8, 0xed, 0x6a, 0x65, 0x6e
+};
+
+static BYTE NLSALLOC(0405) rgbSMONTHNAME11[] = { /* "listopad" */
+ 0x6c, 0x69, 0x73, 0x74, 0x6f, 0x70, 0x61, 0x64
+};
+
+static BYTE NLSALLOC(0405) rgbSMONTHNAME12[] = { /* "prosinec" */
+ 0x70, 0x72, 0x6f, 0x73, 0x69, 0x6e, 0x65, 0x63
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVMONTHNAME1[] = { /* "I" */
+ 0x49
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVMONTHNAME2[] = { /* "II" */
+ 0x49, 0x49
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVMONTHNAME3[] = { /* "III" */
+ 0x49, 0x49, 0x49
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVMONTHNAME4[] = { /* "IV" */
+ 0x49, 0x56
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVMONTHNAME5[] = { /* "V" */
+ 0x56
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVMONTHNAME6[] = { /* "VI" */
+ 0x56, 0x49
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVMONTHNAME7[] = { /* "VII" */
+ 0x56, 0x49, 0x49
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVMONTHNAME8[] = { /* "VIII" */
+ 0x56, 0x49, 0x49, 0x49
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVMONTHNAME9[] = { /* "IX" */
+ 0x49, 0x58
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVMONTHNAME10[] = { /* "X" */
+ 0x58
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVMONTHNAME11[] = { /* "XI" */
+ 0x58, 0x49
+};
+
+static BYTE NLSALLOC(0405) rgbSABBREVMONTHNAME12[] = { /* "XII" */
+ 0x58, 0x49, 0x49
+};
+
+static BYTE NLSALLOC(0405) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0405) rgbIPOSSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0405) rgbINEGSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0405) rgbIPOSSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0405) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0405) rgbINEGSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0405) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0405) rgbSENGCOUNTRY[] = { /* "Czech Republic" */
+ 0x43, 0x7a, 0x65, 0x63, 0x68, 0x20, 0x52, 0x65
+ , 0x70, 0x75, 0x62, 0x6c, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(0405) rgbSENGLANGUAGE[] = { /* "Czech" */
+ 0x43, 0x7a, 0x65, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(0405) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0405) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0405) rgbIDEFAULTANSICODEPAGE[] = { /* "1250" */
+ 0x31, 0x32, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0405) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0405) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0405) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0405) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0405) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0405) g_rglcinfo0405[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 5, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 14, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 15, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 2, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 12, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 4, rgbS1159 }
+ , { 4, rgbS2359 }
+ , { 7, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 6, rgbSDAYNAME3 }
+ , { 7, rgbSDAYNAME4 }
+ , { 5, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 2, rgbSABBREVDAYNAME1 }
+ , { 2, rgbSABBREVDAYNAME2 }
+ , { 2, rgbSABBREVDAYNAME3 }
+ , { 2, rgbSABBREVDAYNAME4 }
+ , { 2, rgbSABBREVDAYNAME5 }
+ , { 2, rgbSABBREVDAYNAME6 }
+ , { 2, rgbSABBREVDAYNAME7 }
+ , { 5, rgbSMONTHNAME1 }
+ , { 4, rgbSMONTHNAME2 }
+ , { 6, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 6, rgbSMONTHNAME5 }
+ , { 6, rgbSMONTHNAME6 }
+ , { 8, rgbSMONTHNAME7 }
+ , { 5, rgbSMONTHNAME8 }
+ , { 4, rgbSMONTHNAME9 }
+ , { 5, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 1, rgbSABBREVMONTHNAME1 }
+ , { 2, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 2, rgbSABBREVMONTHNAME4 }
+ , { 1, rgbSABBREVMONTHNAME5 }
+ , { 2, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 4, rgbSABBREVMONTHNAME8 }
+ , { 2, rgbSABBREVMONTHNAME9 }
+ , { 1, rgbSABBREVMONTHNAME10 }
+ , { 2, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 14, rgbSENGCOUNTRY }
+ , { 5, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0405) g_strinfo0405 = {
+ rgbUCase_0405
+ , rgbLCase_0405
+ , rgwCType12_0405
+ , rgwCType3_0405
+ , rgwSort_0405
+ , rgexp_0405
+ , rgdig_0405
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0406.c b/private/oleauto/src/dispatch/win16/0406.c
new file mode 100644
index 000000000..e6dd8a0f9
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0406.c
@@ -0,0 +1,705 @@
+/****************************************************************************
+* 0406.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Danish - Denmark
+*
+* LCID = 0x0406
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:56:23 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+WORD NLSALLOC(0406) rgwSort_0406[256] = {
+ 0x0000, 0xc007, 0xc008, 0xc009, 0xc00a, 0xc00b, 0xc00c, 0xc00d
+ , 0xc00e, 0x4031, 0x4032, 0x4033, 0x4034, 0x4035, 0xc00f, 0xc010
+ , 0xc011, 0xc012, 0xc013, 0xc014, 0xc015, 0xc016, 0xc017, 0xc018
+ , 0xc019, 0xc01a, 0xc01b, 0xc01c, 0xc01d, 0xc01e, 0xc01f, 0xc020
+ , 0x402f, 0x4036, 0x4037, 0x4038, 0x4039, 0x403a, 0x403b, 0xc02a
+ , 0x403c, 0x403d, 0x403e, 0x4060, 0x403f, 0xc02b, 0x4040, 0x4041
+ , 0x007a, 0x007e, 0x007f, 0x0080, 0x0081, 0x0082, 0x0083, 0x0084
+ , 0x0085, 0x0086, 0x4042, 0x4043, 0x4061, 0x4062, 0x4063, 0x4044
+ , 0x4045, 0x0006, 0x1088, 0x1089, 0x108a, 0x108b, 0x108c, 0x108d
+ , 0x108e, 0x108f, 0x1090, 0x1091, 0x1092, 0x1093, 0x1094, 0x1095
+ , 0x1096, 0x1097, 0x1098, 0x1099, 0x109a, 0x109c, 0x109d, 0x109e
+ , 0x109f, 0x10a0, 0x10a1, 0x4046, 0x4047, 0x4048, 0x4049, 0x404a
+ , 0x404b, 0x0306, 0x0088, 0x0089, 0x008a, 0x008b, 0x008c, 0x008d
+ , 0x008e, 0x008f, 0x0090, 0x0091, 0x0092, 0x0093, 0x0094, 0x0095
+ , 0x0096, 0x0097, 0x0098, 0x0099, 0x009a, 0x009c, 0x009d, 0x009e
+ , 0x009f, 0x00a0, 0x00a1, 0x404c, 0x404d, 0x404e, 0x404f, 0xc021
+ , 0xc022, 0xc023, 0x405a, 0x018c, 0x405d, 0x4078, 0x4075, 0x4076
+ , 0x4149, 0x4079, 0x1199, 0x405e, 0x0305, 0xc024, 0xc025, 0xc026
+ , 0xc027, 0x4058, 0x4059, 0x405b, 0x405c, 0x4077, 0xc02d, 0xc02e
+ , 0x4057, 0x109b, 0x0199, 0x405f, 0x0405, 0xc028, 0xc029, 0x12a0
+ , 0x4030, 0x4050, 0x4069, 0x406a, 0x406b, 0x406c, 0x4051, 0x406d
+ , 0x4052, 0x406e, 0x0887, 0x4065, 0x406f, 0xc02c, 0x4070, 0x4053
+ , 0x4071, 0x4064, 0x087f, 0x0880, 0x4054, 0x4072, 0x4073, 0x4074
+ , 0x4055, 0x087e, 0x0995, 0x4066, 0x007b, 0x007c, 0x007d, 0x4056
+ , 0x1287, 0x1187, 0x1387, 0x1487, 0x11a2, 0x10a4, 0x10a2, 0x1189
+ , 0x128b, 0x118b, 0x138b, 0x148b, 0x128f, 0x118f, 0x138f, 0x148f
+ , 0x118a, 0x1194, 0x1395, 0x1295, 0x1495, 0x1595, 0x10a3, 0x4067
+ , 0x10a3, 0x129c, 0x119c, 0x139c, 0x13a0, 0x11a0, 0x0005, 0x0105
+ , 0x0287, 0x0187, 0x0387, 0x0487, 0x01a2, 0x00a4, 0x00a2, 0x0189
+ , 0x028b, 0x018b, 0x038b, 0x048b, 0x028f, 0x018f, 0x038f, 0x048f
+ , 0x018a, 0x0194, 0x0395, 0x0295, 0x0495, 0x0595, 0x00a3, 0x4068
+ , 0x00a3, 0x029c, 0x019c, 0x039c, 0x03a0, 0x01a0, 0x0205, 0x02a0
+};
+
+DIGRAPH NLSALLOC(0406) rgdig_0406[5] = {
+ { 0x1087, 0x02 }
+ , { 0x19a4, 0x41 }
+ , { 0x11a4, 0x61 }
+ , { 0x0087, 0x02 }
+ , { 0x01a4, 0x61 }
+};
+
+EXPANSION NLSALLOC(0406) rgexp_0406[5] = {
+ { 0x109a, 0x108e }
+ , { 0x0099, 0x0099 }
+ , { 0x009a, 0x008e }
+ , { 0x1095, 0x108b }
+ , { 0x0095, 0x008b }
+};
+
+WORD NLSALLOC(0406) rgwCType12_0406[256] = {
+ 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x9068, 0x0028, 0x0028, 0x0028, 0x0028, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0xa048, 0xb010, 0xb010, 0x5010, 0x5010, 0x5010, 0x1010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0x5010, 0x7010, 0x5010, 0x4010, 0x4010
+ , 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084
+ , 0x3084, 0x3084, 0x7010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010, 0x0020
+ , 0x0020, 0x0020, 0xb010, 0x1112, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x5010, 0x1101, 0xb010, 0x1101, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0xb010, 0x1102, 0xb010, 0x1102, 0x0020, 0x0020, 0x1101
+ , 0xa048, 0xb010, 0x5010, 0x5010, 0x5010, 0x5010, 0xb010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x5010, 0x5010, 0x3014, 0x3014, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x3014, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0xb010
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0xb010
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+};
+
+WORD NLSALLOC(0406) rgwCType3_0406[256] = {
+ 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0008, 0x0008, 0x0008, 0x0008, 0x0008, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0048, 0x0048, 0x0448, 0x0048, 0x0448, 0x0048, 0x0048, 0x0440
+ , 0x0048, 0x0048, 0x0048, 0x0048, 0x0048, 0x0440, 0x0048, 0x0448
+ , 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040
+ , 0x0040, 0x0040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0048, 0x0048
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0448, 0x0048, 0x0448, 0x0448
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0000
+ , 0x0000, 0x0000, 0x0008, 0x8000, 0x0008, 0x0008, 0x0008, 0x0008
+ , 0x0001, 0x0008, 0x8003, 0x0008, 0x8000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0088, 0x0088, 0x0088, 0x0088, 0x0008, 0x0400, 0x0400
+ , 0x0408, 0x0000, 0x8003, 0x0008, 0x8000, 0x0000, 0x0000, 0x8003
+ , 0x0008, 0x0008, 0x0048, 0x0048, 0x0008, 0x0048, 0x0048, 0x0008
+ , 0x0408, 0x0008, 0x0400, 0x0008, 0x0048, 0x0408, 0x0008, 0x0448
+ , 0x0008, 0x0008, 0x0000, 0x0000, 0x0408, 0x0008, 0x0008, 0x0008
+ , 0x0408, 0x0000, 0x0400, 0x0008, 0x0000, 0x0000, 0x0000, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8000, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8000
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8000, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+};
+
+BYTE NLSALLOC(0406) rgbUCase_0406[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x8a, 0x9b, 0x8c, 0x9d, 0x9e, 0x9f
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xf7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0x9f
+};
+
+BYTE NLSALLOC(0406) rgbLCase_0406[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x9a, 0x8b, 0x9c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0xff
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xd7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xdf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
+};
+
+static BYTE NLSALLOC(0406) rgbILANGUAGE[] = { /* "0406" */
+ 0x30, 0x34, 0x30, 0x36
+};
+
+static BYTE NLSALLOC(0406) rgbSLANGUAGE[] = { /* "Danish" */
+ 0x44, 0x61, 0x6e, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVLANGNAME[] = { /* "DAN" */
+ 0x44, 0x41, 0x4e
+};
+
+static BYTE NLSALLOC(0406) rgbSNATIVELANGNAME[] = { /* "dansk" */
+ 0x64, 0x61, 0x6e, 0x73, 0x6b
+};
+
+static BYTE NLSALLOC(0406) rgbICOUNTRY[] = { /* "45" */
+ 0x34, 0x35
+};
+
+static BYTE NLSALLOC(0406) rgbSCOUNTRY[] = { /* "Denmark" */
+ 0x44, 0x65, 0x6e, 0x6d, 0x61, 0x72, 0x6b
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVCTRYNAME[] = { /* "DNK" */
+ 0x44, 0x4e, 0x4b
+};
+
+static BYTE NLSALLOC(0406) rgbSNATIVECTRYNAME[] = { /* "Danmark" */
+ 0x44, 0x61, 0x6e, 0x6d, 0x61, 0x72, 0x6b
+};
+
+static BYTE NLSALLOC(0406) rgbIDEFAULTLANGUAGE[] = { /* "0406" */
+ 0x30, 0x34, 0x30, 0x36
+};
+
+static BYTE NLSALLOC(0406) rgbIDEFAULTCOUNTRY[] = { /* "45" */
+ 0x34, 0x35
+};
+
+static BYTE NLSALLOC(0406) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0406) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0406) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0406) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0406) rgbSTHOUSAND[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0406) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0406) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0406) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0406) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0406) rgbSCURRENCY[] = { /* "kr" */
+ 0x6b, 0x72
+};
+
+static BYTE NLSALLOC(0406) rgbSINTLSYMBOL[] = { /* "DKK" */
+ 0x44, 0x4b, 0x4b
+};
+
+static BYTE NLSALLOC(0406) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0406) rgbSMONTHOUSANDSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0406) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0406) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0406) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0406) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0406) rgbINEGCURR[] = { /* "12" */
+ 0x31, 0x32
+};
+
+static BYTE NLSALLOC(0406) rgbSDATE[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0406) rgbSTIME[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0406) rgbSSHORTDATE[] = { /* "dd-MM-yy" */
+ 0x64, 0x64, 0x2d, 0x4d, 0x4d, 0x2d, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0406) rgbSLONGDATE[] = { /* "d. MMMM yyyy" */
+ 0x64, 0x2e, 0x20, 0x4d, 0x4d, 0x4d, 0x4d, 0x20
+ , 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0406) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0406) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0406) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0406) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0406) rgbITLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0406) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0406) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0406) rgbSDAYNAME1[] = { /* "mandag" */
+ 0x6d, 0x61, 0x6e, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0406) rgbSDAYNAME2[] = { /* "tirsdag" */
+ 0x74, 0x69, 0x72, 0x73, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0406) rgbSDAYNAME3[] = { /* "onsdag" */
+ 0x6f, 0x6e, 0x73, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0406) rgbSDAYNAME4[] = { /* "torsdag" */
+ 0x74, 0x6f, 0x72, 0x73, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0406) rgbSDAYNAME5[] = { /* "fredag" */
+ 0x66, 0x72, 0x65, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0406) rgbSDAYNAME6[] = { /* "lørdag" */
+ 0x6c, 0xf8, 0x72, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0406) rgbSDAYNAME7[] = { /* "søndag" */
+ 0x73, 0xf8, 0x6e, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVDAYNAME1[] = { /* "ma" */
+ 0x6d, 0x61
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVDAYNAME2[] = { /* "ti" */
+ 0x74, 0x69
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVDAYNAME3[] = { /* "on" */
+ 0x6f, 0x6e
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVDAYNAME4[] = { /* "to" */
+ 0x74, 0x6f
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVDAYNAME5[] = { /* "fr" */
+ 0x66, 0x72
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVDAYNAME6[] = { /* "lø" */
+ 0x6c, 0xf8
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVDAYNAME7[] = { /* "sø" */
+ 0x73, 0xf8
+};
+
+static BYTE NLSALLOC(0406) rgbSMONTHNAME1[] = { /* "januar" */
+ 0x6a, 0x61, 0x6e, 0x75, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0406) rgbSMONTHNAME2[] = { /* "februar" */
+ 0x66, 0x65, 0x62, 0x72, 0x75, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0406) rgbSMONTHNAME3[] = { /* "marts" */
+ 0x6d, 0x61, 0x72, 0x74, 0x73
+};
+
+static BYTE NLSALLOC(0406) rgbSMONTHNAME4[] = { /* "april" */
+ 0x61, 0x70, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(0406) rgbSMONTHNAME5[] = { /* "maj" */
+ 0x6d, 0x61, 0x6a
+};
+
+static BYTE NLSALLOC(0406) rgbSMONTHNAME6[] = { /* "juni" */
+ 0x6a, 0x75, 0x6e, 0x69
+};
+
+static BYTE NLSALLOC(0406) rgbSMONTHNAME7[] = { /* "juli" */
+ 0x6a, 0x75, 0x6c, 0x69
+};
+
+static BYTE NLSALLOC(0406) rgbSMONTHNAME8[] = { /* "august" */
+ 0x61, 0x75, 0x67, 0x75, 0x73, 0x74
+};
+
+static BYTE NLSALLOC(0406) rgbSMONTHNAME9[] = { /* "september" */
+ 0x73, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x65
+ , 0x72
+};
+
+static BYTE NLSALLOC(0406) rgbSMONTHNAME10[] = { /* "oktober" */
+ 0x6f, 0x6b, 0x74, 0x6f, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0406) rgbSMONTHNAME11[] = { /* "november" */
+ 0x6e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0406) rgbSMONTHNAME12[] = { /* "december" */
+ 0x64, 0x65, 0x63, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVMONTHNAME1[] = { /* "jan" */
+ 0x6a, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVMONTHNAME2[] = { /* "feb" */
+ 0x66, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVMONTHNAME3[] = { /* "mar" */
+ 0x6d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVMONTHNAME4[] = { /* "apr" */
+ 0x61, 0x70, 0x72
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVMONTHNAME5[] = { /* "maj" */
+ 0x6d, 0x61, 0x6a
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVMONTHNAME6[] = { /* "jun" */
+ 0x6a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVMONTHNAME7[] = { /* "jul" */
+ 0x6a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVMONTHNAME8[] = { /* "aug" */
+ 0x61, 0x75, 0x67
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVMONTHNAME9[] = { /* "sep" */
+ 0x73, 0x65, 0x70
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVMONTHNAME10[] = { /* "okt" */
+ 0x6f, 0x6b, 0x74
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVMONTHNAME11[] = { /* "nov" */
+ 0x6e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(0406) rgbSABBREVMONTHNAME12[] = { /* "dec" */
+ 0x64, 0x65, 0x63
+};
+
+static BYTE NLSALLOC(0406) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0406) rgbIPOSSIGNPOSN[] = { /* "4" */
+ 0x34
+};
+
+static BYTE NLSALLOC(0406) rgbINEGSIGNPOSN[] = { /* "4" */
+ 0x34
+};
+
+static BYTE NLSALLOC(0406) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0406) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0406) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0406) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0406) rgbSENGCOUNTRY[] = { /* "Denmark" */
+ 0x44, 0x65, 0x6e, 0x6d, 0x61, 0x72, 0x6b
+};
+
+static BYTE NLSALLOC(0406) rgbSENGLANGUAGE[] = { /* "Danish" */
+ 0x44, 0x61, 0x6e, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(0406) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0406) rgbIFIRSTWEEKOFYEAR[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0406) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0406) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0406) rgbSTIMEFORMAT[] = { /* "HH.mm.ss" */
+ 0x48, 0x48, 0x2e, 0x6d, 0x6d, 0x2e, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0406) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0406) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0406) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0406) g_rglcinfo0406[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 5, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 7, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 7, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 2, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 2, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 12, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 6, rgbSDAYNAME1 }
+ , { 7, rgbSDAYNAME2 }
+ , { 6, rgbSDAYNAME3 }
+ , { 7, rgbSDAYNAME4 }
+ , { 6, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 2, rgbSABBREVDAYNAME1 }
+ , { 2, rgbSABBREVDAYNAME2 }
+ , { 2, rgbSABBREVDAYNAME3 }
+ , { 2, rgbSABBREVDAYNAME4 }
+ , { 2, rgbSABBREVDAYNAME5 }
+ , { 2, rgbSABBREVDAYNAME6 }
+ , { 2, rgbSABBREVDAYNAME7 }
+ , { 6, rgbSMONTHNAME1 }
+ , { 7, rgbSMONTHNAME2 }
+ , { 5, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 7, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 8, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0406) g_strinfo0406 = {
+ rgbUCase_0406
+ , rgbLCase_0406
+ , rgwCType12_0406
+ , rgwCType3_0406
+ , rgwSort_0406
+ , rgexp_0406
+ , rgdig_0406
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0407.c b/private/oleauto/src/dispatch/win16/0407.c
new file mode 100644
index 000000000..d010e8bff
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0407.c
@@ -0,0 +1,524 @@
+/****************************************************************************
+* 0407.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* German - Germany
+*
+* LCID = 0x0407
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:35:18 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0409[256]; // from 0409:English - United States
+extern EXPANSION rgexp_0409[7];
+extern WORD rgwCType12_0409[256];
+extern WORD rgwCType3_0409[256];
+extern BYTE rgbUCase_0409[256];
+extern BYTE rgbLCase_0409[256];
+
+static BYTE NLSALLOC(0407) rgbILANGUAGE[] = { /* "0407" */
+ 0x30, 0x34, 0x30, 0x37
+};
+
+static BYTE NLSALLOC(0407) rgbSLANGUAGE[] = { /* "German" */
+ 0x47, 0x65, 0x72, 0x6d, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVLANGNAME[] = { /* "DEU" */
+ 0x44, 0x45, 0x55
+};
+
+static BYTE NLSALLOC(0407) rgbSNATIVELANGNAME[] = { /* "Deutsch" */
+ 0x44, 0x65, 0x75, 0x74, 0x73, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(0407) rgbICOUNTRY[] = { /* "49" */
+ 0x34, 0x39
+};
+
+static BYTE NLSALLOC(0407) rgbSCOUNTRY[] = { /* "Germany" */
+ 0x47, 0x65, 0x72, 0x6d, 0x61, 0x6e, 0x79
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVCTRYNAME[] = { /* "DEU" */
+ 0x44, 0x45, 0x55
+};
+
+static BYTE NLSALLOC(0407) rgbSNATIVECTRYNAME[] = { /* "Deutschland" */
+ 0x44, 0x65, 0x75, 0x74, 0x73, 0x63, 0x68, 0x6c
+ , 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(0407) rgbIDEFAULTLANGUAGE[] = { /* "0407" */
+ 0x30, 0x34, 0x30, 0x37
+};
+
+static BYTE NLSALLOC(0407) rgbIDEFAULTCOUNTRY[] = { /* "49" */
+ 0x34, 0x39
+};
+
+static BYTE NLSALLOC(0407) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0407) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0407) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0407) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0407) rgbSTHOUSAND[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0407) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0407) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0407) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0407) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0407) rgbSCURRENCY[] = { /* "DM" */
+ 0x44, 0x4d
+};
+
+static BYTE NLSALLOC(0407) rgbSINTLSYMBOL[] = { /* "DEM" */
+ 0x44, 0x45, 0x4d
+};
+
+static BYTE NLSALLOC(0407) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0407) rgbSMONTHOUSANDSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0407) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0407) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0407) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0407) rgbICURRENCY[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0407) rgbINEGCURR[] = { /* "8" */
+ 0x38
+};
+
+static BYTE NLSALLOC(0407) rgbSDATE[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0407) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0407) rgbSSHORTDATE[] = { /* "dd.MM.yy" */
+ 0x64, 0x64, 0x2e, 0x4d, 0x4d, 0x2e, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0407) rgbSLONGDATE[] = { /* "dddd, d. MMMM yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x2c, 0x20, 0x64, 0x2e
+ , 0x20, 0x4d, 0x4d, 0x4d, 0x4d, 0x20, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0407) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0407) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0407) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0407) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0407) rgbITLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0407) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0407) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0407) rgbSDAYNAME1[] = { /* "Montag" */
+ 0x4d, 0x6f, 0x6e, 0x74, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0407) rgbSDAYNAME2[] = { /* "Dienstag" */
+ 0x44, 0x69, 0x65, 0x6e, 0x73, 0x74, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0407) rgbSDAYNAME3[] = { /* "Mittwoch" */
+ 0x4d, 0x69, 0x74, 0x74, 0x77, 0x6f, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(0407) rgbSDAYNAME4[] = { /* "Donnerstag" */
+ 0x44, 0x6f, 0x6e, 0x6e, 0x65, 0x72, 0x73, 0x74
+ , 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0407) rgbSDAYNAME5[] = { /* "Freitag" */
+ 0x46, 0x72, 0x65, 0x69, 0x74, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0407) rgbSDAYNAME6[] = { /* "Samstag" */
+ 0x53, 0x61, 0x6d, 0x73, 0x74, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0407) rgbSDAYNAME7[] = { /* "Sonntag" */
+ 0x53, 0x6f, 0x6e, 0x6e, 0x74, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVDAYNAME1[] = { /* "Mo" */
+ 0x4d, 0x6f
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVDAYNAME2[] = { /* "Di" */
+ 0x44, 0x69
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVDAYNAME3[] = { /* "Mi" */
+ 0x4d, 0x69
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVDAYNAME4[] = { /* "Do" */
+ 0x44, 0x6f
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVDAYNAME5[] = { /* "Fr" */
+ 0x46, 0x72
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVDAYNAME6[] = { /* "Sa" */
+ 0x53, 0x61
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVDAYNAME7[] = { /* "So" */
+ 0x53, 0x6f
+};
+
+static BYTE NLSALLOC(0407) rgbSMONTHNAME1[] = { /* "Januar" */
+ 0x4a, 0x61, 0x6e, 0x75, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0407) rgbSMONTHNAME2[] = { /* "Februar" */
+ 0x46, 0x65, 0x62, 0x72, 0x75, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0407) rgbSMONTHNAME3[] = { /* "März" */
+ 0x4d, 0xe4, 0x72, 0x7a
+};
+
+static BYTE NLSALLOC(0407) rgbSMONTHNAME4[] = { /* "April" */
+ 0x41, 0x70, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(0407) rgbSMONTHNAME5[] = { /* "Mai" */
+ 0x4d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(0407) rgbSMONTHNAME6[] = { /* "Juni" */
+ 0x4a, 0x75, 0x6e, 0x69
+};
+
+static BYTE NLSALLOC(0407) rgbSMONTHNAME7[] = { /* "Juli" */
+ 0x4a, 0x75, 0x6c, 0x69
+};
+
+static BYTE NLSALLOC(0407) rgbSMONTHNAME8[] = { /* "August" */
+ 0x41, 0x75, 0x67, 0x75, 0x73, 0x74
+};
+
+static BYTE NLSALLOC(0407) rgbSMONTHNAME9[] = { /* "September" */
+ 0x53, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x65
+ , 0x72
+};
+
+static BYTE NLSALLOC(0407) rgbSMONTHNAME10[] = { /* "Oktober" */
+ 0x4f, 0x6b, 0x74, 0x6f, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0407) rgbSMONTHNAME11[] = { /* "November" */
+ 0x4e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0407) rgbSMONTHNAME12[] = { /* "Dezember" */
+ 0x44, 0x65, 0x7a, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVMONTHNAME1[] = { /* "Jan" */
+ 0x4a, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVMONTHNAME2[] = { /* "Feb" */
+ 0x46, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVMONTHNAME3[] = { /* "Mrz" */
+ 0x4d, 0x72, 0x7a
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVMONTHNAME4[] = { /* "Apr" */
+ 0x41, 0x70, 0x72
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVMONTHNAME5[] = { /* "Mai" */
+ 0x4d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVMONTHNAME6[] = { /* "Jun" */
+ 0x4a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVMONTHNAME7[] = { /* "Jul" */
+ 0x4a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVMONTHNAME8[] = { /* "Aug" */
+ 0x41, 0x75, 0x67
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVMONTHNAME9[] = { /* "Sep" */
+ 0x53, 0x65, 0x70
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVMONTHNAME10[] = { /* "Okt" */
+ 0x4f, 0x6b, 0x74
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVMONTHNAME11[] = { /* "Nov" */
+ 0x4e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(0407) rgbSABBREVMONTHNAME12[] = { /* "Dez" */
+ 0x44, 0x65, 0x7a
+};
+
+static BYTE NLSALLOC(0407) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0407) rgbIPOSSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0407) rgbINEGSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0407) rgbIPOSSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0407) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0407) rgbINEGSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0407) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0407) rgbSENGCOUNTRY[] = { /* "Germany" */
+ 0x47, 0x65, 0x72, 0x6d, 0x61, 0x6e, 0x79
+};
+
+static BYTE NLSALLOC(0407) rgbSENGLANGUAGE[] = { /* "German" */
+ 0x47, 0x65, 0x72, 0x6d, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0407) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0407) rgbIFIRSTWEEKOFYEAR[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0407) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0407) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0407) rgbSTIMEFORMAT[] = { /* "HH:mm:ss" */
+ 0x48, 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0407) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0407) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0407) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0407) g_rglcinfo0407[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 7, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 11, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 2, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 18, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 6, rgbSDAYNAME1 }
+ , { 8, rgbSDAYNAME2 }
+ , { 8, rgbSDAYNAME3 }
+ , { 10, rgbSDAYNAME4 }
+ , { 7, rgbSDAYNAME5 }
+ , { 7, rgbSDAYNAME6 }
+ , { 7, rgbSDAYNAME7 }
+ , { 2, rgbSABBREVDAYNAME1 }
+ , { 2, rgbSABBREVDAYNAME2 }
+ , { 2, rgbSABBREVDAYNAME3 }
+ , { 2, rgbSABBREVDAYNAME4 }
+ , { 2, rgbSABBREVDAYNAME5 }
+ , { 2, rgbSABBREVDAYNAME6 }
+ , { 2, rgbSABBREVDAYNAME7 }
+ , { 6, rgbSMONTHNAME1 }
+ , { 7, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 7, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 8, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0407) g_strinfo0407 = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0408.c b/private/oleauto/src/dispatch/win16/0408.c
new file mode 100644
index 000000000..26caf4caf
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0408.c
@@ -0,0 +1,706 @@
+/****************************************************************************
+* 0408.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Greek - Greece
+*
+* LCID = 0x0408
+*
+* CodePage = 1253
+*
+* Generated: Thu Dec 01 18:22:18 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+WORD NLSALLOC(0408) rgwSort_0408[256] = {
+ 0x0000, 0xc007, 0xc008, 0xc009, 0xc00a, 0xc00b, 0xc00c, 0xc00d
+ , 0xc00e, 0x4039, 0x403a, 0x403b, 0x403c, 0x403d, 0xc00f, 0xc010
+ , 0xc011, 0xc012, 0xc013, 0xc014, 0xc015, 0xc016, 0xc017, 0xc018
+ , 0xc019, 0xc01a, 0xc01b, 0xc01c, 0xc01d, 0xc01e, 0xc01f, 0xc020
+ , 0x4037, 0x403e, 0x403f, 0x4040, 0x4041, 0x4042, 0x4043, 0xc031
+ , 0x4044, 0x4045, 0x4046, 0x4064, 0x4047, 0xc032, 0x4048, 0x4049
+ , 0x007b, 0x007d, 0x007e, 0x007f, 0x0080, 0x0081, 0x0082, 0x0083
+ , 0x0084, 0x0085, 0x404a, 0x404b, 0x4065, 0x4066, 0x4067, 0x404c
+ , 0x404d, 0x1886, 0x1887, 0x1888, 0x1889, 0x188a, 0x188b, 0x188c
+ , 0x188d, 0x188e, 0x188f, 0x1890, 0x1891, 0x1892, 0x1893, 0x1894
+ , 0x1895, 0x1896, 0x1897, 0x1898, 0x1899, 0x189b, 0x189c, 0x189d
+ , 0x189e, 0x189f, 0x18a0, 0x404e, 0x404f, 0x4050, 0x4051, 0x4052
+ , 0x4053, 0x0086, 0x0087, 0x0088, 0x0089, 0x008a, 0x008b, 0x008c
+ , 0x008d, 0x008e, 0x008f, 0x0090, 0x0091, 0x0092, 0x0093, 0x0094
+ , 0x0095, 0x0096, 0x0097, 0x0098, 0x0099, 0x009b, 0x009c, 0x009d
+ , 0x009e, 0x009f, 0x00a0, 0x4054, 0x4055, 0x4056, 0x4057, 0xc021
+ , 0xc022, 0xc023, 0x405e, 0x018b, 0x4061, 0x4079, 0x4076, 0x4077
+ , 0xc024, 0x407a, 0xc025, 0x4062, 0xc026, 0xc027, 0xc028, 0xc029
+ , 0xc02a, 0x405c, 0x405d, 0x405f, 0x4060, 0x4078, 0xc034, 0xc035
+ , 0xc02b, 0x189a, 0xc02c, 0x4063, 0xc02d, 0xc02e, 0xc02f, 0xc030
+ , 0x4038, 0x405b, 0x19a1, 0x406b, 0x406c, 0x406d, 0x4058, 0x406e
+ , 0x4059, 0x406f, 0x08b9, 0x4069, 0x4070, 0xc033, 0x4071, 0xc036
+ , 0x4072, 0x4068, 0x107e, 0x107f, 0x405a, 0x4073, 0x4074, 0x4075
+ , 0x18a5, 0x18a7, 0x1aa9, 0x406a, 0x19af, 0x007c, 0x1ab4, 0x19b8
+ , 0x03a9, 0x18a1, 0x18a2, 0x18a3, 0x18a4, 0x18a5, 0x18a6, 0x18a7
+ , 0x18a8, 0x18a9, 0x18aa, 0x18ab, 0x18ac, 0x18ad, 0x18ae, 0x18af
+ , 0x18b0, 0x18b1, 0x08ba, 0x18b2, 0x18b3, 0x18b4, 0x18b5, 0x18b6
+ , 0x18b7, 0x18b8, 0x19a9, 0x19b4, 0x01a1, 0x00a5, 0x00a7, 0x02a9
+ , 0x03b4, 0x00a1, 0x00a2, 0x00a3, 0x00a4, 0x00a5, 0x00a6, 0x00a7
+ , 0x00a8, 0x00a9, 0x00aa, 0x00ab, 0x00ac, 0x00ad, 0x00ae, 0x00af
+ , 0x00b0, 0x00b1, 0x01b2, 0x00b2, 0x00b3, 0x00b4, 0x00b5, 0x00b6
+ , 0x00b7, 0x00b8, 0x01a9, 0x01b4, 0x01af, 0x02b4, 0x01b8, 0x08bb
+};
+
+WORD NLSALLOC(0408) rgwCType12_0408[256] = {
+ 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x9068, 0x0028, 0x0028, 0x0028, 0x0028, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0xa048, 0xb010, 0xb010, 0x5010, 0x5010, 0x5010, 0x1010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0x5010, 0x7010, 0x5010, 0x4010, 0x4010
+ , 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084
+ , 0x3084, 0x3084, 0x7010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010, 0x0020
+ , 0x0020, 0x0020, 0xb010, 0x1112, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x0020, 0x5010, 0x0020, 0xb010, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x0020, 0xb010, 0x0020, 0xb010, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0xa048, 0x1010, 0x1101, 0x5010, 0x5010, 0x5010, 0xb010, 0xb010
+ , 0xb010, 0xb010, 0x0000, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x5010, 0x5010, 0x3014, 0x3014, 0x1010, 0xb010, 0xb010, 0xb010
+ , 0x1101, 0x1101, 0x1101, 0xb010, 0x1101, 0xb010, 0x1101, 0x1101
+ , 0x1102, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x0000, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x0000
+};
+
+WORD NLSALLOC(0408) rgwCType3_0408[256] = {
+ 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0008, 0x0008, 0x0008, 0x0008, 0x0008, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0048, 0x0048, 0x0448, 0x0048, 0x0448, 0x0048, 0x0048, 0x0440
+ , 0x0048, 0x0048, 0x0048, 0x0048, 0x0048, 0x0440, 0x0048, 0x0448
+ , 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040
+ , 0x0040, 0x0040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0048, 0x0048
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0448, 0x0048, 0x0448, 0x0448
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0000
+ , 0x0000, 0x0000, 0x0008, 0x8000, 0x0008, 0x0008, 0x0008, 0x0008
+ , 0x0000, 0x0008, 0x0000, 0x0008, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0088, 0x0088, 0x0088, 0x0088, 0x0008, 0x0400, 0x0400
+ , 0x0000, 0x0000, 0x0000, 0x0008, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0008, 0x0408, 0x8003, 0x0048, 0x0008, 0x0048, 0x0048, 0x0008
+ , 0x0408, 0x0008, 0x0000, 0x0008, 0x0048, 0x0408, 0x0008, 0x0400
+ , 0x0008, 0x0008, 0x0000, 0x0000, 0x0408, 0x0008, 0x0008, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x0008, 0x8003, 0x0000, 0x8003, 0x8003
+ , 0x8003, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000
+ , 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000
+ , 0x8000, 0x8000, 0x0000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000
+ , 0x8000, 0x8000, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8003, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000
+ , 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000
+ , 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000
+ , 0x8000, 0x8000, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0000
+};
+
+BYTE NLSALLOC(0408) rgbUCase_0408[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xa2, 0xb8, 0xb9, 0xba
+ , 0xe0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd3, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xbc, 0xbe, 0xbf, 0xff
+};
+
+BYTE NLSALLOC(0408) rgbLCase_0408[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f
+ , 0xa0, 0xa1, 0xdc, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xdd, 0xde, 0xdf, 0xbb, 0xfc, 0xbd, 0xfd, 0xfe
+ , 0xc0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xd2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xdc, 0xdd, 0xde, 0xdf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
+};
+
+static BYTE NLSALLOC(0408) rgbILANGUAGE[] = { /* "0408" */
+ 0x30, 0x34, 0x30, 0x38
+};
+
+static BYTE NLSALLOC(0408) rgbSLANGUAGE[] = { /* "Greek" */
+ 0x47, 0x72, 0x65, 0x65, 0x6b
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVLANGNAME[] = { /* "ELL" */
+ 0x45, 0x4c, 0x4c
+};
+
+static BYTE NLSALLOC(0408) rgbSNATIVELANGNAME[] = { /* "\x03b5\x03bb\x03bb\x03b7\x03bd\x03b9\x03ba\x03ac" */
+ 0xe5, 0xeb, 0xeb, 0xe7, 0xed, 0xe9, 0xea, 0xdc
+};
+
+static BYTE NLSALLOC(0408) rgbICOUNTRY[] = { /* "30" */
+ 0x33, 0x30
+};
+
+static BYTE NLSALLOC(0408) rgbSCOUNTRY[] = { /* "Greece" */
+ 0x47, 0x72, 0x65, 0x65, 0x63, 0x65
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVCTRYNAME[] = { /* "GRC" */
+ 0x47, 0x52, 0x43
+};
+
+static BYTE NLSALLOC(0408) rgbSNATIVECTRYNAME[] = { /* "\x0395\x03bb\x03bb\x03ac\x03b4\x03b1" */
+ 0xc5, 0xeb, 0xeb, 0xdc, 0xe4, 0xe1
+};
+
+static BYTE NLSALLOC(0408) rgbIDEFAULTLANGUAGE[] = { /* "0408" */
+ 0x30, 0x34, 0x30, 0x38
+};
+
+static BYTE NLSALLOC(0408) rgbIDEFAULTCOUNTRY[] = { /* "30" */
+ 0x33, 0x30
+};
+
+static BYTE NLSALLOC(0408) rgbIDEFAULTCODEPAGE[] = { /* "737" */
+ 0x37, 0x33, 0x37
+};
+
+static BYTE NLSALLOC(0408) rgbSLIST[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0408) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0408) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0408) rgbSTHOUSAND[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0408) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0408) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0408) rgbILZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0408) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0408) rgbSCURRENCY[] = { /* "\x0394\x03c1\x03c7" */
+ 0xc4, 0xf1, 0xf7
+};
+
+static BYTE NLSALLOC(0408) rgbSINTLSYMBOL[] = { /* "GRD" */
+ 0x47, 0x52, 0x44
+};
+
+static BYTE NLSALLOC(0408) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0408) rgbSMONTHOUSANDSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0408) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0408) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0408) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0408) rgbICURRENCY[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0408) rgbINEGCURR[] = { /* "8" */
+ 0x38
+};
+
+static BYTE NLSALLOC(0408) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(0408) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0408) rgbSSHORTDATE[] = { /* "d/M/yyyy" */
+ 0x64, 0x2f, 0x4d, 0x2f, 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0408) rgbSLONGDATE[] = { /* "dddd, d MMMM yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x2c, 0x20, 0x64, 0x20
+ , 0x4d, 0x4d, 0x4d, 0x4d, 0x20, 0x79, 0x79, 0x79
+ , 0x79
+};
+
+static BYTE NLSALLOC(0408) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0408) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0408) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0408) rgbICENTURY[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0408) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0408) rgbIDAYLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0408) rgbIMONLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0408) rgbS1159[] = { /* "\x03c0\x03bc" */
+ 0xf0, 0xec
+};
+
+static BYTE NLSALLOC(0408) rgbS2359[] = { /* "\x03bc\x03bc" */
+ 0xec, 0xec
+};
+
+static BYTE NLSALLOC(0408) rgbSDAYNAME1[] = { /* "\x0394\x03b5\x03c5\x03c4\x03ad\x03c1\x03b1" */
+ 0xc4, 0xe5, 0xf5, 0xf4, 0xdd, 0xf1, 0xe1
+};
+
+static BYTE NLSALLOC(0408) rgbSDAYNAME2[] = { /* "\x03a4\x03c1\x03af\x03c4\x03b7" */
+ 0xd4, 0xf1, 0xdf, 0xf4, 0xe7
+};
+
+static BYTE NLSALLOC(0408) rgbSDAYNAME3[] = { /* "\x03a4\x03b5\x03c4\x03ac\x03c1\x03c4\x03b7" */
+ 0xd4, 0xe5, 0xf4, 0xdc, 0xf1, 0xf4, 0xe7
+};
+
+static BYTE NLSALLOC(0408) rgbSDAYNAME4[] = { /* "\x03a0\x03ad\x03bc\x03c0\x03c4\x03b7" */
+ 0xd0, 0xdd, 0xec, 0xf0, 0xf4, 0xe7
+};
+
+static BYTE NLSALLOC(0408) rgbSDAYNAME5[] = { /* "\x03a0\x03b1\x03c1\x03b1\x03c3\x03ba\x03b5\x03c5\x03ae" */
+ 0xd0, 0xe1, 0xf1, 0xe1, 0xf3, 0xea, 0xe5, 0xf5
+ , 0xde
+};
+
+static BYTE NLSALLOC(0408) rgbSDAYNAME6[] = { /* "\x03a3\x03ac\x03b2\x03b2\x03b1\x03c4\x03bf" */
+ 0xd3, 0xdc, 0xe2, 0xe2, 0xe1, 0xf4, 0xef
+};
+
+static BYTE NLSALLOC(0408) rgbSDAYNAME7[] = { /* "\x039a\x03c5\x03c1\x03b9\x03b1\x03ba\x03ae" */
+ 0xca, 0xf5, 0xf1, 0xe9, 0xe1, 0xea, 0xde
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVDAYNAME1[] = { /* "\x0394\x03b5\x03c5" */
+ 0xc4, 0xe5, 0xf5
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVDAYNAME2[] = { /* "\x03a4\x03c1\x03b9" */
+ 0xd4, 0xf1, 0xe9
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVDAYNAME3[] = { /* "\x03a4\x03b5\x03c4" */
+ 0xd4, 0xe5, 0xf4
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVDAYNAME4[] = { /* "\x03a0\x03b5\x03bc" */
+ 0xd0, 0xe5, 0xec
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVDAYNAME5[] = { /* "\x03a0\x03b1\x03c1" */
+ 0xd0, 0xe1, 0xf1
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVDAYNAME6[] = { /* "\x03a3\x03b1\x03b2" */
+ 0xd3, 0xe1, 0xe2
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVDAYNAME7[] = { /* "\x039a\x03c5\x03c1" */
+ 0xca, 0xf5, 0xf1
+};
+
+static BYTE NLSALLOC(0408) rgbSMONTHNAME1[] = { /* "\x0399\x03b1\x03bd\x03bf\x03c5\x03b1\x03c1\x03af\x03bf\x03c5" */
+ 0xc9, 0xe1, 0xed, 0xef, 0xf5, 0xe1, 0xf1, 0xdf
+ , 0xef, 0xf5
+};
+
+static BYTE NLSALLOC(0408) rgbSMONTHNAME2[] = { /* "\x03a6\x03b5\x03b2\x03c1\x03bf\x03c5\x03b1\x03c1\x03af\x03bf\x03c5" */
+ 0xd6, 0xe5, 0xe2, 0xf1, 0xef, 0xf5, 0xe1, 0xf1
+ , 0xdf, 0xef, 0xf5
+};
+
+static BYTE NLSALLOC(0408) rgbSMONTHNAME3[] = { /* "\x039c\x03b1\x03c1\x03c4\x03af\x03bf\x03c5" */
+ 0xcc, 0xe1, 0xf1, 0xf4, 0xdf, 0xef, 0xf5
+};
+
+static BYTE NLSALLOC(0408) rgbSMONTHNAME4[] = { /* "\x0391\x03c0\x03c1\x03b9\x03bb\x03af\x03bf\x03c5" */
+ 0xc1, 0xf0, 0xf1, 0xe9, 0xeb, 0xdf, 0xef, 0xf5
+};
+
+static BYTE NLSALLOC(0408) rgbSMONTHNAME5[] = { /* "\x039c\x03b1\x0390\x03bf\x03c5" */
+ 0xcc, 0xe1, 0xc0, 0xef, 0xf5
+};
+
+static BYTE NLSALLOC(0408) rgbSMONTHNAME6[] = { /* "\x0399\x03bf\x03c5\x03bd\x03af\x03bf\x03c5" */
+ 0xc9, 0xef, 0xf5, 0xed, 0xdf, 0xef, 0xf5
+};
+
+static BYTE NLSALLOC(0408) rgbSMONTHNAME7[] = { /* "\x0399\x03bf\x03c5\x03bb\x03af\x03bf\x03c5" */
+ 0xc9, 0xef, 0xf5, 0xeb, 0xdf, 0xef, 0xf5
+};
+
+static BYTE NLSALLOC(0408) rgbSMONTHNAME8[] = { /* "\x0391\x03c5\x03b3\x03bf\x03cd\x03c3\x03c4\x03bf\x03c5" */
+ 0xc1, 0xf5, 0xe3, 0xef, 0xfd, 0xf3, 0xf4, 0xef
+ , 0xf5
+};
+
+static BYTE NLSALLOC(0408) rgbSMONTHNAME9[] = { /* "\x03a3\x03b5\x03c0\x03c4\x03b5\x03bc\x03b2\x03c1\x03af\x03bf\x03c5" */
+ 0xd3, 0xe5, 0xf0, 0xf4, 0xe5, 0xec, 0xe2, 0xf1
+ , 0xdf, 0xef, 0xf5
+};
+
+static BYTE NLSALLOC(0408) rgbSMONTHNAME10[] = { /* "\x039f\x03ba\x03c4\x03c9\x03b2\x03c1\x03af\x03bf\x03c5" */
+ 0xcf, 0xea, 0xf4, 0xf9, 0xe2, 0xf1, 0xdf, 0xef
+ , 0xf5
+};
+
+static BYTE NLSALLOC(0408) rgbSMONTHNAME11[] = { /* "\x039d\x03bf\x03b5\x03bc\x03b2\x03c1\x03af\x03bf\x03c5" */
+ 0xcd, 0xef, 0xe5, 0xec, 0xe2, 0xf1, 0xdf, 0xef
+ , 0xf5
+};
+
+static BYTE NLSALLOC(0408) rgbSMONTHNAME12[] = { /* "\x0394\x03b5\x03ba\x03b5\x03bc\x03b2\x03c1\x03af\x03bf\x03c5" */
+ 0xc4, 0xe5, 0xea, 0xe5, 0xec, 0xe2, 0xf1, 0xdf
+ , 0xef, 0xf5
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVMONTHNAME1[] = { /* "\x0399\x03b1\x03bd" */
+ 0xc9, 0xe1, 0xed
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVMONTHNAME2[] = { /* "\x03a6\x03b5\x03b2" */
+ 0xd6, 0xe5, 0xe2
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVMONTHNAME3[] = { /* "\x039c\x03b1\x03c1" */
+ 0xcc, 0xe1, 0xf1
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVMONTHNAME4[] = { /* "\x0391\x03c0\x03c1" */
+ 0xc1, 0xf0, 0xf1
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVMONTHNAME5[] = { /* "\x039c\x03b1\x03ca" */
+ 0xcc, 0xe1, 0xfa
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVMONTHNAME6[] = { /* "\x0399\x03bf\x03c5\x03bd" */
+ 0xc9, 0xef, 0xf5, 0xed
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVMONTHNAME7[] = { /* "\x0399\x03bf\x03c5\x03bb" */
+ 0xc9, 0xef, 0xf5, 0xeb
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVMONTHNAME8[] = { /* "\x0391\x03c5\x03b3" */
+ 0xc1, 0xf5, 0xe3
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVMONTHNAME9[] = { /* "\x03a3\x03b5\x03c0" */
+ 0xd3, 0xe5, 0xf0
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVMONTHNAME10[] = { /* "\x039f\x03ba\x03c4" */
+ 0xcf, 0xea, 0xf4
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVMONTHNAME11[] = { /* "\x039d\x03bf\x03b5" */
+ 0xcd, 0xef, 0xe5
+};
+
+static BYTE NLSALLOC(0408) rgbSABBREVMONTHNAME12[] = { /* "\x0394\x03b5\x03ba" */
+ 0xc4, 0xe5, 0xea
+};
+
+static BYTE NLSALLOC(0408) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0408) rgbIPOSSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0408) rgbINEGSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0408) rgbIPOSSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0408) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0408) rgbINEGSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0408) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0408) rgbSENGCOUNTRY[] = { /* "Greece" */
+ 0x47, 0x72, 0x65, 0x65, 0x63, 0x65
+};
+
+static BYTE NLSALLOC(0408) rgbSENGLANGUAGE[] = { /* "Greek" */
+ 0x47, 0x72, 0x65, 0x65, 0x6b
+};
+
+static BYTE NLSALLOC(0408) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0408) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0408) rgbIDEFAULTANSICODEPAGE[] = { /* "1253" */
+ 0x31, 0x32, 0x35, 0x33
+};
+
+static BYTE NLSALLOC(0408) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0408) rgbSTIMEFORMAT[] = { /* "h:mm:ss tt" */
+ 0x68, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73, 0x20
+ , 0x74, 0x74
+};
+
+static BYTE NLSALLOC(0408) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0408) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0408) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0408) g_rglcinfo0408[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 5, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 8, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 6, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 6, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 3, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 17, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 2, rgbS1159 }
+ , { 2, rgbS2359 }
+ , { 7, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 7, rgbSDAYNAME3 }
+ , { 6, rgbSDAYNAME4 }
+ , { 9, rgbSDAYNAME5 }
+ , { 7, rgbSDAYNAME6 }
+ , { 7, rgbSDAYNAME7 }
+ , { 3, rgbSABBREVDAYNAME1 }
+ , { 3, rgbSABBREVDAYNAME2 }
+ , { 3, rgbSABBREVDAYNAME3 }
+ , { 3, rgbSABBREVDAYNAME4 }
+ , { 3, rgbSABBREVDAYNAME5 }
+ , { 3, rgbSABBREVDAYNAME6 }
+ , { 3, rgbSABBREVDAYNAME7 }
+ , { 10, rgbSMONTHNAME1 }
+ , { 11, rgbSMONTHNAME2 }
+ , { 7, rgbSMONTHNAME3 }
+ , { 8, rgbSMONTHNAME4 }
+ , { 5, rgbSMONTHNAME5 }
+ , { 7, rgbSMONTHNAME6 }
+ , { 7, rgbSMONTHNAME7 }
+ , { 9, rgbSMONTHNAME8 }
+ , { 11, rgbSMONTHNAME9 }
+ , { 9, rgbSMONTHNAME10 }
+ , { 9, rgbSMONTHNAME11 }
+ , { 10, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 4, rgbSABBREVMONTHNAME6 }
+ , { 4, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 6, rgbSENGCOUNTRY }
+ , { 5, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 10, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0408) g_strinfo0408 = {
+ rgbUCase_0408
+ , rgbLCase_0408
+ , rgwCType12_0408
+ , rgwCType3_0408
+ , rgwSort_0408
+ , NULL
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0409.c b/private/oleauto/src/dispatch/win16/0409.c
new file mode 100644
index 000000000..f22eeb2d0
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0409.c
@@ -0,0 +1,714 @@
+/****************************************************************************
+* 0409.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* English - United States
+*
+* LCID = 0x0409
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:33:44 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+WORD NLSALLOC(0409) rgwSort_0409[256] = {
+ 0x0000, 0xc007, 0xc008, 0xc009, 0xc00a, 0xc00b, 0xc00c, 0xc00d
+ , 0xc00e, 0x4031, 0x4032, 0x4033, 0x4034, 0x4035, 0xc00f, 0xc010
+ , 0xc011, 0xc012, 0xc013, 0xc014, 0xc015, 0xc016, 0xc017, 0xc018
+ , 0xc019, 0xc01a, 0xc01b, 0xc01c, 0xc01d, 0xc01e, 0xc01f, 0xc020
+ , 0x402f, 0x4036, 0x4037, 0x4038, 0x4039, 0x403a, 0x403b, 0xc02a
+ , 0x403c, 0x403d, 0x403e, 0x4060, 0x403f, 0xc02b, 0x4040, 0x4041
+ , 0x007a, 0x007e, 0x007f, 0x0080, 0x0081, 0x0082, 0x0083, 0x0084
+ , 0x0085, 0x0086, 0x4042, 0x4043, 0x4061, 0x4062, 0x4063, 0x4044
+ , 0x4045, 0x1087, 0x1088, 0x1089, 0x108a, 0x108b, 0x108c, 0x108d
+ , 0x108e, 0x108f, 0x1090, 0x1091, 0x1092, 0x1093, 0x1094, 0x1095
+ , 0x1096, 0x1097, 0x1098, 0x1099, 0x109a, 0x109c, 0x109d, 0x109e
+ , 0x109f, 0x10a0, 0x10a1, 0x4046, 0x4047, 0x4048, 0x4049, 0x404a
+ , 0x404b, 0x0087, 0x0088, 0x0089, 0x008a, 0x008b, 0x008c, 0x008d
+ , 0x008e, 0x008f, 0x0090, 0x0091, 0x0092, 0x0093, 0x0094, 0x0095
+ , 0x0096, 0x0097, 0x0098, 0x0099, 0x009a, 0x009c, 0x009d, 0x009e
+ , 0x009f, 0x00a0, 0x00a1, 0x404c, 0x404d, 0x404e, 0x404f, 0xc021
+ , 0xc022, 0xc023, 0x405a, 0x018c, 0x405d, 0x4078, 0x4075, 0x4076
+ , 0x4149, 0x4079, 0x1199, 0x405e, 0x0505, 0xc024, 0xc025, 0xc026
+ , 0xc027, 0x4058, 0x4059, 0x405b, 0x405c, 0x4077, 0xc02d, 0xc02e
+ , 0x4057, 0x109b, 0x0199, 0x405f, 0x0605, 0xc028, 0xc029, 0x12a0
+ , 0x4030, 0x4050, 0x4069, 0x406a, 0x406b, 0x406c, 0x4051, 0x406d
+ , 0x4052, 0x406e, 0x0887, 0x4065, 0x406f, 0xc02c, 0x4070, 0x4053
+ , 0x4071, 0x4064, 0x087f, 0x0880, 0x4054, 0x4072, 0x4073, 0x4074
+ , 0x4055, 0x087e, 0x0995, 0x4066, 0x007b, 0x007c, 0x007d, 0x4056
+ , 0x1287, 0x1187, 0x1387, 0x1587, 0x1487, 0x1687, 0x0005, 0x1189
+ , 0x128b, 0x118b, 0x138b, 0x148b, 0x128f, 0x118f, 0x138f, 0x148f
+ , 0x118a, 0x1194, 0x1395, 0x1295, 0x1495, 0x1695, 0x1595, 0x4067
+ , 0x1795, 0x129c, 0x119c, 0x139c, 0x149c, 0x11a0, 0x0105, 0x0205
+ , 0x0287, 0x0187, 0x0387, 0x0587, 0x0487, 0x0687, 0x0305, 0x0189
+ , 0x028b, 0x018b, 0x038b, 0x048b, 0x028f, 0x018f, 0x038f, 0x048f
+ , 0x018a, 0x0194, 0x0395, 0x0295, 0x0495, 0x0695, 0x0595, 0x4068
+ , 0x0795, 0x029c, 0x019c, 0x039c, 0x049c, 0x01a0, 0x0405, 0x02a0
+};
+
+EXPANSION NLSALLOC(0409) rgexp_0409[7] = {
+ { 0x1087, 0x108b }
+ , { 0x109a, 0x108e }
+ , { 0x0099, 0x0099 }
+ , { 0x0087, 0x008b }
+ , { 0x009a, 0x008e }
+ , { 0x1095, 0x108b }
+ , { 0x0095, 0x008b }
+};
+
+WORD NLSALLOC(0409) rgwCType12_0409[256] = {
+ 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x9068, 0x0028, 0x0028, 0x0028, 0x0028, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0xa048, 0xb010, 0xb010, 0x5010, 0x5010, 0x5010, 0x1010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0x5010, 0x7010, 0x5010, 0x4010, 0x4010
+ , 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084
+ , 0x3084, 0x3084, 0x7010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010, 0x0020
+ , 0x0020, 0x0020, 0xb010, 0x1112, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x5010, 0x1101, 0xb010, 0x1101, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0xb010, 0x1102, 0xb010, 0x1102, 0x0020, 0x0020, 0x1101
+ , 0xa048, 0xb010, 0x5010, 0x5010, 0x5010, 0x5010, 0xb010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x5010, 0x5010, 0x3014, 0x3014, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x3014, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0xb010
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0xb010
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+};
+
+WORD NLSALLOC(0409) rgwCType3_0409[256] = {
+ 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0008, 0x0008, 0x0008, 0x0008, 0x0008, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0048, 0x0048, 0x0448, 0x0048, 0x0448, 0x0048, 0x0048, 0x0440
+ , 0x0048, 0x0048, 0x0048, 0x0048, 0x0048, 0x0440, 0x0048, 0x0448
+ , 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040
+ , 0x0040, 0x0040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0048, 0x0048
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0448, 0x0048, 0x0448, 0x0448
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0000
+ , 0x0000, 0x0000, 0x0008, 0x8000, 0x0008, 0x0008, 0x0008, 0x0008
+ , 0x0001, 0x0008, 0x8003, 0x0008, 0x8000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0088, 0x0088, 0x0088, 0x0088, 0x0008, 0x0400, 0x0400
+ , 0x0408, 0x0000, 0x8003, 0x0008, 0x8000, 0x0000, 0x0000, 0x8003
+ , 0x0008, 0x0008, 0x0048, 0x0048, 0x0008, 0x0048, 0x0048, 0x0008
+ , 0x0408, 0x0008, 0x0400, 0x0008, 0x0048, 0x0408, 0x0008, 0x0448
+ , 0x0008, 0x0008, 0x0000, 0x0000, 0x0408, 0x0008, 0x0008, 0x0008
+ , 0x0408, 0x0000, 0x0400, 0x0008, 0x0000, 0x0000, 0x0000, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8000, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8000
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8000, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+};
+
+BYTE NLSALLOC(0409) rgbUCase_0409[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x8a, 0x9b, 0x8c, 0x9d, 0x9e, 0x9f
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xf7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0x9f
+};
+
+BYTE NLSALLOC(0409) rgbLCase_0409[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x9a, 0x8b, 0x9c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0xff
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xd7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xdf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
+};
+
+static BYTE NLSALLOC(0409) rgbILANGUAGE[] = { /* "0409" */
+ 0x30, 0x34, 0x30, 0x39
+};
+
+static BYTE NLSALLOC(0409) rgbSLANGUAGE[] = { /* "U.S. English" */
+ 0x55, 0x2e, 0x53, 0x2e, 0x20, 0x45, 0x6e, 0x67
+ , 0x6c, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVLANGNAME[] = { /* "ENU" */
+ 0x45, 0x4e, 0x55
+};
+
+static BYTE NLSALLOC(0409) rgbSNATIVELANGNAME[] = { /* "English" */
+ 0x45, 0x6e, 0x67, 0x6c, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(0409) rgbICOUNTRY[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0409) rgbSCOUNTRY[] = { /* "United States" */
+ 0x55, 0x6e, 0x69, 0x74, 0x65, 0x64, 0x20, 0x53
+ , 0x74, 0x61, 0x74, 0x65, 0x73
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVCTRYNAME[] = { /* "USA" */
+ 0x55, 0x53, 0x41
+};
+
+static BYTE NLSALLOC(0409) rgbSNATIVECTRYNAME[] = { /* "United States" */
+ 0x55, 0x6e, 0x69, 0x74, 0x65, 0x64, 0x20, 0x53
+ , 0x74, 0x61, 0x74, 0x65, 0x73
+};
+
+static BYTE NLSALLOC(0409) rgbIDEFAULTLANGUAGE[] = { /* "0409" */
+ 0x30, 0x34, 0x30, 0x39
+};
+
+static BYTE NLSALLOC(0409) rgbIDEFAULTCOUNTRY[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0409) rgbIDEFAULTCODEPAGE[] = { /* "437" */
+ 0x34, 0x33, 0x37
+};
+
+static BYTE NLSALLOC(0409) rgbSLIST[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0409) rgbIMEASURE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0409) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0409) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0409) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0409) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0409) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0409) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0409) rgbSCURRENCY[] = { /* "$" */
+ 0x24
+};
+
+static BYTE NLSALLOC(0409) rgbSINTLSYMBOL[] = { /* "USD" */
+ 0x55, 0x53, 0x44
+};
+
+static BYTE NLSALLOC(0409) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0409) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0409) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0409) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0409) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0409) rgbICURRENCY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0409) rgbINEGCURR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0409) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(0409) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0409) rgbSSHORTDATE[] = { /* "M/d/yy" */
+ 0x4d, 0x2f, 0x64, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0409) rgbSLONGDATE[] = { /* "dddd, MMMM dd, yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x2c, 0x20, 0x4d, 0x4d
+ , 0x4d, 0x4d, 0x20, 0x64, 0x64, 0x2c, 0x20, 0x79
+ , 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0409) rgbIDATE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0409) rgbILDATE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0409) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0409) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0409) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0409) rgbIDAYLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0409) rgbIMONLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0409) rgbS1159[] = { /* "AM" */
+ 0x41, 0x4d
+};
+
+static BYTE NLSALLOC(0409) rgbS2359[] = { /* "PM" */
+ 0x50, 0x4d
+};
+
+static BYTE NLSALLOC(0409) rgbSDAYNAME1[] = { /* "Monday" */
+ 0x4d, 0x6f, 0x6e, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0409) rgbSDAYNAME2[] = { /* "Tuesday" */
+ 0x54, 0x75, 0x65, 0x73, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0409) rgbSDAYNAME3[] = { /* "Wednesday" */
+ 0x57, 0x65, 0x64, 0x6e, 0x65, 0x73, 0x64, 0x61
+ , 0x79
+};
+
+static BYTE NLSALLOC(0409) rgbSDAYNAME4[] = { /* "Thursday" */
+ 0x54, 0x68, 0x75, 0x72, 0x73, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0409) rgbSDAYNAME5[] = { /* "Friday" */
+ 0x46, 0x72, 0x69, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0409) rgbSDAYNAME6[] = { /* "Saturday" */
+ 0x53, 0x61, 0x74, 0x75, 0x72, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0409) rgbSDAYNAME7[] = { /* "Sunday" */
+ 0x53, 0x75, 0x6e, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVDAYNAME1[] = { /* "Mon" */
+ 0x4d, 0x6f, 0x6e
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVDAYNAME2[] = { /* "Tue" */
+ 0x54, 0x75, 0x65
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVDAYNAME3[] = { /* "Wed" */
+ 0x57, 0x65, 0x64
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVDAYNAME4[] = { /* "Thu" */
+ 0x54, 0x68, 0x75
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVDAYNAME5[] = { /* "Fri" */
+ 0x46, 0x72, 0x69
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVDAYNAME6[] = { /* "Sat" */
+ 0x53, 0x61, 0x74
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVDAYNAME7[] = { /* "Sun" */
+ 0x53, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0409) rgbSMONTHNAME1[] = { /* "January" */
+ 0x4a, 0x61, 0x6e, 0x75, 0x61, 0x72, 0x79
+};
+
+static BYTE NLSALLOC(0409) rgbSMONTHNAME2[] = { /* "February" */
+ 0x46, 0x65, 0x62, 0x72, 0x75, 0x61, 0x72, 0x79
+};
+
+static BYTE NLSALLOC(0409) rgbSMONTHNAME3[] = { /* "March" */
+ 0x4d, 0x61, 0x72, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(0409) rgbSMONTHNAME4[] = { /* "April" */
+ 0x41, 0x70, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(0409) rgbSMONTHNAME5[] = { /* "May" */
+ 0x4d, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0409) rgbSMONTHNAME6[] = { /* "June" */
+ 0x4a, 0x75, 0x6e, 0x65
+};
+
+static BYTE NLSALLOC(0409) rgbSMONTHNAME7[] = { /* "July" */
+ 0x4a, 0x75, 0x6c, 0x79
+};
+
+static BYTE NLSALLOC(0409) rgbSMONTHNAME8[] = { /* "August" */
+ 0x41, 0x75, 0x67, 0x75, 0x73, 0x74
+};
+
+static BYTE NLSALLOC(0409) rgbSMONTHNAME9[] = { /* "September" */
+ 0x53, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x65
+ , 0x72
+};
+
+static BYTE NLSALLOC(0409) rgbSMONTHNAME10[] = { /* "October" */
+ 0x4f, 0x63, 0x74, 0x6f, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0409) rgbSMONTHNAME11[] = { /* "November" */
+ 0x4e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0409) rgbSMONTHNAME12[] = { /* "December" */
+ 0x44, 0x65, 0x63, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVMONTHNAME1[] = { /* "Jan" */
+ 0x4a, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVMONTHNAME2[] = { /* "Feb" */
+ 0x46, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVMONTHNAME3[] = { /* "Mar" */
+ 0x4d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVMONTHNAME4[] = { /* "Apr" */
+ 0x41, 0x70, 0x72
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVMONTHNAME5[] = { /* "May" */
+ 0x4d, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVMONTHNAME6[] = { /* "Jun" */
+ 0x4a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVMONTHNAME7[] = { /* "Jul" */
+ 0x4a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVMONTHNAME8[] = { /* "Aug" */
+ 0x41, 0x75, 0x67
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVMONTHNAME9[] = { /* "Sep" */
+ 0x53, 0x65, 0x70
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVMONTHNAME10[] = { /* "Oct" */
+ 0x4f, 0x63, 0x74
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVMONTHNAME11[] = { /* "Nov" */
+ 0x4e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(0409) rgbSABBREVMONTHNAME12[] = { /* "Dec" */
+ 0x44, 0x65, 0x63
+};
+
+static BYTE NLSALLOC(0409) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0409) rgbIPOSSIGNPOSN[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0409) rgbINEGSIGNPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0409) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0409) rgbIPOSSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0409) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0409) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0409) rgbSENGCOUNTRY[] = { /* "United States" */
+ 0x55, 0x6e, 0x69, 0x74, 0x65, 0x64, 0x20, 0x53
+ , 0x74, 0x61, 0x74, 0x65, 0x73
+};
+
+static BYTE NLSALLOC(0409) rgbSENGLANGUAGE[] = { /* "English" */
+ 0x45, 0x6e, 0x67, 0x6c, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(0409) rgbIFIRSTDAYOFWEEK[] = { /* "6" */
+ 0x36
+};
+
+static BYTE NLSALLOC(0409) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0409) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0409) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0409) rgbSTIMEFORMAT[] = { /* "h:mm:ss tt" */
+ 0x68, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73, 0x20
+ , 0x74, 0x74
+};
+
+static BYTE NLSALLOC(0409) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0409) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0409) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0409) g_rglcinfo0409[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 12, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 1, rgbICOUNTRY }
+ , { 13, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 13, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 1, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 1, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 6, rgbSSHORTDATE }
+ , { 19, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 2, rgbS1159 }
+ , { 2, rgbS2359 }
+ , { 6, rgbSDAYNAME1 }
+ , { 7, rgbSDAYNAME2 }
+ , { 9, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 6, rgbSDAYNAME5 }
+ , { 8, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 3, rgbSABBREVDAYNAME1 }
+ , { 3, rgbSABBREVDAYNAME2 }
+ , { 3, rgbSABBREVDAYNAME3 }
+ , { 3, rgbSABBREVDAYNAME4 }
+ , { 3, rgbSABBREVDAYNAME5 }
+ , { 3, rgbSABBREVDAYNAME6 }
+ , { 3, rgbSABBREVDAYNAME7 }
+ , { 7, rgbSMONTHNAME1 }
+ , { 8, rgbSMONTHNAME2 }
+ , { 5, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 13, rgbSENGCOUNTRY }
+ , { 7, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 10, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0409) g_strinfo0409 = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/040a.c b/private/oleauto/src/dispatch/win16/040a.c
new file mode 100644
index 000000000..ed65a336c
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/040a.c
@@ -0,0 +1,723 @@
+/****************************************************************************
+* 040a.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Spanish - Spain (Traditional Sort)
+*
+* LCID = 0x040a
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:51:34 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+WORD NLSALLOC(040a) rgwSort_040a[256] = {
+ 0x0000, 0xc007, 0xc008, 0xc009, 0xc00a, 0xc00b, 0xc00c, 0xc00d
+ , 0xc00e, 0x4031, 0x4032, 0x4033, 0x4034, 0x4035, 0xc00f, 0xc010
+ , 0xc011, 0xc012, 0xc013, 0xc014, 0xc015, 0xc016, 0xc017, 0xc018
+ , 0xc019, 0xc01a, 0xc01b, 0xc01c, 0xc01d, 0xc01e, 0xc01f, 0xc020
+ , 0x402f, 0x4036, 0x4037, 0x4038, 0x4039, 0x403a, 0x403b, 0xc02a
+ , 0x403c, 0x403d, 0x403e, 0x4060, 0x403f, 0xc02b, 0x4040, 0x4041
+ , 0x007a, 0x007e, 0x007f, 0x0080, 0x0081, 0x0082, 0x0083, 0x0084
+ , 0x0085, 0x0086, 0x4042, 0x4043, 0x4061, 0x4062, 0x4063, 0x4044
+ , 0x4045, 0x1087, 0x1088, 0x0006, 0x108b, 0x108c, 0x108d, 0x108e
+ , 0x108f, 0x1090, 0x1091, 0x1092, 0x0306, 0x1095, 0x1096, 0x1098
+ , 0x1099, 0x109a, 0x109b, 0x109c, 0x109d, 0x109f, 0x10a0, 0x10a1
+ , 0x10a2, 0x10a3, 0x10a4, 0x4046, 0x4047, 0x4048, 0x4049, 0x404a
+ , 0x404b, 0x0087, 0x0088, 0x0606, 0x008b, 0x008c, 0x008d, 0x008e
+ , 0x008f, 0x0090, 0x0091, 0x0092, 0x0806, 0x0095, 0x0096, 0x0098
+ , 0x0099, 0x009a, 0x009b, 0x009c, 0x009d, 0x009f, 0x00a0, 0x00a1
+ , 0x00a2, 0x00a3, 0x00a4, 0x404c, 0x404d, 0x404e, 0x404f, 0xc021
+ , 0xc022, 0xc023, 0x405a, 0x018d, 0x405d, 0x4078, 0x4075, 0x4076
+ , 0x4149, 0x4079, 0x119c, 0x405e, 0x0505, 0xc024, 0xc025, 0xc026
+ , 0xc027, 0x4058, 0x4059, 0x405b, 0x405c, 0x4077, 0xc02d, 0xc02e
+ , 0x4057, 0x109e, 0x019c, 0x405f, 0x0605, 0xc028, 0xc029, 0x12a3
+ , 0x4030, 0x4050, 0x4069, 0x406a, 0x406b, 0x406c, 0x4051, 0x406d
+ , 0x4052, 0x406e, 0x0887, 0x4065, 0x406f, 0xc02c, 0x4070, 0x4053
+ , 0x4071, 0x4064, 0x087f, 0x0880, 0x4054, 0x4072, 0x4073, 0x4074
+ , 0x4055, 0x087e, 0x0998, 0x4066, 0x007b, 0x007c, 0x007d, 0x4056
+ , 0x1287, 0x1187, 0x1387, 0x1587, 0x1487, 0x1687, 0x0005, 0x1189
+ , 0x128c, 0x118c, 0x138c, 0x148c, 0x1290, 0x1190, 0x1390, 0x1490
+ , 0x118b, 0x1097, 0x1398, 0x1298, 0x1498, 0x1698, 0x1598, 0x4067
+ , 0x1798, 0x129f, 0x119f, 0x139f, 0x149f, 0x11a3, 0x0105, 0x0205
+ , 0x0287, 0x0187, 0x0387, 0x0587, 0x0487, 0x0687, 0x0305, 0x0189
+ , 0x028c, 0x018c, 0x038c, 0x048c, 0x0290, 0x0190, 0x0390, 0x0490
+ , 0x018b, 0x0097, 0x0398, 0x0298, 0x0498, 0x0698, 0x0598, 0x4068
+ , 0x0798, 0x029f, 0x019f, 0x039f, 0x049f, 0x01a3, 0x0405, 0x02a3
+};
+
+DIGRAPH NLSALLOC(040a) rgdig_040a[10] = {
+ { 0x1089, 0x02 }
+ , { 0x188a, 0x48 }
+ , { 0x108a, 0x68 }
+ , { 0x1093, 0x02 }
+ , { 0x1894, 0x4c }
+ , { 0x1094, 0x6c }
+ , { 0x0089, 0x02 }
+ , { 0x008a, 0x68 }
+ , { 0x0093, 0x02 }
+ , { 0x0094, 0x6c }
+};
+
+EXPANSION NLSALLOC(040a) rgexp_040a[7] = {
+ { 0x1087, 0x108c }
+ , { 0x109d, 0x108f }
+ , { 0x009c, 0x009c }
+ , { 0x0087, 0x008c }
+ , { 0x009d, 0x008f }
+ , { 0x1098, 0x108c }
+ , { 0x0098, 0x008c }
+};
+
+WORD NLSALLOC(040a) rgwCType12_040a[256] = {
+ 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x9068, 0x0028, 0x0028, 0x0028, 0x0028, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0xa048, 0xb010, 0xb010, 0x5010, 0x5010, 0x5010, 0x1010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0x5010, 0x7010, 0x5010, 0x4010, 0x4010
+ , 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084
+ , 0x3084, 0x3084, 0x7010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010, 0x0020
+ , 0x0020, 0x0020, 0xb010, 0x1112, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x5010, 0x1101, 0xb010, 0x1101, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0xb010, 0x1102, 0xb010, 0x1102, 0x0020, 0x0020, 0x1101
+ , 0xa048, 0xb010, 0x5010, 0x5010, 0x5010, 0x5010, 0xb010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x5010, 0x5010, 0x3014, 0x3014, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x3014, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0xb010
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0xb010
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+};
+
+WORD NLSALLOC(040a) rgwCType3_040a[256] = {
+ 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0008, 0x0008, 0x0008, 0x0008, 0x0008, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0048, 0x0048, 0x0448, 0x0048, 0x0448, 0x0048, 0x0048, 0x0440
+ , 0x0048, 0x0048, 0x0048, 0x0048, 0x0048, 0x0440, 0x0048, 0x0448
+ , 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040
+ , 0x0040, 0x0040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0048, 0x0048
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0448, 0x0048, 0x0448, 0x0448
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0000
+ , 0x0000, 0x0000, 0x0008, 0x8000, 0x0008, 0x0008, 0x0008, 0x0008
+ , 0x0001, 0x0008, 0x8003, 0x0008, 0x8000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0088, 0x0088, 0x0088, 0x0088, 0x0008, 0x0400, 0x0400
+ , 0x0408, 0x0000, 0x8003, 0x0008, 0x8000, 0x0000, 0x0000, 0x8003
+ , 0x0008, 0x0008, 0x0048, 0x0048, 0x0008, 0x0048, 0x0048, 0x0008
+ , 0x0408, 0x0008, 0x0400, 0x0008, 0x0048, 0x0408, 0x0008, 0x0448
+ , 0x0008, 0x0008, 0x0000, 0x0000, 0x0408, 0x0008, 0x0008, 0x0008
+ , 0x0408, 0x0000, 0x0400, 0x0008, 0x0000, 0x0000, 0x0000, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8000, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8000
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8000, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+};
+
+BYTE NLSALLOC(040a) rgbUCase_040a[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x8a, 0x9b, 0x8c, 0x9d, 0x9e, 0x9f
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xf7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0x9f
+};
+
+BYTE NLSALLOC(040a) rgbLCase_040a[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x9a, 0x8b, 0x9c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0xff
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xd7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xdf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
+};
+
+static BYTE NLSALLOC(040a) rgbILANGUAGE[] = { /* "040a" */
+ 0x30, 0x34, 0x30, 0x61
+};
+
+static BYTE NLSALLOC(040a) rgbSLANGUAGE[] = { /* "Spanish - Traditional Sort" */
+ 0x53, 0x70, 0x61, 0x6e, 0x69, 0x73, 0x68, 0x20
+ , 0x2d, 0x20, 0x54, 0x72, 0x61, 0x64, 0x69, 0x74
+ , 0x69, 0x6f, 0x6e, 0x61, 0x6c, 0x20, 0x53, 0x6f
+ , 0x72, 0x74
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVLANGNAME[] = { /* "ESP" */
+ 0x45, 0x53, 0x50
+};
+
+static BYTE NLSALLOC(040a) rgbSNATIVELANGNAME[] = { /* "Español" */
+ 0x45, 0x73, 0x70, 0x61, 0xf1, 0x6f, 0x6c
+};
+
+static BYTE NLSALLOC(040a) rgbICOUNTRY[] = { /* "34" */
+ 0x33, 0x34
+};
+
+static BYTE NLSALLOC(040a) rgbSCOUNTRY[] = { /* "Spain" */
+ 0x53, 0x70, 0x61, 0x69, 0x6e
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVCTRYNAME[] = { /* "ESP" */
+ 0x45, 0x53, 0x50
+};
+
+static BYTE NLSALLOC(040a) rgbSNATIVECTRYNAME[] = { /* "España" */
+ 0x45, 0x73, 0x70, 0x61, 0xf1, 0x61
+};
+
+static BYTE NLSALLOC(040a) rgbIDEFAULTLANGUAGE[] = { /* "040a" */
+ 0x30, 0x34, 0x30, 0x61
+};
+
+static BYTE NLSALLOC(040a) rgbIDEFAULTCOUNTRY[] = { /* "34" */
+ 0x33, 0x34
+};
+
+static BYTE NLSALLOC(040a) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(040a) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(040a) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040a) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(040a) rgbSTHOUSAND[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(040a) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(040a) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040a) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040a) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(040a) rgbSCURRENCY[] = { /* "Pts" */
+ 0x50, 0x74, 0x73
+};
+
+static BYTE NLSALLOC(040a) rgbSINTLSYMBOL[] = { /* "ESP" */
+ 0x45, 0x53, 0x50
+};
+
+static BYTE NLSALLOC(040a) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(040a) rgbSMONTHOUSANDSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(040a) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(040a) rgbICURRDIGITS[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040a) rgbIINTLCURRDIGITS[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040a) rgbICURRENCY[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(040a) rgbINEGCURR[] = { /* "8" */
+ 0x38
+};
+
+static BYTE NLSALLOC(040a) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(040a) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(040a) rgbSSHORTDATE[] = { /* "d/MM/yy" */
+ 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(040a) rgbSLONGDATE[] = { /* "dddd d' de 'MMMM' de 'yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x20, 0x64, 0x27, 0x20
+ , 0x64, 0x65, 0x20, 0x27, 0x4d, 0x4d, 0x4d, 0x4d
+ , 0x27, 0x20, 0x64, 0x65, 0x20, 0x27, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(040a) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040a) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040a) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040a) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040a) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040a) rgbIDAYLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040a) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040a) rgbSDAYNAME1[] = { /* "lunes" */
+ 0x6c, 0x75, 0x6e, 0x65, 0x73
+};
+
+static BYTE NLSALLOC(040a) rgbSDAYNAME2[] = { /* "martes" */
+ 0x6d, 0x61, 0x72, 0x74, 0x65, 0x73
+};
+
+static BYTE NLSALLOC(040a) rgbSDAYNAME3[] = { /* "miércoles" */
+ 0x6d, 0x69, 0xe9, 0x72, 0x63, 0x6f, 0x6c, 0x65
+ , 0x73
+};
+
+static BYTE NLSALLOC(040a) rgbSDAYNAME4[] = { /* "jueves" */
+ 0x6a, 0x75, 0x65, 0x76, 0x65, 0x73
+};
+
+static BYTE NLSALLOC(040a) rgbSDAYNAME5[] = { /* "viernes" */
+ 0x76, 0x69, 0x65, 0x72, 0x6e, 0x65, 0x73
+};
+
+static BYTE NLSALLOC(040a) rgbSDAYNAME6[] = { /* "sábado" */
+ 0x73, 0xe1, 0x62, 0x61, 0x64, 0x6f
+};
+
+static BYTE NLSALLOC(040a) rgbSDAYNAME7[] = { /* "domingo" */
+ 0x64, 0x6f, 0x6d, 0x69, 0x6e, 0x67, 0x6f
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVDAYNAME1[] = { /* "lun" */
+ 0x6c, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVDAYNAME2[] = { /* "mar" */
+ 0x6d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVDAYNAME3[] = { /* "mié" */
+ 0x6d, 0x69, 0xe9
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVDAYNAME4[] = { /* "jue" */
+ 0x6a, 0x75, 0x65
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVDAYNAME5[] = { /* "vie" */
+ 0x76, 0x69, 0x65
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVDAYNAME6[] = { /* "sáb" */
+ 0x73, 0xe1, 0x62
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVDAYNAME7[] = { /* "dom" */
+ 0x64, 0x6f, 0x6d
+};
+
+static BYTE NLSALLOC(040a) rgbSMONTHNAME1[] = { /* "enero" */
+ 0x65, 0x6e, 0x65, 0x72, 0x6f
+};
+
+static BYTE NLSALLOC(040a) rgbSMONTHNAME2[] = { /* "febrero" */
+ 0x66, 0x65, 0x62, 0x72, 0x65, 0x72, 0x6f
+};
+
+static BYTE NLSALLOC(040a) rgbSMONTHNAME3[] = { /* "marzo" */
+ 0x6d, 0x61, 0x72, 0x7a, 0x6f
+};
+
+static BYTE NLSALLOC(040a) rgbSMONTHNAME4[] = { /* "abril" */
+ 0x61, 0x62, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(040a) rgbSMONTHNAME5[] = { /* "mayo" */
+ 0x6d, 0x61, 0x79, 0x6f
+};
+
+static BYTE NLSALLOC(040a) rgbSMONTHNAME6[] = { /* "junio" */
+ 0x6a, 0x75, 0x6e, 0x69, 0x6f
+};
+
+static BYTE NLSALLOC(040a) rgbSMONTHNAME7[] = { /* "julio" */
+ 0x6a, 0x75, 0x6c, 0x69, 0x6f
+};
+
+static BYTE NLSALLOC(040a) rgbSMONTHNAME8[] = { /* "agosto" */
+ 0x61, 0x67, 0x6f, 0x73, 0x74, 0x6f
+};
+
+static BYTE NLSALLOC(040a) rgbSMONTHNAME9[] = { /* "septiembre" */
+ 0x73, 0x65, 0x70, 0x74, 0x69, 0x65, 0x6d, 0x62
+ , 0x72, 0x65
+};
+
+static BYTE NLSALLOC(040a) rgbSMONTHNAME10[] = { /* "octubre" */
+ 0x6f, 0x63, 0x74, 0x75, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(040a) rgbSMONTHNAME11[] = { /* "noviembre" */
+ 0x6e, 0x6f, 0x76, 0x69, 0x65, 0x6d, 0x62, 0x72
+ , 0x65
+};
+
+static BYTE NLSALLOC(040a) rgbSMONTHNAME12[] = { /* "diciembre" */
+ 0x64, 0x69, 0x63, 0x69, 0x65, 0x6d, 0x62, 0x72
+ , 0x65
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVMONTHNAME1[] = { /* "ene" */
+ 0x65, 0x6e, 0x65
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVMONTHNAME2[] = { /* "feb" */
+ 0x66, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVMONTHNAME3[] = { /* "mar" */
+ 0x6d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVMONTHNAME4[] = { /* "abr" */
+ 0x61, 0x62, 0x72
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVMONTHNAME5[] = { /* "may" */
+ 0x6d, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVMONTHNAME6[] = { /* "jun" */
+ 0x6a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVMONTHNAME7[] = { /* "jul" */
+ 0x6a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVMONTHNAME8[] = { /* "ago" */
+ 0x61, 0x67, 0x6f
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVMONTHNAME9[] = { /* "sep" */
+ 0x73, 0x65, 0x70
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVMONTHNAME10[] = { /* "oct" */
+ 0x6f, 0x63, 0x74
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVMONTHNAME11[] = { /* "nov" */
+ 0x6e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(040a) rgbSABBREVMONTHNAME12[] = { /* "dic" */
+ 0x64, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(040a) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(040a) rgbIPOSSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040a) rgbINEGSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040a) rgbIPOSSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040a) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040a) rgbINEGSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040a) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040a) rgbSENGCOUNTRY[] = { /* "Spain" */
+ 0x53, 0x70, 0x61, 0x69, 0x6e
+};
+
+static BYTE NLSALLOC(040a) rgbSENGLANGUAGE[] = { /* "Spanish - Traditional Sort" */
+ 0x53, 0x70, 0x61, 0x6e, 0x69, 0x73, 0x68, 0x20
+ , 0x2d, 0x20, 0x54, 0x72, 0x61, 0x64, 0x69, 0x74
+ , 0x69, 0x6f, 0x6e, 0x61, 0x6c, 0x20, 0x53, 0x6f
+ , 0x72, 0x74
+};
+
+static BYTE NLSALLOC(040a) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040a) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040a) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(040a) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040a) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(040a) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040a) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040a) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(040a) g_rglcinfo040a[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 26, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 5, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 6, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 3, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 7, rgbSSHORTDATE }
+ , { 26, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 5, rgbSDAYNAME1 }
+ , { 6, rgbSDAYNAME2 }
+ , { 9, rgbSDAYNAME3 }
+ , { 6, rgbSDAYNAME4 }
+ , { 7, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 7, rgbSDAYNAME7 }
+ , { 3, rgbSABBREVDAYNAME1 }
+ , { 3, rgbSABBREVDAYNAME2 }
+ , { 3, rgbSABBREVDAYNAME3 }
+ , { 3, rgbSABBREVDAYNAME4 }
+ , { 3, rgbSABBREVDAYNAME5 }
+ , { 3, rgbSABBREVDAYNAME6 }
+ , { 3, rgbSABBREVDAYNAME7 }
+ , { 5, rgbSMONTHNAME1 }
+ , { 7, rgbSMONTHNAME2 }
+ , { 5, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 4, rgbSMONTHNAME5 }
+ , { 5, rgbSMONTHNAME6 }
+ , { 5, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 10, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 9, rgbSMONTHNAME11 }
+ , { 9, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 5, rgbSENGCOUNTRY }
+ , { 26, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(040a) g_strinfo040a = {
+ rgbUCase_040a
+ , rgbLCase_040a
+ , rgwCType12_040a
+ , rgwCType3_040a
+ , rgwSort_040a
+ , rgexp_040a
+ , rgdig_040a
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/040b.c b/private/oleauto/src/dispatch/win16/040b.c
new file mode 100644
index 000000000..372b500a5
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/040b.c
@@ -0,0 +1,526 @@
+/****************************************************************************
+* 040b.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Finnish - Finland
+*
+* LCID = 0x040b
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 18:00:59 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_041d[256]; // from 041d:Swedish - Sweden
+extern EXPANSION rgexp_041d[7];
+extern WORD rgwCType12_041d[256];
+extern WORD rgwCType3_041d[256];
+extern BYTE rgbUCase_041d[256];
+extern BYTE rgbLCase_041d[256];
+
+static BYTE NLSALLOC(040b) rgbILANGUAGE[] = { /* "040b" */
+ 0x30, 0x34, 0x30, 0x62
+};
+
+static BYTE NLSALLOC(040b) rgbSLANGUAGE[] = { /* "Finnish" */
+ 0x46, 0x69, 0x6e, 0x6e, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVLANGNAME[] = { /* "FIN" */
+ 0x46, 0x49, 0x4e
+};
+
+static BYTE NLSALLOC(040b) rgbSNATIVELANGNAME[] = { /* "suomi" */
+ 0x73, 0x75, 0x6f, 0x6d, 0x69
+};
+
+static BYTE NLSALLOC(040b) rgbICOUNTRY[] = { /* "358" */
+ 0x33, 0x35, 0x38
+};
+
+static BYTE NLSALLOC(040b) rgbSCOUNTRY[] = { /* "Finland" */
+ 0x46, 0x69, 0x6e, 0x6c, 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVCTRYNAME[] = { /* "FIN" */
+ 0x46, 0x49, 0x4e
+};
+
+static BYTE NLSALLOC(040b) rgbSNATIVECTRYNAME[] = { /* "Suomi" */
+ 0x53, 0x75, 0x6f, 0x6d, 0x69
+};
+
+static BYTE NLSALLOC(040b) rgbIDEFAULTLANGUAGE[] = { /* "040b" */
+ 0x30, 0x34, 0x30, 0x62
+};
+
+static BYTE NLSALLOC(040b) rgbIDEFAULTCOUNTRY[] = { /* "358" */
+ 0x33, 0x35, 0x38
+};
+
+static BYTE NLSALLOC(040b) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(040b) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(040b) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040b) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(040b) rgbSTHOUSAND[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(040b) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(040b) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040b) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040b) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(040b) rgbSCURRENCY[] = { /* "mk" */
+ 0x6d, 0x6b
+};
+
+static BYTE NLSALLOC(040b) rgbSINTLSYMBOL[] = { /* "FIM" */
+ 0x46, 0x49, 0x4d
+};
+
+static BYTE NLSALLOC(040b) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(040b) rgbSMONTHOUSANDSEP[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(040b) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(040b) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040b) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040b) rgbICURRENCY[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(040b) rgbINEGCURR[] = { /* "8" */
+ 0x38
+};
+
+static BYTE NLSALLOC(040b) rgbSDATE[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(040b) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(040b) rgbSSHORTDATE[] = { /* "d.M.yyyy" */
+ 0x64, 0x2e, 0x4d, 0x2e, 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(040b) rgbSLONGDATE[] = { /* "d. MMMM'ta 'yyyy" */
+ 0x64, 0x2e, 0x20, 0x4d, 0x4d, 0x4d, 0x4d, 0x27
+ , 0x74, 0x61, 0x20, 0x27, 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(040b) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040b) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040b) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040b) rgbICENTURY[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040b) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040b) rgbIDAYLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040b) rgbIMONLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040b) rgbSDAYNAME1[] = { /* "maanantai" */
+ 0x6d, 0x61, 0x61, 0x6e, 0x61, 0x6e, 0x74, 0x61
+ , 0x69
+};
+
+static BYTE NLSALLOC(040b) rgbSDAYNAME2[] = { /* "tiistai" */
+ 0x74, 0x69, 0x69, 0x73, 0x74, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(040b) rgbSDAYNAME3[] = { /* "keskiviikko" */
+ 0x6b, 0x65, 0x73, 0x6b, 0x69, 0x76, 0x69, 0x69
+ , 0x6b, 0x6b, 0x6f
+};
+
+static BYTE NLSALLOC(040b) rgbSDAYNAME4[] = { /* "torstai" */
+ 0x74, 0x6f, 0x72, 0x73, 0x74, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(040b) rgbSDAYNAME5[] = { /* "perjantai" */
+ 0x70, 0x65, 0x72, 0x6a, 0x61, 0x6e, 0x74, 0x61
+ , 0x69
+};
+
+static BYTE NLSALLOC(040b) rgbSDAYNAME6[] = { /* "lauantai" */
+ 0x6c, 0x61, 0x75, 0x61, 0x6e, 0x74, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(040b) rgbSDAYNAME7[] = { /* "sunnuntai" */
+ 0x73, 0x75, 0x6e, 0x6e, 0x75, 0x6e, 0x74, 0x61
+ , 0x69
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVDAYNAME1[] = { /* "ma" */
+ 0x6d, 0x61
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVDAYNAME2[] = { /* "ti" */
+ 0x74, 0x69
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVDAYNAME3[] = { /* "ke" */
+ 0x6b, 0x65
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVDAYNAME4[] = { /* "to" */
+ 0x74, 0x6f
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVDAYNAME5[] = { /* "pe" */
+ 0x70, 0x65
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVDAYNAME6[] = { /* "la" */
+ 0x6c, 0x61
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVDAYNAME7[] = { /* "su" */
+ 0x73, 0x75
+};
+
+static BYTE NLSALLOC(040b) rgbSMONTHNAME1[] = { /* "tammikuu" */
+ 0x74, 0x61, 0x6d, 0x6d, 0x69, 0x6b, 0x75, 0x75
+};
+
+static BYTE NLSALLOC(040b) rgbSMONTHNAME2[] = { /* "helmikuu" */
+ 0x68, 0x65, 0x6c, 0x6d, 0x69, 0x6b, 0x75, 0x75
+};
+
+static BYTE NLSALLOC(040b) rgbSMONTHNAME3[] = { /* "maaliskuu" */
+ 0x6d, 0x61, 0x61, 0x6c, 0x69, 0x73, 0x6b, 0x75
+ , 0x75
+};
+
+static BYTE NLSALLOC(040b) rgbSMONTHNAME4[] = { /* "huhtikuu" */
+ 0x68, 0x75, 0x68, 0x74, 0x69, 0x6b, 0x75, 0x75
+};
+
+static BYTE NLSALLOC(040b) rgbSMONTHNAME5[] = { /* "toukokuu" */
+ 0x74, 0x6f, 0x75, 0x6b, 0x6f, 0x6b, 0x75, 0x75
+};
+
+static BYTE NLSALLOC(040b) rgbSMONTHNAME6[] = { /* "kesäkuu" */
+ 0x6b, 0x65, 0x73, 0xe4, 0x6b, 0x75, 0x75
+};
+
+static BYTE NLSALLOC(040b) rgbSMONTHNAME7[] = { /* "heinäkuu" */
+ 0x68, 0x65, 0x69, 0x6e, 0xe4, 0x6b, 0x75, 0x75
+};
+
+static BYTE NLSALLOC(040b) rgbSMONTHNAME8[] = { /* "elokuu" */
+ 0x65, 0x6c, 0x6f, 0x6b, 0x75, 0x75
+};
+
+static BYTE NLSALLOC(040b) rgbSMONTHNAME9[] = { /* "syyskuu" */
+ 0x73, 0x79, 0x79, 0x73, 0x6b, 0x75, 0x75
+};
+
+static BYTE NLSALLOC(040b) rgbSMONTHNAME10[] = { /* "lokakuu" */
+ 0x6c, 0x6f, 0x6b, 0x61, 0x6b, 0x75, 0x75
+};
+
+static BYTE NLSALLOC(040b) rgbSMONTHNAME11[] = { /* "marraskuu" */
+ 0x6d, 0x61, 0x72, 0x72, 0x61, 0x73, 0x6b, 0x75
+ , 0x75
+};
+
+static BYTE NLSALLOC(040b) rgbSMONTHNAME12[] = { /* "joulukuu" */
+ 0x6a, 0x6f, 0x75, 0x6c, 0x75, 0x6b, 0x75, 0x75
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVMONTHNAME1[] = { /* "tammi" */
+ 0x74, 0x61, 0x6d, 0x6d, 0x69
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVMONTHNAME2[] = { /* "helmi" */
+ 0x68, 0x65, 0x6c, 0x6d, 0x69
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVMONTHNAME3[] = { /* "maalis" */
+ 0x6d, 0x61, 0x61, 0x6c, 0x69, 0x73
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVMONTHNAME4[] = { /* "huhti" */
+ 0x68, 0x75, 0x68, 0x74, 0x69
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVMONTHNAME5[] = { /* "touko" */
+ 0x74, 0x6f, 0x75, 0x6b, 0x6f
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVMONTHNAME6[] = { /* "kesä" */
+ 0x6b, 0x65, 0x73, 0xe4
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVMONTHNAME7[] = { /* "heinä" */
+ 0x68, 0x65, 0x69, 0x6e, 0xe4
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVMONTHNAME8[] = { /* "elo" */
+ 0x65, 0x6c, 0x6f
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVMONTHNAME9[] = { /* "syys" */
+ 0x73, 0x79, 0x79, 0x73
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVMONTHNAME10[] = { /* "loka" */
+ 0x6c, 0x6f, 0x6b, 0x61
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVMONTHNAME11[] = { /* "marras" */
+ 0x6d, 0x61, 0x72, 0x72, 0x61, 0x73
+};
+
+static BYTE NLSALLOC(040b) rgbSABBREVMONTHNAME12[] = { /* "joulu" */
+ 0x6a, 0x6f, 0x75, 0x6c, 0x75
+};
+
+static BYTE NLSALLOC(040b) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(040b) rgbIPOSSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040b) rgbINEGSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040b) rgbIPOSSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040b) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040b) rgbINEGSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040b) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040b) rgbSENGCOUNTRY[] = { /* "Finland" */
+ 0x46, 0x69, 0x6e, 0x6c, 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(040b) rgbSENGLANGUAGE[] = { /* "Finnish" */
+ 0x46, 0x69, 0x6e, 0x6e, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(040b) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040b) rgbIFIRSTWEEKOFYEAR[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040b) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(040b) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040b) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(040b) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040b) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040b) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(040b) g_rglcinfo040b[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 7, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 5, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 7, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 5, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 2, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 16, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 9, rgbSDAYNAME1 }
+ , { 7, rgbSDAYNAME2 }
+ , { 11, rgbSDAYNAME3 }
+ , { 7, rgbSDAYNAME4 }
+ , { 9, rgbSDAYNAME5 }
+ , { 8, rgbSDAYNAME6 }
+ , { 9, rgbSDAYNAME7 }
+ , { 2, rgbSABBREVDAYNAME1 }
+ , { 2, rgbSABBREVDAYNAME2 }
+ , { 2, rgbSABBREVDAYNAME3 }
+ , { 2, rgbSABBREVDAYNAME4 }
+ , { 2, rgbSABBREVDAYNAME5 }
+ , { 2, rgbSABBREVDAYNAME6 }
+ , { 2, rgbSABBREVDAYNAME7 }
+ , { 8, rgbSMONTHNAME1 }
+ , { 8, rgbSMONTHNAME2 }
+ , { 9, rgbSMONTHNAME3 }
+ , { 8, rgbSMONTHNAME4 }
+ , { 8, rgbSMONTHNAME5 }
+ , { 7, rgbSMONTHNAME6 }
+ , { 8, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 7, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 9, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 5, rgbSABBREVMONTHNAME1 }
+ , { 5, rgbSABBREVMONTHNAME2 }
+ , { 6, rgbSABBREVMONTHNAME3 }
+ , { 5, rgbSABBREVMONTHNAME4 }
+ , { 5, rgbSABBREVMONTHNAME5 }
+ , { 4, rgbSABBREVMONTHNAME6 }
+ , { 5, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 4, rgbSABBREVMONTHNAME9 }
+ , { 4, rgbSABBREVMONTHNAME10 }
+ , { 6, rgbSABBREVMONTHNAME11 }
+ , { 5, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 7, rgbSENGCOUNTRY }
+ , { 7, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(040b) g_strinfo040b = {
+ rgbUCase_041d
+ , rgbLCase_041d
+ , rgwCType12_041d
+ , rgwCType3_041d
+ , rgwSort_041d
+ , rgexp_041d
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/040c.c b/private/oleauto/src/dispatch/win16/040c.c
new file mode 100644
index 000000000..d9d667bed
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/040c.c
@@ -0,0 +1,521 @@
+/****************************************************************************
+* 040c.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* French - France
+*
+* LCID = 0x040c
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:35:52 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0409[256]; // from 0409:English - United States
+extern EXPANSION rgexp_0409[7];
+extern WORD rgwCType12_0409[256];
+extern WORD rgwCType3_0409[256];
+extern BYTE rgbUCase_0409[256];
+extern BYTE rgbLCase_0409[256];
+
+static BYTE NLSALLOC(040c) rgbILANGUAGE[] = { /* "040c" */
+ 0x30, 0x34, 0x30, 0x63
+};
+
+static BYTE NLSALLOC(040c) rgbSLANGUAGE[] = { /* "French" */
+ 0x46, 0x72, 0x65, 0x6e, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVLANGNAME[] = { /* "FRA" */
+ 0x46, 0x52, 0x41
+};
+
+static BYTE NLSALLOC(040c) rgbSNATIVELANGNAME[] = { /* "français" */
+ 0x66, 0x72, 0x61, 0x6e, 0xe7, 0x61, 0x69, 0x73
+};
+
+static BYTE NLSALLOC(040c) rgbICOUNTRY[] = { /* "33" */
+ 0x33, 0x33
+};
+
+static BYTE NLSALLOC(040c) rgbSCOUNTRY[] = { /* "France" */
+ 0x46, 0x72, 0x61, 0x6e, 0x63, 0x65
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVCTRYNAME[] = { /* "FRA" */
+ 0x46, 0x52, 0x41
+};
+
+static BYTE NLSALLOC(040c) rgbSNATIVECTRYNAME[] = { /* "France" */
+ 0x46, 0x72, 0x61, 0x6e, 0x63, 0x65
+};
+
+static BYTE NLSALLOC(040c) rgbIDEFAULTLANGUAGE[] = { /* "040c" */
+ 0x30, 0x34, 0x30, 0x63
+};
+
+static BYTE NLSALLOC(040c) rgbIDEFAULTCOUNTRY[] = { /* "33" */
+ 0x33, 0x33
+};
+
+static BYTE NLSALLOC(040c) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(040c) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(040c) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040c) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(040c) rgbSTHOUSAND[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(040c) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(040c) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040c) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040c) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(040c) rgbSCURRENCY[] = { /* "F" */
+ 0x46
+};
+
+static BYTE NLSALLOC(040c) rgbSINTLSYMBOL[] = { /* "FRF" */
+ 0x46, 0x52, 0x46
+};
+
+static BYTE NLSALLOC(040c) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(040c) rgbSMONTHOUSANDSEP[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(040c) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(040c) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040c) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040c) rgbICURRENCY[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(040c) rgbINEGCURR[] = { /* "8" */
+ 0x38
+};
+
+static BYTE NLSALLOC(040c) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(040c) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(040c) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(040c) rgbSLONGDATE[] = { /* "dddd d MMMM yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x20, 0x64, 0x20, 0x4d
+ , 0x4d, 0x4d, 0x4d, 0x20, 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(040c) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040c) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040c) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040c) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040c) rgbITLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040c) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040c) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040c) rgbSDAYNAME1[] = { /* "lundi" */
+ 0x6c, 0x75, 0x6e, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(040c) rgbSDAYNAME2[] = { /* "mardi" */
+ 0x6d, 0x61, 0x72, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(040c) rgbSDAYNAME3[] = { /* "mercredi" */
+ 0x6d, 0x65, 0x72, 0x63, 0x72, 0x65, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(040c) rgbSDAYNAME4[] = { /* "jeudi" */
+ 0x6a, 0x65, 0x75, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(040c) rgbSDAYNAME5[] = { /* "vendredi" */
+ 0x76, 0x65, 0x6e, 0x64, 0x72, 0x65, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(040c) rgbSDAYNAME6[] = { /* "samedi" */
+ 0x73, 0x61, 0x6d, 0x65, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(040c) rgbSDAYNAME7[] = { /* "dimanche" */
+ 0x64, 0x69, 0x6d, 0x61, 0x6e, 0x63, 0x68, 0x65
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVDAYNAME1[] = { /* "lun." */
+ 0x6c, 0x75, 0x6e, 0x2e
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVDAYNAME2[] = { /* "mar." */
+ 0x6d, 0x61, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVDAYNAME3[] = { /* "mer." */
+ 0x6d, 0x65, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVDAYNAME4[] = { /* "jeu." */
+ 0x6a, 0x65, 0x75, 0x2e
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVDAYNAME5[] = { /* "ven." */
+ 0x76, 0x65, 0x6e, 0x2e
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVDAYNAME6[] = { /* "sam." */
+ 0x73, 0x61, 0x6d, 0x2e
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVDAYNAME7[] = { /* "dim." */
+ 0x64, 0x69, 0x6d, 0x2e
+};
+
+static BYTE NLSALLOC(040c) rgbSMONTHNAME1[] = { /* "janvier" */
+ 0x6a, 0x61, 0x6e, 0x76, 0x69, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(040c) rgbSMONTHNAME2[] = { /* "février" */
+ 0x66, 0xe9, 0x76, 0x72, 0x69, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(040c) rgbSMONTHNAME3[] = { /* "mars" */
+ 0x6d, 0x61, 0x72, 0x73
+};
+
+static BYTE NLSALLOC(040c) rgbSMONTHNAME4[] = { /* "avril" */
+ 0x61, 0x76, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(040c) rgbSMONTHNAME5[] = { /* "mai" */
+ 0x6d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(040c) rgbSMONTHNAME6[] = { /* "juin" */
+ 0x6a, 0x75, 0x69, 0x6e
+};
+
+static BYTE NLSALLOC(040c) rgbSMONTHNAME7[] = { /* "juillet" */
+ 0x6a, 0x75, 0x69, 0x6c, 0x6c, 0x65, 0x74
+};
+
+static BYTE NLSALLOC(040c) rgbSMONTHNAME8[] = { /* "août" */
+ 0x61, 0x6f, 0xfb, 0x74
+};
+
+static BYTE NLSALLOC(040c) rgbSMONTHNAME9[] = { /* "septembre" */
+ 0x73, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x72
+ , 0x65
+};
+
+static BYTE NLSALLOC(040c) rgbSMONTHNAME10[] = { /* "octobre" */
+ 0x6f, 0x63, 0x74, 0x6f, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(040c) rgbSMONTHNAME11[] = { /* "novembre" */
+ 0x6e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(040c) rgbSMONTHNAME12[] = { /* "décembre" */
+ 0x64, 0xe9, 0x63, 0x65, 0x6d, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVMONTHNAME1[] = { /* "janv." */
+ 0x6a, 0x61, 0x6e, 0x76, 0x2e
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVMONTHNAME2[] = { /* "févr." */
+ 0x66, 0xe9, 0x76, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVMONTHNAME3[] = { /* "mars" */
+ 0x6d, 0x61, 0x72, 0x73
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVMONTHNAME4[] = { /* "avr." */
+ 0x61, 0x76, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVMONTHNAME5[] = { /* "mai" */
+ 0x6d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVMONTHNAME6[] = { /* "juin" */
+ 0x6a, 0x75, 0x69, 0x6e
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVMONTHNAME7[] = { /* "juil." */
+ 0x6a, 0x75, 0x69, 0x6c, 0x2e
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVMONTHNAME8[] = { /* "août" */
+ 0x61, 0x6f, 0xfb, 0x74
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVMONTHNAME9[] = { /* "sept." */
+ 0x73, 0x65, 0x70, 0x74, 0x2e
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVMONTHNAME10[] = { /* "oct." */
+ 0x6f, 0x63, 0x74, 0x2e
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVMONTHNAME11[] = { /* "nov." */
+ 0x6e, 0x6f, 0x76, 0x2e
+};
+
+static BYTE NLSALLOC(040c) rgbSABBREVMONTHNAME12[] = { /* "déc." */
+ 0x64, 0xe9, 0x63, 0x2e
+};
+
+static BYTE NLSALLOC(040c) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(040c) rgbIPOSSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040c) rgbINEGSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040c) rgbIPOSSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040c) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040c) rgbINEGSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040c) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040c) rgbSENGCOUNTRY[] = { /* "France" */
+ 0x46, 0x72, 0x61, 0x6e, 0x63, 0x65
+};
+
+static BYTE NLSALLOC(040c) rgbSENGLANGUAGE[] = { /* "French" */
+ 0x46, 0x72, 0x65, 0x6e, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(040c) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040c) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040c) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(040c) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040c) rgbSTIMEFORMAT[] = { /* "HH:mm:ss" */
+ 0x48, 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(040c) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040c) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040c) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(040c) g_rglcinfo040c[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 8, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 6, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 6, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 1, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 16, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 5, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 8, rgbSDAYNAME3 }
+ , { 5, rgbSDAYNAME4 }
+ , { 8, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 8, rgbSDAYNAME7 }
+ , { 4, rgbSABBREVDAYNAME1 }
+ , { 4, rgbSABBREVDAYNAME2 }
+ , { 4, rgbSABBREVDAYNAME3 }
+ , { 4, rgbSABBREVDAYNAME4 }
+ , { 4, rgbSABBREVDAYNAME5 }
+ , { 4, rgbSABBREVDAYNAME6 }
+ , { 4, rgbSABBREVDAYNAME7 }
+ , { 7, rgbSMONTHNAME1 }
+ , { 7, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 7, rgbSMONTHNAME7 }
+ , { 4, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 5, rgbSABBREVMONTHNAME1 }
+ , { 5, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 4, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 4, rgbSABBREVMONTHNAME6 }
+ , { 5, rgbSABBREVMONTHNAME7 }
+ , { 4, rgbSABBREVMONTHNAME8 }
+ , { 5, rgbSABBREVMONTHNAME9 }
+ , { 4, rgbSABBREVMONTHNAME10 }
+ , { 4, rgbSABBREVMONTHNAME11 }
+ , { 4, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 6, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 8, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(040c) g_strinfo040c = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/040d.c b/private/oleauto/src/dispatch/win16/040d.c
new file mode 100644
index 000000000..a8359f0e7
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/040d.c
@@ -0,0 +1,696 @@
+/****************************************************************************
+* 040d.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Hebrew - Israel
+*
+* LCID = 0x040d
+*
+* CodePage = 1255
+*
+* Generated: Thu Dec 01 18:25:21 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+WORD NLSALLOC(040d) rgwSort_040d[256] = {
+ 0x0000, 0xc018, 0xc019, 0xc01a, 0xc01b, 0xc01c, 0xc01d, 0xc01e
+ , 0xc01f, 0x4047, 0x4048, 0x4049, 0x404a, 0x404b, 0xc020, 0xc021
+ , 0xc022, 0xc023, 0xc024, 0xc025, 0xc026, 0xc027, 0xc028, 0xc029
+ , 0xc02a, 0xc02b, 0xc02c, 0xc02d, 0xc02e, 0xc02f, 0xc030, 0xc031
+ , 0x4045, 0x404c, 0x404d, 0x404e, 0x404f, 0x4050, 0x4051, 0xc040
+ , 0x4052, 0x4053, 0x4054, 0x4078, 0x4055, 0xc041, 0x4056, 0x4057
+ , 0x0092, 0x0096, 0x0097, 0x0098, 0x0099, 0x009a, 0x009b, 0x009c
+ , 0x009d, 0x009e, 0x4058, 0x4059, 0x4079, 0x407a, 0x407b, 0x405a
+ , 0x405b, 0x189f, 0x18a0, 0x18a1, 0x18a2, 0x18a3, 0x18a4, 0x18a5
+ , 0x18a6, 0x18a7, 0x18a8, 0x18a9, 0x18aa, 0x18ab, 0x18ac, 0x18ad
+ , 0x18ae, 0x18af, 0x18b0, 0x18b1, 0x18b2, 0x18b4, 0x18b5, 0x18b6
+ , 0x18b7, 0x18b8, 0x18b9, 0x405c, 0x405d, 0x405e, 0x405f, 0x4060
+ , 0x4061, 0x009f, 0x00a0, 0x00a1, 0x00a2, 0x00a3, 0x00a4, 0x00a5
+ , 0x00a6, 0x00a7, 0x00a8, 0x00a9, 0x00aa, 0x00ab, 0x00ac, 0x00ad
+ , 0x00ae, 0x00af, 0x00b0, 0x00b1, 0x00b2, 0x00b4, 0x00b5, 0x00b6
+ , 0x00b7, 0x00b8, 0x00b9, 0x4062, 0x4063, 0x4064, 0x4065, 0xc032
+ , 0xc033, 0xc034, 0x4072, 0x01a4, 0x4075, 0x4090, 0x408d, 0x408e
+ , 0x415f, 0x4091, 0xc035, 0x4076, 0xc036, 0xc037, 0xc038, 0xc039
+ , 0xc03a, 0x4070, 0x4071, 0x4073, 0x4074, 0x408f, 0xc043, 0xc044
+ , 0x406d, 0x18b3, 0xc03b, 0x4077, 0xc03c, 0xc03d, 0xc03e, 0xc03f
+ , 0x4046, 0x4066, 0x4081, 0x4082, 0x4083, 0x4084, 0x4067, 0x4085
+ , 0x4068, 0x4086, 0x407f, 0x407d, 0x4087, 0xc042, 0x4088, 0x4069
+ , 0x4089, 0x407c, 0x1097, 0x1098, 0x406a, 0x408a, 0x408b, 0x408c
+ , 0x406b, 0x1096, 0x4080, 0x407e, 0x0093, 0x0094, 0x0095, 0x406c
+ , 0x4007, 0x4008, 0x4009, 0x400a, 0x400b, 0x400c, 0x400d, 0x400e
+ , 0x400f, 0x4010, 0x08d0, 0x4011, 0x4012, 0x4013, 0x406e, 0x4014
+ , 0x4015, 0x4016, 0x4017, 0x406f, 0x08d1, 0x08d2, 0x08d3, 0x08d4
+ , 0x08d5, 0x08d6, 0x08d7, 0x08d8, 0x08d9, 0x08da, 0x08db, 0x08dc
+ , 0x00ba, 0x00bb, 0x00bc, 0x00bd, 0x00be, 0x00bf, 0x00c0, 0x00c1
+ , 0x00c2, 0x00c3, 0x18c4, 0x00c4, 0x00c5, 0x18c6, 0x00c6, 0x18c7
+ , 0x00c7, 0x00c8, 0x00c9, 0x18ca, 0x00ca, 0x18cb, 0x00cb, 0x00cc
+ , 0x00cd, 0x00ce, 0x00cf, 0x08dd, 0x08de, 0x0000, 0x0000, 0x08df
+};
+
+WORD NLSALLOC(040d) rgwCType12_040d[256] = {
+ 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x9068, 0x0028, 0x0028, 0x0028, 0x0028, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0xa048, 0xb010, 0xb010, 0x5010, 0x5010, 0x5010, 0x1010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0x5010, 0x7010, 0x5010, 0x4010, 0x4010
+ , 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084
+ , 0x3084, 0x3084, 0x7010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010, 0x0020
+ , 0x0020, 0x0020, 0xb010, 0x1112, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x5010, 0x0020, 0xb010, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0xb010, 0x0020, 0xb010, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0xa048, 0xb010, 0x5010, 0x5010, 0x5010, 0x5010, 0xb010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x5010, 0x5010, 0x3014, 0x3014, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x3014, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x2010, 0x2010, 0x2010, 0x2010, 0x2010, 0x2010, 0x2010, 0x2010
+ , 0x2010, 0x2010, 0x0000, 0x2010, 0x2010, 0x2010, 0x2010, 0x2010
+ , 0x2010, 0x2010, 0x2010, 0x2010, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x2100, 0x2100, 0x2100, 0x2100, 0x2100, 0x2100, 0x2100, 0x2100
+ , 0x2100, 0x2100, 0x2100, 0x2100, 0x2100, 0x2100, 0x2100, 0x2100
+ , 0x2100, 0x2100, 0x2100, 0x2100, 0x2100, 0x2100, 0x2100, 0x2100
+ , 0x2100, 0x2100, 0x2100, 0x0000, 0x0000, 0x1010, 0x2010, 0x0000
+};
+
+WORD NLSALLOC(040d) rgwCType3_040d[256] = {
+ 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0008, 0x0008, 0x0008, 0x0008, 0x0008, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0048, 0x0048, 0x0448, 0x0048, 0x0448, 0x0048, 0x0048, 0x0440
+ , 0x0048, 0x0048, 0x0048, 0x0048, 0x0048, 0x0440, 0x0048, 0x0448
+ , 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040
+ , 0x0040, 0x0040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0048, 0x0048
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0448, 0x0048, 0x0448, 0x0448
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0000
+ , 0x0000, 0x0000, 0x0008, 0x8000, 0x0008, 0x0008, 0x0008, 0x0008
+ , 0x0001, 0x0008, 0x0000, 0x0008, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0088, 0x0088, 0x0088, 0x0088, 0x0008, 0x0400, 0x0400
+ , 0x0408, 0x0000, 0x0000, 0x0008, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0008, 0x0008, 0x0048, 0x0048, 0x0008, 0x0048, 0x0048, 0x0008
+ , 0x0408, 0x0008, 0x0008, 0x0008, 0x0048, 0x0408, 0x0008, 0x0448
+ , 0x0008, 0x0008, 0x0000, 0x0000, 0x0408, 0x0008, 0x0008, 0x0008
+ , 0x0408, 0x0000, 0x0008, 0x0008, 0x0000, 0x0000, 0x0000, 0x0008
+ , 0x0001, 0x0001, 0x0001, 0x0001, 0x0001, 0x0001, 0x0001, 0x0001
+ , 0x0001, 0x0001, 0x0000, 0x0001, 0x0001, 0x0001, 0x0008, 0x0001
+ , 0x0008, 0x0001, 0x0001, 0x0008, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000
+ , 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000
+ , 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000
+ , 0x8000, 0x8000, 0x8000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+};
+
+BYTE NLSALLOC(040d) rgbUCase_040d[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
+};
+
+BYTE NLSALLOC(040d) rgbLCase_040d[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
+};
+
+static BYTE NLSALLOC(040d) rgbILANGUAGE[] = { /* "040d" */
+ 0x30, 0x34, 0x30, 0x64
+};
+
+static BYTE NLSALLOC(040d) rgbSLANGUAGE[] = { /* "Hebrew" */
+ 0x48, 0x65, 0x62, 0x72, 0x65, 0x77
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVLANGNAME[] = { /* "HEB" */
+ 0x48, 0x45, 0x42
+};
+
+static BYTE NLSALLOC(040d) rgbSNATIVELANGNAME[] = { /* "\x05e2\x05d1\x05e8\x05d9\x05ea" */
+ 0xf2, 0xe1, 0xf8, 0xe9, 0xfa
+};
+
+static BYTE NLSALLOC(040d) rgbICOUNTRY[] = { /* "972" */
+ 0x39, 0x37, 0x32
+};
+
+static BYTE NLSALLOC(040d) rgbSCOUNTRY[] = { /* "Israel" */
+ 0x49, 0x73, 0x72, 0x61, 0x65, 0x6c
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVCTRYNAME[] = { /* "ISR" */
+ 0x49, 0x53, 0x52
+};
+
+static BYTE NLSALLOC(040d) rgbSNATIVECTRYNAME[] = { /* "\x05d9\x05e9\x05e8\x05d0\x05dc" */
+ 0xe9, 0xf9, 0xf8, 0xe0, 0xec
+};
+
+static BYTE NLSALLOC(040d) rgbIDEFAULTLANGUAGE[] = { /* "040d" */
+ 0x30, 0x34, 0x30, 0x64
+};
+
+static BYTE NLSALLOC(040d) rgbIDEFAULTCOUNTRY[] = { /* "972" */
+ 0x39, 0x37, 0x32
+};
+
+static BYTE NLSALLOC(040d) rgbIDEFAULTCODEPAGE[] = { /* "862" */
+ 0x38, 0x36, 0x32
+};
+
+static BYTE NLSALLOC(040d) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(040d) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040d) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(040d) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(040d) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(040d) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040d) rgbILZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040d) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(040d) rgbSCURRENCY[] = { /* "\x00a4" */
+ 0xa4
+};
+
+static BYTE NLSALLOC(040d) rgbSINTLSYMBOL[] = { /* "ILS" */
+ 0x49, 0x4c, 0x53
+};
+
+static BYTE NLSALLOC(040d) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(040d) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(040d) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(040d) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040d) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040d) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040d) rgbINEGCURR[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040d) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(040d) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(040d) rgbSSHORTDATE[] = { /* "MM/dd/yy" */
+ 0x4d, 0x4d, 0x2f, 0x64, 0x64, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(040d) rgbSLONGDATE[] = { /* "MMMM dd, yyyy" */
+ 0x4d, 0x4d, 0x4d, 0x4d, 0x20, 0x64, 0x64, 0x2c
+ , 0x20, 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(040d) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040d) rgbILDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040d) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040d) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040d) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040d) rgbIDAYLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040d) rgbIMONLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040d) rgbS1159[] = { /* "AM" */
+ 0x41, 0x4d
+};
+
+static BYTE NLSALLOC(040d) rgbS2359[] = { /* "PM" */
+ 0x50, 0x4d
+};
+
+static BYTE NLSALLOC(040d) rgbSDAYNAME1[] = { /* "\x05e8\x05d0\x05e9\x05d5\x05df" */
+ 0xf8, 0xe0, 0xf9, 0xe5, 0xef
+};
+
+static BYTE NLSALLOC(040d) rgbSDAYNAME2[] = { /* "\x05e9\x05e0\x05d9" */
+ 0xf9, 0xf0, 0xe9
+};
+
+static BYTE NLSALLOC(040d) rgbSDAYNAME3[] = { /* "\x05e9\x05dc\x05d9\x05e9\x05d9" */
+ 0xf9, 0xec, 0xe9, 0xf9, 0xe9
+};
+
+static BYTE NLSALLOC(040d) rgbSDAYNAME4[] = { /* "\x05e8\x05d1\x05d9\x05e2\x05d9" */
+ 0xf8, 0xe1, 0xe9, 0xf2, 0xe9
+};
+
+static BYTE NLSALLOC(040d) rgbSDAYNAME5[] = { /* "\x05d7\x05de\x05d9\x05e9\x05d9" */
+ 0xe7, 0xee, 0xe9, 0xf9, 0xe9
+};
+
+static BYTE NLSALLOC(040d) rgbSDAYNAME6[] = { /* "\x05e9\x05e9\x05d9" */
+ 0xf9, 0xf9, 0xe9
+};
+
+static BYTE NLSALLOC(040d) rgbSDAYNAME7[] = { /* "\x05e9\x05d1\x05ea" */
+ 0xf9, 0xe1, 0xfa
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVDAYNAME1[] = { /* "\x05d0" */
+ 0xe0
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVDAYNAME2[] = { /* "\x05d1" */
+ 0xe1
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVDAYNAME3[] = { /* "\x05d2" */
+ 0xe2
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVDAYNAME4[] = { /* "\x05d3" */
+ 0xe3
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVDAYNAME5[] = { /* "\x05d4" */
+ 0xe4
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVDAYNAME6[] = { /* "\x05d5" */
+ 0xe5
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVDAYNAME7[] = { /* "\x05e9" */
+ 0xf9
+};
+
+static BYTE NLSALLOC(040d) rgbSMONTHNAME1[] = { /* "\x05ea\x05e9\x05e8\x05d9" */
+ 0xfa, 0xf9, 0xf8, 0xe9
+};
+
+static BYTE NLSALLOC(040d) rgbSMONTHNAME2[] = { /* "\x05d7\x05e9\x05d5\x05df" */
+ 0xe7, 0xf9, 0xe5, 0xef
+};
+
+static BYTE NLSALLOC(040d) rgbSMONTHNAME3[] = { /* "\x05db\x05e1\x05dc\x05d5" */
+ 0xeb, 0xf1, 0xec, 0xe5
+};
+
+static BYTE NLSALLOC(040d) rgbSMONTHNAME4[] = { /* "\x05d8\x05d1\x05ea" */
+ 0xe8, 0xe1, 0xfa
+};
+
+static BYTE NLSALLOC(040d) rgbSMONTHNAME5[] = { /* "\x05e9\x05d1\x05d8" */
+ 0xf9, 0xe1, 0xe8
+};
+
+static BYTE NLSALLOC(040d) rgbSMONTHNAME6[] = { /* "\x05d0\x05d3\x05e8" */
+ 0xe0, 0xe3, 0xf8
+};
+
+static BYTE NLSALLOC(040d) rgbSMONTHNAME7[] = { /* "\x05e0\x05d9\x05e1\x05df" */
+ 0xf0, 0xe9, 0xf1, 0xef
+};
+
+static BYTE NLSALLOC(040d) rgbSMONTHNAME8[] = { /* "\x05d0\x05d9\x05d9\x05e8" */
+ 0xe0, 0xe9, 0xe9, 0xf8
+};
+
+static BYTE NLSALLOC(040d) rgbSMONTHNAME9[] = { /* "\x05e1\x05d9\x05d5\x05df" */
+ 0xf1, 0xe9, 0xe5, 0xef
+};
+
+static BYTE NLSALLOC(040d) rgbSMONTHNAME10[] = { /* "\x05ea\x05de\x05d5\x05d6" */
+ 0xfa, 0xee, 0xe5, 0xe6
+};
+
+static BYTE NLSALLOC(040d) rgbSMONTHNAME11[] = { /* "\x05d0\x05d1" */
+ 0xe0, 0xe1
+};
+
+static BYTE NLSALLOC(040d) rgbSMONTHNAME12[] = { /* "\x05d0\x05dc\x05d5\x05dc" */
+ 0xe0, 0xec, 0xe5, 0xec
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVMONTHNAME1[] = { /* "\x05ea\x05e9\x05e8" */
+ 0xfa, 0xf9, 0xf8
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVMONTHNAME2[] = { /* "\x05d7\x05e9\x05d5" */
+ 0xe7, 0xf9, 0xe5
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVMONTHNAME3[] = { /* "\x05db\x05e1\x05dc" */
+ 0xeb, 0xf1, 0xec
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVMONTHNAME4[] = { /* "\x05d8\x05d1\x05ea" */
+ 0xe8, 0xe1, 0xfa
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVMONTHNAME5[] = { /* "\x05e9\x05d1\x05d8" */
+ 0xf9, 0xe1, 0xe8
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVMONTHNAME6[] = { /* "\x05d0\x05d3\x05e8" */
+ 0xe0, 0xe3, 0xf8
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVMONTHNAME7[] = { /* "\x05e0\x05d9\x05e1" */
+ 0xf0, 0xe9, 0xf1
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVMONTHNAME8[] = { /* "\x05d0\x05d9\x05d9" */
+ 0xe0, 0xe9, 0xe9
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVMONTHNAME9[] = { /* "\x05e1\x05d9\x05d5" */
+ 0xf1, 0xe9, 0xe5
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVMONTHNAME10[] = { /* "\x05ea\x05de\x05d5" */
+ 0xfa, 0xee, 0xe5
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVMONTHNAME11[] = { /* "\x05d0\x05d1" */
+ 0xe0, 0xe1
+};
+
+static BYTE NLSALLOC(040d) rgbSABBREVMONTHNAME12[] = { /* "\x05d0\x05dc\x05d5" */
+ 0xe0, 0xec, 0xe5
+};
+
+static BYTE NLSALLOC(040d) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(040d) rgbIPOSSIGNPOSN[] = { /* "4" */
+ 0x34
+};
+
+static BYTE NLSALLOC(040d) rgbINEGSIGNPOSN[] = { /* "4" */
+ 0x34
+};
+
+static BYTE NLSALLOC(040d) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040d) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040d) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040d) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040d) rgbSENGCOUNTRY[] = { /* "Israel" */
+ 0x49, 0x73, 0x72, 0x61, 0x65, 0x6c
+};
+
+static BYTE NLSALLOC(040d) rgbSENGLANGUAGE[] = { /* "Hebrew" */
+ 0x48, 0x65, 0x62, 0x72, 0x65, 0x77
+};
+
+static BYTE NLSALLOC(040d) rgbIFIRSTDAYOFWEEK[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040d) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040d) rgbIDEFAULTANSICODEPAGE[] = { /* "1255" */
+ 0x31, 0x32, 0x35, 0x35
+};
+
+static BYTE NLSALLOC(040d) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040d) rgbSTIMEFORMAT[] = { /* "HH:mm:ss" */
+ 0x48, 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(040d) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040d) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040d) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(040d) g_rglcinfo040d[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 5, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 6, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 5, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 1, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 13, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 2, rgbS1159 }
+ , { 2, rgbS2359 }
+ , { 5, rgbSDAYNAME1 }
+ , { 3, rgbSDAYNAME2 }
+ , { 5, rgbSDAYNAME3 }
+ , { 5, rgbSDAYNAME4 }
+ , { 5, rgbSDAYNAME5 }
+ , { 3, rgbSDAYNAME6 }
+ , { 3, rgbSDAYNAME7 }
+ , { 1, rgbSABBREVDAYNAME1 }
+ , { 1, rgbSABBREVDAYNAME2 }
+ , { 1, rgbSABBREVDAYNAME3 }
+ , { 1, rgbSABBREVDAYNAME4 }
+ , { 1, rgbSABBREVDAYNAME5 }
+ , { 1, rgbSABBREVDAYNAME6 }
+ , { 1, rgbSABBREVDAYNAME7 }
+ , { 4, rgbSMONTHNAME1 }
+ , { 4, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 3, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 3, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 4, rgbSMONTHNAME8 }
+ , { 4, rgbSMONTHNAME9 }
+ , { 4, rgbSMONTHNAME10 }
+ , { 2, rgbSMONTHNAME11 }
+ , { 4, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 2, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 6, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 8, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(040d) g_strinfo040d = {
+ rgbUCase_040d
+ , rgbLCase_040d
+ , rgwCType12_040d
+ , rgwCType3_040d
+ , rgwSort_040d
+ , NULL
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/040e.c b/private/oleauto/src/dispatch/win16/040e.c
new file mode 100644
index 000000000..96b5b89f7
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/040e.c
@@ -0,0 +1,750 @@
+/****************************************************************************
+* 040e.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Hungarian - Hungary
+*
+* LCID = 0x040e
+*
+* CodePage = 1250
+*
+* Generated: Thu Dec 01 18:07:58 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+WORD NLSALLOC(040e) rgwSort_040e[256] = {
+ 0x0000, 0xc007, 0xc008, 0xc009, 0xc00a, 0xc00b, 0xc00c, 0xc00d
+ , 0xc00e, 0x402f, 0x4030, 0x4031, 0x4032, 0x4033, 0xc00f, 0xc010
+ , 0xc011, 0xc012, 0xc013, 0xc014, 0xc015, 0xc016, 0xc017, 0xc018
+ , 0xc019, 0xc01a, 0xc01b, 0xc01c, 0xc01d, 0xc01e, 0xc01f, 0xc020
+ , 0x402d, 0x4034, 0x4035, 0x4036, 0x4037, 0x4038, 0x4039, 0xc028
+ , 0x403a, 0x403b, 0x403c, 0x405e, 0x403d, 0xc029, 0x403e, 0x403f
+ , 0x0075, 0x0076, 0x0077, 0x0078, 0x0079, 0x007a, 0x007b, 0x007c
+ , 0x007d, 0x007e, 0x4040, 0x4041, 0x405f, 0x4060, 0x4061, 0x4042
+ , 0x4043, 0x087f, 0x0880, 0x0006, 0x0306, 0x0885, 0x0886, 0x0606
+ , 0x0889, 0x088a, 0x088b, 0x088c, 0x0906, 0x088f, 0x0c06, 0x0892
+ , 0x0894, 0x0895, 0x0896, 0x0f06, 0x1206, 0x089c, 0x089e, 0x089f
+ , 0x08a0, 0x08a1, 0x1506, 0x4044, 0x4045, 0x4046, 0x4047, 0x4048
+ , 0x4049, 0x007f, 0x0080, 0x1806, 0x1a06, 0x0085, 0x0086, 0x1c06
+ , 0x0089, 0x008a, 0x008b, 0x008c, 0x1e06, 0x008f, 0x2006, 0x0092
+ , 0x0094, 0x0095, 0x0096, 0x2206, 0x2406, 0x009c, 0x009e, 0x009f
+ , 0x00a0, 0x00a1, 0x2606, 0x404a, 0x404b, 0x404c, 0x404d, 0xc021
+ , 0xc022, 0xc023, 0x4058, 0xc024, 0x405b, 0x4073, 0x4070, 0x4071
+ , 0xc025, 0x4074, 0x0a97, 0x405c, 0x0997, 0x0999, 0x0aa2, 0x08a2
+ , 0xc026, 0x4056, 0x4057, 0x4059, 0x405a, 0x4072, 0xc02b, 0xc02c
+ , 0xc027, 0x089a, 0x0297, 0x405d, 0x0197, 0x0199, 0x02a2, 0x00a2
+ , 0x402e, 0x4052, 0x4152, 0x0b8d, 0x4067, 0x0d7f, 0x404e, 0x4068
+ , 0x404f, 0x4069, 0x0b97, 0x4063, 0x406a, 0xc02a, 0x406b, 0x09a2
+ , 0x406c, 0x4062, 0x4054, 0x038d, 0x4050, 0x406d, 0x406e, 0x406f
+ , 0x4051, 0x057f, 0x0397, 0x4064, 0x0a8d, 0x4055, 0x028d, 0x01a2
+ , 0x0996, 0x097f, 0x0a7f, 0x0c7f, 0x0b7f, 0x098d, 0x0981, 0x0b81
+ , 0x0a81, 0x0985, 0x0c85, 0x0a85, 0x0b85, 0x098a, 0x0a8a, 0x0983
+ , 0x0a83, 0x0990, 0x0a90, 0x0992, 0x0a92, 0x0993, 0x0893, 0x4065
+ , 0x0a96, 0x0a9c, 0x099c, 0x099d, 0x089d, 0x09a1, 0x0a99, 0x0005
+ , 0x0196, 0x017f, 0x027f, 0x047f, 0x037f, 0x018d, 0x0181, 0x0381
+ , 0x0281, 0x0185, 0x0485, 0x0285, 0x0385, 0x018a, 0x028a, 0x0183
+ , 0x0283, 0x0190, 0x0290, 0x0192, 0x0292, 0x0193, 0x0093, 0x4066
+ , 0x0296, 0x029c, 0x019c, 0x019d, 0x009d, 0x01a1, 0x0299, 0x4053
+};
+
+DIGRAPH NLSALLOC(040e) rgdig_040e[40] = {
+ { 0x0881, 0x02 }
+ , { 0x1082, 0x53 }
+ , { 0x0882, 0x73 }
+ , { 0x0883, 0x02 }
+ , { 0x1084, 0x5a }
+ , { 0x0884, 0x7a }
+ , { 0x0887, 0x02 }
+ , { 0x1088, 0x59 }
+ , { 0x0888, 0x79 }
+ , { 0x088d, 0x02 }
+ , { 0x108e, 0x59 }
+ , { 0x088e, 0x79 }
+ , { 0x0890, 0x02 }
+ , { 0x1091, 0x59 }
+ , { 0x0891, 0x79 }
+ , { 0x0897, 0x02 }
+ , { 0x1098, 0x5a }
+ , { 0x0898, 0x7a }
+ , { 0x0899, 0x02 }
+ , { 0x109b, 0x59 }
+ , { 0x089b, 0x79 }
+ , { 0x08a2, 0x02 }
+ , { 0x10a3, 0x53 }
+ , { 0x08a3, 0x73 }
+ , { 0x0081, 0x02 }
+ , { 0x0082, 0x73 }
+ , { 0x0083, 0x02 }
+ , { 0x0084, 0x7a }
+ , { 0x0087, 0x02 }
+ , { 0x0088, 0x79 }
+ , { 0x008d, 0x02 }
+ , { 0x008e, 0x79 }
+ , { 0x0090, 0x02 }
+ , { 0x0091, 0x79 }
+ , { 0x0097, 0x02 }
+ , { 0x0098, 0x7a }
+ , { 0x0099, 0x02 }
+ , { 0x009b, 0x79 }
+ , { 0x00a2, 0x02 }
+ , { 0x00a3, 0x73 }
+};
+
+EXPANSION NLSALLOC(040e) rgexp_040e[1] = {
+ { 0x0097, 0x0097 }
+};
+
+WORD NLSALLOC(040e) rgwCType12_040e[256] = {
+ 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x9068, 0x0028, 0x0028, 0x0028, 0x0028, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0xa048, 0xb010, 0xb010, 0x5010, 0x5010, 0x5010, 0x1010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0x5010, 0x7010, 0x5010, 0x4010, 0x4010
+ , 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084
+ , 0x3084, 0x3084, 0x7010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010, 0x0020
+ , 0x0020, 0x0020, 0xb010, 0x0020, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x0020, 0x5010, 0x1101, 0xb010, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x0020, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x0020, 0xb010, 0x1102, 0xb010, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0xa048, 0x1010, 0x1010, 0x1101, 0x5010, 0x1101, 0xb010, 0xb010
+ , 0xb010, 0xb010, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0x1101
+ , 0x5010, 0x5010, 0x1010, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x1102, 0x1102, 0xb010, 0x1101, 0x1010, 0x1102, 0x1102
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0xb010
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0xb010
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1010
+};
+
+WORD NLSALLOC(040e) rgwCType3_040e[256] = {
+ 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0008, 0x0008, 0x0008, 0x0008, 0x0008, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0048, 0x0048, 0x0448, 0x0048, 0x0448, 0x0048, 0x0048, 0x0440
+ , 0x0048, 0x0048, 0x0048, 0x0048, 0x0048, 0x0440, 0x0048, 0x0448
+ , 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040
+ , 0x0040, 0x0040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0048, 0x0048
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0448, 0x0048, 0x0448, 0x0448
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0000
+ , 0x0000, 0x0000, 0x0008, 0x0000, 0x0008, 0x0008, 0x0008, 0x0008
+ , 0x0000, 0x0008, 0x8003, 0x0008, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x0000, 0x0088, 0x0088, 0x0088, 0x0088, 0x0008, 0x0400, 0x0400
+ , 0x0000, 0x0000, 0x8003, 0x0008, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x0008, 0x0401, 0x0408, 0x8003, 0x0008, 0x8003, 0x0048, 0x0008
+ , 0x0408, 0x0008, 0x8003, 0x0008, 0x0048, 0x0408, 0x0008, 0x8003
+ , 0x0008, 0x0008, 0x0408, 0x8003, 0x0408, 0x0008, 0x0008, 0x0008
+ , 0x0408, 0x8003, 0x8003, 0x0008, 0x8003, 0x0408, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0408
+};
+
+BYTE NLSALLOC(040e) rgbUCase_040e[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x8a, 0x9b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xa3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xa5, 0xaa, 0xbb, 0xbc, 0xbd, 0xbc, 0xaf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xf7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xff
+};
+
+BYTE NLSALLOC(040e) rgbLCase_040e[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x9a, 0x8b, 0x9c, 0x9d, 0x9e, 0x9f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f
+ , 0xa0, 0xa1, 0xa2, 0xb3, 0xa4, 0xb9, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xba, 0xab, 0xac, 0xad, 0xae, 0xbf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbe, 0xbd, 0xbe, 0xbf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xd7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xdf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
+};
+
+static BYTE NLSALLOC(040e) rgbILANGUAGE[] = { /* "040e" */
+ 0x30, 0x34, 0x30, 0x65
+};
+
+static BYTE NLSALLOC(040e) rgbSLANGUAGE[] = { /* "Hungarian" */
+ 0x48, 0x75, 0x6e, 0x67, 0x61, 0x72, 0x69, 0x61
+ , 0x6e
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVLANGNAME[] = { /* "HUN" */
+ 0x48, 0x55, 0x4e
+};
+
+static BYTE NLSALLOC(040e) rgbSNATIVELANGNAME[] = { /* "magyar" */
+ 0x6d, 0x61, 0x67, 0x79, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(040e) rgbICOUNTRY[] = { /* "36" */
+ 0x33, 0x36
+};
+
+static BYTE NLSALLOC(040e) rgbSCOUNTRY[] = { /* "Hungary" */
+ 0x48, 0x75, 0x6e, 0x67, 0x61, 0x72, 0x79
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVCTRYNAME[] = { /* "HUN" */
+ 0x48, 0x55, 0x4e
+};
+
+static BYTE NLSALLOC(040e) rgbSNATIVECTRYNAME[] = { /* "Magyarország" */
+ 0x4d, 0x61, 0x67, 0x79, 0x61, 0x72, 0x6f, 0x72
+ , 0x73, 0x7a, 0xe1, 0x67
+};
+
+static BYTE NLSALLOC(040e) rgbIDEFAULTLANGUAGE[] = { /* "040e" */
+ 0x30, 0x34, 0x30, 0x65
+};
+
+static BYTE NLSALLOC(040e) rgbIDEFAULTCOUNTRY[] = { /* "36" */
+ 0x33, 0x36
+};
+
+static BYTE NLSALLOC(040e) rgbIDEFAULTCODEPAGE[] = { /* "852" */
+ 0x38, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(040e) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(040e) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040e) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(040e) rgbSTHOUSAND[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(040e) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(040e) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040e) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040e) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(040e) rgbSCURRENCY[] = { /* "Ft" */
+ 0x46, 0x74
+};
+
+static BYTE NLSALLOC(040e) rgbSINTLSYMBOL[] = { /* "HUF" */
+ 0x48, 0x55, 0x46
+};
+
+static BYTE NLSALLOC(040e) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(040e) rgbSMONTHOUSANDSEP[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(040e) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(040e) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040e) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040e) rgbICURRENCY[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(040e) rgbINEGCURR[] = { /* "8" */
+ 0x38
+};
+
+static BYTE NLSALLOC(040e) rgbSDATE[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(040e) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(040e) rgbSSHORTDATE[] = { /* "yyyy. MM. dd." */
+ 0x79, 0x79, 0x79, 0x79, 0x2e, 0x20, 0x4d, 0x4d
+ , 0x2e, 0x20, 0x64, 0x64, 0x2e
+};
+
+static BYTE NLSALLOC(040e) rgbSLONGDATE[] = { /* "yyyy. MMMM d." */
+ 0x79, 0x79, 0x79, 0x79, 0x2e, 0x20, 0x4d, 0x4d
+ , 0x4d, 0x4d, 0x20, 0x64, 0x2e
+};
+
+static BYTE NLSALLOC(040e) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040e) rgbILDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040e) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040e) rgbICENTURY[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040e) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040e) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040e) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040e) rgbS1159[] = { /* "DE" */
+ 0x44, 0x45
+};
+
+static BYTE NLSALLOC(040e) rgbS2359[] = { /* "DU" */
+ 0x44, 0x55
+};
+
+static BYTE NLSALLOC(040e) rgbSDAYNAME1[] = { /* "h\x00e9tf\x0151" */
+ 0x68, 0xe9, 0x74, 0x66, 0xf5
+};
+
+static BYTE NLSALLOC(040e) rgbSDAYNAME2[] = { /* "kedd" */
+ 0x6b, 0x65, 0x64, 0x64
+};
+
+static BYTE NLSALLOC(040e) rgbSDAYNAME3[] = { /* "szerda" */
+ 0x73, 0x7a, 0x65, 0x72, 0x64, 0x61
+};
+
+static BYTE NLSALLOC(040e) rgbSDAYNAME4[] = { /* "csütörtök" */
+ 0x63, 0x73, 0xfc, 0x74, 0xf6, 0x72, 0x74, 0xf6
+ , 0x6b
+};
+
+static BYTE NLSALLOC(040e) rgbSDAYNAME5[] = { /* "péntek" */
+ 0x70, 0xe9, 0x6e, 0x74, 0x65, 0x6b
+};
+
+static BYTE NLSALLOC(040e) rgbSDAYNAME6[] = { /* "szombat" */
+ 0x73, 0x7a, 0x6f, 0x6d, 0x62, 0x61, 0x74
+};
+
+static BYTE NLSALLOC(040e) rgbSDAYNAME7[] = { /* "vasárnap" */
+ 0x76, 0x61, 0x73, 0xe1, 0x72, 0x6e, 0x61, 0x70
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVDAYNAME1[] = { /* "H" */
+ 0x48
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVDAYNAME2[] = { /* "K" */
+ 0x4b
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVDAYNAME3[] = { /* "Sze" */
+ 0x53, 0x7a, 0x65
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVDAYNAME4[] = { /* "Cs" */
+ 0x43, 0x73
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVDAYNAME5[] = { /* "P" */
+ 0x50
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVDAYNAME6[] = { /* "Szo" */
+ 0x53, 0x7a, 0x6f
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVDAYNAME7[] = { /* "V" */
+ 0x56
+};
+
+static BYTE NLSALLOC(040e) rgbSMONTHNAME1[] = { /* "január" */
+ 0x6a, 0x61, 0x6e, 0x75, 0xe1, 0x72
+};
+
+static BYTE NLSALLOC(040e) rgbSMONTHNAME2[] = { /* "február" */
+ 0x66, 0x65, 0x62, 0x72, 0x75, 0xe1, 0x72
+};
+
+static BYTE NLSALLOC(040e) rgbSMONTHNAME3[] = { /* "március" */
+ 0x6d, 0xe1, 0x72, 0x63, 0x69, 0x75, 0x73
+};
+
+static BYTE NLSALLOC(040e) rgbSMONTHNAME4[] = { /* "április" */
+ 0xe1, 0x70, 0x72, 0x69, 0x6c, 0x69, 0x73
+};
+
+static BYTE NLSALLOC(040e) rgbSMONTHNAME5[] = { /* "május" */
+ 0x6d, 0xe1, 0x6a, 0x75, 0x73
+};
+
+static BYTE NLSALLOC(040e) rgbSMONTHNAME6[] = { /* "június" */
+ 0x6a, 0xfa, 0x6e, 0x69, 0x75, 0x73
+};
+
+static BYTE NLSALLOC(040e) rgbSMONTHNAME7[] = { /* "július" */
+ 0x6a, 0xfa, 0x6c, 0x69, 0x75, 0x73
+};
+
+static BYTE NLSALLOC(040e) rgbSMONTHNAME8[] = { /* "augusztus" */
+ 0x61, 0x75, 0x67, 0x75, 0x73, 0x7a, 0x74, 0x75
+ , 0x73
+};
+
+static BYTE NLSALLOC(040e) rgbSMONTHNAME9[] = { /* "szeptember" */
+ 0x73, 0x7a, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62
+ , 0x65, 0x72
+};
+
+static BYTE NLSALLOC(040e) rgbSMONTHNAME10[] = { /* "október" */
+ 0x6f, 0x6b, 0x74, 0xf3, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(040e) rgbSMONTHNAME11[] = { /* "november" */
+ 0x6e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(040e) rgbSMONTHNAME12[] = { /* "december" */
+ 0x64, 0x65, 0x63, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVMONTHNAME1[] = { /* "jan." */
+ 0x6a, 0x61, 0x6e, 0x2e
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVMONTHNAME2[] = { /* "febr." */
+ 0x66, 0x65, 0x62, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVMONTHNAME3[] = { /* "márc." */
+ 0x6d, 0xe1, 0x72, 0x63, 0x2e
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVMONTHNAME4[] = { /* "ápr." */
+ 0xe1, 0x70, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVMONTHNAME5[] = { /* "máj." */
+ 0x6d, 0xe1, 0x6a, 0x2e
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVMONTHNAME6[] = { /* "jún." */
+ 0x6a, 0xfa, 0x6e, 0x2e
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVMONTHNAME7[] = { /* "júl." */
+ 0x6a, 0xfa, 0x6c, 0x2e
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVMONTHNAME8[] = { /* "aug." */
+ 0x61, 0x75, 0x67, 0x2e
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVMONTHNAME9[] = { /* "szept." */
+ 0x73, 0x7a, 0x65, 0x70, 0x74, 0x2e
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVMONTHNAME10[] = { /* "okt." */
+ 0x6f, 0x6b, 0x74, 0x2e
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVMONTHNAME11[] = { /* "nov." */
+ 0x6e, 0x6f, 0x76, 0x2e
+};
+
+static BYTE NLSALLOC(040e) rgbSABBREVMONTHNAME12[] = { /* "dec." */
+ 0x64, 0x65, 0x63, 0x2e
+};
+
+static BYTE NLSALLOC(040e) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(040e) rgbIPOSSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040e) rgbINEGSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040e) rgbIPOSSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040e) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040e) rgbINEGSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040e) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040e) rgbSENGCOUNTRY[] = { /* "Hungary" */
+ 0x48, 0x75, 0x6e, 0x67, 0x61, 0x72, 0x79
+};
+
+static BYTE NLSALLOC(040e) rgbSENGLANGUAGE[] = { /* "Hungarian" */
+ 0x48, 0x75, 0x6e, 0x67, 0x61, 0x72, 0x69, 0x61
+ , 0x6e
+};
+
+static BYTE NLSALLOC(040e) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040e) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040e) rgbIDEFAULTANSICODEPAGE[] = { /* "1250" */
+ 0x31, 0x32, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(040e) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040e) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(040e) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040e) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040e) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(040e) g_rglcinfo040e[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 9, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 6, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 7, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 12, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 2, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 13, rgbSSHORTDATE }
+ , { 13, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 2, rgbS1159 }
+ , { 2, rgbS2359 }
+ , { 5, rgbSDAYNAME1 }
+ , { 4, rgbSDAYNAME2 }
+ , { 6, rgbSDAYNAME3 }
+ , { 9, rgbSDAYNAME4 }
+ , { 6, rgbSDAYNAME5 }
+ , { 7, rgbSDAYNAME6 }
+ , { 8, rgbSDAYNAME7 }
+ , { 1, rgbSABBREVDAYNAME1 }
+ , { 1, rgbSABBREVDAYNAME2 }
+ , { 3, rgbSABBREVDAYNAME3 }
+ , { 2, rgbSABBREVDAYNAME4 }
+ , { 1, rgbSABBREVDAYNAME5 }
+ , { 3, rgbSABBREVDAYNAME6 }
+ , { 1, rgbSABBREVDAYNAME7 }
+ , { 6, rgbSMONTHNAME1 }
+ , { 7, rgbSMONTHNAME2 }
+ , { 7, rgbSMONTHNAME3 }
+ , { 7, rgbSMONTHNAME4 }
+ , { 5, rgbSMONTHNAME5 }
+ , { 6, rgbSMONTHNAME6 }
+ , { 6, rgbSMONTHNAME7 }
+ , { 9, rgbSMONTHNAME8 }
+ , { 10, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 4, rgbSABBREVMONTHNAME1 }
+ , { 5, rgbSABBREVMONTHNAME2 }
+ , { 5, rgbSABBREVMONTHNAME3 }
+ , { 4, rgbSABBREVMONTHNAME4 }
+ , { 4, rgbSABBREVMONTHNAME5 }
+ , { 4, rgbSABBREVMONTHNAME6 }
+ , { 4, rgbSABBREVMONTHNAME7 }
+ , { 4, rgbSABBREVMONTHNAME8 }
+ , { 6, rgbSABBREVMONTHNAME9 }
+ , { 4, rgbSABBREVMONTHNAME10 }
+ , { 4, rgbSABBREVMONTHNAME11 }
+ , { 4, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 7, rgbSENGCOUNTRY }
+ , { 9, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(040e) g_strinfo040e = {
+ rgbUCase_040e
+ , rgbLCase_040e
+ , rgwCType12_040e
+ , rgwCType3_040e
+ , rgwSort_040e
+ , rgexp_040e
+ , rgdig_040e
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/040f.c b/private/oleauto/src/dispatch/win16/040f.c
new file mode 100644
index 000000000..93d059aac
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/040f.c
@@ -0,0 +1,704 @@
+/****************************************************************************
+* 040f.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Icelandic - Iceland
+*
+* LCID = 0x040f
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 18:02:06 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+WORD NLSALLOC(040f) rgwSort_040f[256] = {
+ 0x0000, 0xc007, 0xc008, 0xc009, 0xc00a, 0xc00b, 0xc00c, 0xc00d
+ , 0xc00e, 0x4031, 0x4032, 0x4033, 0x4034, 0x4035, 0xc00f, 0xc010
+ , 0xc011, 0xc012, 0xc013, 0xc014, 0xc015, 0xc016, 0xc017, 0xc018
+ , 0xc019, 0xc01a, 0xc01b, 0xc01c, 0xc01d, 0xc01e, 0xc01f, 0xc020
+ , 0x402f, 0x4036, 0x4037, 0x4038, 0x4039, 0x403a, 0x403b, 0xc02a
+ , 0x403c, 0x403d, 0x403e, 0x4060, 0x403f, 0xc02b, 0x4040, 0x4041
+ , 0x007a, 0x007e, 0x007f, 0x0080, 0x0081, 0x0082, 0x0083, 0x0084
+ , 0x0085, 0x0086, 0x4042, 0x4043, 0x4061, 0x4062, 0x4063, 0x4044
+ , 0x4045, 0x1087, 0x1089, 0x108a, 0x108b, 0x108c, 0x108e, 0x108f
+ , 0x1090, 0x1091, 0x1093, 0x1094, 0x1095, 0x1096, 0x1097, 0x1098
+ , 0x109a, 0x109b, 0x109c, 0x109d, 0x109e, 0x10a0, 0x10a2, 0x10a3
+ , 0x10a4, 0x10a5, 0x10a7, 0x4046, 0x4047, 0x4048, 0x4049, 0x404a
+ , 0x404b, 0x0087, 0x0089, 0x008a, 0x008b, 0x008c, 0x008e, 0x008f
+ , 0x0090, 0x0091, 0x0093, 0x0094, 0x0095, 0x0096, 0x0097, 0x0098
+ , 0x009a, 0x009b, 0x009c, 0x009d, 0x009e, 0x00a0, 0x00a2, 0x00a3
+ , 0x00a4, 0x00a5, 0x00a7, 0x404c, 0x404d, 0x404e, 0x404f, 0xc021
+ , 0xc022, 0xc023, 0x405a, 0x018e, 0x405d, 0x4078, 0x4075, 0x4076
+ , 0x4149, 0x4079, 0x119d, 0x405e, 0x0105, 0xc024, 0xc025, 0xc026
+ , 0xc027, 0x4058, 0x4059, 0x405b, 0x405c, 0x4077, 0xc02d, 0xc02e
+ , 0x4057, 0x109f, 0x019d, 0x405f, 0x0205, 0xc028, 0xc029, 0x10a5
+ , 0x4030, 0x4050, 0x4069, 0x406a, 0x406b, 0x406c, 0x4051, 0x406d
+ , 0x4052, 0x406e, 0x0887, 0x4065, 0x406f, 0xc02c, 0x4070, 0x4053
+ , 0x4071, 0x4064, 0x087f, 0x0880, 0x4054, 0x4072, 0x4073, 0x4074
+ , 0x4055, 0x087e, 0x0998, 0x4066, 0x007b, 0x007c, 0x007d, 0x4056
+ , 0x1187, 0x1088, 0x1287, 0x1487, 0x1387, 0x1587, 0x10a9, 0x118a
+ , 0x118c, 0x108d, 0x128c, 0x138c, 0x1191, 0x1092, 0x1291, 0x1391
+ , 0x118b, 0x1197, 0x1298, 0x1099, 0x1398, 0x1498, 0x10aa, 0x4067
+ , 0x11aa, 0x11a0, 0x10a1, 0x12a0, 0x13a0, 0x10a6, 0x10a8, 0x0005
+ , 0x0187, 0x0088, 0x0287, 0x0487, 0x0387, 0x0587, 0x00a9, 0x018a
+ , 0x018c, 0x008d, 0x028c, 0x038c, 0x0191, 0x0092, 0x0291, 0x0391
+ , 0x018b, 0x0197, 0x0298, 0x0099, 0x0398, 0x0498, 0x00aa, 0x4068
+ , 0x01aa, 0x01a0, 0x00a1, 0x02a0, 0x03a0, 0x00a6, 0x00a8, 0x00a5
+};
+
+EXPANSION NLSALLOC(040f) rgexp_040f[3] = {
+ { 0x009d, 0x009d }
+ , { 0x1098, 0x108c }
+ , { 0x0098, 0x008c }
+};
+
+WORD NLSALLOC(040f) rgwCType12_040f[256] = {
+ 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x9068, 0x0028, 0x0028, 0x0028, 0x0028, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0xa048, 0xb010, 0xb010, 0x5010, 0x5010, 0x5010, 0x1010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0x5010, 0x7010, 0x5010, 0x4010, 0x4010
+ , 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084
+ , 0x3084, 0x3084, 0x7010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010, 0x0020
+ , 0x0020, 0x0020, 0xb010, 0x1112, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x5010, 0x1101, 0xb010, 0x1101, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0xb010, 0x1102, 0xb010, 0x1102, 0x0020, 0x0020, 0x1101
+ , 0xa048, 0xb010, 0x5010, 0x5010, 0x5010, 0x5010, 0xb010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x5010, 0x5010, 0x3014, 0x3014, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x3014, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0xb010
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0xb010
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+};
+
+WORD NLSALLOC(040f) rgwCType3_040f[256] = {
+ 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0008, 0x0008, 0x0008, 0x0008, 0x0008, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0048, 0x0048, 0x0448, 0x0048, 0x0448, 0x0048, 0x0048, 0x0440
+ , 0x0048, 0x0048, 0x0048, 0x0048, 0x0048, 0x0440, 0x0048, 0x0448
+ , 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040
+ , 0x0040, 0x0040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0048, 0x0048
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0448, 0x0048, 0x0448, 0x0448
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0000
+ , 0x0000, 0x0000, 0x0008, 0x8000, 0x0008, 0x0008, 0x0008, 0x0008
+ , 0x0001, 0x0008, 0x8003, 0x0008, 0x8000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0088, 0x0088, 0x0088, 0x0088, 0x0008, 0x0400, 0x0400
+ , 0x0408, 0x0000, 0x8003, 0x0008, 0x8000, 0x0000, 0x0000, 0x8003
+ , 0x0008, 0x0008, 0x0048, 0x0048, 0x0008, 0x0048, 0x0048, 0x0008
+ , 0x0408, 0x0008, 0x0400, 0x0008, 0x0048, 0x0408, 0x0008, 0x0448
+ , 0x0008, 0x0008, 0x0000, 0x0000, 0x0408, 0x0008, 0x0008, 0x0008
+ , 0x0408, 0x0000, 0x0400, 0x0008, 0x0000, 0x0000, 0x0000, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8000, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8000
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8000, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+};
+
+BYTE NLSALLOC(040f) rgbUCase_040f[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x8a, 0x9b, 0x8c, 0x9d, 0x9e, 0x9f
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xf7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0x9f
+};
+
+BYTE NLSALLOC(040f) rgbLCase_040f[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x9a, 0x8b, 0x9c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0xff
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xd7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xdf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
+};
+
+static BYTE NLSALLOC(040f) rgbILANGUAGE[] = { /* "040f" */
+ 0x30, 0x34, 0x30, 0x66
+};
+
+static BYTE NLSALLOC(040f) rgbSLANGUAGE[] = { /* "Icelandic" */
+ 0x49, 0x63, 0x65, 0x6c, 0x61, 0x6e, 0x64, 0x69
+ , 0x63
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVLANGNAME[] = { /* "ISL" */
+ 0x49, 0x53, 0x4c
+};
+
+static BYTE NLSALLOC(040f) rgbSNATIVELANGNAME[] = { /* "íslenska" */
+ 0xed, 0x73, 0x6c, 0x65, 0x6e, 0x73, 0x6b, 0x61
+};
+
+static BYTE NLSALLOC(040f) rgbICOUNTRY[] = { /* "354" */
+ 0x33, 0x35, 0x34
+};
+
+static BYTE NLSALLOC(040f) rgbSCOUNTRY[] = { /* "Iceland" */
+ 0x49, 0x63, 0x65, 0x6c, 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVCTRYNAME[] = { /* "ISL" */
+ 0x49, 0x53, 0x4c
+};
+
+static BYTE NLSALLOC(040f) rgbSNATIVECTRYNAME[] = { /* "Ísland" */
+ 0xcd, 0x73, 0x6c, 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(040f) rgbIDEFAULTLANGUAGE[] = { /* "040f" */
+ 0x30, 0x34, 0x30, 0x66
+};
+
+static BYTE NLSALLOC(040f) rgbIDEFAULTCOUNTRY[] = { /* "354" */
+ 0x33, 0x35, 0x34
+};
+
+static BYTE NLSALLOC(040f) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(040f) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(040f) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040f) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(040f) rgbSTHOUSAND[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(040f) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040f) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040f) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(040f) rgbSCURRENCY[] = { /* "kr." */
+ 0x6b, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSINTLSYMBOL[] = { /* "ISK" */
+ 0x49, 0x53, 0x4b
+};
+
+static BYTE NLSALLOC(040f) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(040f) rgbSMONTHOUSANDSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(040f) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040f) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040f) rgbICURRENCY[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(040f) rgbINEGCURR[] = { /* "8" */
+ 0x38
+};
+
+static BYTE NLSALLOC(040f) rgbSDATE[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(040f) rgbSSHORTDATE[] = { /* "d.M.yyyy" */
+ 0x64, 0x2e, 0x4d, 0x2e, 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(040f) rgbSLONGDATE[] = { /* "d. MMMM yyyy" */
+ 0x64, 0x2e, 0x20, 0x4d, 0x4d, 0x4d, 0x4d, 0x20
+ , 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(040f) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040f) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040f) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040f) rgbICENTURY[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040f) rgbITLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040f) rgbIDAYLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040f) rgbIMONLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040f) rgbSDAYNAME1[] = { /* "mánudagur" */
+ 0x6d, 0xe1, 0x6e, 0x75, 0x64, 0x61, 0x67, 0x75
+ , 0x72
+};
+
+static BYTE NLSALLOC(040f) rgbSDAYNAME2[] = { /* "þriðjudagur" */
+ 0xfe, 0x72, 0x69, 0xf0, 0x6a, 0x75, 0x64, 0x61
+ , 0x67, 0x75, 0x72
+};
+
+static BYTE NLSALLOC(040f) rgbSDAYNAME3[] = { /* "miðvikudagur" */
+ 0x6d, 0x69, 0xf0, 0x76, 0x69, 0x6b, 0x75, 0x64
+ , 0x61, 0x67, 0x75, 0x72
+};
+
+static BYTE NLSALLOC(040f) rgbSDAYNAME4[] = { /* "fimmtudagur" */
+ 0x66, 0x69, 0x6d, 0x6d, 0x74, 0x75, 0x64, 0x61
+ , 0x67, 0x75, 0x72
+};
+
+static BYTE NLSALLOC(040f) rgbSDAYNAME5[] = { /* "föstudagur" */
+ 0x66, 0xf6, 0x73, 0x74, 0x75, 0x64, 0x61, 0x67
+ , 0x75, 0x72
+};
+
+static BYTE NLSALLOC(040f) rgbSDAYNAME6[] = { /* "laugardagur" */
+ 0x6c, 0x61, 0x75, 0x67, 0x61, 0x72, 0x64, 0x61
+ , 0x67, 0x75, 0x72
+};
+
+static BYTE NLSALLOC(040f) rgbSDAYNAME7[] = { /* "sunnudagur" */
+ 0x73, 0x75, 0x6e, 0x6e, 0x75, 0x64, 0x61, 0x67
+ , 0x75, 0x72
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVDAYNAME1[] = { /* "mán." */
+ 0x6d, 0xe1, 0x6e, 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVDAYNAME2[] = { /* "þri." */
+ 0xfe, 0x72, 0x69, 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVDAYNAME3[] = { /* "mið." */
+ 0x6d, 0x69, 0xf0, 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVDAYNAME4[] = { /* "fim." */
+ 0x66, 0x69, 0x6d, 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVDAYNAME5[] = { /* "fös." */
+ 0x66, 0xf6, 0x73, 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVDAYNAME6[] = { /* "lau." */
+ 0x6c, 0x61, 0x75, 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVDAYNAME7[] = { /* "sun." */
+ 0x73, 0x75, 0x6e, 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSMONTHNAME1[] = { /* "janúar" */
+ 0x6a, 0x61, 0x6e, 0xfa, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(040f) rgbSMONTHNAME2[] = { /* "febrúar" */
+ 0x66, 0x65, 0x62, 0x72, 0xfa, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(040f) rgbSMONTHNAME3[] = { /* "mars" */
+ 0x6d, 0x61, 0x72, 0x73
+};
+
+static BYTE NLSALLOC(040f) rgbSMONTHNAME4[] = { /* "apríl" */
+ 0x61, 0x70, 0x72, 0xed, 0x6c
+};
+
+static BYTE NLSALLOC(040f) rgbSMONTHNAME5[] = { /* "maí" */
+ 0x6d, 0x61, 0xed
+};
+
+static BYTE NLSALLOC(040f) rgbSMONTHNAME6[] = { /* "júní" */
+ 0x6a, 0xfa, 0x6e, 0xed
+};
+
+static BYTE NLSALLOC(040f) rgbSMONTHNAME7[] = { /* "júlí" */
+ 0x6a, 0xfa, 0x6c, 0xed
+};
+
+static BYTE NLSALLOC(040f) rgbSMONTHNAME8[] = { /* "ágúst" */
+ 0xe1, 0x67, 0xfa, 0x73, 0x74
+};
+
+static BYTE NLSALLOC(040f) rgbSMONTHNAME9[] = { /* "september" */
+ 0x73, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x65
+ , 0x72
+};
+
+static BYTE NLSALLOC(040f) rgbSMONTHNAME10[] = { /* "október" */
+ 0x6f, 0x6b, 0x74, 0xf3, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(040f) rgbSMONTHNAME11[] = { /* "nóvember" */
+ 0x6e, 0xf3, 0x76, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(040f) rgbSMONTHNAME12[] = { /* "desember" */
+ 0x64, 0x65, 0x73, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVMONTHNAME1[] = { /* "jan." */
+ 0x6a, 0x61, 0x6e, 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVMONTHNAME2[] = { /* "feb." */
+ 0x66, 0x65, 0x62, 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVMONTHNAME3[] = { /* "mar." */
+ 0x6d, 0x61, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVMONTHNAME4[] = { /* "apr." */
+ 0x61, 0x70, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVMONTHNAME5[] = { /* "maí" */
+ 0x6d, 0x61, 0xed
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVMONTHNAME6[] = { /* "jún." */
+ 0x6a, 0xfa, 0x6e, 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVMONTHNAME7[] = { /* "júl." */
+ 0x6a, 0xfa, 0x6c, 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVMONTHNAME8[] = { /* "ágú." */
+ 0xe1, 0x67, 0xfa, 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVMONTHNAME9[] = { /* "sep." */
+ 0x73, 0x65, 0x70, 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVMONTHNAME10[] = { /* "okt." */
+ 0x6f, 0x6b, 0x74, 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVMONTHNAME11[] = { /* "nóv." */
+ 0x6e, 0xf3, 0x76, 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSABBREVMONTHNAME12[] = { /* "des." */
+ 0x64, 0x65, 0x73, 0x2e
+};
+
+static BYTE NLSALLOC(040f) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(040f) rgbIPOSSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040f) rgbINEGSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040f) rgbIPOSSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040f) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040f) rgbINEGSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040f) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040f) rgbSENGCOUNTRY[] = { /* "Iceland" */
+ 0x49, 0x63, 0x65, 0x6c, 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(040f) rgbSENGLANGUAGE[] = { /* "Icelandic" */
+ 0x49, 0x63, 0x65, 0x6c, 0x61, 0x6e, 0x64, 0x69
+ , 0x63
+};
+
+static BYTE NLSALLOC(040f) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040f) rgbIFIRSTWEEKOFYEAR[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(040f) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(040f) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040f) rgbSTIMEFORMAT[] = { /* "HH:mm:ss" */
+ 0x48, 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(040f) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(040f) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(040f) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(040f) g_rglcinfo040f[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 9, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 8, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 7, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 6, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 3, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 12, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 9, rgbSDAYNAME1 }
+ , { 11, rgbSDAYNAME2 }
+ , { 12, rgbSDAYNAME3 }
+ , { 11, rgbSDAYNAME4 }
+ , { 10, rgbSDAYNAME5 }
+ , { 11, rgbSDAYNAME6 }
+ , { 10, rgbSDAYNAME7 }
+ , { 4, rgbSABBREVDAYNAME1 }
+ , { 4, rgbSABBREVDAYNAME2 }
+ , { 4, rgbSABBREVDAYNAME3 }
+ , { 4, rgbSABBREVDAYNAME4 }
+ , { 4, rgbSABBREVDAYNAME5 }
+ , { 4, rgbSABBREVDAYNAME6 }
+ , { 4, rgbSABBREVDAYNAME7 }
+ , { 6, rgbSMONTHNAME1 }
+ , { 7, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 5, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 4, rgbSABBREVMONTHNAME1 }
+ , { 4, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 4, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 4, rgbSABBREVMONTHNAME6 }
+ , { 4, rgbSABBREVMONTHNAME7 }
+ , { 4, rgbSABBREVMONTHNAME8 }
+ , { 4, rgbSABBREVMONTHNAME9 }
+ , { 4, rgbSABBREVMONTHNAME10 }
+ , { 4, rgbSABBREVMONTHNAME11 }
+ , { 4, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 7, rgbSENGCOUNTRY }
+ , { 9, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 8, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(040f) g_strinfo040f = {
+ rgbUCase_040f
+ , rgbLCase_040f
+ , rgwCType12_040f
+ , rgwCType3_040f
+ , rgwSort_040f
+ , rgexp_040f
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0410.c b/private/oleauto/src/dispatch/win16/0410.c
new file mode 100644
index 000000000..0a40e9c71
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0410.c
@@ -0,0 +1,518 @@
+/****************************************************************************
+* 0410.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Italian - Italy
+*
+* LCID = 0x0410
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:36:27 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0409[256]; // from 0409:English - United States
+extern EXPANSION rgexp_0409[7];
+extern WORD rgwCType12_0409[256];
+extern WORD rgwCType3_0409[256];
+extern BYTE rgbUCase_0409[256];
+extern BYTE rgbLCase_0409[256];
+
+static BYTE NLSALLOC(0410) rgbILANGUAGE[] = { /* "0410" */
+ 0x30, 0x34, 0x31, 0x30
+};
+
+static BYTE NLSALLOC(0410) rgbSLANGUAGE[] = { /* "Italian" */
+ 0x49, 0x74, 0x61, 0x6c, 0x69, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVLANGNAME[] = { /* "ITA" */
+ 0x49, 0x54, 0x41
+};
+
+static BYTE NLSALLOC(0410) rgbSNATIVELANGNAME[] = { /* "Italiano" */
+ 0x49, 0x74, 0x61, 0x6c, 0x69, 0x61, 0x6e, 0x6f
+};
+
+static BYTE NLSALLOC(0410) rgbICOUNTRY[] = { /* "39" */
+ 0x33, 0x39
+};
+
+static BYTE NLSALLOC(0410) rgbSCOUNTRY[] = { /* "Italy" */
+ 0x49, 0x74, 0x61, 0x6c, 0x79
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVCTRYNAME[] = { /* "ITA" */
+ 0x49, 0x54, 0x41
+};
+
+static BYTE NLSALLOC(0410) rgbSNATIVECTRYNAME[] = { /* "Italia" */
+ 0x49, 0x74, 0x61, 0x6c, 0x69, 0x61
+};
+
+static BYTE NLSALLOC(0410) rgbIDEFAULTLANGUAGE[] = { /* "0410" */
+ 0x30, 0x34, 0x31, 0x30
+};
+
+static BYTE NLSALLOC(0410) rgbIDEFAULTCOUNTRY[] = { /* "39" */
+ 0x33, 0x39
+};
+
+static BYTE NLSALLOC(0410) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0410) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0410) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0410) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0410) rgbSTHOUSAND[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0410) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0410) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0410) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0410) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0410) rgbSCURRENCY[] = { /* "L." */
+ 0x4c, 0x2e
+};
+
+static BYTE NLSALLOC(0410) rgbSINTLSYMBOL[] = { /* "ITL" */
+ 0x49, 0x54, 0x4c
+};
+
+static BYTE NLSALLOC(0410) rgbSMONTHOUSANDSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0410) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0410) rgbICURRDIGITS[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0410) rgbIINTLCURRDIGITS[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0410) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0410) rgbINEGCURR[] = { /* "9" */
+ 0x39
+};
+
+static BYTE NLSALLOC(0410) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(0410) rgbSTIME[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0410) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0410) rgbSLONGDATE[] = { /* "dddd d MMMM yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x20, 0x64, 0x20, 0x4d
+ , 0x4d, 0x4d, 0x4d, 0x20, 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0410) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0410) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0410) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0410) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0410) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0410) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0410) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0410) rgbSDAYNAME1[] = { /* "lunedì" */
+ 0x6c, 0x75, 0x6e, 0x65, 0x64, 0xec
+};
+
+static BYTE NLSALLOC(0410) rgbSDAYNAME2[] = { /* "martedì" */
+ 0x6d, 0x61, 0x72, 0x74, 0x65, 0x64, 0xec
+};
+
+static BYTE NLSALLOC(0410) rgbSDAYNAME3[] = { /* "mercoledì" */
+ 0x6d, 0x65, 0x72, 0x63, 0x6f, 0x6c, 0x65, 0x64
+ , 0xec
+};
+
+static BYTE NLSALLOC(0410) rgbSDAYNAME4[] = { /* "giovedì" */
+ 0x67, 0x69, 0x6f, 0x76, 0x65, 0x64, 0xec
+};
+
+static BYTE NLSALLOC(0410) rgbSDAYNAME5[] = { /* "venerdì" */
+ 0x76, 0x65, 0x6e, 0x65, 0x72, 0x64, 0xec
+};
+
+static BYTE NLSALLOC(0410) rgbSDAYNAME6[] = { /* "sabato" */
+ 0x73, 0x61, 0x62, 0x61, 0x74, 0x6f
+};
+
+static BYTE NLSALLOC(0410) rgbSDAYNAME7[] = { /* "domenica" */
+ 0x64, 0x6f, 0x6d, 0x65, 0x6e, 0x69, 0x63, 0x61
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVDAYNAME1[] = { /* "lun" */
+ 0x6c, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVDAYNAME2[] = { /* "mar" */
+ 0x6d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVDAYNAME3[] = { /* "mer" */
+ 0x6d, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVDAYNAME4[] = { /* "gio" */
+ 0x67, 0x69, 0x6f
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVDAYNAME5[] = { /* "ven" */
+ 0x76, 0x65, 0x6e
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVDAYNAME6[] = { /* "sab" */
+ 0x73, 0x61, 0x62
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVDAYNAME7[] = { /* "dom" */
+ 0x64, 0x6f, 0x6d
+};
+
+static BYTE NLSALLOC(0410) rgbSMONTHNAME1[] = { /* "gennaio" */
+ 0x67, 0x65, 0x6e, 0x6e, 0x61, 0x69, 0x6f
+};
+
+static BYTE NLSALLOC(0410) rgbSMONTHNAME2[] = { /* "febbraio" */
+ 0x66, 0x65, 0x62, 0x62, 0x72, 0x61, 0x69, 0x6f
+};
+
+static BYTE NLSALLOC(0410) rgbSMONTHNAME3[] = { /* "marzo" */
+ 0x6d, 0x61, 0x72, 0x7a, 0x6f
+};
+
+static BYTE NLSALLOC(0410) rgbSMONTHNAME4[] = { /* "aprile" */
+ 0x61, 0x70, 0x72, 0x69, 0x6c, 0x65
+};
+
+static BYTE NLSALLOC(0410) rgbSMONTHNAME5[] = { /* "maggio" */
+ 0x6d, 0x61, 0x67, 0x67, 0x69, 0x6f
+};
+
+static BYTE NLSALLOC(0410) rgbSMONTHNAME6[] = { /* "giugno" */
+ 0x67, 0x69, 0x75, 0x67, 0x6e, 0x6f
+};
+
+static BYTE NLSALLOC(0410) rgbSMONTHNAME7[] = { /* "luglio" */
+ 0x6c, 0x75, 0x67, 0x6c, 0x69, 0x6f
+};
+
+static BYTE NLSALLOC(0410) rgbSMONTHNAME8[] = { /* "agosto" */
+ 0x61, 0x67, 0x6f, 0x73, 0x74, 0x6f
+};
+
+static BYTE NLSALLOC(0410) rgbSMONTHNAME9[] = { /* "settembre" */
+ 0x73, 0x65, 0x74, 0x74, 0x65, 0x6d, 0x62, 0x72
+ , 0x65
+};
+
+static BYTE NLSALLOC(0410) rgbSMONTHNAME10[] = { /* "ottobre" */
+ 0x6f, 0x74, 0x74, 0x6f, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(0410) rgbSMONTHNAME11[] = { /* "novembre" */
+ 0x6e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(0410) rgbSMONTHNAME12[] = { /* "dicembre" */
+ 0x64, 0x69, 0x63, 0x65, 0x6d, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVMONTHNAME1[] = { /* "gen" */
+ 0x67, 0x65, 0x6e
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVMONTHNAME2[] = { /* "feb" */
+ 0x66, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVMONTHNAME3[] = { /* "mar" */
+ 0x6d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVMONTHNAME4[] = { /* "apr" */
+ 0x61, 0x70, 0x72
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVMONTHNAME5[] = { /* "mag" */
+ 0x6d, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVMONTHNAME6[] = { /* "giu" */
+ 0x67, 0x69, 0x75
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVMONTHNAME7[] = { /* "lug" */
+ 0x6c, 0x75, 0x67
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVMONTHNAME8[] = { /* "ago" */
+ 0x61, 0x67, 0x6f
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVMONTHNAME9[] = { /* "set" */
+ 0x73, 0x65, 0x74
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVMONTHNAME10[] = { /* "ott" */
+ 0x6f, 0x74, 0x74
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVMONTHNAME11[] = { /* "nov" */
+ 0x6e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(0410) rgbSABBREVMONTHNAME12[] = { /* "dic" */
+ 0x64, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(0410) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0410) rgbIPOSSIGNPOSN[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0410) rgbINEGSIGNPOSN[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0410) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0410) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0410) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0410) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0410) rgbSENGCOUNTRY[] = { /* "Italy" */
+ 0x49, 0x74, 0x61, 0x6c, 0x79
+};
+
+static BYTE NLSALLOC(0410) rgbSENGLANGUAGE[] = { /* "Italian" */
+ 0x49, 0x74, 0x61, 0x6c, 0x69, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0410) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0410) rgbIFIRSTWEEKOFYEAR[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0410) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0410) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0410) rgbSTIMEFORMAT[] = { /* "H.mm.ss" */
+ 0x48, 0x2e, 0x6d, 0x6d, 0x2e, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0410) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0410) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0410) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0410) g_rglcinfo0410[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 7, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 8, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 5, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 6, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 2, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 0, NULL } /* SMONDECIMALSEP */
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 16, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 6, rgbSDAYNAME1 }
+ , { 7, rgbSDAYNAME2 }
+ , { 9, rgbSDAYNAME3 }
+ , { 7, rgbSDAYNAME4 }
+ , { 7, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 8, rgbSDAYNAME7 }
+ , { 3, rgbSABBREVDAYNAME1 }
+ , { 3, rgbSABBREVDAYNAME2 }
+ , { 3, rgbSABBREVDAYNAME3 }
+ , { 3, rgbSABBREVDAYNAME4 }
+ , { 3, rgbSABBREVDAYNAME5 }
+ , { 3, rgbSABBREVDAYNAME6 }
+ , { 3, rgbSABBREVDAYNAME7 }
+ , { 7, rgbSMONTHNAME1 }
+ , { 8, rgbSMONTHNAME2 }
+ , { 5, rgbSMONTHNAME3 }
+ , { 6, rgbSMONTHNAME4 }
+ , { 6, rgbSMONTHNAME5 }
+ , { 6, rgbSMONTHNAME6 }
+ , { 6, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 5, rgbSENGCOUNTRY }
+ , { 7, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0410) g_strinfo0410 = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0411.c b/private/oleauto/src/dispatch/win16/0411.c
new file mode 100644
index 000000000..fe210daf9
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0411.c
@@ -0,0 +1,1679 @@
+/***
+*0411.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+*
+* Japan, Japanese
+*
+* LCID = 0x0411
+* CodePage = 1252
+*
+*
+*Generated: 9/12/93 - by hand from lcid_jpn.txt
+*
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+#include "nlsdbcs.h"
+
+static unsigned char NLSALLOC(0411) rgbPriHi[] = {
+0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,
+0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,
+0x13,0x14,0x15,0x16,0x17,0x18,0x19,0x1A,0x1B,0x1C,0x1D,0x1E,0x1F,0x20,0x21,0x22,
+0x56,0x57,0x58,0x59,0x5A,0x5B,0x5C,0x5D,0x5E,0x5F,0x23,0x24,0x25,0x26,0x27,0x28,
+0x29,0x60,0x61,0x62,0x63,0x64,0x65,0x66,0x67,0x68,0x69,0x6A,0x6B,0x6C,0x6D,0x6E,
+0x6F,0x70,0x71,0x72,0x73,0x74,0x75,0x76,0x77,0x78,0x79,0x2A,0x2B,0x2C,0x2D,0x2E,
+0x2F,0x60,0x61,0x62,0x63,0x64,0x65,0x66,0x67,0x68,0x69,0x6A,0x6B,0x6C,0x6D,0x6E,
+0x6F,0x70,0x71,0x72,0x73,0x74,0x75,0x76,0x77,0x78,0x79,0x30,0x31,0x32,0x33,0x12,
+0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,
+0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,
+0x13,0x38,0x3C,0x3D,0x37,0x43,0xB8,0x87,0x88,0x89,0x8A,0x8B,0xAA,0xAC,0xAE,0x98,
+0x44,0x87,0x88,0x89,0x8A,0x8B,0x8C,0x8D,0x8E,0x8F,0x90,0x91,0x92,0x93,0x94,0x95,
+0x96,0x97,0x98,0x99,0x9A,0x9B,0x9C,0x9D,0x9E,0x9F,0xA0,0xA1,0xA2,0xA3,0xA4,0xA5,
+0xA6,0xA7,0xA8,0xA9,0xAA,0xAC,0xAE,0xAF,0xB0,0xB1,0xB2,0xB3,0xB4,0xB9,0x3F,0x40,
+0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,
+0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,0x12,
+0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,
+0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,
+0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,
+0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,
+0x13,0x37,0x38,0x1F,0x21,0x43,0x23,0x24,0x28,0x14,0x3F,0x40,0x34,0x2F,0x34,0x2D,
+0x33,0x2e,0x45,0x46,0x41,0x42,0x39,0x47,0x3A,0x3B,0x3B,0x44,0x35,0x34,0x22,0x47,
+0x47,0x36,0x31,0x36,0x36,0x1A,0x1A,0x15,0x15,0x1B,0x1C,0x3E,0x3E,0x2A,0x2C,0x30,
+0x32,0x3B,0x3B,0x3B,0x3B,0x3C,0x3D,0x3E,0x3E,0x3E,0x3E,0x1E,0x20,0x34,0x34,0xC1,
+0x34,0x26,0x36,0x25,0x27,0x36,0x36,0x36,0x36,0x36,0x36,0x34,0x36,0x36,0x36,0x2B,
+0x17,0x47,0x47,0x18,0x16,0x19,0x1D,0x29,0x34,0x36,0x36,0x36,0x36,0x36,0x36,0x36,
+0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x3E,0x36,0x36,0x36,0x36,0x3E,0xC1,0xC1,0xC1,
+0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,
+0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0x36,0x36,0x47,0x36,0x36,0x36,0x36,0xC1,
+0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0x36,0x36,0x36,0x36,0x36,0x36,
+0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,0xC1,
+0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x34,0xC1,0xC1,0xC1,0xC1,0x36,0xC1,0xC1,0xC1,
+0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,
+0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,
+0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,
+0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,
+0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0x56,
+0x57,0x58,0x59,0x5A,0x5B,0x5C,0x5D,0x5E,0x5F,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,
+0x60,0x61,0x62,0x63,0x64,0x65,0x66,0x67,0x68,0x69,0x6A,0x6B,0x6C,0x6D,0x6E,0x6F,
+0x70,0x71,0x72,0x73,0x74,0x75,0x76,0x77,0x78,0x79,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,
+0xC2,0x60,0x61,0x62,0x63,0x64,0x65,0x66,0x67,0x68,0x69,0x6A,0x6B,0x6C,0x6D,0x6E,
+0x6F,0x70,0x71,0x72,0x73,0x74,0x75,0x76,0x77,0x78,0x79,0xC2,0xC2,0xC2,0xC2,0x87,
+0x87,0x88,0x88,0x89,0x89,0x8A,0x8A,0x8B,0x8B,0x8C,0x8C,0x8D,0x8D,0x8E,0x8E,0x8F,
+0x8F,0x90,0x90,0x91,0x91,0x92,0x92,0x93,0x93,0x94,0x94,0x95,0x95,0x96,0x96,0x97,
+0x97,0x98,0x98,0x98,0x99,0x99,0x9A,0x9A,0x9B,0x9C,0x9D,0x9E,0x9F,0xA0,0xA0,0xA0,
+0xA1,0xA1,0xA1,0xA2,0xA2,0xA2,0xA3,0xA3,0xA3,0xA4,0xA4,0xA4,0xA5,0xA6,0xA7,0xA8,
+0xA9,0xAA,0xAA,0xAC,0xAC,0xAE,0xAE,0xAF,0xB0,0xB1,0xB2,0xB3,0xB4,0xB4,0xB5,0xB7,
+0xB8,0xB9,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,0xC2,
+0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,
+0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,
+0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,
+0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,
+0x87,0x87,0x88,0x88,0x89,0x89,0x8A,0x8A,0x8B,0x8B,0x8C,0x8C,0x8D,0x8D,0x8E,0x8E,
+0x8F,0x8F,0x90,0x90,0x91,0x91,0x92,0x92,0x93,0x93,0x94,0x94,0x95,0x95,0x96,0x96,
+0x97,0x97,0x98,0x98,0x98,0x99,0x99,0x9A,0x9A,0x9B,0x9C,0x9D,0x9E,0x9F,0xA0,0xA0,
+0xA0,0xA1,0xA1,0xA1,0xA2,0xA2,0xA2,0xA3,0xA3,0xA3,0xA4,0xA4,0xA4,0xA5,0xA6,0xC3,
+0xA7,0xA8,0xA9,0xAA,0xAA,0xAC,0xAC,0xAE,0xAE,0xAF,0xB0,0xB1,0xB2,0xB3,0xB4,0xB4,
+0xB5,0xB7,0xB8,0xB9,0x89,0x8C,0x8F,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0x7C,
+0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,
+0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0x7C,
+0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,
+0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0x7C,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,
+0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,
+0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,0xC3,
+0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,
+0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,
+0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,
+0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,
+0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,
+0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,
+0x7D,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,
+0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0xC4,
+0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,0x7D,
+0x7D,0x7D,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0x36,
+0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,
+0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0xC4,
+0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,
+0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,
+0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,
+0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,0xC4,
+0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,
+0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,
+0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,
+0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,
+0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,
+0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,
+0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,
+0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,
+0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,
+0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,
+0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,
+0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,
+0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,
+0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,
+0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,
+0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,0xC5,
+0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,
+0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,
+0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,
+0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,
+0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,
+0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,
+0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,
+0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,
+0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,
+0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,
+0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,
+0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,
+0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,
+0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,
+0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,
+0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,0xC6,
+0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,
+0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,
+0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,
+0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,
+0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,
+0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0xC7,0x47,
+0x47,0x47,0x47,0x47,0x47,0x47,0x47,0x47,0x47,0x47,0x47,0x47,0x47,0x47,0x47,0x47,
+0x47,0x47,0x47,0x47,0x47,0x47,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0xC7,0x47,0xC7,
+0x3E,0x3E,0x36,0x47,0x36,0x47,0x47,0x47,0x47,0x47,0x47,0x47,0x47,0x47,0x47,0x47,
+0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0x36,0xC7,0xC7,0xC7
+};
+
+static unsigned char NLSALLOC(0411) rgbPriLo[] = {
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,
+0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,
+0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,
+0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,
+0x10,0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19,0x1A,0x1B,0x1C,0x1D,0x1E,0x1F,
+0x20,0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29,0x2A,0x2B,0x2C,0x2D,0x2E,0x2F,
+0x30,0x31,0x32,0x33,0x34,0x35,0x36,0x37,0x38,0x39,0x3A,0x3B,0x3C,0x3D,0x3E,0x3F,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x05,0x00,0x02,0x00,
+0x00,0x00,0xFF,0xFF,0xFF,0xFF,0x00,0x28,0xFF,0x03,0x04,0xFF,0xFF,0x09,0x00,0x29,
+0x2A,0x2B,0x00,0x04,0x03,0x00,0x00,0x00,0x00,0x00,0x00,0x07,0x08,0x00,0x00,0x00,
+0x00,0x05,0x06,0x07,0x08,0x00,0x00,0x01,0x02,0x03,0x04,0x00,0x00,0x04,0x07,0x7F,
+0x08,0x00,0x3C,0x00,0x00,0x3F,0x40,0x27,0x36,0x8E,0x8D,0x03,0x06,0x07,0x09,0x00,
+0x00,0x2B,0x2C,0x00,0x00,0x00,0x00,0x00,0x01,0x8C,0x8B,0x87,0x89,0x88,0x86,0x85,
+0x80,0x7F,0x82,0x81,0x84,0x83,0x08,0x05,0x19,0x17,0x18,0x1A,0x06,0xAD,0xAE,0xAF,
+0xB0,0xB1,0xB2,0xB3,0xB4,0xB5,0xB6,0xB7,0x21,0x22,0x45,0x46,0x43,0x44,0x30,0x2E,
+0xC0,0xC1,0xC2,0xC3,0xC4,0xC5,0xC6,0xC7,0x2C,0x2D,0x2D,0x1B,0x1C,0x1D,0x1F,0xCF,
+0xD0,0xD1,0xD2,0xD3,0xD4,0xD5,0xD6,0xD7,0xD8,0xD9,0x29,0x47,0x4A,0x1E,0x20,0x3D,
+0x3A,0x41,0x42,0x24,0x39,0x26,0x37,0x32,0x34,0xE9,0xEA,0xEB,0xEC,0xED,0xEE,0xEF,
+0x0C,0x05,0x91,0x90,0x8F,0x01,0x02,0x06,0xF8,0xF9,0xFA,0xFB,0x8A,0xFD,0xFE,0xFF,
+0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,
+0x10,0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19,0x1A,0x1B,0x1C,0x1D,0x1E,0x1F,
+0x20,0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29,0x2A,0x2B,0x2C,0x2D,0x2E,0x2F,
+0x30,0x31,0x32,0x33,0x34,0x35,0x36,0x37,0x38,0x39,0x3A,0x3B,0x3C,0x3D,0x3E,0x3F,
+0x40,0x41,0x42,0x43,0x44,0x45,0x46,0x47,0x48,0x49,0x4A,0x4B,0x4C,0x4D,0x4E,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x59,0x5A,0x5B,0x5C,0x5D,0x5E,0x5F,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7A,0x7B,0x7C,0x7D,0x7E,0x7F,
+0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x9B,0x9C,0x9D,0x9E,0xFF,
+0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0x00,0xFF,0x00,0xFF,0x00,0xFF,
+0x00,0xFF,0x00,0xFF,0x00,0xFF,0x00,0xFF,0x00,0xFF,0x00,0xFF,0x00,0xFF,0x00,0xFF,
+0x00,0xFF,0xFF,0x00,0xFF,0x00,0xFF,0x00,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0x00,0x00,
+0xFF,0x00,0x00,0xFF,0x00,0x00,0xFF,0x00,0x00,0xFF,0x00,0x00,0xFF,0xFF,0xFF,0xFF,
+0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,
+0xFF,0xFF,0xF2,0xF3,0xF4,0xF5,0xF6,0xF7,0xF8,0xF9,0xFA,0xFB,0xFC,0xFD,0xFE,0xFF,
+0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,
+0x10,0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19,0x1A,0x1B,0x1C,0x1D,0x1E,0x1F,
+0x20,0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29,0x2A,0x2B,0x2C,0x2D,0x2E,0x2F,
+0x30,0x31,0x32,0x33,0x34,0x35,0x36,0x37,0x38,0x39,0x3A,0x3B,0x3C,0x3D,0x3E,0x3F,
+0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0x00,0xFF,0x00,0xFF,0x00,
+0xFF,0x00,0xFF,0x00,0xFF,0x00,0xFF,0x00,0xFF,0x00,0xFF,0x00,0xFF,0x00,0xFF,0x00,
+0xFF,0x00,0xFF,0xFF,0x00,0xFF,0x00,0xFF,0x00,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0x00,
+0x00,0xFF,0x00,0x00,0xFF,0x00,0x00,0xFF,0x00,0x00,0xFF,0x00,0x00,0xFF,0xFF,0x7F,
+0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,
+0xFF,0xFF,0xFF,0xFF,0x00,0xFF,0xFF,0x97,0x98,0x99,0x9A,0x9B,0x9C,0x9D,0x9E,0x11,
+0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19,0x1A,0x1B,0x1C,0x1D,0x1E,0x1F,0x20,0x21,
+0x22,0x23,0x24,0x25,0x26,0x27,0x28,0xB7,0xB8,0xB9,0xBA,0xBB,0xBC,0xBD,0xBE,0x11,
+0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19,0x1A,0x1B,0x1C,0x1D,0x1E,0x1F,0x20,0x21,
+0x22,0x23,0x24,0x25,0x26,0x27,0x28,0xD7,0xD8,0xD9,0xDA,0xDB,0xDC,0xDD,0xDE,0xDF,
+0xE0,0xE1,0xE2,0xE3,0xE4,0xE5,0xE6,0xE7,0xE8,0xE9,0xEA,0xEB,0xEC,0xED,0xEE,0xEF,
+0xF0,0xF1,0xF2,0xF3,0xF4,0xF5,0xF6,0xF7,0xF8,0xF9,0xFA,0xFB,0xFC,0xFD,0xFE,0xFF,
+0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,
+0x10,0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19,0x1A,0x1B,0x1C,0x1D,0x1E,0x1F,
+0x20,0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29,0x2A,0x2B,0x2C,0x2D,0x2E,0x2F,
+0x30,0x31,0x32,0x33,0x34,0x35,0x36,0x37,0x38,0x39,0x3A,0x3B,0x3C,0x3D,0x3E,0x3F,
+0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19,0x1A,0x1B,0x1C,0x1D,0x1E,0x1F,0x20,
+0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29,0x2A,0x2B,0x2C,0x2D,0x2E,0x2F,0x30,
+0x31,0x61,0x62,0x63,0x64,0x65,0x66,0x67,0x68,0x69,0x6A,0x6B,0x6C,0x6D,0x6E,0x6F,
+0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19,0x1A,0x1B,0x1C,0x1D,0x1E,0x1F,0x7F,
+0x20,0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29,0x2A,0x2B,0x2C,0x2D,0x2E,0x2F,
+0x30,0x31,0x92,0x93,0x94,0x95,0x96,0x97,0x98,0x99,0x9A,0x9B,0x9C,0x9D,0x9E,0x5F,
+0x61,0x63,0x65,0x69,0x67,0x6B,0x73,0x6F,0x77,0x7B,0x60,0x62,0x64,0x66,0x6A,0x68,
+0x6E,0x76,0x72,0x7A,0x7E,0x6D,0x74,0x71,0x78,0x7C,0x6C,0x75,0x70,0x79,0x7D,0xBF,
+0xC0,0xC1,0xC2,0xC3,0xC4,0xC5,0xC6,0xC7,0xC8,0xC9,0xCA,0xCB,0xCC,0xCD,0xCE,0xCF,
+0xD0,0xD1,0xD2,0xD3,0xD4,0xD5,0xD6,0xD7,0xD8,0xD9,0xDA,0xDB,0xDC,0xDD,0xDE,0xDF,
+0xE0,0xE1,0xE2,0xE3,0xE4,0xE5,0xE6,0xE7,0xE8,0xE9,0xEA,0xEB,0xEC,0xED,0xEE,0xEF,
+0xF0,0xF1,0xF2,0xF3,0xF4,0xF5,0xF6,0xF7,0xF8,0xF9,0xFA,0xFB,0xFC,0xFD,0xFE,0xFF,
+0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09,0x0A,0x0B,0x0C,0x0D,0x0E,0x0F,
+0x10,0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19,0x1A,0x1B,0x1C,0x1D,0x1E,0x1F,
+0x20,0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29,0x2A,0x2B,0x2C,0x2D,0x2E,0x2F,
+0x30,0x31,0x32,0x33,0x34,0x35,0x36,0x37,0x38,0x39,0x3A,0x3B,0x3C,0x3D,0x3E,0x3F,
+0x40,0x41,0x42,0x43,0x44,0x45,0x46,0x47,0x48,0x49,0x4A,0x4B,0x4C,0x4D,0x4E,0x4F,
+0x50,0x51,0x52,0x53,0x54,0x55,0x56,0x57,0x58,0x59,0x5A,0x5B,0x5C,0x5D,0x5E,0x5F,
+0x60,0x61,0x62,0x63,0x64,0x65,0x66,0x67,0x68,0x69,0x6A,0x6B,0x6C,0x6D,0x6E,0x6F,
+0x70,0x71,0x72,0x73,0x74,0x75,0x76,0x77,0x78,0x79,0x7A,0x7B,0x7C,0x7D,0x7E,0x7F,
+0x80,0x81,0x82,0x83,0x84,0x85,0x86,0x87,0x88,0x89,0x8A,0x8B,0x8C,0x8D,0x8E,0x8F,
+0x90,0x91,0x92,0x93,0x94,0x95,0x96,0x97,0x98,0x99,0x9A,0x9B,0x9C,0x9D,0x9E,0x9F,
+0xA0,0xA1,0xA2,0xA3,0xA4,0xA5,0xA6,0xA7,0xA8,0xA9,0xAA,0xAB,0xAC,0xAD,0xAE,0xAF,
+0xB0,0xB1,0xB2,0xB3,0xB4,0xB5,0xB6,0xB7,0xB8,0xB9,0xBA,0xBB,0xBC,0xBD,0xBE,0xBF,
+0xC0,0xC1,0xC2,0xC3,0xC4,0xC5,0xC6,0xC7,0xC8,0xC9,0xCA,0xCB,0xCC,0xCD,0xCE,0xCF,
+0xD0,0xD1,0xD2,0xD3,0xD4,0xD5,0xD6,0xD7,0xD8,0xD9,0xDA,0xDB,0xDC,0xDD,0xDE,0xDF,
+0xE0,0xE1,0xE2,0xE3,0xE4,0xE5,0xE6,0xE7,0xE8,0xE9,0xEA,0xEB,0xEC,0xED,0xEE,0xEF,
+0xF0,0xF1,0xF2,0xF3,0xF4,0xF5,0xF6,0xF7,0xF8,0xF9,0xFA,0xFB,0xFC,0xFD,0xFE,0xFF,
+0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09,0x0A,0x0B,0x0C,0x0D,0x0E,0x0F,
+0x10,0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19,0x1A,0x1B,0x1C,0x1D,0x1E,0x1F,
+0x20,0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29,0x2A,0x2B,0x2C,0x2D,0x2E,0x2F,
+0x30,0x31,0x32,0x33,0x34,0x35,0x36,0x37,0x38,0x39,0x3A,0x3B,0x3C,0x3D,0x3E,0x3F,
+0x40,0x41,0x42,0x43,0x44,0x45,0x46,0x47,0x48,0x49,0x4A,0x4B,0x4C,0x4D,0x4E,0x4F,
+0x50,0x51,0x52,0x53,0x54,0x55,0x56,0x57,0x58,0x59,0x5A,0x5B,0x5C,0x5D,0x5E,0x5F,
+0x60,0x61,0x62,0x63,0x64,0x65,0x66,0x67,0x68,0x69,0x6A,0x6B,0x6C,0x6D,0x6E,0x6F,
+0x70,0x71,0x72,0x73,0x74,0x75,0x76,0x77,0x78,0x79,0x7A,0x7B,0x7C,0x7D,0x7E,0x7F,
+0x80,0x81,0x82,0x83,0x84,0x85,0x86,0x87,0x88,0x89,0x8A,0x8B,0x8C,0x8D,0x8E,0x8F,
+0x90,0x91,0x92,0x93,0x94,0x95,0x96,0x97,0x98,0x99,0x9A,0x9B,0x9C,0x9D,0x9E,0x9F,
+0xA0,0xA1,0xA2,0xA3,0xA4,0xA5,0xA6,0xA7,0xA8,0xA9,0xAA,0xAB,0xAC,0xAD,0xAE,0xAF,
+0xB0,0xB1,0xB2,0xB3,0xB4,0xB5,0xB6,0xB7,0xB8,0xB9,0xBA,0xBB,0xBC,0xBD,0xBE,0xBF,
+0xC0,0xC1,0xC2,0xC3,0xC4,0xC5,0xC6,0xC7,0xC8,0xC9,0xCA,0xCB,0xCC,0xCD,0xCE,0xCF,
+0xD0,0xD1,0xD2,0xD3,0xD4,0xD5,0xD6,0xD7,0xD8,0xD9,0xDA,0xDB,0xDC,0xDD,0xDE,0xDF,
+0xE0,0xE1,0xE2,0xE3,0xE4,0xE5,0xE6,0xE7,0xE8,0xE9,0xEA,0xEB,0xEC,0xED,0xEE,0xEF,
+0xF0,0xF1,0xF2,0xF3,0xF4,0xF5,0xF6,0xF7,0xF8,0xF9,0xFA,0xFB,0xFC,0xFD,0xFE,0xFF,
+0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09,0x0A,0x0B,0x0C,0x0D,0x0E,0x0F,
+0x10,0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19,0x1A,0x1B,0x1C,0x1D,0x1E,0x1F,
+0x20,0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29,0x2A,0x2B,0x2C,0x2D,0x2E,0x2F,
+0x30,0x31,0x32,0x33,0x34,0x35,0x36,0x37,0x38,0x39,0x3A,0x3B,0x3C,0x3D,0x3E,0x3F,
+0x4B,0x4C,0x4D,0x4E,0x4F,0x50,0x51,0x52,0x53,0x54,0x55,0x56,0x57,0x58,0x59,0x5A,
+0x5B,0x5C,0x5D,0x5E,0x0D,0x0E,0x0F,0x10,0x11,0x12,0x13,0x14,0x15,0x16,0x5E,0x17,
+0x0E,0x10,0x19,0x0F,0x13,0x0C,0x15,0x1A,0x1B,0x0D,0x12,0x11,0x14,0x18,0x16,0x22,
+0x23,0x24,0x20,0x21,0x26,0x25,0x76,0x77,0x78,0x79,0x7A,0x7B,0x7C,0x7D,0x1C,0x7F,
+0x09,0x0A,0x0A,0x27,0x0B,0x07,0x08,0x09,0x0A,0x0B,0x04,0x05,0x06,0x1F,0x1E,0x1D,
+0x3B,0x3E,0x33,0x35,0x23,0x25,0x48,0x2A,0x28,0x49,0x38,0x2F,0x31,0x9D,0x9E,0x9F
+};
+
+static unsigned char NLSALLOC(0411) rgbSecwgt[] = {
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x04,0x00,0x00,0x00,0x00,0x04,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,
+0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x14,0x04,0x04,0x04,0x04,0x04,0x04,0x00,0x00,0x04,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x04,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x04,0x04,0x04,0x00,0x00,0x00,0x00,0x00,0x04,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x00,0x40,0x00,0x40,
+0x40,0x40,0x08,0x09,0x08,0x09,0x00,0x00,0x08,0x00,0x00,0x54,0x54,0x00,0x40,0x00,
+0x00,0x00,0x40,0x00,0x00,0x40,0x44,0x40,0x44,0x40,0x40,0x00,0x00,0x40,0x40,0x40,
+0x40,0x00,0x00,0x00,0x00,0x40,0x40,0x00,0x00,0x00,0x00,0x40,0x40,0x00,0x00,0x00,
+0x00,0x40,0x00,0x40,0x40,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x40,
+0x40,0x00,0x00,0x40,0x40,0x40,0x40,0x40,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x40,
+0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x60,0x60,0x60,0x60,0x60,0x60,0x60,0x60,0x60,0x60,0x60,0x60,0x60,0x60,0x60,0x60,
+0x60,0x60,0x60,0x60,0x60,0x60,0x60,0x60,0x60,0x60,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,
+0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x00,0x00,0x00,0x00,0x60,
+0x64,0x60,0x64,0x60,0x64,0x60,0x64,0x60,0x64,0x64,0x65,0x60,0x61,0x60,0x61,0x64,
+0x65,0x60,0x61,0x60,0x61,0x60,0x61,0x60,0x61,0x60,0x61,0x60,0x61,0x60,0x61,0x60,
+0x61,0x60,0x64,0x65,0x60,0x61,0x60,0x61,0x60,0x60,0x60,0x60,0x60,0x60,0x61,0x62,
+0x60,0x61,0x62,0x60,0x61,0x62,0x60,0x61,0x62,0x60,0x61,0x62,0x60,0x60,0x60,0x60,
+0x60,0x60,0x64,0x60,0x64,0x60,0x64,0x60,0x60,0x60,0x60,0x60,0x60,0x64,0x20,0x20,
+0x60,0x60,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x40,0x44,0x40,0x44,0x40,0x44,0x40,0x44,0x40,0x44,0x44,0x45,0x40,0x41,0x40,0x41,
+0x44,0x45,0x40,0x41,0x40,0x41,0x40,0x41,0x40,0x41,0x40,0x41,0x40,0x41,0x40,0x41,
+0x40,0x41,0x40,0x44,0x45,0x40,0x41,0x40,0x41,0x40,0x40,0x40,0x40,0x40,0x40,0x41,
+0x42,0x40,0x41,0x42,0x40,0x41,0x42,0x40,0x41,0x42,0x40,0x41,0x42,0x40,0x40,0x00,
+0x40,0x40,0x40,0x40,0x44,0x40,0x44,0x40,0x44,0x40,0x40,0x40,0x40,0x40,0x40,0x44,
+0x00,0x00,0x40,0x40,0x45,0x40,0x40,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x20,
+0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,
+0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,
+0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,
+0x20,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00
+};
+
+static unsigned char NLSALLOC(0411) rgbSecflg[] = {
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x20,0x20,0x22,0x20,0x20,0x20,0x20,0x22,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,
+0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,
+0x20,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,
+0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x20,0x20,0x20,0x20,0x20,
+0x20,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,
+0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x20,0x20,0x20,0x20,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x20,0x20,0x20,0x20,0x20,0x20,0x35,0x37,0x37,0x37,0x37,0x37,0x37,0x37,0x37,0x37,
+0x37,0x37,0x37,0x37,0x37,0x37,0x37,0x35,0x35,0x37,0x35,0x35,0x35,0x35,0x35,0x35,
+0x35,0x35,0x37,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,
+0x35,0x35,0x35,0x35,0x37,0x37,0x37,0x35,0x35,0x35,0x35,0x35,0x37,0x35,0x20,0x20,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x00,0x20,0x00,0x20,
+0x20,0x20,0x05,0x05,0x05,0x05,0x00,0x00,0x04,0x00,0x00,0x37,0x37,0x00,0x20,0x00,
+0x00,0x00,0x20,0x00,0x00,0x22,0x22,0x22,0x22,0x20,0x20,0x00,0x00,0x20,0x20,0x20,
+0x20,0x00,0x00,0x00,0x00,0x20,0x20,0x00,0x00,0x00,0x00,0x20,0x20,0x00,0x00,0x00,
+0x00,0x20,0x00,0x20,0x20,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x20,
+0x20,0x00,0x00,0x20,0x20,0x20,0x20,0x20,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x20,
+0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,
+0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,
+0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x28,0x00,0x00,0x00,0x00,0x37,
+0x37,0x37,0x37,0x37,0x37,0x37,0x37,0x37,0x37,0x37,0x37,0x35,0x35,0x35,0x35,0x37,
+0x37,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,
+0x35,0x37,0x37,0x37,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,
+0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,
+0x35,0x37,0x37,0x37,0x37,0x37,0x37,0x35,0x35,0x35,0x35,0x35,0x37,0x37,0x15,0x15,
+0x35,0x35,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x37,0x37,0x37,0x37,0x37,0x37,0x37,0x37,0x37,0x37,0x37,0x37,0x35,0x35,0x35,0x35,
+0x37,0x37,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,
+0x35,0x35,0x37,0x37,0x37,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,
+0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x35,0x00,
+0x35,0x35,0x35,0x37,0x37,0x37,0x37,0x37,0x37,0x35,0x35,0x35,0x35,0x35,0x37,0x37,
+0x15,0x15,0x35,0x35,0x37,0x37,0x37,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x08,
+0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,
+0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x08,
+0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,
+0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,
+0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,
+0x08,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x00,
+0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,
+0x08,0x08,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00
+};
+
+static unsigned char NLSALLOC(0411) rgbMasks[] = {
+ 0x03, 0x01, 0x00, 0x02
+ , 0x04, 0x02, 0x02, 0x01
+ , 0x18, 0x04, 0x03, 0x02
+ , 0x20, 0x18, 0x05, 0x01
+ , 0x40, 0x20, 0x06, 0x01
+ , 0x00, 0x00, 0x00, 0x00
+};
+
+static unsigned char NLSALLOC(0411) rgbMaps[] = {
+ 0x20, 0x08, 0x02, 0x00, 0x01, 0x00
+ , 0x20, 0x10, 0x20, 0x00, 0x40, 0x00
+ , 0x40, 0x20, 0x10, 0x00, 0x08, 0x00
+ , 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
+};
+
+static unsigned char NLSALLOC(0411) rgbIgnore[] = {
+ 0x1F, 0x07, 0x00, 0x02
+ , 0x20, 0x08, 0x00, 0x01
+ , 0x20, 0x10, 0x00, 0x40
+ , 0x40, 0x20, 0x00, 0x08
+ , 0x00, 0x00, 0x00, 0x00
+};
+
+static unsigned char NLSALLOC(0411) rgbC1JPN[] = {
+0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x20,
+0x00,0x20,0x00,0x68,0x00,0x28,0x00,0x28,0x00,0x28,0x00,0x28,0x00,0x20,0x00,0x20,
+0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x20,
+0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x20,0x00,0x20,
+0x00,0x48,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x84,0x00,0x84,0x00,0x84,0x00,0x84,0x00,0x84,0x00,0x84,0x00,0x84,0x00,0x84,
+0x00,0x84,0x00,0x84,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x01,0x81,0x01,0x81,0x01,0x81,0x01,0x81,0x01,0x81,0x01,0x81,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x01,0x82,0x01,0x82,0x01,0x82,0x01,0x82,0x01,0x82,0x01,0x82,0x01,0x02,
+0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,
+0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,
+0x01,0x02,0x01,0x02,0x01,0x02,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x48,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x48,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x01,0x00,0x01,0x00,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x00,0x10,0x00,0x10,
+0x01,0x00,0x00,0x10,0x00,0x10,0x01,0x00,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x00,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x84,
+0x00,0x84,0x00,0x84,0x00,0x84,0x00,0x84,0x00,0x84,0x00,0x84,0x00,0x84,0x00,0x84,
+0x00,0x84,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x01,0x81,0x01,0x81,0x01,0x81,0x01,0x81,0x01,0x81,0x01,0x81,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x01,0x82,0x01,0x82,0x01,0x82,0x01,0x82,0x01,0x82,0x01,0x82,0x01,0x02,
+0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,
+0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,
+0x01,0x02,0x01,0x02,0x01,0x02,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x00,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,
+0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x02,
+0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,
+0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,
+0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,
+0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x00,0x00,
+0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,
+0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,0x01,0x02,
+0x01,0x02,0x01,0x02,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x00,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x10,0x00,0x00,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,
+0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x00,0x00,0x00,0x00,0x00
+};
+
+static unsigned char NLSALLOC(0411) rgbC2JPN[] = {
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x09,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x0A,0x0B,0x0B,0x05,0x05,0x05,0x01,0x0B,0x0B,0x0B,0x0B,0x05,0x07,0x05,0x04,0x04,
+0x03,0x03,0x03,0x03,0x03,0x03,0x03,0x03,0x03,0x03,0x07,0x0B,0x0B,0x0B,0x0B,0x0B,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x0B,0x0B,0x0B,0x0B,0x0B,
+0x0B,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x0B,0x0B,0x0B,0x0B,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x0A,0x0B,0x0B,0x0B,0x0B,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x0A,0x0B,0x0B,0x07,0x04,0x01,0x07,0x0B,0x0B,0x0B,0x01,0x01,0x0B,0x0B,0x0B,0x0B,
+0x0B,0x0B,0x01,0x01,0x01,0x01,0x0B,0x0B,0x0B,0x0B,0x0B,0x01,0x0B,0x0B,0x04,0x0B,
+0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,
+0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x05,0x05,0x05,0x0B,0x00,
+0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x05,0x05,0x05,0x0B,0x05,
+0x05,0x05,0x05,0x05,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,
+0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,
+0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x0B,0x05,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x03,
+0x03,0x03,0x03,0x03,0x03,0x03,0x03,0x03,0x03,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x00,0x00,0x00,0x00,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x00,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x00,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x0B,
+0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,
+0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,
+0x0B,0x0B,0x0B,0x0B,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x00,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x01,0x01,0x01,0x01,0x01,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x00,
+0x0B,0x0B,0x0B,0x01,0x0B,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
+0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x0B,0x00,0x00,0x00
+};
+
+static unsigned char NLSALLOC(0411) rgbC3JPN[] = {
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x00,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x00,0x00,0x08,0x00,0x08,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,
+0x00,0x08,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,
+0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,
+0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,
+0x80,0x00,0x80,0x00,0x80,0x00,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,
+0x00,0x08,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,
+0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,
+0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,
+0x80,0x00,0x80,0x00,0x80,0x00,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x08,0x00,0x48,0x00,0x48,0x00,0x48,0x00,0x48,0x00,0x48,0x80,0x50,0x80,0x53,
+0x80,0x53,0x80,0x53,0x80,0x53,0x80,0x53,0x80,0x53,0x80,0x53,0x80,0x53,0x80,0x53,
+0x80,0x73,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,
+0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,
+0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,
+0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,
+0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,
+0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x50,0x80,0x73,0x80,0x73,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x88,0x00,0x88,0x00,0x08,0x00,0x88,0x00,0x88,
+0x00,0x88,0x00,0x88,0x80,0xB3,0x80,0xB3,0x00,0x08,0x00,0x88,0x00,0x08,0x00,0x88,
+0x00,0x88,0x00,0x88,0x80,0x10,0x80,0x13,0x80,0x20,0x80,0x23,0x00,0x08,0x00,0x08,
+0x80,0x00,0x00,0x08,0x00,0x08,0x80,0x33,0x00,0x08,0x00,0x08,0x00,0x88,0x00,0x88,
+0x00,0x88,0x00,0x08,0x00,0x88,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,
+0x00,0x08,0x00,0x88,0x00,0x88,0x00,0x08,0x00,0x08,0x00,0x88,0x00,0x88,0x00,0x88,
+0x00,0x88,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x88,0x00,0x80,0x00,0x08,0x00,0x08,0x00,0x00,
+0x00,0x08,0x00,0x88,0x00,0x08,0x00,0x88,0x00,0x88,0x00,0x08,0x00,0x08,0x00,0x08,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x88,
+0x00,0x88,0x00,0x88,0x00,0x88,0x00,0x88,0x00,0x88,0x00,0x88,0x00,0x88,0x00,0x88,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x08,0x00,0x08,0x00,0x88,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,
+0x00,0x08,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x80,
+0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,
+0x00,0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,
+0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,
+0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,
+0x80,0x80,0x80,0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,
+0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,
+0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x80,
+0x80,0x80,0x80,0x80,0x80,0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x80,0xA3,
+0x80,0xA0,0x80,0xA3,0x80,0xA0,0x80,0xA3,0x80,0xA0,0x80,0xA3,0x80,0xA0,0x80,0xA3,
+0x80,0xA0,0x80,0xA0,0x80,0xA3,0x80,0xA0,0x80,0xA3,0x80,0xA0,0x80,0xA3,0x80,0xA0,
+0x80,0xA3,0x80,0xA0,0x80,0xA3,0x80,0xA0,0x80,0xA3,0x80,0xA0,0x80,0xA3,0x80,0xA0,
+0x80,0xA3,0x80,0xA0,0x80,0xA3,0x80,0xA0,0x80,0xA3,0x80,0xA0,0x80,0xA3,0x80,0xA0,
+0x80,0xA3,0x80,0xA3,0x80,0xA0,0x80,0xA3,0x80,0xA0,0x80,0xA3,0x80,0xA0,0x80,0xA3,
+0x80,0xA0,0x80,0xA0,0x80,0xA0,0x80,0xA0,0x80,0xA0,0x80,0xA0,0x80,0xA3,0x80,0xA3,
+0x80,0xA0,0x80,0xA3,0x80,0xA3,0x80,0xA0,0x80,0xA3,0x80,0xA3,0x80,0xA0,0x80,0xA3,
+0x80,0xA3,0x80,0xA0,0x80,0xA3,0x80,0xA3,0x80,0xA0,0x80,0xA0,0x80,0xA0,0x80,0xA0,
+0x80,0xA0,0x80,0xA3,0x80,0xA0,0x80,0xA3,0x80,0xA0,0x80,0xA3,0x80,0xA0,0x80,0xA0,
+0x80,0xA0,0x80,0xA0,0x80,0xA0,0x80,0xA0,0x80,0xA3,0x80,0xA0,0x80,0xA0,0x80,0xA0,
+0x80,0xA0,0x80,0xA0,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x80,0x93,0x80,0x90,0x80,0x93,0x80,0x90,0x80,0x93,0x80,0x90,0x80,0x93,0x80,0x90,
+0x80,0x93,0x80,0x90,0x80,0x90,0x80,0x93,0x80,0x90,0x80,0x93,0x80,0x90,0x80,0x93,
+0x80,0x90,0x80,0x93,0x80,0x90,0x80,0x93,0x80,0x90,0x80,0x93,0x80,0x90,0x80,0x93,
+0x80,0x90,0x80,0x93,0x80,0x90,0x80,0x93,0x80,0x90,0x80,0x93,0x80,0x90,0x80,0x93,
+0x80,0x90,0x80,0x93,0x80,0x93,0x80,0x90,0x80,0x93,0x80,0x90,0x80,0x93,0x80,0x90,
+0x80,0x93,0x80,0x90,0x80,0x90,0x80,0x90,0x80,0x90,0x80,0x90,0x80,0x90,0x80,0x93,
+0x80,0x93,0x80,0x90,0x80,0x93,0x80,0x93,0x80,0x90,0x80,0x93,0x80,0x93,0x80,0x90,
+0x80,0x93,0x80,0x93,0x80,0x90,0x80,0x93,0x80,0x93,0x80,0x90,0x80,0x90,0x00,0x00,
+0x80,0x90,0x80,0x90,0x80,0x90,0x80,0x93,0x80,0x90,0x80,0x93,0x80,0x90,0x80,0x93,
+0x80,0x90,0x80,0x90,0x80,0x90,0x80,0x90,0x80,0x90,0x80,0x90,0x80,0x93,0x80,0x90,
+0x80,0x90,0x80,0x90,0x80,0x90,0x80,0x90,0x80,0x93,0x80,0x93,0x80,0x93,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x80,0x00,
+0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,
+0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,
+0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x80,0x00,
+0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,
+0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,
+0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x03,0x80,0x00,
+0x80,0x00,0x80,0x00,0x80,0x03,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,
+0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,
+0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,
+0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x03,0x80,0x00,
+0x80,0x00,0x80,0x00,0x80,0x03,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x00,0x00,
+0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,
+0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,0x80,0x00,
+0x80,0x00,0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x08,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x08,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x00,0x00,0x00,
+0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x08,0x00,0x00,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,
+0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0x00,0x00,0x00,0x00,0x00
+};
+
+
+static unsigned char NLSALLOC(0411) rgbILANGUAGE[] = {
+ '0', '4', '1', '1'
+};
+
+static unsigned char NLSALLOC(0411) rgbSLANGUAGE[] = {
+ 0x93, 0xfa, 0x96, 0x7b, 0x8c, 0xea
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVLANGNAME[] = {
+ 'J', 'P', 'N'
+};
+
+static unsigned char NLSALLOC(0411) rgbSNATIVELANGNAME[] = {
+ 0x93, 0xfa, 0x96, 0x7b, 0x8c, 0xea
+};
+
+static unsigned char NLSALLOC(0411) rgbICOUNTRY[] = {
+ '8', '1'
+};
+
+static unsigned char NLSALLOC(0411) rgbSCOUNTRY[] = {
+ 0x93, 0xfa, 0x96, 0x7b
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVCTRYNAME[] = {
+ 'J', 'P', 'N'
+};
+
+static unsigned char NLSALLOC(0411) rgbSNATIVECTRYNAME[] = {
+ 0x93, 0xfa, 0x96, 0x7b
+};
+
+static unsigned char NLSALLOC(0411) rgbIDEFAULTLANGUAGE[] = {
+ '0', '4', '1', '1'
+};
+
+static unsigned char NLSALLOC(0411) rgbIDEFAULTCOUNTRY[] = {
+ '8', '1'
+};
+
+static unsigned char NLSALLOC(0411) rgbIDEFAULTCODEPAGE[] = {
+ '9', '3', '2'
+};
+
+static unsigned char NLSALLOC(0411) rgbSLIST[] = {
+ ','
+};
+
+static unsigned char NLSALLOC(0411) rgbIMEASURE[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0411) rgbSDECIMAL[] = {
+ '.'
+};
+
+static unsigned char NLSALLOC(0411) rgbSTHOUSAND[] = {
+ ','
+};
+
+static unsigned char NLSALLOC(0411) rgbSGROUPING[] = {
+ '3', ';', '0'
+};
+
+static unsigned char NLSALLOC(0411) rgbIDIGITS[] = {
+ '2'
+};
+
+static unsigned char NLSALLOC(0411) rgbILZERO[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0411) rgbSNATIVEDIGITS[] = {
+ '0', '1', '2', '3', '4', '5', '6', '7', '8', '9'
+};
+
+static unsigned char NLSALLOC(0411) rgbSCURRENCY[] = {
+ 0x5c
+};
+
+static unsigned char NLSALLOC(0411) rgbSINTLSYMBOL[] = {
+ 'J', 'P', 'Y'
+};
+
+static unsigned char NLSALLOC(0411) rgbSMONDECIMALSEP[] = {
+ '.'
+};
+
+static unsigned char NLSALLOC(0411) rgbSMONTHOUSANDSEP[] = {
+ ','
+};
+
+static unsigned char NLSALLOC(0411) rgbSMONGROUPING[] = {
+ '3', ';', '0'
+};
+
+static unsigned char NLSALLOC(0411) rgbICURRDIGITS[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0411) rgbIINTLCURRDIGITS[] = {
+ '2'
+};
+
+static unsigned char NLSALLOC(0411) rgbICURRENCY[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0411) rgbINEGCURR[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0411) rgbSDATE[] = {
+ '/'
+};
+
+static unsigned char NLSALLOC(0411) rgbSTIME[] = {
+ ':'
+};
+
+static unsigned char NLSALLOC(0411) rgbSSHORTDATE[] = {
+ 'y', 'y', '/', 'M', 'M', '/', 'd', 'd'
+};
+
+static unsigned char NLSALLOC(0411) rgbSLONGDATE[] = {
+ 'y', 'y', 'y', 'y',
+ 0x27, 0x94, 0x4e, 0x27,
+ 'M',
+ 0x27, 0x8c, 0x8e, 0x27,
+ 'd',
+ 0x27, 0x93, 0xfa, 0x27
+};
+
+static unsigned char NLSALLOC(0411) rgbIDATE[] = {
+ '2'
+};
+
+static unsigned char NLSALLOC(0411) rgbILDATE[] = {
+ '2'
+};
+
+static unsigned char NLSALLOC(0411) rgbITIME[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0411) rgbICENTURY[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0411) rgbITLZERO[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0411) rgbIDAYLZERO[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0411) rgbIMONLZERO[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0411) rgbS1159[] = {
+ 0x8c, 0xdf, 0x91, 0x4f
+};
+
+static unsigned char NLSALLOC(0411) rgbS2359[] = {
+ 0x8c, 0xdf, 0x8c, 0xe3
+};
+
+static unsigned char NLSALLOC(0411) rgbSDAYNAME1[] = {
+ 0x8c, 0x8e, 0x97, 0x6a, 0x93, 0xfa
+};
+
+static unsigned char NLSALLOC(0411) rgbSDAYNAME2[] = {
+ 0x89, 0xce ,0x97, 0x6a, 0x93, 0xfa
+};
+
+static unsigned char NLSALLOC(0411) rgbSDAYNAME3[] = {
+ 0x90, 0x85 ,0x97, 0x6a, 0x93, 0xfa
+};
+
+static unsigned char NLSALLOC(0411) rgbSDAYNAME4[] = {
+ 0x96, 0xd8 ,0x97, 0x6a, 0x93, 0xfa
+};
+
+static unsigned char NLSALLOC(0411) rgbSDAYNAME5[] = {
+ 0x8b, 0xe0 ,0x97, 0x6a, 0x93, 0xfa
+};
+
+static unsigned char NLSALLOC(0411) rgbSDAYNAME6[] = {
+ 0x93, 0x79 ,0x97, 0x6a, 0x93, 0xfa
+};
+
+static unsigned char NLSALLOC(0411) rgbSDAYNAME7[] = {
+ 0x93, 0xfa ,0x97, 0x6a, 0x93, 0xfa
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVDAYNAME1[] = {
+ 0x8c, 0x8e
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVDAYNAME2[] = {
+ 0x89, 0xce
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVDAYNAME3[] = {
+ 0x90, 0x85
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVDAYNAME4[] = {
+ 0x96, 0xd8
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVDAYNAME5[] = {
+ 0x8b, 0xe0
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVDAYNAME6[] = {
+ 0x93, 0x79
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVDAYNAME7[] = {
+ 0x93, 0xfa
+};
+
+static unsigned char NLSALLOC(0411) rgbSMONTHNAME1[] = {
+ '1', 0x8c, 0x8e
+};
+
+static unsigned char NLSALLOC(0411) rgbSMONTHNAME2[] = {
+ '2', 0x8c, 0x8e
+};
+
+static unsigned char NLSALLOC(0411) rgbSMONTHNAME3[] = {
+ '3', 0x8c, 0x8e
+};
+
+static unsigned char NLSALLOC(0411) rgbSMONTHNAME4[] = {
+ '4', 0x8c, 0x8e
+};
+
+static unsigned char NLSALLOC(0411) rgbSMONTHNAME5[] = {
+ '5', 0x8c, 0x8e
+};
+
+static unsigned char NLSALLOC(0411) rgbSMONTHNAME6[] = {
+ '6', 0x8c, 0x8e
+};
+
+static unsigned char NLSALLOC(0411) rgbSMONTHNAME7[] = {
+ '7', 0x8c, 0x8e
+};
+
+static unsigned char NLSALLOC(0411) rgbSMONTHNAME8[] = {
+ '8', 0x8c, 0x8e
+};
+
+static unsigned char NLSALLOC(0411) rgbSMONTHNAME9[] = {
+ '9', 0x8c, 0x8e
+};
+
+static unsigned char NLSALLOC(0411) rgbSMONTHNAME10[] = {
+ '1' ,'0', 0x8c, 0x8e
+};
+
+static unsigned char NLSALLOC(0411) rgbSMONTHNAME11[] = {
+ '1' ,'1' ,0x8c, 0x8e
+};
+
+static unsigned char NLSALLOC(0411) rgbSMONTHNAME12[] = {
+ '1' ,'2' ,0x8c, 0x8e
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVMONTHNAME1[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVMONTHNAME2[] = {
+ '2'
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVMONTHNAME3[] = {
+ '3'
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVMONTHNAME4[] = {
+ '4'
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVMONTHNAME5[] = {
+ '5'
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVMONTHNAME6[] = {
+ '6'
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVMONTHNAME7[] = {
+ '7'
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVMONTHNAME8[] = {
+ '8'
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVMONTHNAME9[] = {
+ '9'
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVMONTHNAME10[] = {
+ '1','0'
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVMONTHNAME11[] = {
+ '1','1'
+};
+
+static unsigned char NLSALLOC(0411) rgbSABBREVMONTHNAME12[] = {
+ '1','2'
+};
+
+static unsigned char NLSALLOC(0411) rgbSNEGATIVESIGN[] = {
+ '-'
+};
+
+static unsigned char NLSALLOC(0411) rgbIPOSSIGNPOSN[] = {
+ '3'
+};
+
+static unsigned char NLSALLOC(0411) rgbINEGSIGNPOSN[] = {
+ '3'
+};
+
+static unsigned char NLSALLOC(0411) rgbIPOSSYMPRECEDES[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0411) rgbIPOSSEPBYSPACE[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0411) rgbINEGSYMPRECEDES[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0411) rgbINEGSEPBYSPACE[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0411) rgbSENGCOUNTRY[] = {
+ 'J', 'a', 'p', 'a', 'n'
+};
+
+static unsigned char NLSALLOC(0411) rgbSENGLANGUAGE[] = {
+ 'J', 'a', 'p', 'a', 'n', 'e', 's', 'e'
+};
+
+#if defined(VBA2) //hand-edited this locale info based on daytona [bassam]
+static BYTE NLSALLOC(0411) rgbIFIRSTDAYOFWEEK[] = { /* "6" */
+ 0x36
+};
+
+static BYTE NLSALLOC(0411) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0411) rgbIDEFAULTANSICODEPAGE[] = { /* "932" */
+ 0x39, 0x33, 0x32
+};
+
+static BYTE NLSALLOC(0411) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0411) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0411) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0411) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0411) rgbIOPTIONALCALENDAR[] = { /* "3" */
+ 0x33
+};
+#endif
+
+
+#define LCINFODAT(X) { DIM(X), (X) }
+LCINFO NLSALLOC(0411) g_rglcinfo0411[] = {
+ { 0, NULL}
+ , LCINFODAT(rgbILANGUAGE)
+ , LCINFODAT(rgbSLANGUAGE)
+ , LCINFODAT(rgbSABBREVLANGNAME)
+ , LCINFODAT(rgbSNATIVELANGNAME)
+ , LCINFODAT(rgbICOUNTRY)
+ , LCINFODAT(rgbSCOUNTRY)
+ , LCINFODAT(rgbSABBREVCTRYNAME)
+ , LCINFODAT(rgbSNATIVECTRYNAME)
+ , LCINFODAT(rgbIDEFAULTLANGUAGE)
+ , LCINFODAT(rgbIDEFAULTCOUNTRY)
+ , LCINFODAT(rgbIDEFAULTCODEPAGE)
+ , LCINFODAT(rgbSLIST)
+ , LCINFODAT(rgbIMEASURE)
+ , LCINFODAT(rgbSDECIMAL)
+ , LCINFODAT(rgbSTHOUSAND)
+ , LCINFODAT(rgbSGROUPING)
+ , LCINFODAT(rgbIDIGITS)
+ , LCINFODAT(rgbILZERO)
+ , LCINFODAT(rgbSNATIVEDIGITS)
+ , LCINFODAT(rgbSCURRENCY)
+ , LCINFODAT(rgbSINTLSYMBOL)
+ , LCINFODAT(rgbSMONDECIMALSEP)
+ , LCINFODAT(rgbSMONTHOUSANDSEP)
+ , LCINFODAT(rgbSMONGROUPING)
+ , LCINFODAT(rgbICURRDIGITS)
+ , LCINFODAT(rgbIINTLCURRDIGITS)
+ , LCINFODAT(rgbICURRENCY)
+ , LCINFODAT(rgbINEGCURR)
+ , LCINFODAT(rgbSDATE)
+ , LCINFODAT(rgbSTIME)
+ , LCINFODAT(rgbSSHORTDATE)
+ , LCINFODAT(rgbSLONGDATE)
+ , LCINFODAT(rgbIDATE)
+ , LCINFODAT(rgbILDATE)
+ , LCINFODAT(rgbITIME)
+ , LCINFODAT(rgbICENTURY)
+ , LCINFODAT(rgbITLZERO)
+ , LCINFODAT(rgbIDAYLZERO)
+ , LCINFODAT(rgbIMONLZERO)
+ , LCINFODAT(rgbS1159)
+ , LCINFODAT(rgbS2359)
+ , LCINFODAT(rgbSDAYNAME1)
+ , LCINFODAT(rgbSDAYNAME2)
+ , LCINFODAT(rgbSDAYNAME3)
+ , LCINFODAT(rgbSDAYNAME4)
+ , LCINFODAT(rgbSDAYNAME5)
+ , LCINFODAT(rgbSDAYNAME6)
+ , LCINFODAT(rgbSDAYNAME7)
+ , LCINFODAT(rgbSABBREVDAYNAME1)
+ , LCINFODAT(rgbSABBREVDAYNAME2)
+ , LCINFODAT(rgbSABBREVDAYNAME3)
+ , LCINFODAT(rgbSABBREVDAYNAME4)
+ , LCINFODAT(rgbSABBREVDAYNAME5)
+ , LCINFODAT(rgbSABBREVDAYNAME6)
+ , LCINFODAT(rgbSABBREVDAYNAME7)
+ , LCINFODAT(rgbSMONTHNAME1)
+ , LCINFODAT(rgbSMONTHNAME2)
+ , LCINFODAT(rgbSMONTHNAME3)
+ , LCINFODAT(rgbSMONTHNAME4)
+ , LCINFODAT(rgbSMONTHNAME5)
+ , LCINFODAT(rgbSMONTHNAME6)
+ , LCINFODAT(rgbSMONTHNAME7)
+ , LCINFODAT(rgbSMONTHNAME8)
+ , LCINFODAT(rgbSMONTHNAME9)
+ , LCINFODAT(rgbSMONTHNAME10)
+ , LCINFODAT(rgbSMONTHNAME11)
+ , LCINFODAT(rgbSMONTHNAME12)
+ , LCINFODAT(rgbSABBREVMONTHNAME1)
+ , LCINFODAT(rgbSABBREVMONTHNAME2)
+ , LCINFODAT(rgbSABBREVMONTHNAME3)
+ , LCINFODAT(rgbSABBREVMONTHNAME4)
+ , LCINFODAT(rgbSABBREVMONTHNAME5)
+ , LCINFODAT(rgbSABBREVMONTHNAME6)
+ , LCINFODAT(rgbSABBREVMONTHNAME7)
+ , LCINFODAT(rgbSABBREVMONTHNAME8)
+ , LCINFODAT(rgbSABBREVMONTHNAME9)
+ , LCINFODAT(rgbSABBREVMONTHNAME10)
+ , LCINFODAT(rgbSABBREVMONTHNAME11)
+ , LCINFODAT(rgbSABBREVMONTHNAME12)
+ , { 0, NULL }
+ , LCINFODAT(rgbSNEGATIVESIGN)
+ , LCINFODAT(rgbIPOSSIGNPOSN)
+ , LCINFODAT(rgbINEGSIGNPOSN)
+ , LCINFODAT(rgbIPOSSYMPRECEDES)
+ , LCINFODAT(rgbIPOSSEPBYSPACE)
+ , LCINFODAT(rgbINEGSYMPRECEDES)
+ , LCINFODAT(rgbINEGSEPBYSPACE)
+ , LCINFODAT(rgbSENGCOUNTRY)
+ , LCINFODAT(rgbSENGLANGUAGE)
+#if defined(VBA2)
+ , LCINFODAT(rgbIFIRSTDAYOFWEEK)
+ , LCINFODAT(rgbIFIRSTWEEKOFYEAR)
+ , LCINFODAT(rgbIDEFAULTANSICODEPAGE)
+ , LCINFODAT(rgbINEGNUMBER)
+ , LCINFODAT(rgbSTIMEFORMAT)
+ , LCINFODAT(rgbITIMEMARKPOSN)
+ , LCINFODAT(rgbICALENDARTYPE)
+ , LCINFODAT(rgbIOPTIONALCALENDAR)
+ , { 0, NULL }
+ , { 0, NULL }
+#endif
+
+};
+#undef LCINFODAT
+
+STRINFO_J NLSALLOC(0411) g_strinfo0411 = {
+ rgbPriHi
+ , rgbPriLo
+ , rgbSecwgt
+ , rgbSecflg
+ , rgbMasks
+ , rgbMaps
+ , rgbIgnore
+ , rgbC1JPN
+ , rgbC2JPN
+ , rgbC3JPN
+};
diff --git a/private/oleauto/src/dispatch/win16/0412.c b/private/oleauto/src/dispatch/win16/0412.c
new file mode 100644
index 000000000..c9bccdb4a
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0412.c
@@ -0,0 +1,1729 @@
+/***
+*0412.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+*
+* Korea, Korean
+*
+* LCID = 0x0412
+*
+*
+*Generated: 9/22/93 - by hand from lcid_kor.txt
+*
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+#include "nlsdbcs.h"
+
+
+#if 1
+static SORTWEIGHT NLSALLOC(0412) rgsortweight[] = {
+ { 0x0000, 0x7800, 0x00, 0x00 }
+ , { 0x0020, 0x1020, 0x00, 0x02 }
+ , { 0x0030, 0x2030, 0x00, 0x02 }
+ , { 0x003A, 0x103A, 0x00, 0x02 }
+ , { 0x0041, 0x6041, 0x00, 0x02 }
+ , { 0x005B, 0x105B, 0x00, 0x02 }
+ , { 0x0061, 0x6041, 0x02, 0x02 }
+ , { 0x007B, 0x107B, 0x00, 0x02 }
+ , { 0x007F, 0x7002, 0x00, 0x00 }
+ , { 0xA1A1, 0x1020, 0x01, 0x02 }
+ , { 0xA1A2, 0x71A2, 0x01, 0x00 }
+ , { 0xA3A1, 0x1021, 0x01, 0x02 }
+ , { 0xA3B0, 0x2030, 0x01, 0x02 }
+ , { 0xA3BA, 0x103A, 0x01, 0x02 }
+ , { 0xA3C1, 0x6041, 0x01, 0x02 }
+ , { 0xA3DB, 0x105B, 0x01, 0x02 }
+ , { 0xA3E1, 0x6041, 0x03, 0x02 }
+ , { 0xA3FB, 0x107B, 0x01, 0x02 }
+ , { 0xA4A1, 0x3002, 0x00, 0x00 }
+ , { 0xA4A2, 0x3202, 0x00, 0x00 }
+ , { 0xA4A3, 0x3502, 0x00, 0x00 }
+ , { 0xA4A5, 0x3702, 0x00, 0x00 }
+ , { 0xA4A8, 0x3902, 0x00, 0x00 }
+ , { 0xA4A9, 0x3B02, 0x00, 0x00 }
+ , { 0xA4AA, 0x3E02, 0x00, 0x00 }
+ , { 0xA4B2, 0x4002, 0x00, 0x00 }
+ , { 0xA4B3, 0x4202, 0x00, 0x00 }
+ , { 0xA4B4, 0x4402, 0x00, 0x00 }
+ , { 0xA4B6, 0x4702, 0x00, 0x00 }
+ , { 0xA4B7, 0x4902, 0x00, 0x00 }
+ , { 0xA4B8, 0x4C02, 0x00, 0x00 }
+ , { 0xA4B9, 0x4F02, 0x00, 0x00 }
+ , { 0xA4BA, 0x5002, 0x00, 0x00 }
+ , { 0xA4BB, 0x5302, 0x00, 0x00 }
+ , { 0xA4BC, 0x5502, 0x00, 0x00 }
+ , { 0xA4BD, 0x5702, 0x00, 0x00 }
+ , { 0xA4BE, 0x5902, 0x00, 0x00 }
+ , { 0xA4BF, 0x5C02, 0x00, 0x00 }
+ , { 0xA5A1, 0x73A1, 0x00, 0x00 }
+ , { 0xB0A1, 0x30A1, 0x00, 0x00 }
+ , { 0xB1EE, 0x32EE, 0x00, 0x00 }
+ , { 0xB3AA, 0x35AA, 0x00, 0x00 }
+ , { 0xB4D9, 0x37D9, 0x00, 0x00 }
+ , { 0xB5FB, 0x39FB, 0x00, 0x00 }
+ , { 0xB6F3, 0x3BF3, 0x00, 0x00 }
+ , { 0xB8B6, 0x3EB6, 0x00, 0x00 }
+ , { 0xB9D9, 0x40D9, 0x00, 0x00 }
+ , { 0xBAFC, 0x42FC, 0x00, 0x00 }
+ , { 0xBBE7, 0x44E7, 0x00, 0x00 }
+ , { 0xBDCE, 0x47CE, 0x00, 0x00 }
+ , { 0xBEC6, 0x49C6, 0x00, 0x00 }
+ , { 0xC0DA, 0x4CDA, 0x00, 0x00 }
+ , { 0xC2A5, 0x4FA5, 0x00, 0x00 }
+ , { 0xC2F7, 0x50F7, 0x00, 0x00 }
+ , { 0xC4AB, 0x53AB, 0x00, 0x00 }
+ , { 0xC5B8, 0x55B8, 0x00, 0x00 }
+ , { 0xC6C4, 0x57C4, 0x00, 0x00 }
+ , { 0xC7CF, 0x59CF, 0x00, 0x00 }
+ , { 0xCAA1, 0x30A1, 0x01, 0x01 }
+ , { 0xCABE, 0x30A2, 0x01, 0x01 }
+ , { 0xCAC9, 0x30A3, 0x01, 0x01 }
+ , { 0xCAE1, 0x30A5, 0x01, 0x01 }
+ , { 0xCAEB, 0x30A8, 0x01, 0x01 }
+ , { 0xCBA1, 0x30A9, 0x01, 0x01 }
+ , { 0xCBA7, 0x30AD, 0x01, 0x01 }
+ , { 0xCBBF, 0x30B3, 0x01, 0x01 }
+ , { 0xCBD3, 0x30B4, 0x01, 0x01 }
+ , { 0xCBD5, 0x30BB, 0x01, 0x01 }
+ , { 0xCBD9, 0x30BD, 0x01, 0x01 }
+ , { 0xCBDA, 0x30C5, 0x01, 0x01 }
+ , { 0xCBEB, 0x30C7, 0x01, 0x01 }
+ , { 0xCBF7, 0x30C9, 0x01, 0x01 }
+ , { 0xCBFB, 0x30CB, 0x01, 0x01 }
+ , { 0xCCA4, 0x30CC, 0x01, 0x01 }
+ , { 0xCCA7, 0x30D4, 0x01, 0x01 }
+ , { 0xCCAA, 0x30DD, 0x01, 0x01 }
+ , { 0xCCB1, 0x30DF, 0x01, 0x01 }
+ , { 0xCCBC, 0x30E1, 0x01, 0x01 }
+ , { 0xCCC2, 0x30E2, 0x01, 0x01 }
+ , { 0xCCC8, 0x30E6, 0x01, 0x01 }
+ , { 0xCCF5, 0x30E8, 0x01, 0x01 }
+ , { 0xCDAF, 0x30ED, 0x01, 0x01 }
+ , { 0xCDD6, 0x30EE, 0x01, 0x01 }
+ , { 0xCDDD, 0x30EF, 0x01, 0x01 }
+ , { 0xCDE7, 0x30F1, 0x01, 0x01 }
+ , { 0xCDEA, 0x30F8, 0x01, 0x01 }
+ , { 0xCDFA, 0x30F9, 0x01, 0x01 }
+ , { 0xCDFB, 0x30FA, 0x01, 0x01 }
+ , { 0xCEA9, 0x30FB, 0x01, 0x01 }
+ , { 0xCEAD, 0x30FC, 0x01, 0x01 }
+ , { 0xCEBE, 0x30FD, 0x01, 0x01 }
+ , { 0xCEC2, 0x31A4, 0x01, 0x01 }
+ , { 0xCECF, 0x31A5, 0x01, 0x01 }
+ , { 0xCED2, 0x31AB, 0x01, 0x01 }
+ , { 0xCEDB, 0x31B2, 0x01, 0x01 }
+ , { 0xCEDF, 0x31B3, 0x01, 0x01 }
+ , { 0xCEF8, 0x31B8, 0x01, 0x01 }
+ , { 0xCFD0, 0x31B9, 0x01, 0x01 }
+ , { 0xCFD6, 0x31BA, 0x01, 0x01 }
+ , { 0xCFDC, 0x31BC, 0x01, 0x01 }
+ , { 0xCFE0, 0x31C3, 0x01, 0x01 }
+ , { 0xCFE6, 0x31C7, 0x01, 0x01 }
+ , { 0xCFF0, 0x31C8, 0x01, 0x01 }
+ , { 0xCFF5, 0x31CB, 0x01, 0x01 }
+ , { 0xCFFB, 0x31CD, 0x01, 0x01 }
+ , { 0xD0A3, 0x31D4, 0x01, 0x01 }
+ , { 0xD0B2, 0x31D5, 0x01, 0x01 }
+ , { 0xD0B9, 0x31D6, 0x01, 0x01 }
+ , { 0xD0BA, 0x31D8, 0x01, 0x01 }
+ , { 0xD0C1, 0x31D9, 0x01, 0x01 }
+ , { 0xD0D0, 0x31DB, 0x01, 0x01 }
+ , { 0xD0D1, 0x31DD, 0x01, 0x01 }
+ , { 0xD0DF, 0x31DE, 0x01, 0x01 }
+ , { 0xD0E6, 0x31E0, 0x01, 0x01 }
+ , { 0xD0EA, 0x31E2, 0x01, 0x01 }
+ , { 0xD1CC, 0x31E4, 0x01, 0x01 }
+ , { 0xD1CD, 0x31E6, 0x01, 0x01 }
+ , { 0xD1D1, 0x31E8, 0x01, 0x01 }
+ , { 0xD1D2, 0x34A3, 0x01, 0x01 }
+ , { 0xD1D3, 0x35AA, 0x01, 0x01 }
+ , { 0xD1E2, 0x35AB, 0x01, 0x01 }
+ , { 0xD1EA, 0x35AD, 0x01, 0x01 }
+ , { 0xD1F3, 0x35AF, 0x01, 0x01 }
+ , { 0xD1F5, 0x35B2, 0x01, 0x01 }
+ , { 0xD1FE, 0x35B3, 0x01, 0x01 }
+ , { 0xD2A5, 0x35B6, 0x01, 0x01 }
+ , { 0xD2AC, 0x35BB, 0x01, 0x01 }
+ , { 0xD2B2, 0x35C3, 0x01, 0x01 }
+ , { 0xD2B3, 0x35E0, 0x01, 0x01 }
+ , { 0xD2B4, 0x35E2, 0x01, 0x01 }
+ , { 0xD2B7, 0x35E4, 0x01, 0x01 }
+ , { 0xD2BB, 0x35E7, 0x01, 0x01 }
+ , { 0xD2BD, 0x35EB, 0x01, 0x01 }
+ , { 0xD2CF, 0x35EC, 0x01, 0x01 }
+ , { 0xD2D5, 0x35ED, 0x01, 0x01 }
+ , { 0xD2D6, 0x35F3, 0x01, 0x01 }
+ , { 0xD2DD, 0x35FA, 0x01, 0x01 }
+ , { 0xD2E3, 0x36A2, 0x01, 0x01 }
+ , { 0xD2E4, 0x36A9, 0x01, 0x01 }
+ , { 0xD2EC, 0x36AB, 0x01, 0x01 }
+ , { 0xD2ED, 0x36AD, 0x01, 0x01 }
+ , { 0xD2EE, 0x36BA, 0x01, 0x01 }
+ , { 0xD2F0, 0x36C1, 0x01, 0x01 }
+ , { 0xD2F2, 0x36C6, 0x01, 0x01 }
+ , { 0xD2F3, 0x36C9, 0x01, 0x01 }
+ , { 0xD2F9, 0x36CF, 0x01, 0x01 }
+ , { 0xD2FB, 0x36D0, 0x01, 0x01 }
+ , { 0xD2FD, 0x37D9, 0x01, 0x01 }
+ , { 0xD3A1, 0x37DC, 0x01, 0x01 }
+ , { 0xD3B5, 0x37DE, 0x01, 0x01 }
+ , { 0xD3BA, 0x37E3, 0x01, 0x01 }
+ , { 0xD3CB, 0x37E4, 0x01, 0x01 }
+ , { 0xD3D0, 0x37E7, 0x01, 0x01 }
+ , { 0xD3DB, 0x37EB, 0x01, 0x01 }
+ , { 0xD3EB, 0x37EC, 0x01, 0x01 }
+ , { 0xD3EC, 0x37F6, 0x01, 0x01 }
+ , { 0xD3EE, 0x38B5, 0x01, 0x01 }
+ , { 0xD4B8, 0x38B6, 0x01, 0x01 }
+ , { 0xD4C2, 0x38B7, 0x01, 0x01 }
+ , { 0xD4CC, 0x38B9, 0x01, 0x01 }
+ , { 0xD4CE, 0x38BF, 0x01, 0x01 }
+ , { 0xD4DF, 0x38CE, 0x01, 0x01 }
+ , { 0xD4EA, 0x38D0, 0x01, 0x01 }
+ , { 0xD4F0, 0x38E6, 0x01, 0x01 }
+ , { 0xD4F1, 0x38EE, 0x01, 0x01 }
+ , { 0xD4FA, 0x3BF3, 0x01, 0x01 }
+ , { 0xD5A5, 0x3BF4, 0x01, 0x01 }
+ , { 0xD5AE, 0x3BF5, 0x01, 0x01 }
+ , { 0xD5B7, 0x3BF6, 0x01, 0x01 }
+ , { 0xD5B9, 0x3BF7, 0x01, 0x01 }
+ , { 0xD5C3, 0x3BF8, 0x01, 0x01 }
+ , { 0xD5C6, 0x3BFB, 0x01, 0x01 }
+ , { 0xD5CE, 0x3CA1, 0x01, 0x01 }
+ , { 0xD5D2, 0x3CA9, 0x01, 0x01 }
+ , { 0xD5D3, 0x3CAB, 0x01, 0x01 }
+ , { 0xD5D5, 0x3CAE, 0x01, 0x01 }
+ , { 0xD5E2, 0x3CC1, 0x01, 0x01 }
+ , { 0xD5F4, 0x3CC2, 0x01, 0x01 }
+ , { 0xD5FB, 0x3CC3, 0x01, 0x01 }
+ , { 0xD6A9, 0x3CC4, 0x01, 0x01 }
+ , { 0xD6AF, 0x3CC5, 0x01, 0x01 }
+ , { 0xD6B4, 0x3CC6, 0x01, 0x01 }
+ , { 0xD6B5, 0x3CC9, 0x01, 0x01 }
+ , { 0xD6C7, 0x3CCA, 0x01, 0x01 }
+ , { 0xD6CC, 0x3CCE, 0x01, 0x01 }
+ , { 0xD6DE, 0x3CCF, 0x01, 0x01 }
+ , { 0xD6E5, 0x3CD0, 0x01, 0x01 }
+ , { 0xD6E6, 0x3CD5, 0x01, 0x01 }
+ , { 0xD6ED, 0x3CDA, 0x01, 0x01 }
+ , { 0xD6F5, 0x3CE1, 0x01, 0x01 }
+ , { 0xD7A3, 0x3CE6, 0x01, 0x01 }
+ , { 0xD7A4, 0x3CE7, 0x01, 0x01 }
+ , { 0xD7B1, 0x3CF9, 0x01, 0x01 }
+ , { 0xD7BF, 0x3CFA, 0x01, 0x01 }
+ , { 0xD7C2, 0x3CFB, 0x01, 0x01 }
+ , { 0xD7C8, 0x3CFC, 0x01, 0x01 }
+ , { 0xD7CC, 0x3DA2, 0x01, 0x01 }
+ , { 0xD7CD, 0x3DA4, 0x01, 0x01 }
+ , { 0xD7CF, 0x3DA7, 0x01, 0x01 }
+ , { 0xD7D0, 0x3DAA, 0x01, 0x01 }
+ , { 0xD7D6, 0x3DAE, 0x01, 0x01 }
+ , { 0xD7F0, 0x3DB0, 0x01, 0x01 }
+ , { 0xD7F9, 0x3DB2, 0x01, 0x01 }
+ , { 0xD7FE, 0x3DB3, 0x01, 0x01 }
+ , { 0xD8A4, 0x3EB6, 0x01, 0x01 }
+ , { 0xD8AC, 0x3EB7, 0x01, 0x01 }
+ , { 0xD8B2, 0x3EB8, 0x01, 0x01 }
+ , { 0xD8C5, 0x3EBB, 0x01, 0x01 }
+ , { 0xD8CC, 0x3EC1, 0x01, 0x01 }
+ , { 0xD8D8, 0x3EC5, 0x01, 0x01 }
+ , { 0xD8E6, 0x3EC6, 0x01, 0x01 }
+ , { 0xD8EB, 0x3ECD, 0x01, 0x01 }
+ , { 0xD8F1, 0x3EE8, 0x01, 0x01 }
+ , { 0xD8F3, 0x3EE9, 0x01, 0x01 }
+ , { 0xD8FE, 0x3EEA, 0x01, 0x01 }
+ , { 0xD9A2, 0x3EED, 0x01, 0x01 }
+ , { 0xD9B1, 0x3EEF, 0x01, 0x01 }
+ , { 0xD9B2, 0x3EF0, 0x01, 0x01 }
+ , { 0xD9CA, 0x3EF1, 0x01, 0x01 }
+ , { 0xD9D1, 0x3EF4, 0x01, 0x01 }
+ , { 0xD9D3, 0x3EF9, 0x01, 0x01 }
+ , { 0xD9D6, 0x3FA6, 0x01, 0x01 }
+ , { 0xD9E2, 0x3FAB, 0x01, 0x01 }
+ , { 0xD9F8, 0x3FAC, 0x01, 0x01 }
+ , { 0xD9FA, 0x3FAE, 0x01, 0x01 }
+ , { 0xDAA8, 0x3FB0, 0x01, 0x01 }
+ , { 0xDAAB, 0x3FCC, 0x01, 0x01 }
+ , { 0xDABE, 0x3FCE, 0x01, 0x01 }
+ , { 0xDACB, 0x3FD0, 0x01, 0x01 }
+ , { 0xDACE, 0x40DA, 0x01, 0x01 }
+ , { 0xDAE1, 0x40DD, 0x01, 0x01 }
+ , { 0xDAFA, 0x40DF, 0x01, 0x01 }
+ , { 0xDBA7, 0x40E6, 0x01, 0x01 }
+ , { 0xDBC3, 0x40E8, 0x01, 0x01 }
+ , { 0xDBD7, 0x40E9, 0x01, 0x01 }
+ , { 0xDBDF, 0x40F8, 0x01, 0x01 }
+ , { 0xDBE9, 0x40FA, 0x01, 0x01 }
+ , { 0xDBED, 0x40FC, 0x01, 0x01 }
+ , { 0xDBF6, 0x40FD, 0x01, 0x01 }
+ , { 0xDBF8, 0x41AE, 0x01, 0x01 }
+ , { 0xDCA5, 0x41AF, 0x01, 0x01 }
+ , { 0xDCAC, 0x41B0, 0x01, 0x01 }
+ , { 0xDCB0, 0x41B4, 0x01, 0x01 }
+ , { 0xDCC1, 0x41B8, 0x01, 0x01 }
+ , { 0xDCD1, 0x41B9, 0x01, 0x01 }
+ , { 0xDCE2, 0x41BB, 0x01, 0x01 }
+ , { 0xDCE3, 0x41BC, 0x01, 0x01 }
+ , { 0xDCE4, 0x41C0, 0x01, 0x01 }
+ , { 0xDCF4, 0x41CE, 0x01, 0x01 }
+ , { 0xDDC1, 0x41CF, 0x01, 0x01 }
+ , { 0xDDC2, 0x41D0, 0x01, 0x01 }
+ , { 0xDDD5, 0x41D2, 0x01, 0x01 }
+ , { 0xDDDA, 0x41D8, 0x01, 0x01 }
+ , { 0xDDE0, 0x41F1, 0x01, 0x01 }
+ , { 0xDEAD, 0x41F3, 0x01, 0x01 }
+ , { 0xDEBB, 0x41F9, 0x01, 0x01 }
+ , { 0xDEBF, 0x44E7, 0x01, 0x01 }
+ , { 0xDEFB, 0x44E8, 0x01, 0x01 }
+ , { 0xDFA1, 0x44EA, 0x01, 0x01 }
+ , { 0xDFAD, 0x44EC, 0x01, 0x01 }
+ , { 0xDFB2, 0x44EF, 0x01, 0x01 }
+ , { 0xDFBA, 0x44F0, 0x01, 0x01 }
+ , { 0xDFBE, 0x44F3, 0x01, 0x01 }
+ , { 0xDFDD, 0x44F5, 0x01, 0x01 }
+ , { 0xDFE0, 0x44F6, 0x01, 0x01 }
+ , { 0xDFE5, 0x44FD, 0x01, 0x01 }
+ , { 0xDFEA, 0x45AD, 0x01, 0x01 }
+ , { 0xE0AA, 0x45AE, 0x01, 0x01 }
+ , { 0xE0B9, 0x45B1, 0x01, 0x01 }
+ , { 0xE0D9, 0x45B3, 0x01, 0x01 }
+ , { 0xE0E6, 0x45B6, 0x01, 0x01 }
+ , { 0xE0EE, 0x45B7, 0x01, 0x01 }
+ , { 0xE0F2, 0x45BA, 0x01, 0x01 }
+ , { 0xE1A6, 0x45BC, 0x01, 0x01 }
+ , { 0xE1AF, 0x45D2, 0x01, 0x01 }
+ , { 0xE1D4, 0x45D3, 0x01, 0x01 }
+ , { 0xE1DD, 0x45D5, 0x01, 0x01 }
+ , { 0xE1E3, 0x45D6, 0x01, 0x01 }
+ , { 0xE1E4, 0x45DB, 0x01, 0x01 }
+ , { 0xE1EC, 0x45E2, 0x01, 0x01 }
+ , { 0xE1F1, 0x45E8, 0x01, 0x01 }
+ , { 0xE1F3, 0x45F6, 0x01, 0x01 }
+ , { 0xE2D2, 0x45F7, 0x01, 0x01 }
+ , { 0xE2DE, 0x45F8, 0x01, 0x01 }
+ , { 0xE2F9, 0x45FA, 0x01, 0x01 }
+ , { 0xE2FD, 0x45FE, 0x01, 0x01 }
+ , { 0xE3A2, 0x46BD, 0x01, 0x01 }
+ , { 0xE3A5, 0x46C0, 0x01, 0x01 }
+ , { 0xE3AA, 0x46C2, 0x01, 0x01 }
+ , { 0xE3B4, 0x46C3, 0x01, 0x01 }
+ , { 0xE3D0, 0x46C4, 0x01, 0x01 }
+ , { 0xE3DF, 0x46C5, 0x01, 0x01 }
+ , { 0xE3F7, 0x46C7, 0x01, 0x01 }
+ , { 0xE3FB, 0x46C9, 0x01, 0x01 }
+ , { 0xE4A7, 0x46CA, 0x01, 0x01 }
+ , { 0xE4AA, 0x47D6, 0x01, 0x01 }
+ , { 0xE4AB, 0x48BE, 0x01, 0x01 }
+ , { 0xE4AC, 0x49C6, 0x01, 0x01 }
+ , { 0xE4BE, 0x49C7, 0x01, 0x01 }
+ , { 0xE4CC, 0x49C8, 0x01, 0x01 }
+ , { 0xE4D6, 0x49CB, 0x01, 0x01 }
+ , { 0xE4DA, 0x49CF, 0x01, 0x01 }
+ , { 0xE4E2, 0x49D0, 0x01, 0x01 }
+ , { 0xE4E6, 0x49D3, 0x01, 0x01 }
+ , { 0xE4ED, 0x49D6, 0x01, 0x01 }
+ , { 0xE4F8, 0x49D7, 0x01, 0x01 }
+ , { 0xE5A1, 0x49DE, 0x01, 0x01 }
+ , { 0xE5A5, 0x49DF, 0x01, 0x01 }
+ , { 0xE5B0, 0x49E0, 0x01, 0x01 }
+ , { 0xE5B9, 0x49E7, 0x01, 0x01 }
+ , { 0xE5D8, 0x49EE, 0x01, 0x01 }
+ , { 0xE5E2, 0x49EF, 0x01, 0x01 }
+ , { 0xE5E7, 0x49F0, 0x01, 0x01 }
+ , { 0xE5ED, 0x49F3, 0x01, 0x01 }
+ , { 0xE5EF, 0x49F6, 0x01, 0x01 }
+ , { 0xE5F5, 0x49F7, 0x01, 0x01 }
+ , { 0xE5F7, 0x4AA3, 0x01, 0x01 }
+ , { 0xE5F8, 0x4AA9, 0x01, 0x01 }
+ , { 0xE6B2, 0x4AAA, 0x01, 0x01 }
+ , { 0xE6BF, 0x4AAC, 0x01, 0x01 }
+ , { 0xE6EA, 0x4AAD, 0x01, 0x01 }
+ , { 0xE6F4, 0x4AB0, 0x01, 0x01 }
+ , { 0xE7A5, 0x4AB1, 0x01, 0x01 }
+ , { 0xE7A9, 0x4AB5, 0x01, 0x01 }
+ , { 0xE7D1, 0x4AB9, 0x01, 0x01 }
+ , { 0xE7E9, 0x4AC0, 0x01, 0x01 }
+ , { 0xE8A9, 0x4AC1, 0x01, 0x01 }
+ , { 0xE8AE, 0x4AC2, 0x01, 0x01 }
+ , { 0xE8B4, 0x4AC3, 0x01, 0x01 }
+ , { 0xE8B5, 0x4ACB, 0x01, 0x01 }
+ , { 0xE8BE, 0x4ACD, 0x01, 0x01 }
+ , { 0xE8C6, 0x4ACF, 0x01, 0x01 }
+ , { 0xE8D8, 0x4AD0, 0x01, 0x01 }
+ , { 0xE8D9, 0x4AD5, 0x01, 0x01 }
+ , { 0xE8DE, 0x4AD6, 0x01, 0x01 }
+ , { 0xE8E2, 0x4ADC, 0x01, 0x01 }
+ , { 0xE8E7, 0x4AE4, 0x01, 0x01 }
+ , { 0xE9AF, 0x4AE5, 0x01, 0x01 }
+ , { 0xE9B5, 0x4AEB, 0x01, 0x01 }
+ , { 0xE9CD, 0x4AEC, 0x01, 0x01 }
+ , { 0xE9ED, 0x4AED, 0x01, 0x01 }
+ , { 0xE9F6, 0x4AEE, 0x01, 0x01 }
+ , { 0xEAA5, 0x4AEF, 0x01, 0x01 }
+ , { 0xEAA8, 0x4AF5, 0x01, 0x01 }
+ , { 0xEAAA, 0x4AF8, 0x01, 0x01 }
+ , { 0xEAC5, 0x4AF9, 0x01, 0x01 }
+ , { 0xEAC8, 0x4BA7, 0x01, 0x01 }
+ , { 0xEAE1, 0x4BAF, 0x01, 0x01 }
+ , { 0xEBBB, 0x4BB0, 0x01, 0x01 }
+ , { 0xEBC2, 0x4BB1, 0x01, 0x01 }
+ , { 0xEBCF, 0x4BB2, 0x01, 0x01 }
+ , { 0xEBD4, 0x4BB6, 0x01, 0x01 }
+ , { 0xEBD9, 0x4BBA, 0x01, 0x01 }
+ , { 0xEBE0, 0x4BBB, 0x01, 0x01 }
+ , { 0xEBE1, 0x4BBD, 0x01, 0x01 }
+ , { 0xEBE7, 0x4BBE, 0x01, 0x01 }
+ , { 0xEBEA, 0x4BC0, 0x01, 0x01 }
+ , { 0xEBEE, 0x4BC7, 0x01, 0x01 }
+ , { 0xECA3, 0x4BCC, 0x01, 0x01 }
+ , { 0xECC9, 0x4BCD, 0x01, 0x01 }
+ , { 0xECD1, 0x4BCE, 0x01, 0x01 }
+ , { 0xECE9, 0x4BCF, 0x01, 0x01 }
+ , { 0xECF2, 0x4BD3, 0x01, 0x01 }
+ , { 0xECFD, 0x4BD4, 0x01, 0x01 }
+ , { 0xEDA4, 0x4BD7, 0x01, 0x01 }
+ , { 0xEDA8, 0x4CDA, 0x01, 0x01 }
+ , { 0xEDC2, 0x4CDB, 0x01, 0x01 }
+ , { 0xEDCF, 0x4CDC, 0x01, 0x01 }
+ , { 0xEDD4, 0x4CE1, 0x01, 0x01 }
+ , { 0xEDDA, 0x4CE2, 0x01, 0x01 }
+ , { 0xEDDB, 0x4CE5, 0x01, 0x01 }
+ , { 0xEEA2, 0x4CE7, 0x01, 0x01 }
+ , { 0xEEB3, 0x4CEF, 0x01, 0x01 }
+ , { 0xEEB7, 0x4CFA, 0x01, 0x01 }
+ , { 0xEED3, 0x4CFB, 0x01, 0x01 }
+ , { 0xEEEC, 0x4CFC, 0x01, 0x01 }
+ , { 0xEFB7, 0x4CFD, 0x01, 0x01 }
+ , { 0xEFBF, 0x4DA1, 0x01, 0x01 }
+ , { 0xEFC8, 0x4DA2, 0x01, 0x01 }
+ , { 0xEFCB, 0x4DA4, 0x01, 0x01 }
+ , { 0xF0A4, 0x4DA6, 0x01, 0x01 }
+ , { 0xF0BB, 0x4DB6, 0x01, 0x01 }
+ , { 0xF0E9, 0x4DB7, 0x01, 0x01 }
+ , { 0xF0ED, 0x4DB8, 0x01, 0x01 }
+ , { 0xF0EF, 0x4DB9, 0x01, 0x01 }
+ , { 0xF0F2, 0x4DBE, 0x01, 0x01 }
+ , { 0xF1A5, 0x4DC2, 0x01, 0x01 }
+ , { 0xF1AA, 0x4DCB, 0x01, 0x01 }
+ , { 0xF1AB, 0x4DD6, 0x01, 0x01 }
+ , { 0xF1D3, 0x4DD7, 0x01, 0x01 }
+ , { 0xF1D5, 0x4DD8, 0x01, 0x01 }
+ , { 0xF1E8, 0x4DD9, 0x01, 0x01 }
+ , { 0xF1E9, 0x4DDF, 0x01, 0x01 }
+ , { 0xF1ED, 0x4DEF, 0x01, 0x01 }
+ , { 0xF1EE, 0x4DF1, 0x01, 0x01 }
+ , { 0xF1EF, 0x4DF3, 0x01, 0x01 }
+ , { 0xF1F2, 0x4DF5, 0x01, 0x01 }
+ , { 0xF1FD, 0x4DF6, 0x01, 0x01 }
+ , { 0xF2C1, 0x4DF7, 0x01, 0x01 }
+ , { 0xF2C6, 0x4DF8, 0x01, 0x01 }
+ , { 0xF2E9, 0x4DFA, 0x01, 0x01 }
+ , { 0xF2F8, 0x4DFC, 0x01, 0x01 }
+ , { 0xF2FA, 0x4DFD, 0x01, 0x01 }
+ , { 0xF3A3, 0x4EA1, 0x01, 0x01 }
+ , { 0xF3A6, 0x50F7, 0x01, 0x01 }
+ , { 0xF3B5, 0x50F8, 0x01, 0x01 }
+ , { 0xF3BC, 0x50F9, 0x01, 0x01 }
+ , { 0xF3CB, 0x50FB, 0x01, 0x01 }
+ , { 0xF3D0, 0x50FC, 0x01, 0x01 }
+ , { 0xF3DA, 0x51A2, 0x01, 0x01 }
+ , { 0xF3F0, 0x51A4, 0x01, 0x01 }
+ , { 0xF3FC, 0x51A5, 0x01, 0x01 }
+ , { 0xF4A2, 0x51B3, 0x01, 0x01 }
+ , { 0xF4A6, 0x51B4, 0x01, 0x01 }
+ , { 0xF4B5, 0x51B5, 0x01, 0x01 }
+ , { 0xF4C8, 0x51B6, 0x01, 0x01 }
+ , { 0xF4D2, 0x51B7, 0x01, 0x01 }
+ , { 0xF4DC, 0x51B8, 0x01, 0x01 }
+ , { 0xF4E6, 0x51BB, 0x01, 0x01 }
+ , { 0xF4EE, 0x51BC, 0x01, 0x01 }
+ , { 0xF4F8, 0x51CA, 0x01, 0x01 }
+ , { 0xF5B5, 0x51CB, 0x01, 0x01 }
+ , { 0xF5BB, 0x51CC, 0x01, 0x01 }
+ , { 0xF5BF, 0x51D1, 0x01, 0x01 }
+ , { 0xF5C9, 0x51D4, 0x01, 0x01 }
+ , { 0xF5CA, 0x51D6, 0x01, 0x01 }
+ , { 0xF5CD, 0x51DF, 0x01, 0x01 }
+ , { 0xF5E4, 0x51E0, 0x01, 0x01 }
+ , { 0xF5F0, 0x51E1, 0x01, 0x01 }
+ , { 0xF5F3, 0x51E2, 0x01, 0x01 }
+ , { 0xF5F6, 0x51E6, 0x01, 0x01 }
+ , { 0xF5FC, 0x51E9, 0x01, 0x01 }
+ , { 0xF6A2, 0x51EB, 0x01, 0x01 }
+ , { 0xF6B0, 0x51F8, 0x01, 0x01 }
+ , { 0xF6B5, 0x51FE, 0x01, 0x01 }
+ , { 0xF6B6, 0x52A1, 0x01, 0x01 }
+ , { 0xF6CE, 0x52A2, 0x01, 0x01 }
+ , { 0xF6D1, 0x52A3, 0x01, 0x01 }
+ , { 0xF6D2, 0x52A5, 0x01, 0x01 }
+ , { 0xF6D5, 0x52A7, 0x01, 0x01 }
+ , { 0xF6DE, 0x52A8, 0x01, 0x01 }
+ , { 0xF6DF, 0x52AA, 0x01, 0x01 }
+ , { 0xF6E1, 0x53E8, 0x01, 0x01 }
+ , { 0xF6E2, 0x55B8, 0x01, 0x01 }
+ , { 0xF6F0, 0x55B9, 0x01, 0x01 }
+ , { 0xF7A2, 0x55BA, 0x01, 0x01 }
+ , { 0xF7AC, 0x55BB, 0x01, 0x01 }
+ , { 0xF7AE, 0x55BD, 0x01, 0x01 }
+ , { 0xF7B2, 0x55BE, 0x01, 0x01 }
+ , { 0xF7B5, 0x55C1, 0x01, 0x01 }
+ , { 0xF7BA, 0x55C2, 0x01, 0x01 }
+ , { 0xF7C8, 0x55C3, 0x01, 0x01 }
+ , { 0xF7CB, 0x55CA, 0x01, 0x01 }
+ , { 0xF7CC, 0x55CD, 0x01, 0x01 }
+ , { 0xF7CD, 0x55E4, 0x01, 0x01 }
+ , { 0xF7D1, 0x55EB, 0x01, 0x01 }
+ , { 0xF7D8, 0x55F0, 0x01, 0x01 }
+ , { 0xF7DE, 0x55F5, 0x01, 0x01 }
+ , { 0xF7E4, 0x56AF, 0x01, 0x01 }
+ , { 0xF7E6, 0x56B4, 0x01, 0x01 }
+ , { 0xF7E7, 0x57C4, 0x01, 0x01 }
+ , { 0xF7F7, 0x57C7, 0x01, 0x01 }
+ , { 0xF8A2, 0x57C8, 0x01, 0x01 }
+ , { 0xF8A5, 0x57D0, 0x01, 0x01 }
+ , { 0xF8B0, 0x57D8, 0x01, 0x01 }
+ , { 0xF8B4, 0x57DA, 0x01, 0x01 }
+ , { 0xF8B5, 0x57ED, 0x01, 0x01 }
+ , { 0xF8BF, 0x57EF, 0x01, 0x01 }
+ , { 0xF8C0, 0x57F2, 0x01, 0x01 }
+ , { 0xF8C5, 0x57F3, 0x01, 0x01 }
+ , { 0xF8CF, 0x57F7, 0x01, 0x01 }
+ , { 0xF8EB, 0x57F8, 0x01, 0x01 }
+ , { 0xF8F1, 0x58A5, 0x01, 0x01 }
+ , { 0xF9A1, 0x58B0, 0x01, 0x01 }
+ , { 0xF9A3, 0x58B3, 0x01, 0x01 }
+ , { 0xF9A8, 0x58C7, 0x01, 0x01 }
+ , { 0xF9AF, 0x58CA, 0x01, 0x01 }
+ , { 0xF9B9, 0x58CC, 0x01, 0x01 }
+ , { 0xF9BB, 0x59CF, 0x01, 0x01 }
+ , { 0xF9C9, 0x59D0, 0x01, 0x01 }
+ , { 0xF9CE, 0x59D1, 0x01, 0x01 }
+ , { 0xF9DC, 0x59D2, 0x01, 0x01 }
+ , { 0xF9DE, 0x59D4, 0x01, 0x01 }
+ , { 0xF9EA, 0x59D5, 0x01, 0x01 }
+ , { 0xF9F1, 0x59D7, 0x01, 0x01 }
+ , { 0xFAA4, 0x59D8, 0x01, 0x01 }
+ , { 0xFAB6, 0x59D9, 0x01, 0x01 }
+ , { 0xFAB8, 0x59E0, 0x01, 0x01 }
+ , { 0xFABD, 0x59E2, 0x01, 0x01 }
+ , { 0xFAC6, 0x59E3, 0x01, 0x01 }
+ , { 0xFACA, 0x59E5, 0x01, 0x01 }
+ , { 0xFACE, 0x59E6, 0x01, 0x01 }
+ , { 0xFACF, 0x59E8, 0x01, 0x01 }
+ , { 0xFAD1, 0x59F5, 0x01, 0x01 }
+ , { 0xFAD5, 0x59F6, 0x01, 0x01 }
+ , { 0xFAEA, 0x59F7, 0x01, 0x01 }
+ , { 0xFAEE, 0x59F8, 0x01, 0x01 }
+ , { 0xFAEF, 0x59F9, 0x01, 0x01 }
+ , { 0xFAFB, 0x59FC, 0x01, 0x01 }
+ , { 0xFBB1, 0x59FD, 0x01, 0x01 }
+ , { 0xFBBA, 0x5AA3, 0x01, 0x01 }
+ , { 0xFBE3, 0x5AA4, 0x01, 0x01 }
+ , { 0xFBE6, 0x5AA5, 0x01, 0x01 }
+ , { 0xFBEC, 0x5AA6, 0x01, 0x01 }
+ , { 0xFBEF, 0x5AAB, 0x01, 0x01 }
+ , { 0xFBF9, 0x5AAD, 0x01, 0x01 }
+ , { 0xFCA9, 0x5AAE, 0x01, 0x01 }
+ , { 0xFCAF, 0x5AAF, 0x01, 0x01 }
+ , { 0xFCC0, 0x5AB0, 0x01, 0x01 }
+ , { 0xFCC5, 0x5AB2, 0x01, 0x01 }
+ , { 0xFCDD, 0x5AB8, 0x01, 0x01 }
+ , { 0xFCF1, 0x5AB9, 0x01, 0x01 }
+ , { 0xFCF3, 0x5ABE, 0x01, 0x01 }
+ , { 0xFCF6, 0x5ABF, 0x01, 0x01 }
+ , { 0xFDA5, 0x5AC4, 0x01, 0x01 }
+ , { 0xFDB2, 0x5AC6, 0x01, 0x01 }
+ , { 0xFDBC, 0x5ACB, 0x01, 0x01 }
+ , { 0xFDBD, 0x5ACD, 0x01, 0x01 }
+ , { 0xFDC1, 0x5AD1, 0x01, 0x01 }
+ , { 0xFDC4, 0x5AD6, 0x01, 0x01 }
+ , { 0xFDCC, 0x5ADE, 0x01, 0x01 }
+ , { 0xFDD1, 0x5AE1, 0x01, 0x01 }
+ , { 0xFDD4, 0x5AE4, 0x01, 0x01 }
+ , { 0xFDD9, 0x5AE6, 0x01, 0x01 }
+ , { 0xFDDA, 0x5AE7, 0x01, 0x01 }
+ , { 0xFDDE, 0x5AEA, 0x01, 0x01 }
+ , { 0xFDE2, 0x5AEC, 0x01, 0x01 }
+ , { 0xFDE5, 0x5AED, 0x01, 0x01 }
+ , { 0xFDE9, 0x5AEF, 0x01, 0x01 }
+ , { 0xFDEA, 0x5AF1, 0x01, 0x01 }
+ , { 0xFDFE, 0x5AFA, 0x01, 0x01 }
+ , { 0xFDFF, 0xFDFF, 0x00, 0x00 }
+};
+static MAPTABLE NLSALLOC(0412) rgmaptable[] = {
+ { 0x1020, 0x0001, 0x0020, 0xA1A1, 0x0020, 0xA1A1 }
+ , { 0x1021, 0x005F, 0x0021, 0xA3A1, 0x0021, 0xA3A1 }
+ , { 0x2030, 0x000A, 0x0030, 0xA3B0, 0x0030, 0xA3B0 }
+ , { 0x6041, 0x001A, 0x0041, 0xA3C1, 0x0061, 0xA3E1 }
+};
+static TYPETABLE NLSALLOC(0412) rgtypetable[] = {
+ { 0x0000, 0x0020, 0x00, 0x00 }
+ , { 0x0009, 0x0068, 0x09, 0x00 }
+ , { 0x000A, 0x0028, 0x00, 0x00 }
+ , { 0x000E, 0x0020, 0x00, 0x00 }
+ , { 0x0020, 0x0048, 0x0A, 0x00 }
+ , { 0x0021, 0x0010, 0x0B, 0x08 }
+ , { 0x0024, 0x0010, 0x05, 0x08 }
+ , { 0x0026, 0x0010, 0x01, 0x08 }
+ , { 0x002B, 0x0010, 0x05, 0x08 }
+ , { 0x002C, 0x0010, 0x07, 0x08 }
+ , { 0x002D, 0x0010, 0x05, 0x08 }
+ , { 0x002E, 0x0010, 0x03, 0x08 }
+ , { 0x0030, 0x0084, 0x03, 0x00 }
+ , { 0x003A, 0x0010, 0x07, 0x08 }
+ , { 0x003B, 0x0010, 0x0B, 0x08 }
+ , { 0x0040, 0x0010, 0x01, 0x08 }
+ , { 0x0041, 0x0181, 0x01, 0x00 }
+ , { 0x0047, 0x0101, 0x01, 0x00 }
+ , { 0x005B, 0x0010, 0x0B, 0x08 }
+ , { 0x0061, 0x0182, 0x01, 0x00 }
+ , { 0x0067, 0x0102, 0x01, 0x00 }
+ , { 0x007B, 0x0010, 0x0B, 0x08 }
+ , { 0x007F, 0x0020, 0x00, 0x00 }
+ , { 0x0080, 0x0000, 0x0B, 0x08 }
+ , { 0xA1A1, 0x0048, 0x0A, 0x00 }
+ , { 0xA1A2, 0x0000, 0x0B, 0x08 }
+ , { 0xA3A1, 0x0010, 0x0B, 0x08 }
+ , { 0xA3A4, 0x0010, 0x05, 0x08 }
+ , { 0xA3A6, 0x0010, 0x01, 0x08 }
+ , { 0xA3AB, 0x0010, 0x05, 0x08 }
+ , { 0xA3AC, 0x0010, 0x07, 0x08 }
+ , { 0xA3AD, 0x0010, 0x05, 0x08 }
+ , { 0xA3AE, 0x0010, 0x03, 0x08 }
+ , { 0xA3B0, 0x0084, 0x03, 0x00 }
+ , { 0xA3BA, 0x0010, 0x07, 0x08 }
+ , { 0xA3BB, 0x0010, 0x0B, 0x08 }
+ , { 0xA3C0, 0x0010, 0x01, 0x08 }
+ , { 0xA3C1, 0x0181, 0x01, 0x00 }
+ , { 0xA3C7, 0x0101, 0x01, 0x00 }
+ , { 0xA3DB, 0x0010, 0x0B, 0x08 }
+ , { 0xA3E1, 0x0182, 0x01, 0x00 }
+ , { 0xA3E7, 0x0102, 0x01, 0x00 }
+ , { 0xA3FB, 0x0010, 0x0B, 0x08 }
+ , { 0xA4A1, 0x0100, 0x01, 0x00 }
+ , { 0xA5A1, 0x0000, 0x0B, 0x08 }
+ , { 0xB0A1, 0x0100, 0x01, 0x00 }
+};
+
+#else
+static unsigned char NLSALLOC(0412) rgsortweight[] = {
+ 0x00, 0x00, 0x00, 0x78, 0x00, 0x00
+ , 0x20, 0x00, 0x20, 0x10, 0x00, 0x02
+ , 0x30, 0x00, 0x30, 0x20, 0x00, 0x02
+ , 0x3A, 0x00, 0x3A, 0x10, 0x00, 0x02
+ , 0x41, 0x00, 0x41, 0x60, 0x00, 0x02
+ , 0x5B, 0x00, 0x5B, 0x10, 0x00, 0x02
+ , 0x61, 0x00, 0x41, 0x60, 0x02, 0x02
+ , 0x7B, 0x00, 0x7B, 0x10, 0x00, 0x02
+ , 0x7F, 0x00, 0x02, 0x70, 0x00, 0x00
+ , 0xA1, 0xA1, 0x20, 0x10, 0x01, 0x02
+ , 0xA2, 0xA1, 0xA2, 0x72, 0x01, 0x00
+ , 0xA1, 0xA3, 0x21, 0x10, 0x01, 0x02
+ , 0xB0, 0xA3, 0x30, 0x20, 0x01, 0x02
+ , 0xBA, 0xA3, 0x3A, 0x10, 0x01, 0x02
+ , 0xC1, 0xA3, 0x41, 0x60, 0x01, 0x02
+ , 0xDB, 0xA3, 0x5B, 0x10, 0x01, 0x02
+ , 0xE1, 0xA3, 0x41, 0x60, 0x03, 0x02
+ , 0xFB, 0xA3, 0x7B, 0x10, 0x01, 0x02
+ , 0xA1, 0xA4, 0x02, 0x30, 0x00, 0x00
+ , 0xA2, 0xA4, 0x02, 0x32, 0x00, 0x00
+ , 0xA3, 0xA4, 0x02, 0x35, 0x00, 0x00
+ , 0xA5, 0xA4, 0x02, 0x37, 0x00, 0x00
+ , 0xA8, 0xA4, 0x02, 0x39, 0x00, 0x00
+ , 0xA9, 0xA4, 0x02, 0x3B, 0x00, 0x00
+ , 0xAA, 0xA4, 0x02, 0x3E, 0x00, 0x00
+ , 0xB2, 0xA4, 0x02, 0x40, 0x00, 0x00
+ , 0xB3, 0xA4, 0x02, 0x42, 0x00, 0x00
+ , 0xB4, 0xA4, 0x02, 0x44, 0x00, 0x00
+ , 0xB6, 0xA4, 0x02, 0x47, 0x00, 0x00
+ , 0xB7, 0xA4, 0x02, 0x49, 0x00, 0x00
+ , 0xB8, 0xA4, 0x02, 0x4C, 0x00, 0x00
+ , 0xB9, 0xA4, 0x02, 0x4F, 0x00, 0x00
+ , 0xBA, 0xA4, 0x02, 0x50, 0x00, 0x00
+ , 0xBB, 0xA4, 0x02, 0x53, 0x00, 0x00
+ , 0xBC, 0xA4, 0x02, 0x55, 0x00, 0x00
+ , 0xBD, 0xA4, 0x02, 0x57, 0x00, 0x00
+ , 0xBE, 0xA4, 0x02, 0x59, 0x00, 0x00
+ , 0xBF, 0xA4, 0x02, 0x5C, 0x00, 0x00
+ , 0xA1, 0xA5, 0xA1, 0x73, 0x00, 0x00
+ , 0xA1, 0xB0, 0xA1, 0x30, 0x00, 0x00
+ , 0xEE, 0xB1, 0xEE, 0x32, 0x00, 0x00
+ , 0xAA, 0xB3, 0xAA, 0x35, 0x00, 0x00
+ , 0xD9, 0xB4, 0xD9, 0x37, 0x00, 0x00
+ , 0xFB, 0xB5, 0xFB, 0x39, 0x00, 0x00
+ , 0xF3, 0xB6, 0xF3, 0x3B, 0x00, 0x00
+ , 0xB6, 0xB8, 0xB6, 0x3E, 0x00, 0x00
+ , 0xD9, 0xB9, 0xD9, 0x40, 0x00, 0x00
+ , 0xFC, 0xBA, 0xFC, 0x42, 0x00, 0x00
+ , 0xE7, 0xBB, 0xE7, 0x44, 0x00, 0x00
+ , 0xCE, 0xBD, 0xCE, 0x47, 0x00, 0x00
+ , 0xC6, 0xBE, 0xC6, 0x49, 0x00, 0x00
+ , 0xDA, 0xC0, 0xDA, 0x4C, 0x00, 0x00
+ , 0xA5, 0xC2, 0xA5, 0x4F, 0x00, 0x00
+ , 0xF7, 0xC2, 0xF7, 0x50, 0x00, 0x00
+ , 0xAB, 0xC4, 0xAB, 0x53, 0x00, 0x00
+ , 0xB8, 0xC5, 0xB8, 0x55, 0x00, 0x00
+ , 0xC4, 0xC6, 0xC4, 0x57, 0x00, 0x00
+ , 0xCF, 0xC7, 0xCF, 0x59, 0x00, 0x00
+ , 0xA1, 0xCA, 0xA1, 0x30, 0x01, 0x01
+ , 0xBE, 0xCA, 0xA2, 0x30, 0x01, 0x01
+ , 0xC9, 0xCA, 0xA3, 0x30, 0x01, 0x01
+ , 0xE1, 0xCA, 0xA5, 0x30, 0x01, 0x01
+ , 0xEB, 0xCA, 0xA8, 0x30, 0x01, 0x01
+ , 0xA1, 0xCB, 0xA9, 0x30, 0x01, 0x01
+ , 0xA7, 0xCB, 0xAD, 0x30, 0x01, 0x01
+ , 0xBF, 0xCB, 0xB3, 0x30, 0x01, 0x01
+ , 0xD3, 0xCB, 0xB4, 0x30, 0x01, 0x01
+ , 0xD5, 0xCB, 0xBB, 0x30, 0x01, 0x01
+ , 0xD9, 0xCB, 0xBD, 0x30, 0x01, 0x01
+ , 0xDA, 0xCB, 0xC5, 0x30, 0x01, 0x01
+ , 0xEB, 0xCB, 0xC7, 0x30, 0x01, 0x01
+ , 0xF7, 0xCB, 0xC9, 0x30, 0x01, 0x01
+ , 0xFB, 0xCB, 0xCB, 0x30, 0x01, 0x01
+ , 0xA4, 0xCC, 0xCC, 0x30, 0x01, 0x01
+ , 0xA7, 0xCC, 0xD4, 0x30, 0x01, 0x01
+ , 0xAA, 0xCC, 0xDD, 0x30, 0x01, 0x01
+ , 0xB1, 0xCC, 0xDF, 0x30, 0x01, 0x01
+ , 0xBC, 0xCC, 0xE1, 0x30, 0x01, 0x01
+ , 0xC2, 0xCC, 0xE2, 0x30, 0x01, 0x01
+ , 0xC8, 0xCC, 0xE6, 0x30, 0x01, 0x01
+ , 0xF5, 0xCC, 0xE8, 0x30, 0x01, 0x01
+ , 0xAF, 0xCD, 0xED, 0x30, 0x01, 0x01
+ , 0xD6, 0xCD, 0xEE, 0x30, 0x01, 0x01
+ , 0xDD, 0xCD, 0xEF, 0x30, 0x01, 0x01
+ , 0xE7, 0xCD, 0xF1, 0x30, 0x01, 0x01
+ , 0xEA, 0xCD, 0xF8, 0x30, 0x01, 0x01
+ , 0xFA, 0xCD, 0xF9, 0x30, 0x01, 0x01
+ , 0xFB, 0xCD, 0xFA, 0x30, 0x01, 0x01
+ , 0xA9, 0xCE, 0xFB, 0x30, 0x01, 0x01
+ , 0xAD, 0xCE, 0xFC, 0x30, 0x01, 0x01
+ , 0xBE, 0xCE, 0xFD, 0x30, 0x01, 0x01
+ , 0xC2, 0xCE, 0xA4, 0x31, 0x01, 0x01
+ , 0xCF, 0xCE, 0xA5, 0x31, 0x01, 0x01
+ , 0xD2, 0xCE, 0xAB, 0x31, 0x01, 0x01
+ , 0xDB, 0xCE, 0xB2, 0x31, 0x01, 0x01
+ , 0xDF, 0xCE, 0xB3, 0x31, 0x01, 0x01
+ , 0xF8, 0xCE, 0xB8, 0x31, 0x01, 0x01
+ , 0xD0, 0xCF, 0xB9, 0x31, 0x01, 0x01
+ , 0xD6, 0xCF, 0xBA, 0x31, 0x01, 0x01
+ , 0xDC, 0xCF, 0xBC, 0x31, 0x01, 0x01
+ , 0xE0, 0xCF, 0xC3, 0x31, 0x01, 0x01
+ , 0xE6, 0xCF, 0xC7, 0x31, 0x01, 0x01
+ , 0xF0, 0xCF, 0xC8, 0x31, 0x01, 0x01
+ , 0xF5, 0xCF, 0xCB, 0x31, 0x01, 0x01
+ , 0xFB, 0xCF, 0xCD, 0x31, 0x01, 0x01
+ , 0xA3, 0xD0, 0xD4, 0x31, 0x01, 0x01
+ , 0xB2, 0xD0, 0xD5, 0x31, 0x01, 0x01
+ , 0xB9, 0xD0, 0xD6, 0x31, 0x01, 0x01
+ , 0xBA, 0xD0, 0xD8, 0x31, 0x01, 0x01
+ , 0xC1, 0xD0, 0xD9, 0x31, 0x01, 0x01
+ , 0xD0, 0xD0, 0xDB, 0x31, 0x01, 0x01
+ , 0xD1, 0xD0, 0xDD, 0x31, 0x01, 0x01
+ , 0xDF, 0xD0, 0xDE, 0x31, 0x01, 0x01
+ , 0xE6, 0xD0, 0xE0, 0x31, 0x01, 0x01
+ , 0xEA, 0xD0, 0xE2, 0x31, 0x01, 0x01
+ , 0xCC, 0xD1, 0xE4, 0x31, 0x01, 0x01
+ , 0xCD, 0xD1, 0xE6, 0x31, 0x01, 0x01
+ , 0xD1, 0xD1, 0xE8, 0x31, 0x01, 0x01
+ , 0xD2, 0xD1, 0xA3, 0x34, 0x01, 0x01
+ , 0xD3, 0xD1, 0xAA, 0x35, 0x01, 0x01
+ , 0xE2, 0xD1, 0xAB, 0x35, 0x01, 0x01
+ , 0xEA, 0xD1, 0xAD, 0x35, 0x01, 0x01
+ , 0xF3, 0xD1, 0xAF, 0x35, 0x01, 0x01
+ , 0xF5, 0xD1, 0xB2, 0x35, 0x01, 0x01
+ , 0xFE, 0xD1, 0xB3, 0x35, 0x01, 0x01
+ , 0xA5, 0xD2, 0xB6, 0x35, 0x01, 0x01
+ , 0xAC, 0xD2, 0xBB, 0x35, 0x01, 0x01
+ , 0xB2, 0xD2, 0xC3, 0x35, 0x01, 0x01
+ , 0xB3, 0xD2, 0xE0, 0x35, 0x01, 0x01
+ , 0xB4, 0xD2, 0xE2, 0x35, 0x01, 0x01
+ , 0xB7, 0xD2, 0xE4, 0x35, 0x01, 0x01
+ , 0xBB, 0xD2, 0xE7, 0x35, 0x01, 0x01
+ , 0xBD, 0xD2, 0xEB, 0x35, 0x01, 0x01
+ , 0xCF, 0xD2, 0xEC, 0x35, 0x01, 0x01
+ , 0xD5, 0xD2, 0xED, 0x35, 0x01, 0x01
+ , 0xD6, 0xD2, 0xF3, 0x35, 0x01, 0x01
+ , 0xDD, 0xD2, 0xFA, 0x35, 0x01, 0x01
+ , 0xE3, 0xD2, 0xA2, 0x36, 0x01, 0x01
+ , 0xE4, 0xD2, 0xA9, 0x36, 0x01, 0x01
+ , 0xEC, 0xD2, 0xAB, 0x36, 0x01, 0x01
+ , 0xED, 0xD2, 0xAD, 0x36, 0x01, 0x01
+ , 0xEE, 0xD2, 0xBA, 0x36, 0x01, 0x01
+ , 0xF0, 0xD2, 0xC1, 0x36, 0x01, 0x01
+ , 0xF2, 0xD2, 0xC6, 0x36, 0x01, 0x01
+ , 0xF3, 0xD2, 0xC9, 0x36, 0x01, 0x01
+ , 0xF9, 0xD2, 0xCF, 0x36, 0x01, 0x01
+ , 0xFB, 0xD2, 0xD0, 0x36, 0x01, 0x01
+ , 0xFD, 0xD2, 0xD9, 0x37, 0x01, 0x01
+ , 0xA1, 0xD3, 0xDC, 0x37, 0x01, 0x01
+ , 0xB5, 0xD3, 0xDE, 0x37, 0x01, 0x01
+ , 0xBA, 0xD3, 0xE3, 0x37, 0x01, 0x01
+ , 0xCB, 0xD3, 0xE4, 0x37, 0x01, 0x01
+ , 0xD0, 0xD3, 0xE7, 0x37, 0x01, 0x01
+ , 0xDB, 0xD3, 0xEB, 0x37, 0x01, 0x01
+ , 0xEB, 0xD3, 0xEC, 0x37, 0x01, 0x01
+ , 0xEC, 0xD3, 0xF6, 0x37, 0x01, 0x01
+ , 0xEE, 0xD3, 0xB5, 0x38, 0x01, 0x01
+ , 0xB8, 0xD4, 0xB6, 0x38, 0x01, 0x01
+ , 0xC2, 0xD4, 0xB7, 0x38, 0x01, 0x01
+ , 0xCC, 0xD4, 0xB9, 0x38, 0x01, 0x01
+ , 0xCE, 0xD4, 0xBF, 0x38, 0x01, 0x01
+ , 0xDF, 0xD4, 0xCE, 0x38, 0x01, 0x01
+ , 0xEA, 0xD4, 0xD0, 0x38, 0x01, 0x01
+ , 0xF0, 0xD4, 0xE6, 0x38, 0x01, 0x01
+ , 0xF1, 0xD4, 0xEE, 0x38, 0x01, 0x01
+ , 0xFA, 0xD4, 0xF3, 0x3B, 0x01, 0x01
+ , 0xA5, 0xD5, 0xF4, 0x3B, 0x01, 0x01
+ , 0xAE, 0xD5, 0xF5, 0x3B, 0x01, 0x01
+ , 0xB7, 0xD5, 0xF6, 0x3B, 0x01, 0x01
+ , 0xB9, 0xD5, 0xF7, 0x3B, 0x01, 0x01
+ , 0xC3, 0xD5, 0xF8, 0x3B, 0x01, 0x01
+ , 0xC6, 0xD5, 0xFB, 0x3B, 0x01, 0x01
+ , 0xCE, 0xD5, 0xA1, 0x3C, 0x01, 0x01
+ , 0xD2, 0xD5, 0xA9, 0x3C, 0x01, 0x01
+ , 0xD3, 0xD5, 0xAB, 0x3C, 0x01, 0x01
+ , 0xD5, 0xD5, 0xAE, 0x3C, 0x01, 0x01
+ , 0xE2, 0xD5, 0xC1, 0x3C, 0x01, 0x01
+ , 0xF4, 0xD5, 0xC2, 0x3C, 0x01, 0x01
+ , 0xFB, 0xD5, 0xC3, 0x3C, 0x01, 0x01
+ , 0xA9, 0xD6, 0xC4, 0x3C, 0x01, 0x01
+ , 0xAF, 0xD6, 0xC5, 0x3C, 0x01, 0x01
+ , 0xB4, 0xD6, 0xC6, 0x3C, 0x01, 0x01
+ , 0xB5, 0xD6, 0xC9, 0x3C, 0x01, 0x01
+ , 0xC7, 0xD6, 0xCA, 0x3C, 0x01, 0x01
+ , 0xCC, 0xD6, 0xCE, 0x3C, 0x01, 0x01
+ , 0xDE, 0xD6, 0xCF, 0x3C, 0x01, 0x01
+ , 0xE5, 0xD6, 0xD0, 0x3C, 0x01, 0x01
+ , 0xE6, 0xD6, 0xD5, 0x3C, 0x01, 0x01
+ , 0xED, 0xD6, 0xDA, 0x3C, 0x01, 0x01
+ , 0xF5, 0xD6, 0xE1, 0x3C, 0x01, 0x01
+ , 0xA3, 0xD7, 0xE6, 0x3C, 0x01, 0x01
+ , 0xA4, 0xD7, 0xE7, 0x3C, 0x01, 0x01
+ , 0xB1, 0xD7, 0xF9, 0x3C, 0x01, 0x01
+ , 0xBF, 0xD7, 0xFA, 0x3C, 0x01, 0x01
+ , 0xC2, 0xD7, 0xFB, 0x3C, 0x01, 0x01
+ , 0xC8, 0xD7, 0xFC, 0x3C, 0x01, 0x01
+ , 0xCC, 0xD7, 0xA2, 0x3D, 0x01, 0x01
+ , 0xCD, 0xD7, 0xA4, 0x3D, 0x01, 0x01
+ , 0xCF, 0xD7, 0xA7, 0x3D, 0x01, 0x01
+ , 0xD0, 0xD7, 0xAA, 0x3D, 0x01, 0x01
+ , 0xD6, 0xD7, 0xAE, 0x3D, 0x01, 0x01
+ , 0xF0, 0xD7, 0xB0, 0x3D, 0x01, 0x01
+ , 0xF9, 0xD7, 0xB2, 0x3D, 0x01, 0x01
+ , 0xFE, 0xD7, 0xB3, 0x3D, 0x01, 0x01
+ , 0xA4, 0xD8, 0xB6, 0x3E, 0x01, 0x01
+ , 0xAC, 0xD8, 0xB7, 0x3E, 0x01, 0x01
+ , 0xB2, 0xD8, 0xB8, 0x3E, 0x01, 0x01
+ , 0xC5, 0xD8, 0xBB, 0x3E, 0x01, 0x01
+ , 0xCC, 0xD8, 0xC1, 0x3E, 0x01, 0x01
+ , 0xD8, 0xD8, 0xC5, 0x3E, 0x01, 0x01
+ , 0xE6, 0xD8, 0xC6, 0x3E, 0x01, 0x01
+ , 0xEB, 0xD8, 0xCD, 0x3E, 0x01, 0x01
+ , 0xF1, 0xD8, 0xE8, 0x3E, 0x01, 0x01
+ , 0xF3, 0xD8, 0xE9, 0x3E, 0x01, 0x01
+ , 0xFE, 0xD8, 0xEA, 0x3E, 0x01, 0x01
+ , 0xA2, 0xD9, 0xED, 0x3E, 0x01, 0x01
+ , 0xB1, 0xD9, 0xEF, 0x3E, 0x01, 0x01
+ , 0xB2, 0xD9, 0xF0, 0x3E, 0x01, 0x01
+ , 0xCA, 0xD9, 0xF1, 0x3E, 0x01, 0x01
+ , 0xD1, 0xD9, 0xF4, 0x3E, 0x01, 0x01
+ , 0xD3, 0xD9, 0xF9, 0x3E, 0x01, 0x01
+ , 0xD6, 0xD9, 0xA6, 0x3F, 0x01, 0x01
+ , 0xE2, 0xD9, 0xAB, 0x3F, 0x01, 0x01
+ , 0xF8, 0xD9, 0xAC, 0x3F, 0x01, 0x01
+ , 0xFA, 0xD9, 0xAE, 0x3F, 0x01, 0x01
+ , 0xA8, 0xDA, 0xB0, 0x3F, 0x01, 0x01
+ , 0xAB, 0xDA, 0xCC, 0x3F, 0x01, 0x01
+ , 0xBE, 0xDA, 0xCE, 0x3F, 0x01, 0x01
+ , 0xCB, 0xDA, 0xD0, 0x3F, 0x01, 0x01
+ , 0xCE, 0xDA, 0xDA, 0x40, 0x01, 0x01
+ , 0xE1, 0xDA, 0xDD, 0x40, 0x01, 0x01
+ , 0xFA, 0xDA, 0xDF, 0x40, 0x01, 0x01
+ , 0xA7, 0xDB, 0xE6, 0x40, 0x01, 0x01
+ , 0xC3, 0xDB, 0xE8, 0x40, 0x01, 0x01
+ , 0xD7, 0xDB, 0xE9, 0x40, 0x01, 0x01
+ , 0xDF, 0xDB, 0xF8, 0x40, 0x01, 0x01
+ , 0xE9, 0xDB, 0xFA, 0x40, 0x01, 0x01
+ , 0xED, 0xDB, 0xFC, 0x40, 0x01, 0x01
+ , 0xF6, 0xDB, 0xFD, 0x40, 0x01, 0x01
+ , 0xF8, 0xDB, 0xAE, 0x41, 0x01, 0x01
+ , 0xA5, 0xDC, 0xAF, 0x41, 0x01, 0x01
+ , 0xAC, 0xDC, 0xB0, 0x41, 0x01, 0x01
+ , 0xB0, 0xDC, 0xB4, 0x41, 0x01, 0x01
+ , 0xC1, 0xDC, 0xB8, 0x41, 0x01, 0x01
+ , 0xD1, 0xDC, 0xB9, 0x41, 0x01, 0x01
+ , 0xE2, 0xDC, 0xBB, 0x41, 0x01, 0x01
+ , 0xE3, 0xDC, 0xBC, 0x41, 0x01, 0x01
+ , 0xE4, 0xDC, 0xC0, 0x41, 0x01, 0x01
+ , 0xF4, 0xDC, 0xCE, 0x41, 0x01, 0x01
+ , 0xC1, 0xDD, 0xCF, 0x41, 0x01, 0x01
+ , 0xC2, 0xDD, 0xD0, 0x41, 0x01, 0x01
+ , 0xD5, 0xDD, 0xD2, 0x41, 0x01, 0x01
+ , 0xDA, 0xDD, 0xD8, 0x41, 0x01, 0x01
+ , 0xE0, 0xDD, 0xF1, 0x41, 0x01, 0x01
+ , 0xAD, 0xDE, 0xF3, 0x41, 0x01, 0x01
+ , 0xBB, 0xDE, 0xF9, 0x41, 0x01, 0x01
+ , 0xBF, 0xDE, 0xE7, 0x44, 0x01, 0x01
+ , 0xFB, 0xDE, 0xE8, 0x44, 0x01, 0x01
+ , 0xA1, 0xDF, 0xEA, 0x44, 0x01, 0x01
+ , 0xAD, 0xDF, 0xEC, 0x44, 0x01, 0x01
+ , 0xB2, 0xDF, 0xEF, 0x44, 0x01, 0x01
+ , 0xBA, 0xDF, 0xF0, 0x44, 0x01, 0x01
+ , 0xBE, 0xDF, 0xF3, 0x44, 0x01, 0x01
+ , 0xDD, 0xDF, 0xF5, 0x44, 0x01, 0x01
+ , 0xE0, 0xDF, 0xF6, 0x44, 0x01, 0x01
+ , 0xE5, 0xDF, 0xFD, 0x44, 0x01, 0x01
+ , 0xEA, 0xDF, 0xAD, 0x45, 0x01, 0x01
+ , 0xAA, 0xE0, 0xAE, 0x45, 0x01, 0x01
+ , 0xB9, 0xE0, 0xB1, 0x45, 0x01, 0x01
+ , 0xD9, 0xE0, 0xB3, 0x45, 0x01, 0x01
+ , 0xE6, 0xE0, 0xB6, 0x45, 0x01, 0x01
+ , 0xEE, 0xE0, 0xB7, 0x45, 0x01, 0x01
+ , 0xF2, 0xE0, 0xBA, 0x45, 0x01, 0x01
+ , 0xA6, 0xE1, 0xBC, 0x45, 0x01, 0x01
+ , 0xAF, 0xE1, 0xD2, 0x45, 0x01, 0x01
+ , 0xD4, 0xE1, 0xD3, 0x45, 0x01, 0x01
+ , 0xDD, 0xE1, 0xD5, 0x45, 0x01, 0x01
+ , 0xE3, 0xE1, 0xD6, 0x45, 0x01, 0x01
+ , 0xE4, 0xE1, 0xDB, 0x45, 0x01, 0x01
+ , 0xEC, 0xE1, 0xE2, 0x45, 0x01, 0x01
+ , 0xF1, 0xE1, 0xE8, 0x45, 0x01, 0x01
+ , 0xF3, 0xE1, 0xF6, 0x45, 0x01, 0x01
+ , 0xD2, 0xE2, 0xF7, 0x45, 0x01, 0x01
+ , 0xDE, 0xE2, 0xF8, 0x45, 0x01, 0x01
+ , 0xF9, 0xE2, 0xFA, 0x45, 0x01, 0x01
+ , 0xFD, 0xE2, 0xFE, 0x45, 0x01, 0x01
+ , 0xA2, 0xE3, 0xBD, 0x46, 0x01, 0x01
+ , 0xA5, 0xE3, 0xC0, 0x46, 0x01, 0x01
+ , 0xAA, 0xE3, 0xC2, 0x46, 0x01, 0x01
+ , 0xB4, 0xE3, 0xC3, 0x46, 0x01, 0x01
+ , 0xD0, 0xE3, 0xC4, 0x46, 0x01, 0x01
+ , 0xDF, 0xE3, 0xC5, 0x46, 0x01, 0x01
+ , 0xF7, 0xE3, 0xC7, 0x46, 0x01, 0x01
+ , 0xFB, 0xE3, 0xC9, 0x46, 0x01, 0x01
+ , 0xA7, 0xE4, 0xCA, 0x46, 0x01, 0x01
+ , 0xAA, 0xE4, 0xD6, 0x47, 0x01, 0x01
+ , 0xAB, 0xE4, 0xBE, 0x48, 0x01, 0x01
+ , 0xAC, 0xE4, 0xC6, 0x49, 0x01, 0x01
+ , 0xBE, 0xE4, 0xC7, 0x49, 0x01, 0x01
+ , 0xCC, 0xE4, 0xC8, 0x49, 0x01, 0x01
+ , 0xD6, 0xE4, 0xCB, 0x49, 0x01, 0x01
+ , 0xDA, 0xE4, 0xCF, 0x49, 0x01, 0x01
+ , 0xE2, 0xE4, 0xD0, 0x49, 0x01, 0x01
+ , 0xE6, 0xE4, 0xD3, 0x49, 0x01, 0x01
+ , 0xED, 0xE4, 0xD6, 0x49, 0x01, 0x01
+ , 0xF8, 0xE4, 0xD7, 0x49, 0x01, 0x01
+ , 0xA1, 0xE5, 0xDE, 0x49, 0x01, 0x01
+ , 0xA5, 0xE5, 0xDF, 0x49, 0x01, 0x01
+ , 0xB0, 0xE5, 0xE0, 0x49, 0x01, 0x01
+ , 0xB9, 0xE5, 0xE7, 0x49, 0x01, 0x01
+ , 0xD8, 0xE5, 0xEE, 0x49, 0x01, 0x01
+ , 0xE2, 0xE5, 0xEF, 0x49, 0x01, 0x01
+ , 0xE7, 0xE5, 0xF0, 0x49, 0x01, 0x01
+ , 0xED, 0xE5, 0xF3, 0x49, 0x01, 0x01
+ , 0xEF, 0xE5, 0xF6, 0x49, 0x01, 0x01
+ , 0xF5, 0xE5, 0xF7, 0x49, 0x01, 0x01
+ , 0xF7, 0xE5, 0xA3, 0x4A, 0x01, 0x01
+ , 0xF8, 0xE5, 0xA9, 0x4A, 0x01, 0x01
+ , 0xB2, 0xE6, 0xAA, 0x4A, 0x01, 0x01
+ , 0xBF, 0xE6, 0xAC, 0x4A, 0x01, 0x01
+ , 0xEA, 0xE6, 0xAD, 0x4A, 0x01, 0x01
+ , 0xF4, 0xE6, 0xB0, 0x4A, 0x01, 0x01
+ , 0xA5, 0xE7, 0xB1, 0x4A, 0x01, 0x01
+ , 0xA9, 0xE7, 0xB5, 0x4A, 0x01, 0x01
+ , 0xD1, 0xE7, 0xB9, 0x4A, 0x01, 0x01
+ , 0xE9, 0xE7, 0xC0, 0x4A, 0x01, 0x01
+ , 0xA9, 0xE8, 0xC1, 0x4A, 0x01, 0x01
+ , 0xAE, 0xE8, 0xC2, 0x4A, 0x01, 0x01
+ , 0xB4, 0xE8, 0xC3, 0x4A, 0x01, 0x01
+ , 0xB5, 0xE8, 0xCB, 0x4A, 0x01, 0x01
+ , 0xBE, 0xE8, 0xCD, 0x4A, 0x01, 0x01
+ , 0xC6, 0xE8, 0xCF, 0x4A, 0x01, 0x01
+ , 0xD8, 0xE8, 0xD0, 0x4A, 0x01, 0x01
+ , 0xD9, 0xE8, 0xD5, 0x4A, 0x01, 0x01
+ , 0xDE, 0xE8, 0xD6, 0x4A, 0x01, 0x01
+ , 0xE2, 0xE8, 0xDC, 0x4A, 0x01, 0x01
+ , 0xE7, 0xE8, 0xE4, 0x4A, 0x01, 0x01
+ , 0xAF, 0xE9, 0xE5, 0x4A, 0x01, 0x01
+ , 0xB5, 0xE9, 0xEB, 0x4A, 0x01, 0x01
+ , 0xCD, 0xE9, 0xEC, 0x4A, 0x01, 0x01
+ , 0xED, 0xE9, 0xED, 0x4A, 0x01, 0x01
+ , 0xF6, 0xE9, 0xEE, 0x4A, 0x01, 0x01
+ , 0xA5, 0xEA, 0xEF, 0x4A, 0x01, 0x01
+ , 0xA8, 0xEA, 0xF5, 0x4A, 0x01, 0x01
+ , 0xAA, 0xEA, 0xF8, 0x4A, 0x01, 0x01
+ , 0xC5, 0xEA, 0xF9, 0x4A, 0x01, 0x01
+ , 0xC8, 0xEA, 0xA7, 0x4B, 0x01, 0x01
+ , 0xE1, 0xEA, 0xAF, 0x4B, 0x01, 0x01
+ , 0xBB, 0xEB, 0xB0, 0x4B, 0x01, 0x01
+ , 0xC2, 0xEB, 0xB1, 0x4B, 0x01, 0x01
+ , 0xCF, 0xEB, 0xB2, 0x4B, 0x01, 0x01
+ , 0xD4, 0xEB, 0xB6, 0x4B, 0x01, 0x01
+ , 0xD9, 0xEB, 0xBA, 0x4B, 0x01, 0x01
+ , 0xE0, 0xEB, 0xBB, 0x4B, 0x01, 0x01
+ , 0xE1, 0xEB, 0xBD, 0x4B, 0x01, 0x01
+ , 0xE7, 0xEB, 0xBE, 0x4B, 0x01, 0x01
+ , 0xEA, 0xEB, 0xC0, 0x4B, 0x01, 0x01
+ , 0xEE, 0xEB, 0xC7, 0x4B, 0x01, 0x01
+ , 0xA3, 0xEC, 0xCC, 0x4B, 0x01, 0x01
+ , 0xC9, 0xEC, 0xCD, 0x4B, 0x01, 0x01
+ , 0xD1, 0xEC, 0xCE, 0x4B, 0x01, 0x01
+ , 0xE9, 0xEC, 0xCF, 0x4B, 0x01, 0x01
+ , 0xF2, 0xEC, 0xD3, 0x4B, 0x01, 0x01
+ , 0xFD, 0xEC, 0xD4, 0x4B, 0x01, 0x01
+ , 0xA4, 0xED, 0xD7, 0x4B, 0x01, 0x01
+ , 0xA8, 0xED, 0xDA, 0x4C, 0x01, 0x01
+ , 0xC2, 0xED, 0xDB, 0x4C, 0x01, 0x01
+ , 0xCF, 0xED, 0xDC, 0x4C, 0x01, 0x01
+ , 0xD4, 0xED, 0xE1, 0x4C, 0x01, 0x01
+ , 0xDA, 0xED, 0xE2, 0x4C, 0x01, 0x01
+ , 0xDB, 0xED, 0xE5, 0x4C, 0x01, 0x01
+ , 0xA2, 0xEE, 0xE7, 0x4C, 0x01, 0x01
+ , 0xB3, 0xEE, 0xEF, 0x4C, 0x01, 0x01
+ , 0xB7, 0xEE, 0xFA, 0x4C, 0x01, 0x01
+ , 0xD3, 0xEE, 0xFB, 0x4C, 0x01, 0x01
+ , 0xEC, 0xEE, 0xFC, 0x4C, 0x01, 0x01
+ , 0xB7, 0xEF, 0xFD, 0x4C, 0x01, 0x01
+ , 0xBF, 0xEF, 0xA1, 0x4D, 0x01, 0x01
+ , 0xC8, 0xEF, 0xA2, 0x4D, 0x01, 0x01
+ , 0xCB, 0xEF, 0xA4, 0x4D, 0x01, 0x01
+ , 0xA4, 0xF0, 0xA6, 0x4D, 0x01, 0x01
+ , 0xBB, 0xF0, 0xB6, 0x4D, 0x01, 0x01
+ , 0xE9, 0xF0, 0xB7, 0x4D, 0x01, 0x01
+ , 0xED, 0xF0, 0xB8, 0x4D, 0x01, 0x01
+ , 0xEF, 0xF0, 0xB9, 0x4D, 0x01, 0x01
+ , 0xF2, 0xF0, 0xBE, 0x4D, 0x01, 0x01
+ , 0xA5, 0xF1, 0xC2, 0x4D, 0x01, 0x01
+ , 0xAA, 0xF1, 0xCB, 0x4D, 0x01, 0x01
+ , 0xAB, 0xF1, 0xD6, 0x4D, 0x01, 0x01
+ , 0xD3, 0xF1, 0xD7, 0x4D, 0x01, 0x01
+ , 0xD5, 0xF1, 0xD8, 0x4D, 0x01, 0x01
+ , 0xE8, 0xF1, 0xD9, 0x4D, 0x01, 0x01
+ , 0xE9, 0xF1, 0xDF, 0x4D, 0x01, 0x01
+ , 0xED, 0xF1, 0xEF, 0x4D, 0x01, 0x01
+ , 0xEE, 0xF1, 0xF1, 0x4D, 0x01, 0x01
+ , 0xEF, 0xF1, 0xF3, 0x4D, 0x01, 0x01
+ , 0xF2, 0xF1, 0xF5, 0x4D, 0x01, 0x01
+ , 0xFD, 0xF1, 0xF6, 0x4D, 0x01, 0x01
+ , 0xC1, 0xF2, 0xF7, 0x4D, 0x01, 0x01
+ , 0xC6, 0xF2, 0xF8, 0x4D, 0x01, 0x01
+ , 0xE9, 0xF2, 0xFA, 0x4D, 0x01, 0x01
+ , 0xF8, 0xF2, 0xFC, 0x4D, 0x01, 0x01
+ , 0xFA, 0xF2, 0xFD, 0x4D, 0x01, 0x01
+ , 0xA3, 0xF3, 0xA1, 0x4E, 0x01, 0x01
+ , 0xA6, 0xF3, 0xF7, 0x50, 0x01, 0x01
+ , 0xB5, 0xF3, 0xF8, 0x50, 0x01, 0x01
+ , 0xBC, 0xF3, 0xF9, 0x50, 0x01, 0x01
+ , 0xCB, 0xF3, 0xFB, 0x50, 0x01, 0x01
+ , 0xD0, 0xF3, 0xFC, 0x50, 0x01, 0x01
+ , 0xDA, 0xF3, 0xA2, 0x51, 0x01, 0x01
+ , 0xF0, 0xF3, 0xA4, 0x51, 0x01, 0x01
+ , 0xFC, 0xF3, 0xA5, 0x51, 0x01, 0x01
+ , 0xA2, 0xF4, 0xB3, 0x51, 0x01, 0x01
+ , 0xA6, 0xF4, 0xB4, 0x51, 0x01, 0x01
+ , 0xB5, 0xF4, 0xB5, 0x51, 0x01, 0x01
+ , 0xC8, 0xF4, 0xB6, 0x51, 0x01, 0x01
+ , 0xD2, 0xF4, 0xB7, 0x51, 0x01, 0x01
+ , 0xDC, 0xF4, 0xB8, 0x51, 0x01, 0x01
+ , 0xE6, 0xF4, 0xBB, 0x51, 0x01, 0x01
+ , 0xEE, 0xF4, 0xBC, 0x51, 0x01, 0x01
+ , 0xF8, 0xF4, 0xCA, 0x51, 0x01, 0x01
+ , 0xB5, 0xF5, 0xCB, 0x51, 0x01, 0x01
+ , 0xBB, 0xF5, 0xCC, 0x51, 0x01, 0x01
+ , 0xBF, 0xF5, 0xD1, 0x51, 0x01, 0x01
+ , 0xC9, 0xF5, 0xD4, 0x51, 0x01, 0x01
+ , 0xCA, 0xF5, 0xD6, 0x51, 0x01, 0x01
+ , 0xCD, 0xF5, 0xDF, 0x51, 0x01, 0x01
+ , 0xE4, 0xF5, 0xE0, 0x51, 0x01, 0x01
+ , 0xF0, 0xF5, 0xE1, 0x51, 0x01, 0x01
+ , 0xF3, 0xF5, 0xE2, 0x51, 0x01, 0x01
+ , 0xF6, 0xF5, 0xE6, 0x51, 0x01, 0x01
+ , 0xFC, 0xF5, 0xE9, 0x51, 0x01, 0x01
+ , 0xA2, 0xF6, 0xEB, 0x51, 0x01, 0x01
+ , 0xB0, 0xF6, 0xF8, 0x51, 0x01, 0x01
+ , 0xB5, 0xF6, 0xFE, 0x51, 0x01, 0x01
+ , 0xB6, 0xF6, 0xA1, 0x52, 0x01, 0x01
+ , 0xCE, 0xF6, 0xA2, 0x52, 0x01, 0x01
+ , 0xD1, 0xF6, 0xA3, 0x52, 0x01, 0x01
+ , 0xD2, 0xF6, 0xA5, 0x52, 0x01, 0x01
+ , 0xD5, 0xF6, 0xA7, 0x52, 0x01, 0x01
+ , 0xDE, 0xF6, 0xA8, 0x52, 0x01, 0x01
+ , 0xDF, 0xF6, 0xAA, 0x52, 0x01, 0x01
+ , 0xE1, 0xF6, 0xE8, 0x53, 0x01, 0x01
+ , 0xE2, 0xF6, 0xB8, 0x55, 0x01, 0x01
+ , 0xF0, 0xF6, 0xB9, 0x55, 0x01, 0x01
+ , 0xA2, 0xF7, 0xBA, 0x55, 0x01, 0x01
+ , 0xAC, 0xF7, 0xBB, 0x55, 0x01, 0x01
+ , 0xAE, 0xF7, 0xBD, 0x55, 0x01, 0x01
+ , 0xB2, 0xF7, 0xBE, 0x55, 0x01, 0x01
+ , 0xB5, 0xF7, 0xC1, 0x55, 0x01, 0x01
+ , 0xBA, 0xF7, 0xC2, 0x55, 0x01, 0x01
+ , 0xC8, 0xF7, 0xC3, 0x55, 0x01, 0x01
+ , 0xCB, 0xF7, 0xCA, 0x55, 0x01, 0x01
+ , 0xCC, 0xF7, 0xCD, 0x55, 0x01, 0x01
+ , 0xCD, 0xF7, 0xE4, 0x55, 0x01, 0x01
+ , 0xD1, 0xF7, 0xEB, 0x55, 0x01, 0x01
+ , 0xD8, 0xF7, 0xF0, 0x55, 0x01, 0x01
+ , 0xDE, 0xF7, 0xF5, 0x55, 0x01, 0x01
+ , 0xE4, 0xF7, 0xAF, 0x56, 0x01, 0x01
+ , 0xE6, 0xF7, 0xB4, 0x56, 0x01, 0x01
+ , 0xE7, 0xF7, 0xC4, 0x57, 0x01, 0x01
+ , 0xF7, 0xF7, 0xC7, 0x57, 0x01, 0x01
+ , 0xA2, 0xF8, 0xC8, 0x57, 0x01, 0x01
+ , 0xA5, 0xF8, 0xD0, 0x57, 0x01, 0x01
+ , 0xB0, 0xF8, 0xD8, 0x57, 0x01, 0x01
+ , 0xB4, 0xF8, 0xDA, 0x57, 0x01, 0x01
+ , 0xB5, 0xF8, 0xED, 0x57, 0x01, 0x01
+ , 0xBF, 0xF8, 0xEF, 0x57, 0x01, 0x01
+ , 0xC0, 0xF8, 0xF2, 0x57, 0x01, 0x01
+ , 0xC5, 0xF8, 0xF3, 0x57, 0x01, 0x01
+ , 0xCF, 0xF8, 0xF7, 0x57, 0x01, 0x01
+ , 0xEB, 0xF8, 0xF8, 0x57, 0x01, 0x01
+ , 0xF1, 0xF8, 0xA5, 0x58, 0x01, 0x01
+ , 0xA1, 0xF9, 0xB0, 0x58, 0x01, 0x01
+ , 0xA3, 0xF9, 0xB3, 0x58, 0x01, 0x01
+ , 0xA8, 0xF9, 0xC7, 0x58, 0x01, 0x01
+ , 0xAF, 0xF9, 0xCA, 0x58, 0x01, 0x01
+ , 0xB9, 0xF9, 0xCC, 0x58, 0x01, 0x01
+ , 0xBB, 0xF9, 0xCF, 0x59, 0x01, 0x01
+ , 0xC9, 0xF9, 0xD0, 0x59, 0x01, 0x01
+ , 0xCE, 0xF9, 0xD1, 0x59, 0x01, 0x01
+ , 0xDC, 0xF9, 0xD2, 0x59, 0x01, 0x01
+ , 0xDE, 0xF9, 0xD4, 0x59, 0x01, 0x01
+ , 0xEA, 0xF9, 0xD5, 0x59, 0x01, 0x01
+ , 0xF1, 0xF9, 0xD7, 0x59, 0x01, 0x01
+ , 0xA4, 0xFA, 0xD8, 0x59, 0x01, 0x01
+ , 0xB6, 0xFA, 0xD9, 0x59, 0x01, 0x01
+ , 0xB8, 0xFA, 0xE0, 0x59, 0x01, 0x01
+ , 0xBD, 0xFA, 0xE2, 0x59, 0x01, 0x01
+ , 0xC6, 0xFA, 0xE3, 0x59, 0x01, 0x01
+ , 0xCA, 0xFA, 0xE5, 0x59, 0x01, 0x01
+ , 0xCE, 0xFA, 0xE6, 0x59, 0x01, 0x01
+ , 0xCF, 0xFA, 0xE8, 0x59, 0x01, 0x01
+ , 0xD1, 0xFA, 0xF5, 0x59, 0x01, 0x01
+ , 0xD5, 0xFA, 0xF6, 0x59, 0x01, 0x01
+ , 0xEA, 0xFA, 0xF7, 0x59, 0x01, 0x01
+ , 0xEE, 0xFA, 0xF8, 0x59, 0x01, 0x01
+ , 0xEF, 0xFA, 0xF9, 0x59, 0x01, 0x01
+ , 0xFB, 0xFA, 0xFC, 0x59, 0x01, 0x01
+ , 0xB1, 0xFB, 0xFD, 0x59, 0x01, 0x01
+ , 0xBA, 0xFB, 0xA3, 0x5A, 0x01, 0x01
+ , 0xE3, 0xFB, 0xA4, 0x5A, 0x01, 0x01
+ , 0xE6, 0xFB, 0xA5, 0x5A, 0x01, 0x01
+ , 0xEC, 0xFB, 0xA6, 0x5A, 0x01, 0x01
+ , 0xEF, 0xFB, 0xAB, 0x5A, 0x01, 0x01
+ , 0xF9, 0xFB, 0xAD, 0x5A, 0x01, 0x01
+ , 0xA9, 0xFC, 0xAE, 0x5A, 0x01, 0x01
+ , 0xAF, 0xFC, 0xAF, 0x5A, 0x01, 0x01
+ , 0xC0, 0xFC, 0xB0, 0x5A, 0x01, 0x01
+ , 0xC5, 0xFC, 0xB2, 0x5A, 0x01, 0x01
+ , 0xDD, 0xFC, 0xB8, 0x5A, 0x01, 0x01
+ , 0xF1, 0xFC, 0xB9, 0x5A, 0x01, 0x01
+ , 0xF3, 0xFC, 0xBE, 0x5A, 0x01, 0x01
+ , 0xF6, 0xFC, 0xBF, 0x5A, 0x01, 0x01
+ , 0xA5, 0xFD, 0xC4, 0x5A, 0x01, 0x01
+ , 0xB2, 0xFD, 0xC6, 0x5A, 0x01, 0x01
+ , 0xBC, 0xFD, 0xCB, 0x5A, 0x01, 0x01
+ , 0xBD, 0xFD, 0xCD, 0x5A, 0x01, 0x01
+ , 0xC1, 0xFD, 0xD1, 0x5A, 0x01, 0x01
+ , 0xC4, 0xFD, 0xD6, 0x5A, 0x01, 0x01
+ , 0xCC, 0xFD, 0xDE, 0x5A, 0x01, 0x01
+ , 0xD1, 0xFD, 0xE1, 0x5A, 0x01, 0x01
+ , 0xD4, 0xFD, 0xE4, 0x5A, 0x01, 0x01
+ , 0xD9, 0xFD, 0xE6, 0x5A, 0x01, 0x01
+ , 0xDA, 0xFD, 0xE7, 0x5A, 0x01, 0x01
+ , 0xDE, 0xFD, 0xEA, 0x5A, 0x01, 0x01
+ , 0xE2, 0xFD, 0xEC, 0x5A, 0x01, 0x01
+ , 0xE5, 0xFD, 0xED, 0x5A, 0x01, 0x01
+ , 0xE9, 0xFD, 0xEF, 0x5A, 0x01, 0x01
+ , 0xEA, 0xFD, 0xF1, 0x5A, 0x01, 0x01
+ , 0xFE, 0xFD, 0xFA, 0x5A, 0x01, 0x01
+ , 0xFF, 0xFD, 0xFF, 0xFD, 0x00, 0x00
+};
+
+static unsigned char NLSALLOC(0412) rgmaptable[] = {
+ 0x20, 0x10, 0x01, 0x00, 0x20, 0x00
+ , 0xA1, 0xA1, 0x20, 0x00, 0xA1, 0xA1
+ , 0x21, 0x10, 0x5F, 0x00, 0x21, 0x00
+ , 0xA1, 0xA3, 0x21, 0x00, 0xA1, 0xA3
+ , 0x30, 0x20, 0x0A, 0x00, 0x30, 0x00
+ , 0xB0, 0xA3, 0x30, 0x00, 0xB0, 0xA3
+ , 0x41, 0x60, 0x1A, 0x00, 0x41, 0x00
+ , 0xC1, 0xA3, 0x61, 0x00, 0xE1, 0xA3
+};
+
+static unsigned char NLSALLOC(0412) rgtypetable[] = {
+ 0x00, 0x00, 0x20, 0x00, 0x00, 0x00
+ , 0x09, 0x00, 0x68, 0x00, 0x09, 0x00
+ , 0x0A, 0x00, 0x28, 0x00, 0x00, 0x00
+ , 0x0E, 0x00, 0x20, 0x00, 0x00, 0x00
+ , 0x20, 0x00, 0x48, 0x00, 0x0A, 0x00
+ , 0x21, 0x00, 0x10, 0x00, 0x0B, 0x08
+ , 0x24, 0x00, 0x10, 0x00, 0x05, 0x08
+ , 0x26, 0x00, 0x10, 0x00, 0x01, 0x08
+ , 0x2B, 0x00, 0x10, 0x00, 0x05, 0x08
+ , 0x2C, 0x00, 0x10, 0x00, 0x07, 0x08
+ , 0x2D, 0x00, 0x10, 0x00, 0x05, 0x08
+ , 0x2E, 0x00, 0x10, 0x00, 0x03, 0x08
+ , 0x30, 0x00, 0x84, 0x00, 0x03, 0x00
+ , 0x3A, 0x00, 0x10, 0x00, 0x07, 0x08
+ , 0x3B, 0x00, 0x10, 0x00, 0x0B, 0x08
+ , 0x40, 0x00, 0x10, 0x00, 0x01, 0x08
+ , 0x41, 0x00, 0x81, 0x01, 0x01, 0x00
+ , 0x47, 0x00, 0x01, 0x01, 0x01, 0x00
+ , 0x5B, 0x00, 0x10, 0x00, 0x0B, 0x08
+ , 0x61, 0x00, 0x82, 0x01, 0x01, 0x00
+ , 0x67, 0x00, 0x02, 0x01, 0x01, 0x00
+ , 0x7B, 0x00, 0x10, 0x00, 0x0B, 0x08
+ , 0x7F, 0x00, 0x20, 0x00, 0x00, 0x00
+ , 0x80, 0x00, 0x00, 0x00, 0x0B, 0x08
+ , 0xA1, 0xA1, 0x48, 0x00, 0x0A, 0x00
+ , 0xA2, 0xA1, 0x00, 0x00, 0x0B, 0x08
+ , 0xA1, 0xA3, 0x10, 0x00, 0x0B, 0x08
+ , 0xA4, 0xA3, 0x10, 0x00, 0x05, 0x08
+ , 0xA6, 0xA3, 0x10, 0x00, 0x01, 0x08
+ , 0xAB, 0xA3, 0x10, 0x00, 0x05, 0x08
+ , 0xAC, 0xA3, 0x10, 0x00, 0x07, 0x08
+ , 0xAD, 0xA3, 0x10, 0x00, 0x05, 0x08
+ , 0xAE, 0xA3, 0x10, 0x00, 0x03, 0x08
+ , 0xB0, 0xA3, 0x84, 0x00, 0x03, 0x00
+ , 0xBA, 0xA3, 0x10, 0x00, 0x07, 0x08
+ , 0xBB, 0xA3, 0x10, 0x00, 0x0B, 0x08
+ , 0xC0, 0xA3, 0x10, 0x00, 0x01, 0x08
+ , 0xC1, 0xA3, 0x81, 0x01, 0x01, 0x00
+ , 0xC7, 0xA3, 0x01, 0x01, 0x01, 0x00
+ , 0xDB, 0xA3, 0x10, 0x00, 0x0B, 0x08
+ , 0xE1, 0xA3, 0x82, 0x01, 0x01, 0x00
+ , 0xE7, 0xA3, 0x02, 0x01, 0x01, 0x00
+ , 0xFB, 0xA3, 0x10, 0x00, 0x0B, 0x08
+ , 0xA1, 0xA4, 0x00, 0x01, 0x01, 0x00
+ , 0xA1, 0xA5, 0x00, 0x00, 0x0B, 0x08
+ , 0xA1, 0xB0, 0x00, 0x01, 0x01, 0x00
+};
+#endif
+
+static unsigned char NLSALLOC(0412) rgbSENGCOUNTRY[] = {
+ 'K', 'o', 'r', 'e', 'a'
+};
+
+static unsigned char NLSALLOC(0412) rgbSENGLANGUAGE[] = {
+ 'K', 'o', 'r', 'e', 'a', 'n'
+};
+
+#if defined(VBA2) //hand-edited this locale info based on daytona [bassam]
+static BYTE NLSALLOC(0412) rgbIFIRSTDAYOFWEEK[] = { /* "6" */
+ 0x36
+};
+
+static BYTE NLSALLOC(0412) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0412) rgbIDEFAULTANSICODEPAGE[] = { /* "949" */
+ 0x39, 0x34, 0x39
+};
+
+static BYTE NLSALLOC(0412) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0412) rgbSTIMEFORMAT[] = { /* "HH:mm:ss" */
+ 0x48, 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0412) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0412) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0412) rgbIOPTIONALCALENDAR[] = { /* "2" */
+ 0x32
+};
+#endif
+
+
+static unsigned char NLSALLOC(0412) rgbILANGUAGE[] = {
+ '0', '4', '1', '2'
+};
+
+static unsigned char NLSALLOC(0412) rgbSLANGUAGE[] = {
+ 0xc7, 0xd1, 0xb1, 0xb9, 0xbe, 0xee, '(', 'K', 'o', 'r', 'e', 'a', 'n', ')'
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVLANGNAME[] = {
+ 'K', 'O', 'R'
+};
+
+static unsigned char NLSALLOC(0412) rgbSNATIVELANGNAME[] = {
+ 0xc7, 0xd1, 0xb1, 0xb9, 0xbe, 0xee
+};
+
+static unsigned char NLSALLOC(0412) rgbICOUNTRY[] = {
+ '8', '2'
+};
+
+static unsigned char NLSALLOC(0412) rgbSCOUNTRY[] = {
+ 0xb4, 0xeb, 0xc7, 0xd1, 0xb9, 0xce, 0xb1, 0xb9, '(', 'K', 'o', 'r', 'e', 'a', ')'
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVCTRYNAME[] = {
+ 'K', 'O', 'R'
+};
+
+static unsigned char NLSALLOC(0412) rgbSNATIVECTRYNAME[] = {
+ 0xb4, 0xeb, 0xc7, 0xd1, 0xb9, 0xce, 0xb1, 0xb9
+};
+
+static unsigned char NLSALLOC(0412) rgbIDEFAULTLANGUAGE[] = {
+ '0', '4', '1', '2'
+};
+
+static unsigned char NLSALLOC(0412) rgbIDEFAULTCOUNTRY[] = {
+ '8', '2'
+};
+
+static unsigned char NLSALLOC(0412) rgbIDEFAULTCODEPAGE[] = {
+ '9', '4', '9'
+};
+
+static unsigned char NLSALLOC(0412) rgbSLIST[] = {
+ ','
+};
+
+static unsigned char NLSALLOC(0412) rgbIMEASURE[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0412) rgbSDECIMAL[] = {
+ '.'
+};
+
+static unsigned char NLSALLOC(0412) rgbSTHOUSAND[] = {
+ ','
+};
+
+static unsigned char NLSALLOC(0412) rgbSGROUPING[] = {
+ '3', ';', '0'
+};
+
+static unsigned char NLSALLOC(0412) rgbIDIGITS[] = {
+ '2'
+};
+
+static unsigned char NLSALLOC(0412) rgbILZERO[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0412) rgbSNATIVEDIGITS[] = {
+ '0', '1', '2', '3', '4', '5', '6', '7', '8', '9'
+};
+
+static unsigned char NLSALLOC(0412) rgbSCURRENCY[] = {
+ 0x5c
+};
+
+static unsigned char NLSALLOC(0412) rgbSINTLSYMBOL[] = {
+ 'K', 'R', 'W'
+};
+
+static unsigned char NLSALLOC(0412) rgbSMONDECIMALSEP[] = {
+ '.'
+};
+
+static unsigned char NLSALLOC(0412) rgbSMONTHOUSANDSEP[] = {
+ ','
+};
+
+static unsigned char NLSALLOC(0412) rgbSMONGROUPING[] = {
+ '3', ';', '0'
+};
+
+static unsigned char NLSALLOC(0412) rgbICURRDIGITS[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0412) rgbIINTLCURRDIGITS[] = {
+ '2'
+};
+
+static unsigned char NLSALLOC(0412) rgbICURRENCY[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0412) rgbINEGCURR[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0412) rgbSDATE[] = {
+ '-'
+};
+
+static unsigned char NLSALLOC(0412) rgbSTIME[] = {
+ ':'
+};
+
+static unsigned char NLSALLOC(0412) rgbSSHORTDATE[] = {
+ 'y', 'y', '-', 'M', 'M', '-', 'd', 'd'
+};
+
+static unsigned char NLSALLOC(0412) rgbSLONGDATE[] = {
+ 'y', 'y', 'y', 'y',
+ 0xb3, 0xe2,
+ ' ', 'M',
+ 0xbf, 0xf9,
+ ' ', 'd',
+ 0xc0, 0xcf
+};
+
+static unsigned char NLSALLOC(0412) rgbIDATE[] = {
+ '2'
+};
+
+static unsigned char NLSALLOC(0412) rgbILDATE[] = {
+ '2'
+};
+
+static unsigned char NLSALLOC(0412) rgbITIME[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0412) rgbICENTURY[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0412) rgbITLZERO[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0412) rgbIDAYLZERO[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0412) rgbIMONLZERO[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0412) rgbS1159[] = {
+ 0xbf, 0xc0, 0xc0, 0xfc
+};
+
+static unsigned char NLSALLOC(0412) rgbS2359[] = {
+ 0xbf, 0xc0, 0xc8, 0xc4
+};
+
+static unsigned char NLSALLOC(0412) rgbSDAYNAME1[] = {
+ 0xbf, 0xf9, 0xbf, 0xe4, 0xc0, 0xcf
+};
+
+static unsigned char NLSALLOC(0412) rgbSDAYNAME2[] = {
+ 0xc8, 0xad, 0xbf, 0xe4, 0xc0, 0xcf
+};
+
+static unsigned char NLSALLOC(0412) rgbSDAYNAME3[] = {
+ 0xbc, 0xf6, 0xbf, 0xe4, 0xc0, 0xcf
+};
+
+static unsigned char NLSALLOC(0412) rgbSDAYNAME4[] = {
+ 0xb8, 0xf1, 0xbf, 0xe4, 0xc0, 0xcf
+};
+
+static unsigned char NLSALLOC(0412) rgbSDAYNAME5[] = {
+ 0xb1, 0xdd, 0xbf, 0xe4, 0xc0, 0xcf
+};
+
+static unsigned char NLSALLOC(0412) rgbSDAYNAME6[] = {
+ 0xc5, 0xe4, 0xbf, 0xe4, 0xc0, 0xcf
+};
+
+static unsigned char NLSALLOC(0412) rgbSDAYNAME7[] = {
+ 0xc0, 0xcf, 0xbf, 0xe4, 0xc0, 0xcf
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVDAYNAME1[] = {
+ 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVDAYNAME2[] = {
+ 0xc8, 0xad
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVDAYNAME3[] = {
+ 0xbc, 0xf6
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVDAYNAME4[] = {
+ 0xb8, 0xf1
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVDAYNAME5[] = {
+ 0xb1, 0xdd
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVDAYNAME6[] = {
+ 0xc5, 0xe4
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVDAYNAME7[] = {
+ 0xc0, 0xcf
+};
+
+static unsigned char NLSALLOC(0412) rgbSMONTHNAME1[] = {
+ 0x31, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSMONTHNAME2[] = {
+ 0x32, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSMONTHNAME3[] = {
+ 0x33, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSMONTHNAME4[] = {
+ 0x34, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSMONTHNAME5[] = {
+ 0x35, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSMONTHNAME6[] = {
+ 0x36, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSMONTHNAME7[] = {
+ 0x37, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSMONTHNAME8[] = {
+ 0x38, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSMONTHNAME9[] = {
+ 0x39, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSMONTHNAME10[] = {
+ 0x31, 0x30, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSMONTHNAME11[] = {
+ 0x31, 0x31, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSMONTHNAME12[] = {
+ 0x31, 0x32, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVMONTHNAME1[] = {
+ 0x31, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVMONTHNAME2[] = {
+ 0x32, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVMONTHNAME3[] = {
+ 0x33, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVMONTHNAME4[] = {
+ 0x34, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVMONTHNAME5[] = {
+ 0x35, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVMONTHNAME6[] = {
+ 0x36, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVMONTHNAME7[] = {
+ 0x37, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVMONTHNAME8[] = {
+ 0x38, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVMONTHNAME9[] = {
+ 0x39, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVMONTHNAME10[] = {
+ 0x31, 0x30, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVMONTHNAME11[] = {
+ 0x31, 0x31, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSABBREVMONTHNAME12[] = {
+ 0x31, 0x32, 0xbf, 0xf9
+};
+
+static unsigned char NLSALLOC(0412) rgbSNEGATIVESIGN[] = {
+ '-'
+};
+
+static unsigned char NLSALLOC(0412) rgbIPOSSIGNPOSN[] = {
+ '3'
+};
+
+static unsigned char NLSALLOC(0412) rgbINEGSIGNPOSN[] = {
+ '3'
+};
+
+static unsigned char NLSALLOC(0412) rgbIPOSSYMPRECEDES[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0412) rgbIPOSSEPBYSPACE[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0412) rgbINEGSYMPRECEDES[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0412) rgbINEGSEPBYSPACE[] = {
+ '0'
+};
+
+#define LCINFODAT(X) { DIM(X), (X) }
+LCINFO NLSALLOC(0412) g_rglcinfo0412[] = {
+ { 0, NULL}
+ , LCINFODAT(rgbILANGUAGE)
+ , LCINFODAT(rgbSLANGUAGE)
+ , LCINFODAT(rgbSABBREVLANGNAME)
+ , LCINFODAT(rgbSNATIVELANGNAME)
+ , LCINFODAT(rgbICOUNTRY)
+ , LCINFODAT(rgbSCOUNTRY)
+ , LCINFODAT(rgbSABBREVCTRYNAME)
+ , LCINFODAT(rgbSNATIVECTRYNAME)
+ , LCINFODAT(rgbIDEFAULTLANGUAGE)
+ , LCINFODAT(rgbIDEFAULTCOUNTRY)
+ , LCINFODAT(rgbIDEFAULTCODEPAGE)
+ , LCINFODAT(rgbSLIST)
+ , LCINFODAT(rgbIMEASURE)
+ , LCINFODAT(rgbSDECIMAL)
+ , LCINFODAT(rgbSTHOUSAND)
+ , LCINFODAT(rgbSGROUPING)
+ , LCINFODAT(rgbIDIGITS)
+ , LCINFODAT(rgbILZERO)
+ , LCINFODAT(rgbSNATIVEDIGITS)
+ , LCINFODAT(rgbSCURRENCY)
+ , LCINFODAT(rgbSINTLSYMBOL)
+ , LCINFODAT(rgbSMONDECIMALSEP)
+ , LCINFODAT(rgbSMONTHOUSANDSEP)
+ , LCINFODAT(rgbSMONGROUPING)
+ , LCINFODAT(rgbICURRDIGITS)
+ , LCINFODAT(rgbIINTLCURRDIGITS)
+ , LCINFODAT(rgbICURRENCY)
+ , LCINFODAT(rgbINEGCURR)
+ , LCINFODAT(rgbSDATE)
+ , LCINFODAT(rgbSTIME)
+ , LCINFODAT(rgbSSHORTDATE)
+ , LCINFODAT(rgbSLONGDATE)
+ , LCINFODAT(rgbIDATE)
+ , LCINFODAT(rgbILDATE)
+ , LCINFODAT(rgbITIME)
+ , LCINFODAT(rgbICENTURY)
+ , LCINFODAT(rgbITLZERO)
+ , LCINFODAT(rgbIDAYLZERO)
+ , LCINFODAT(rgbIMONLZERO)
+ , LCINFODAT(rgbS1159)
+ , LCINFODAT(rgbS2359)
+ , LCINFODAT(rgbSDAYNAME1)
+ , LCINFODAT(rgbSDAYNAME2)
+ , LCINFODAT(rgbSDAYNAME3)
+ , LCINFODAT(rgbSDAYNAME4)
+ , LCINFODAT(rgbSDAYNAME5)
+ , LCINFODAT(rgbSDAYNAME6)
+ , LCINFODAT(rgbSDAYNAME7)
+ , LCINFODAT(rgbSABBREVDAYNAME1)
+ , LCINFODAT(rgbSABBREVDAYNAME2)
+ , LCINFODAT(rgbSABBREVDAYNAME3)
+ , LCINFODAT(rgbSABBREVDAYNAME4)
+ , LCINFODAT(rgbSABBREVDAYNAME5)
+ , LCINFODAT(rgbSABBREVDAYNAME6)
+ , LCINFODAT(rgbSABBREVDAYNAME7)
+ , LCINFODAT(rgbSMONTHNAME1)
+ , LCINFODAT(rgbSMONTHNAME2)
+ , LCINFODAT(rgbSMONTHNAME3)
+ , LCINFODAT(rgbSMONTHNAME4)
+ , LCINFODAT(rgbSMONTHNAME5)
+ , LCINFODAT(rgbSMONTHNAME6)
+ , LCINFODAT(rgbSMONTHNAME7)
+ , LCINFODAT(rgbSMONTHNAME8)
+ , LCINFODAT(rgbSMONTHNAME9)
+ , LCINFODAT(rgbSMONTHNAME10)
+ , LCINFODAT(rgbSMONTHNAME11)
+ , LCINFODAT(rgbSMONTHNAME12)
+ , LCINFODAT(rgbSABBREVMONTHNAME1)
+ , LCINFODAT(rgbSABBREVMONTHNAME2)
+ , LCINFODAT(rgbSABBREVMONTHNAME3)
+ , LCINFODAT(rgbSABBREVMONTHNAME4)
+ , LCINFODAT(rgbSABBREVMONTHNAME5)
+ , LCINFODAT(rgbSABBREVMONTHNAME6)
+ , LCINFODAT(rgbSABBREVMONTHNAME7)
+ , LCINFODAT(rgbSABBREVMONTHNAME8)
+ , LCINFODAT(rgbSABBREVMONTHNAME9)
+ , LCINFODAT(rgbSABBREVMONTHNAME10)
+ , LCINFODAT(rgbSABBREVMONTHNAME11)
+ , LCINFODAT(rgbSABBREVMONTHNAME12)
+ , { 0, NULL }
+ , LCINFODAT(rgbSNEGATIVESIGN)
+ , LCINFODAT(rgbIPOSSIGNPOSN)
+ , LCINFODAT(rgbINEGSIGNPOSN)
+ , LCINFODAT(rgbIPOSSYMPRECEDES)
+ , LCINFODAT(rgbIPOSSEPBYSPACE)
+ , LCINFODAT(rgbINEGSYMPRECEDES)
+ , LCINFODAT(rgbINEGSEPBYSPACE)
+ , LCINFODAT(rgbSENGCOUNTRY)
+ , LCINFODAT(rgbSENGLANGUAGE)
+#if defined(VBA2)
+ , LCINFODAT(rgbIFIRSTDAYOFWEEK)
+ , LCINFODAT(rgbIFIRSTWEEKOFYEAR)
+ , LCINFODAT(rgbIDEFAULTANSICODEPAGE)
+ , LCINFODAT(rgbINEGNUMBER)
+ , LCINFODAT(rgbSTIMEFORMAT)
+ , LCINFODAT(rgbITIMEMARKPOSN)
+ , LCINFODAT(rgbICALENDARTYPE)
+ , LCINFODAT(rgbIOPTIONALCALENDAR)
+ , { 0, NULL }
+ , { 0, NULL }
+#endif
+};
+#undef LCINFODAT
+
+
+#if 1
+STRINFO_KTP NLSALLOC(0412) g_strinfo0412 = {
+ rgsortweight
+ , rgmaptable
+ , rgtypetable
+ , DIM(rgsortweight)
+ , DIM(rgmaptable)
+ , DIM(rgtypetable)
+};
+#else
+STRINFO_KTP NLSALLOC(0412) g_strinfo0412 = {
+ (SORTWEIGHT FAR*) rgsortweight
+ , (MAPTABLE FAR*) rgmaptable
+ , (TYPETABLE FAR*) rgtypetable
+ , DIM(rgsortweight)
+ , DIM(rgmaptable)
+ , DIM(rgtypetable)
+};
+#endif
diff --git a/private/oleauto/src/dispatch/win16/0413.c b/private/oleauto/src/dispatch/win16/0413.c
new file mode 100644
index 000000000..6ea67bf2d
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0413.c
@@ -0,0 +1,526 @@
+/****************************************************************************
+* 0413.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Dutch - Netherlands
+*
+* LCID = 0x0413
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:37:03 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0409[256]; // from 0409:English - United States
+extern EXPANSION rgexp_0409[7];
+extern WORD rgwCType12_0409[256];
+extern WORD rgwCType3_0409[256];
+extern BYTE rgbUCase_0409[256];
+extern BYTE rgbLCase_0409[256];
+
+static BYTE NLSALLOC(0413) rgbILANGUAGE[] = { /* "0413" */
+ 0x30, 0x34, 0x31, 0x33
+};
+
+static BYTE NLSALLOC(0413) rgbSLANGUAGE[] = { /* "Dutch" */
+ 0x44, 0x75, 0x74, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVLANGNAME[] = { /* "NLD" */
+ 0x4e, 0x4c, 0x44
+};
+
+static BYTE NLSALLOC(0413) rgbSNATIVELANGNAME[] = { /* "Nederlands" */
+ 0x4e, 0x65, 0x64, 0x65, 0x72, 0x6c, 0x61, 0x6e
+ , 0x64, 0x73
+};
+
+static BYTE NLSALLOC(0413) rgbICOUNTRY[] = { /* "31" */
+ 0x33, 0x31
+};
+
+static BYTE NLSALLOC(0413) rgbSCOUNTRY[] = { /* "Netherlands" */
+ 0x4e, 0x65, 0x74, 0x68, 0x65, 0x72, 0x6c, 0x61
+ , 0x6e, 0x64, 0x73
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVCTRYNAME[] = { /* "NLD" */
+ 0x4e, 0x4c, 0x44
+};
+
+static BYTE NLSALLOC(0413) rgbSNATIVECTRYNAME[] = { /* "Nederland" */
+ 0x4e, 0x65, 0x64, 0x65, 0x72, 0x6c, 0x61, 0x6e
+ , 0x64
+};
+
+static BYTE NLSALLOC(0413) rgbIDEFAULTLANGUAGE[] = { /* "0413" */
+ 0x30, 0x34, 0x31, 0x33
+};
+
+static BYTE NLSALLOC(0413) rgbIDEFAULTCOUNTRY[] = { /* "31" */
+ 0x33, 0x31
+};
+
+static BYTE NLSALLOC(0413) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0413) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0413) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0413) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0413) rgbSTHOUSAND[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0413) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0413) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0413) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0413) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0413) rgbSCURRENCY[] = { /* "F" */
+ 0x46
+};
+
+static BYTE NLSALLOC(0413) rgbSINTLSYMBOL[] = { /* "NLG" */
+ 0x4e, 0x4c, 0x47
+};
+
+static BYTE NLSALLOC(0413) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0413) rgbSMONTHOUSANDSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0413) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0413) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0413) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0413) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0413) rgbINEGCURR[] = { /* "11" */
+ 0x31, 0x31
+};
+
+static BYTE NLSALLOC(0413) rgbSDATE[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0413) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0413) rgbSSHORTDATE[] = { /* "d-MM-yy" */
+ 0x64, 0x2d, 0x4d, 0x4d, 0x2d, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0413) rgbSLONGDATE[] = { /* "dddd d MMMM yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x20, 0x64, 0x20, 0x4d
+ , 0x4d, 0x4d, 0x4d, 0x20, 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0413) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0413) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0413) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0413) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0413) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0413) rgbIDAYLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0413) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0413) rgbSDAYNAME1[] = { /* "maandag" */
+ 0x6d, 0x61, 0x61, 0x6e, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0413) rgbSDAYNAME2[] = { /* "dinsdag" */
+ 0x64, 0x69, 0x6e, 0x73, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0413) rgbSDAYNAME3[] = { /* "woensdag" */
+ 0x77, 0x6f, 0x65, 0x6e, 0x73, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0413) rgbSDAYNAME4[] = { /* "donderdag" */
+ 0x64, 0x6f, 0x6e, 0x64, 0x65, 0x72, 0x64, 0x61
+ , 0x67
+};
+
+static BYTE NLSALLOC(0413) rgbSDAYNAME5[] = { /* "vrijdag" */
+ 0x76, 0x72, 0x69, 0x6a, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0413) rgbSDAYNAME6[] = { /* "zaterdag" */
+ 0x7a, 0x61, 0x74, 0x65, 0x72, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0413) rgbSDAYNAME7[] = { /* "zondag" */
+ 0x7a, 0x6f, 0x6e, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVDAYNAME1[] = { /* "ma" */
+ 0x6d, 0x61
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVDAYNAME2[] = { /* "di" */
+ 0x64, 0x69
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVDAYNAME3[] = { /* "wo" */
+ 0x77, 0x6f
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVDAYNAME4[] = { /* "do" */
+ 0x64, 0x6f
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVDAYNAME5[] = { /* "vr" */
+ 0x76, 0x72
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVDAYNAME6[] = { /* "za" */
+ 0x7a, 0x61
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVDAYNAME7[] = { /* "zo" */
+ 0x7a, 0x6f
+};
+
+static BYTE NLSALLOC(0413) rgbSMONTHNAME1[] = { /* "januari" */
+ 0x6a, 0x61, 0x6e, 0x75, 0x61, 0x72, 0x69
+};
+
+static BYTE NLSALLOC(0413) rgbSMONTHNAME2[] = { /* "februari" */
+ 0x66, 0x65, 0x62, 0x72, 0x75, 0x61, 0x72, 0x69
+};
+
+static BYTE NLSALLOC(0413) rgbSMONTHNAME3[] = { /* "maart" */
+ 0x6d, 0x61, 0x61, 0x72, 0x74
+};
+
+static BYTE NLSALLOC(0413) rgbSMONTHNAME4[] = { /* "april" */
+ 0x61, 0x70, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(0413) rgbSMONTHNAME5[] = { /* "mei" */
+ 0x6d, 0x65, 0x69
+};
+
+static BYTE NLSALLOC(0413) rgbSMONTHNAME6[] = { /* "juni" */
+ 0x6a, 0x75, 0x6e, 0x69
+};
+
+static BYTE NLSALLOC(0413) rgbSMONTHNAME7[] = { /* "juli" */
+ 0x6a, 0x75, 0x6c, 0x69
+};
+
+static BYTE NLSALLOC(0413) rgbSMONTHNAME8[] = { /* "augustus" */
+ 0x61, 0x75, 0x67, 0x75, 0x73, 0x74, 0x75, 0x73
+};
+
+static BYTE NLSALLOC(0413) rgbSMONTHNAME9[] = { /* "september" */
+ 0x73, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x65
+ , 0x72
+};
+
+static BYTE NLSALLOC(0413) rgbSMONTHNAME10[] = { /* "oktober" */
+ 0x6f, 0x6b, 0x74, 0x6f, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0413) rgbSMONTHNAME11[] = { /* "november" */
+ 0x6e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0413) rgbSMONTHNAME12[] = { /* "december" */
+ 0x64, 0x65, 0x63, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVMONTHNAME1[] = { /* "jan" */
+ 0x6a, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVMONTHNAME2[] = { /* "feb" */
+ 0x66, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVMONTHNAME3[] = { /* "mrt" */
+ 0x6d, 0x72, 0x74
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVMONTHNAME4[] = { /* "apr" */
+ 0x61, 0x70, 0x72
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVMONTHNAME5[] = { /* "mei" */
+ 0x6d, 0x65, 0x69
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVMONTHNAME6[] = { /* "jun" */
+ 0x6a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVMONTHNAME7[] = { /* "jul" */
+ 0x6a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVMONTHNAME8[] = { /* "aug" */
+ 0x61, 0x75, 0x67
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVMONTHNAME9[] = { /* "sep" */
+ 0x73, 0x65, 0x70
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVMONTHNAME10[] = { /* "okt" */
+ 0x6f, 0x6b, 0x74
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVMONTHNAME11[] = { /* "nov" */
+ 0x6e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(0413) rgbSABBREVMONTHNAME12[] = { /* "dec" */
+ 0x64, 0x65, 0x63
+};
+
+static BYTE NLSALLOC(0413) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0413) rgbIPOSSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0413) rgbINEGSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0413) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0413) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0413) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0413) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0413) rgbSENGCOUNTRY[] = { /* "Netherlands" */
+ 0x4e, 0x65, 0x74, 0x68, 0x65, 0x72, 0x6c, 0x61
+ , 0x6e, 0x64, 0x73
+};
+
+static BYTE NLSALLOC(0413) rgbSENGLANGUAGE[] = { /* "Dutch" */
+ 0x44, 0x75, 0x74, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(0413) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0413) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0413) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0413) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0413) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0413) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0413) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0413) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0413) g_rglcinfo0413[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 5, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 10, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 11, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 9, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 1, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 2, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 7, rgbSSHORTDATE }
+ , { 16, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 7, rgbSDAYNAME1 }
+ , { 7, rgbSDAYNAME2 }
+ , { 8, rgbSDAYNAME3 }
+ , { 9, rgbSDAYNAME4 }
+ , { 7, rgbSDAYNAME5 }
+ , { 8, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 2, rgbSABBREVDAYNAME1 }
+ , { 2, rgbSABBREVDAYNAME2 }
+ , { 2, rgbSABBREVDAYNAME3 }
+ , { 2, rgbSABBREVDAYNAME4 }
+ , { 2, rgbSABBREVDAYNAME5 }
+ , { 2, rgbSABBREVDAYNAME6 }
+ , { 2, rgbSABBREVDAYNAME7 }
+ , { 7, rgbSMONTHNAME1 }
+ , { 8, rgbSMONTHNAME2 }
+ , { 5, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 8, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 11, rgbSENGCOUNTRY }
+ , { 5, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0413) g_strinfo0413 = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0414.c b/private/oleauto/src/dispatch/win16/0414.c
new file mode 100644
index 000000000..b6ce456b0
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0414.c
@@ -0,0 +1,526 @@
+/****************************************************************************
+* 0414.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Norwegian - Norway (Bokmål)
+*
+* LCID = 0x0414
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:57:45 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0406[256]; // from 0406:Danish - Denmark
+extern EXPANSION rgexp_0406[5];
+extern DIGRAPH rgdig_0406[5];
+extern WORD rgwCType12_0406[256];
+extern WORD rgwCType3_0406[256];
+extern BYTE rgbUCase_0406[256];
+extern BYTE rgbLCase_0406[256];
+
+static BYTE NLSALLOC(0414) rgbILANGUAGE[] = { /* "0414" */
+ 0x30, 0x34, 0x31, 0x34
+};
+
+static BYTE NLSALLOC(0414) rgbSLANGUAGE[] = { /* "Norwegian - Bokmal" */
+ 0x4e, 0x6f, 0x72, 0x77, 0x65, 0x67, 0x69, 0x61
+ , 0x6e, 0x20, 0x2d, 0x20, 0x42, 0x6f, 0x6b, 0x6d
+ , 0x61, 0x6c
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVLANGNAME[] = { /* "NOR" */
+ 0x4e, 0x4f, 0x52
+};
+
+static BYTE NLSALLOC(0414) rgbSNATIVELANGNAME[] = { /* "bokmål" */
+ 0x62, 0x6f, 0x6b, 0x6d, 0xe5, 0x6c
+};
+
+static BYTE NLSALLOC(0414) rgbICOUNTRY[] = { /* "47" */
+ 0x34, 0x37
+};
+
+static BYTE NLSALLOC(0414) rgbSCOUNTRY[] = { /* "Norway" */
+ 0x4e, 0x6f, 0x72, 0x77, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVCTRYNAME[] = { /* "NOR" */
+ 0x4e, 0x4f, 0x52
+};
+
+static BYTE NLSALLOC(0414) rgbSNATIVECTRYNAME[] = { /* "Norge" */
+ 0x4e, 0x6f, 0x72, 0x67, 0x65
+};
+
+static BYTE NLSALLOC(0414) rgbIDEFAULTLANGUAGE[] = { /* "0414" */
+ 0x30, 0x34, 0x31, 0x34
+};
+
+static BYTE NLSALLOC(0414) rgbIDEFAULTCOUNTRY[] = { /* "47" */
+ 0x34, 0x37
+};
+
+static BYTE NLSALLOC(0414) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0414) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0414) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0414) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0414) rgbSTHOUSAND[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(0414) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0414) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0414) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0414) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0414) rgbSCURRENCY[] = { /* "kr" */
+ 0x6b, 0x72
+};
+
+static BYTE NLSALLOC(0414) rgbSINTLSYMBOL[] = { /* "NOK" */
+ 0x4e, 0x4f, 0x4b
+};
+
+static BYTE NLSALLOC(0414) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0414) rgbSMONTHOUSANDSEP[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(0414) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0414) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0414) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0414) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0414) rgbINEGCURR[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0414) rgbSDATE[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0414) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0414) rgbSSHORTDATE[] = { /* "dd.MM.yy" */
+ 0x64, 0x64, 0x2e, 0x4d, 0x4d, 0x2e, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0414) rgbSLONGDATE[] = { /* "d. MMMM yyyy" */
+ 0x64, 0x2e, 0x20, 0x4d, 0x4d, 0x4d, 0x4d, 0x20
+ , 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0414) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0414) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0414) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0414) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0414) rgbITLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0414) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0414) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0414) rgbSDAYNAME1[] = { /* "mandag" */
+ 0x6d, 0x61, 0x6e, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0414) rgbSDAYNAME2[] = { /* "tirsdag" */
+ 0x74, 0x69, 0x72, 0x73, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0414) rgbSDAYNAME3[] = { /* "onsdag" */
+ 0x6f, 0x6e, 0x73, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0414) rgbSDAYNAME4[] = { /* "torsdag" */
+ 0x74, 0x6f, 0x72, 0x73, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0414) rgbSDAYNAME5[] = { /* "fredag" */
+ 0x66, 0x72, 0x65, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0414) rgbSDAYNAME6[] = { /* "lørdag" */
+ 0x6c, 0xf8, 0x72, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0414) rgbSDAYNAME7[] = { /* "søndag" */
+ 0x73, 0xf8, 0x6e, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVDAYNAME1[] = { /* "ma" */
+ 0x6d, 0x61
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVDAYNAME2[] = { /* "ti" */
+ 0x74, 0x69
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVDAYNAME3[] = { /* "on" */
+ 0x6f, 0x6e
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVDAYNAME4[] = { /* "to" */
+ 0x74, 0x6f
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVDAYNAME5[] = { /* "fr" */
+ 0x66, 0x72
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVDAYNAME6[] = { /* "lø" */
+ 0x6c, 0xf8
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVDAYNAME7[] = { /* "sø" */
+ 0x73, 0xf8
+};
+
+static BYTE NLSALLOC(0414) rgbSMONTHNAME1[] = { /* "januar" */
+ 0x6a, 0x61, 0x6e, 0x75, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0414) rgbSMONTHNAME2[] = { /* "februar" */
+ 0x66, 0x65, 0x62, 0x72, 0x75, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0414) rgbSMONTHNAME3[] = { /* "mars" */
+ 0x6d, 0x61, 0x72, 0x73
+};
+
+static BYTE NLSALLOC(0414) rgbSMONTHNAME4[] = { /* "april" */
+ 0x61, 0x70, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(0414) rgbSMONTHNAME5[] = { /* "mai" */
+ 0x6d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(0414) rgbSMONTHNAME6[] = { /* "juni" */
+ 0x6a, 0x75, 0x6e, 0x69
+};
+
+static BYTE NLSALLOC(0414) rgbSMONTHNAME7[] = { /* "juli" */
+ 0x6a, 0x75, 0x6c, 0x69
+};
+
+static BYTE NLSALLOC(0414) rgbSMONTHNAME8[] = { /* "august" */
+ 0x61, 0x75, 0x67, 0x75, 0x73, 0x74
+};
+
+static BYTE NLSALLOC(0414) rgbSMONTHNAME9[] = { /* "september" */
+ 0x73, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x65
+ , 0x72
+};
+
+static BYTE NLSALLOC(0414) rgbSMONTHNAME10[] = { /* "oktober" */
+ 0x6f, 0x6b, 0x74, 0x6f, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0414) rgbSMONTHNAME11[] = { /* "november" */
+ 0x6e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0414) rgbSMONTHNAME12[] = { /* "desember" */
+ 0x64, 0x65, 0x73, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVMONTHNAME1[] = { /* "jan" */
+ 0x6a, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVMONTHNAME2[] = { /* "feb" */
+ 0x66, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVMONTHNAME3[] = { /* "mar" */
+ 0x6d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVMONTHNAME4[] = { /* "apr" */
+ 0x61, 0x70, 0x72
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVMONTHNAME5[] = { /* "mai" */
+ 0x6d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVMONTHNAME6[] = { /* "jun" */
+ 0x6a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVMONTHNAME7[] = { /* "jul" */
+ 0x6a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVMONTHNAME8[] = { /* "aug" */
+ 0x61, 0x75, 0x67
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVMONTHNAME9[] = { /* "sep" */
+ 0x73, 0x65, 0x70
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVMONTHNAME10[] = { /* "okt" */
+ 0x6f, 0x6b, 0x74
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVMONTHNAME11[] = { /* "nov" */
+ 0x6e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(0414) rgbSABBREVMONTHNAME12[] = { /* "des" */
+ 0x64, 0x65, 0x73
+};
+
+static BYTE NLSALLOC(0414) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0414) rgbIPOSSIGNPOSN[] = { /* "4" */
+ 0x34
+};
+
+static BYTE NLSALLOC(0414) rgbINEGSIGNPOSN[] = { /* "4" */
+ 0x34
+};
+
+static BYTE NLSALLOC(0414) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0414) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0414) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0414) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0414) rgbSENGCOUNTRY[] = { /* "Norway" */
+ 0x4e, 0x6f, 0x72, 0x77, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0414) rgbSENGLANGUAGE[] = { /* "Norwegian (Bokmål)" */
+ 0x4e, 0x6f, 0x72, 0x77, 0x65, 0x67, 0x69, 0x61
+ , 0x6e, 0x20, 0x28, 0x42, 0x6f, 0x6b, 0x6d, 0xe5
+ , 0x6c, 0x29
+};
+
+static BYTE NLSALLOC(0414) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0414) rgbIFIRSTWEEKOFYEAR[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0414) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0414) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0414) rgbSTIMEFORMAT[] = { /* "HH:mm:ss" */
+ 0x48, 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0414) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0414) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0414) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0414) g_rglcinfo0414[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 18, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 6, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 6, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 5, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 2, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 12, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 6, rgbSDAYNAME1 }
+ , { 7, rgbSDAYNAME2 }
+ , { 6, rgbSDAYNAME3 }
+ , { 7, rgbSDAYNAME4 }
+ , { 6, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 2, rgbSABBREVDAYNAME1 }
+ , { 2, rgbSABBREVDAYNAME2 }
+ , { 2, rgbSABBREVDAYNAME3 }
+ , { 2, rgbSABBREVDAYNAME4 }
+ , { 2, rgbSABBREVDAYNAME5 }
+ , { 2, rgbSABBREVDAYNAME6 }
+ , { 2, rgbSABBREVDAYNAME7 }
+ , { 6, rgbSMONTHNAME1 }
+ , { 7, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 6, rgbSENGCOUNTRY }
+ , { 18, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 8, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0414) g_strinfo0414 = {
+ rgbUCase_0406
+ , rgbLCase_0406
+ , rgwCType12_0406
+ , rgwCType3_0406
+ , rgwSort_0406
+ , rgexp_0406
+ , rgdig_0406
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0415.c b/private/oleauto/src/dispatch/win16/0415.c
new file mode 100644
index 000000000..7aca6b5cd
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0415.c
@@ -0,0 +1,695 @@
+/****************************************************************************
+* 0415.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Polish - Poland
+*
+* LCID = 0x0415
+*
+* CodePage = 1250
+*
+* Generated: Thu Dec 01 18:09:30 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+WORD NLSALLOC(0415) rgwSort_0415[256] = {
+ 0x0000, 0xc007, 0xc008, 0xc009, 0xc00a, 0xc00b, 0xc00c, 0xc00d
+ , 0xc00e, 0x402f, 0x4030, 0x4031, 0x4032, 0x4033, 0xc00f, 0xc010
+ , 0xc011, 0xc012, 0xc013, 0xc014, 0xc015, 0xc016, 0xc017, 0xc018
+ , 0xc019, 0xc01a, 0xc01b, 0xc01c, 0xc01d, 0xc01e, 0xc01f, 0xc020
+ , 0x402d, 0x4034, 0x4035, 0x4036, 0x4037, 0x4038, 0x4039, 0xc028
+ , 0x403a, 0x403b, 0x403c, 0x405e, 0x403d, 0xc029, 0x403e, 0x403f
+ , 0x0075, 0x0076, 0x0077, 0x0078, 0x0079, 0x007a, 0x007b, 0x007c
+ , 0x007d, 0x007e, 0x4040, 0x4041, 0x405f, 0x4060, 0x4061, 0x4042
+ , 0x4043, 0x087f, 0x0881, 0x0882, 0x0884, 0x0885, 0x0887, 0x0888
+ , 0x0889, 0x088a, 0x088b, 0x088c, 0x088d, 0x088f, 0x0890, 0x0892
+ , 0x0894, 0x0895, 0x0896, 0x0897, 0x0899, 0x089b, 0x089c, 0x089d
+ , 0x089e, 0x089f, 0x08a0, 0x4044, 0x4045, 0x4046, 0x4047, 0x4048
+ , 0x4049, 0x007f, 0x0081, 0x0082, 0x0084, 0x0085, 0x0087, 0x0088
+ , 0x0089, 0x008a, 0x008b, 0x008c, 0x008d, 0x008f, 0x0090, 0x0092
+ , 0x0094, 0x0095, 0x0096, 0x0097, 0x0099, 0x009b, 0x009c, 0x009d
+ , 0x009e, 0x009f, 0x00a0, 0x404a, 0x404b, 0x404c, 0x404d, 0xc021
+ , 0xc022, 0xc023, 0x4058, 0xc024, 0x405b, 0x4073, 0x4070, 0x4071
+ , 0xc025, 0x4074, 0x0897, 0x405c, 0x0898, 0x0999, 0x09a0, 0x08a1
+ , 0xc026, 0x4056, 0x4057, 0x4059, 0x405a, 0x4072, 0xc02b, 0xc02c
+ , 0xc027, 0x089a, 0x0097, 0x405d, 0x0098, 0x0199, 0x01a0, 0x00a1
+ , 0x402e, 0x4052, 0x4152, 0x088e, 0x4067, 0x0880, 0x404e, 0x4068
+ , 0x404f, 0x4069, 0x0997, 0x4063, 0x406a, 0xc02a, 0x406b, 0x08a2
+ , 0x406c, 0x4062, 0x4054, 0x008e, 0x4050, 0x406d, 0x406e, 0x406f
+ , 0x4051, 0x0080, 0x0197, 0x4064, 0x0a8d, 0x4055, 0x028d, 0x00a2
+ , 0x0996, 0x097f, 0x0a7f, 0x0c7f, 0x0b7f, 0x098d, 0x0883, 0x0a82
+ , 0x0982, 0x0985, 0x0886, 0x0a85, 0x0b85, 0x098a, 0x0a8a, 0x0984
+ , 0x0a84, 0x0891, 0x0890, 0x0893, 0x0992, 0x0b92, 0x0a92, 0x4065
+ , 0x0a96, 0x0b9b, 0x099b, 0x0c9b, 0x0a9b, 0x099f, 0x0a99, 0x0005
+ , 0x0196, 0x017f, 0x027f, 0x047f, 0x037f, 0x018d, 0x0083, 0x0282
+ , 0x0182, 0x0185, 0x0086, 0x0285, 0x0385, 0x018a, 0x028a, 0x0184
+ , 0x0284, 0x0091, 0x0090, 0x0093, 0x0192, 0x0392, 0x0292, 0x4066
+ , 0x0296, 0x039b, 0x019b, 0x049b, 0x029b, 0x019f, 0x0299, 0x4053
+};
+
+EXPANSION NLSALLOC(0415) rgexp_0415[1] = {
+ { 0x0097, 0x0097 }
+};
+
+WORD NLSALLOC(0415) rgwCType12_0415[256] = {
+ 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x9068, 0x0028, 0x0028, 0x0028, 0x0028, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0xa048, 0xb010, 0xb010, 0x5010, 0x5010, 0x5010, 0x1010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0x5010, 0x7010, 0x5010, 0x4010, 0x4010
+ , 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084
+ , 0x3084, 0x3084, 0x7010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010, 0x0020
+ , 0x0020, 0x0020, 0xb010, 0x0020, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x0020, 0x5010, 0x1101, 0xb010, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x0020, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x0020, 0xb010, 0x1102, 0xb010, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0xa048, 0x1010, 0x1010, 0x1101, 0x5010, 0x1101, 0xb010, 0xb010
+ , 0xb010, 0xb010, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0x1101
+ , 0x5010, 0x5010, 0x1010, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x1102, 0x1102, 0xb010, 0x1101, 0x1010, 0x1102, 0x1102
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0xb010
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0xb010
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1010
+};
+
+WORD NLSALLOC(0415) rgwCType3_0415[256] = {
+ 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0008, 0x0008, 0x0008, 0x0008, 0x0008, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0048, 0x0048, 0x0448, 0x0048, 0x0448, 0x0048, 0x0048, 0x0440
+ , 0x0048, 0x0048, 0x0048, 0x0048, 0x0048, 0x0440, 0x0048, 0x0448
+ , 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040
+ , 0x0040, 0x0040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0048, 0x0048
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0448, 0x0048, 0x0448, 0x0448
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0000
+ , 0x0000, 0x0000, 0x0008, 0x0000, 0x0008, 0x0008, 0x0008, 0x0008
+ , 0x0000, 0x0008, 0x8003, 0x0008, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x0000, 0x0088, 0x0088, 0x0088, 0x0088, 0x0008, 0x0400, 0x0400
+ , 0x0000, 0x0000, 0x8003, 0x0008, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x0008, 0x0401, 0x0408, 0x8003, 0x0008, 0x8003, 0x0048, 0x0008
+ , 0x0408, 0x0008, 0x8003, 0x0008, 0x0048, 0x0408, 0x0008, 0x8003
+ , 0x0008, 0x0008, 0x0408, 0x8003, 0x0408, 0x0008, 0x0008, 0x0008
+ , 0x0408, 0x8003, 0x8003, 0x0008, 0x8003, 0x0408, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0408
+};
+
+BYTE NLSALLOC(0415) rgbUCase_0415[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x8a, 0x9b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xa3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xa5, 0xaa, 0xbb, 0xbc, 0xbd, 0xbc, 0xaf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xf7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xff
+};
+
+BYTE NLSALLOC(0415) rgbLCase_0415[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x9a, 0x8b, 0x9c, 0x9d, 0x9e, 0x9f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f
+ , 0xa0, 0xa1, 0xa2, 0xb3, 0xa4, 0xb9, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xba, 0xab, 0xac, 0xad, 0xae, 0xbf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbe, 0xbd, 0xbe, 0xbf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xd7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xdf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
+};
+
+static BYTE NLSALLOC(0415) rgbILANGUAGE[] = { /* "0415" */
+ 0x30, 0x34, 0x31, 0x35
+};
+
+static BYTE NLSALLOC(0415) rgbSLANGUAGE[] = { /* "Polish" */
+ 0x50, 0x6f, 0x6c, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVLANGNAME[] = { /* "PLK" */
+ 0x50, 0x4c, 0x4b
+};
+
+static BYTE NLSALLOC(0415) rgbSNATIVELANGNAME[] = { /* "polski" */
+ 0x70, 0x6f, 0x6c, 0x73, 0x6b, 0x69
+};
+
+static BYTE NLSALLOC(0415) rgbICOUNTRY[] = { /* "48" */
+ 0x34, 0x38
+};
+
+static BYTE NLSALLOC(0415) rgbSCOUNTRY[] = { /* "Poland" */
+ 0x50, 0x6f, 0x6c, 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVCTRYNAME[] = { /* "POL" */
+ 0x50, 0x4f, 0x4c
+};
+
+static BYTE NLSALLOC(0415) rgbSNATIVECTRYNAME[] = { /* "Polska" */
+ 0x50, 0x6f, 0x6c, 0x73, 0x6b, 0x61
+};
+
+static BYTE NLSALLOC(0415) rgbIDEFAULTLANGUAGE[] = { /* "0415" */
+ 0x30, 0x34, 0x31, 0x35
+};
+
+static BYTE NLSALLOC(0415) rgbIDEFAULTCOUNTRY[] = { /* "48" */
+ 0x34, 0x38
+};
+
+static BYTE NLSALLOC(0415) rgbIDEFAULTCODEPAGE[] = { /* "852" */
+ 0x38, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0415) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0415) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0415) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0415) rgbSTHOUSAND[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(0415) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0415) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0415) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0415) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0415) rgbSCURRENCY[] = { /* "z\x0142" */
+ 0x7a, 0xb3
+};
+
+static BYTE NLSALLOC(0415) rgbSINTLSYMBOL[] = { /* "PLZ" */
+ 0x50, 0x4c, 0x5a
+};
+
+static BYTE NLSALLOC(0415) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0415) rgbSMONTHOUSANDSEP[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(0415) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0415) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0415) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0415) rgbICURRENCY[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0415) rgbINEGCURR[] = { /* "8" */
+ 0x38
+};
+
+static BYTE NLSALLOC(0415) rgbSDATE[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0415) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0415) rgbSSHORTDATE[] = { /* "d.MM.yy" */
+ 0x64, 0x2e, 0x4d, 0x4d, 0x2e, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0415) rgbSLONGDATE[] = { /* "d MMMM yyyy" */
+ 0x64, 0x20, 0x4d, 0x4d, 0x4d, 0x4d, 0x20, 0x79
+ , 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0415) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0415) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0415) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0415) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0415) rgbITLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0415) rgbIDAYLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0415) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0415) rgbSDAYNAME1[] = { /* "poniedzia\x0142ek" */
+ 0x70, 0x6f, 0x6e, 0x69, 0x65, 0x64, 0x7a, 0x69
+ , 0x61, 0xb3, 0x65, 0x6b
+};
+
+static BYTE NLSALLOC(0415) rgbSDAYNAME2[] = { /* "wtorek" */
+ 0x77, 0x74, 0x6f, 0x72, 0x65, 0x6b
+};
+
+static BYTE NLSALLOC(0415) rgbSDAYNAME3[] = { /* "\x015broda" */
+ 0x9c, 0x72, 0x6f, 0x64, 0x61
+};
+
+static BYTE NLSALLOC(0415) rgbSDAYNAME4[] = { /* "czwartek" */
+ 0x63, 0x7a, 0x77, 0x61, 0x72, 0x74, 0x65, 0x6b
+};
+
+static BYTE NLSALLOC(0415) rgbSDAYNAME5[] = { /* "pi\x0105tek" */
+ 0x70, 0x69, 0xb9, 0x74, 0x65, 0x6b
+};
+
+static BYTE NLSALLOC(0415) rgbSDAYNAME6[] = { /* "sobota" */
+ 0x73, 0x6f, 0x62, 0x6f, 0x74, 0x61
+};
+
+static BYTE NLSALLOC(0415) rgbSDAYNAME7[] = { /* "niedziela" */
+ 0x6e, 0x69, 0x65, 0x64, 0x7a, 0x69, 0x65, 0x6c
+ , 0x61
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVDAYNAME1[] = { /* "Pn." */
+ 0x50, 0x6e, 0x2e
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVDAYNAME2[] = { /* "Wt." */
+ 0x57, 0x74, 0x2e
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVDAYNAME3[] = { /* "\x015ar." */
+ 0x8c, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVDAYNAME4[] = { /* "Cz." */
+ 0x43, 0x7a, 0x2e
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVDAYNAME5[] = { /* "Pt." */
+ 0x50, 0x74, 0x2e
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVDAYNAME6[] = { /* "So." */
+ 0x53, 0x6f, 0x2e
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVDAYNAME7[] = { /* "N." */
+ 0x4e, 0x2e
+};
+
+static BYTE NLSALLOC(0415) rgbSMONTHNAME1[] = { /* "stycze\x0144" */
+ 0x73, 0x74, 0x79, 0x63, 0x7a, 0x65, 0xf1
+};
+
+static BYTE NLSALLOC(0415) rgbSMONTHNAME2[] = { /* "luty" */
+ 0x6c, 0x75, 0x74, 0x79
+};
+
+static BYTE NLSALLOC(0415) rgbSMONTHNAME3[] = { /* "marzec" */
+ 0x6d, 0x61, 0x72, 0x7a, 0x65, 0x63
+};
+
+static BYTE NLSALLOC(0415) rgbSMONTHNAME4[] = { /* "kwiecie\x0144" */
+ 0x6b, 0x77, 0x69, 0x65, 0x63, 0x69, 0x65, 0xf1
+};
+
+static BYTE NLSALLOC(0415) rgbSMONTHNAME5[] = { /* "maj" */
+ 0x6d, 0x61, 0x6a
+};
+
+static BYTE NLSALLOC(0415) rgbSMONTHNAME6[] = { /* "czerwiec" */
+ 0x63, 0x7a, 0x65, 0x72, 0x77, 0x69, 0x65, 0x63
+};
+
+static BYTE NLSALLOC(0415) rgbSMONTHNAME7[] = { /* "lipiec" */
+ 0x6c, 0x69, 0x70, 0x69, 0x65, 0x63
+};
+
+static BYTE NLSALLOC(0415) rgbSMONTHNAME8[] = { /* "sierpie\x0144" */
+ 0x73, 0x69, 0x65, 0x72, 0x70, 0x69, 0x65, 0xf1
+};
+
+static BYTE NLSALLOC(0415) rgbSMONTHNAME9[] = { /* "wrzesie\x0144" */
+ 0x77, 0x72, 0x7a, 0x65, 0x73, 0x69, 0x65, 0xf1
+};
+
+static BYTE NLSALLOC(0415) rgbSMONTHNAME10[] = { /* "pa\x017adziernik" */
+ 0x70, 0x61, 0x9f, 0x64, 0x7a, 0x69, 0x65, 0x72
+ , 0x6e, 0x69, 0x6b
+};
+
+static BYTE NLSALLOC(0415) rgbSMONTHNAME11[] = { /* "listopad" */
+ 0x6c, 0x69, 0x73, 0x74, 0x6f, 0x70, 0x61, 0x64
+};
+
+static BYTE NLSALLOC(0415) rgbSMONTHNAME12[] = { /* "grudzie\x0144" */
+ 0x67, 0x72, 0x75, 0x64, 0x7a, 0x69, 0x65, 0xf1
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVMONTHNAME1[] = { /* "I" */
+ 0x49
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVMONTHNAME2[] = { /* "II" */
+ 0x49, 0x49
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVMONTHNAME3[] = { /* "III" */
+ 0x49, 0x49, 0x49
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVMONTHNAME4[] = { /* "IV" */
+ 0x49, 0x56
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVMONTHNAME5[] = { /* "V" */
+ 0x56
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVMONTHNAME6[] = { /* "VI" */
+ 0x56, 0x49
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVMONTHNAME7[] = { /* "VII" */
+ 0x56, 0x49, 0x49
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVMONTHNAME8[] = { /* "VIII" */
+ 0x56, 0x49, 0x49, 0x49
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVMONTHNAME9[] = { /* "IX" */
+ 0x49, 0x58
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVMONTHNAME10[] = { /* "X" */
+ 0x58
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVMONTHNAME11[] = { /* "XI" */
+ 0x58, 0x49
+};
+
+static BYTE NLSALLOC(0415) rgbSABBREVMONTHNAME12[] = { /* "XII" */
+ 0x58, 0x49, 0x49
+};
+
+static BYTE NLSALLOC(0415) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0415) rgbIPOSSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0415) rgbINEGSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0415) rgbIPOSSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0415) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0415) rgbINEGSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0415) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0415) rgbSENGCOUNTRY[] = { /* "Poland" */
+ 0x50, 0x6f, 0x6c, 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(0415) rgbSENGLANGUAGE[] = { /* "Polish" */
+ 0x50, 0x6f, 0x6c, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(0415) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0415) rgbIFIRSTWEEKOFYEAR[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0415) rgbIDEFAULTANSICODEPAGE[] = { /* "1250" */
+ 0x31, 0x32, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0415) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0415) rgbSTIMEFORMAT[] = { /* "HH:mm:ss" */
+ 0x48, 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0415) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0415) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0415) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0415) g_rglcinfo0415[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 6, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 6, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 6, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 2, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 7, rgbSSHORTDATE }
+ , { 11, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 12, rgbSDAYNAME1 }
+ , { 6, rgbSDAYNAME2 }
+ , { 5, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 6, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 9, rgbSDAYNAME7 }
+ , { 3, rgbSABBREVDAYNAME1 }
+ , { 3, rgbSABBREVDAYNAME2 }
+ , { 3, rgbSABBREVDAYNAME3 }
+ , { 3, rgbSABBREVDAYNAME4 }
+ , { 3, rgbSABBREVDAYNAME5 }
+ , { 3, rgbSABBREVDAYNAME6 }
+ , { 2, rgbSABBREVDAYNAME7 }
+ , { 7, rgbSMONTHNAME1 }
+ , { 4, rgbSMONTHNAME2 }
+ , { 6, rgbSMONTHNAME3 }
+ , { 8, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 8, rgbSMONTHNAME6 }
+ , { 6, rgbSMONTHNAME7 }
+ , { 8, rgbSMONTHNAME8 }
+ , { 8, rgbSMONTHNAME9 }
+ , { 11, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 1, rgbSABBREVMONTHNAME1 }
+ , { 2, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 2, rgbSABBREVMONTHNAME4 }
+ , { 1, rgbSABBREVMONTHNAME5 }
+ , { 2, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 4, rgbSABBREVMONTHNAME8 }
+ , { 2, rgbSABBREVMONTHNAME9 }
+ , { 1, rgbSABBREVMONTHNAME10 }
+ , { 2, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 6, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 8, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0415) g_strinfo0415 = {
+ rgbUCase_0415
+ , rgbLCase_0415
+ , rgwCType12_0415
+ , rgwCType3_0415
+ , rgwSort_0415
+ , rgexp_0415
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0416.c b/private/oleauto/src/dispatch/win16/0416.c
new file mode 100644
index 000000000..a3e74adfb
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0416.c
@@ -0,0 +1,532 @@
+/****************************************************************************
+* 0416.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Portuguese - Brazil
+*
+* LCID = 0x0416
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:37:39 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0409[256]; // from 0409:English - United States
+extern EXPANSION rgexp_0409[7];
+extern WORD rgwCType12_0409[256];
+extern WORD rgwCType3_0409[256];
+extern BYTE rgbUCase_0409[256];
+extern BYTE rgbLCase_0409[256];
+
+static BYTE NLSALLOC(0416) rgbILANGUAGE[] = { /* "0416" */
+ 0x30, 0x34, 0x31, 0x36
+};
+
+static BYTE NLSALLOC(0416) rgbSLANGUAGE[] = { /* "Brazilian Portuguese" */
+ 0x42, 0x72, 0x61, 0x7a, 0x69, 0x6c, 0x69, 0x61
+ , 0x6e, 0x20, 0x50, 0x6f, 0x72, 0x74, 0x75, 0x67
+ , 0x75, 0x65, 0x73, 0x65
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVLANGNAME[] = { /* "PTB" */
+ 0x50, 0x54, 0x42
+};
+
+static BYTE NLSALLOC(0416) rgbSNATIVELANGNAME[] = { /* "Português" */
+ 0x50, 0x6f, 0x72, 0x74, 0x75, 0x67, 0x75, 0xea
+ , 0x73
+};
+
+static BYTE NLSALLOC(0416) rgbICOUNTRY[] = { /* "55" */
+ 0x35, 0x35
+};
+
+static BYTE NLSALLOC(0416) rgbSCOUNTRY[] = { /* "Brazil" */
+ 0x42, 0x72, 0x61, 0x7a, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVCTRYNAME[] = { /* "BRA" */
+ 0x42, 0x52, 0x41
+};
+
+static BYTE NLSALLOC(0416) rgbSNATIVECTRYNAME[] = { /* "Brasil" */
+ 0x42, 0x72, 0x61, 0x73, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(0416) rgbIDEFAULTLANGUAGE[] = { /* "0416" */
+ 0x30, 0x34, 0x31, 0x36
+};
+
+static BYTE NLSALLOC(0416) rgbIDEFAULTCOUNTRY[] = { /* "55" */
+ 0x35, 0x35
+};
+
+static BYTE NLSALLOC(0416) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0416) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0416) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0416) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0416) rgbSTHOUSAND[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0416) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0416) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0416) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0416) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0416) rgbSCURRENCY[] = { /* "Cr$" */
+ 0x43, 0x72, 0x24
+};
+
+static BYTE NLSALLOC(0416) rgbSINTLSYMBOL[] = { /* "BRR" */
+ 0x42, 0x52, 0x52
+};
+
+static BYTE NLSALLOC(0416) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0416) rgbSMONTHOUSANDSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0416) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0416) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0416) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0416) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0416) rgbINEGCURR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0416) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(0416) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0416) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0416) rgbSLONGDATE[] = { /* "dddd, d' de 'MMMM' de 'yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x2c, 0x20, 0x64, 0x27
+ , 0x20, 0x64, 0x65, 0x20, 0x27, 0x4d, 0x4d, 0x4d
+ , 0x4d, 0x27, 0x20, 0x64, 0x65, 0x20, 0x27, 0x79
+ , 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0416) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0416) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0416) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0416) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0416) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0416) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0416) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0416) rgbSDAYNAME1[] = { /* "segunda-feira" */
+ 0x73, 0x65, 0x67, 0x75, 0x6e, 0x64, 0x61, 0x2d
+ , 0x66, 0x65, 0x69, 0x72, 0x61
+};
+
+static BYTE NLSALLOC(0416) rgbSDAYNAME2[] = { /* "terça-feira" */
+ 0x74, 0x65, 0x72, 0xe7, 0x61, 0x2d, 0x66, 0x65
+ , 0x69, 0x72, 0x61
+};
+
+static BYTE NLSALLOC(0416) rgbSDAYNAME3[] = { /* "quarta-feira" */
+ 0x71, 0x75, 0x61, 0x72, 0x74, 0x61, 0x2d, 0x66
+ , 0x65, 0x69, 0x72, 0x61
+};
+
+static BYTE NLSALLOC(0416) rgbSDAYNAME4[] = { /* "quinta-feira" */
+ 0x71, 0x75, 0x69, 0x6e, 0x74, 0x61, 0x2d, 0x66
+ , 0x65, 0x69, 0x72, 0x61
+};
+
+static BYTE NLSALLOC(0416) rgbSDAYNAME5[] = { /* "sexta-feira" */
+ 0x73, 0x65, 0x78, 0x74, 0x61, 0x2d, 0x66, 0x65
+ , 0x69, 0x72, 0x61
+};
+
+static BYTE NLSALLOC(0416) rgbSDAYNAME6[] = { /* "sábado" */
+ 0x73, 0xe1, 0x62, 0x61, 0x64, 0x6f
+};
+
+static BYTE NLSALLOC(0416) rgbSDAYNAME7[] = { /* "domingo" */
+ 0x64, 0x6f, 0x6d, 0x69, 0x6e, 0x67, 0x6f
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVDAYNAME1[] = { /* "seg" */
+ 0x73, 0x65, 0x67
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVDAYNAME2[] = { /* "ter" */
+ 0x74, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVDAYNAME3[] = { /* "qua" */
+ 0x71, 0x75, 0x61
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVDAYNAME4[] = { /* "qui" */
+ 0x71, 0x75, 0x69
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVDAYNAME5[] = { /* "sex" */
+ 0x73, 0x65, 0x78
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVDAYNAME6[] = { /* "sáb" */
+ 0x73, 0xe1, 0x62
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVDAYNAME7[] = { /* "dom" */
+ 0x64, 0x6f, 0x6d
+};
+
+static BYTE NLSALLOC(0416) rgbSMONTHNAME1[] = { /* "janeiro" */
+ 0x6a, 0x61, 0x6e, 0x65, 0x69, 0x72, 0x6f
+};
+
+static BYTE NLSALLOC(0416) rgbSMONTHNAME2[] = { /* "fevereiro" */
+ 0x66, 0x65, 0x76, 0x65, 0x72, 0x65, 0x69, 0x72
+ , 0x6f
+};
+
+static BYTE NLSALLOC(0416) rgbSMONTHNAME3[] = { /* "março" */
+ 0x6d, 0x61, 0x72, 0xe7, 0x6f
+};
+
+static BYTE NLSALLOC(0416) rgbSMONTHNAME4[] = { /* "abril" */
+ 0x61, 0x62, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(0416) rgbSMONTHNAME5[] = { /* "maio" */
+ 0x6d, 0x61, 0x69, 0x6f
+};
+
+static BYTE NLSALLOC(0416) rgbSMONTHNAME6[] = { /* "junho" */
+ 0x6a, 0x75, 0x6e, 0x68, 0x6f
+};
+
+static BYTE NLSALLOC(0416) rgbSMONTHNAME7[] = { /* "julho" */
+ 0x6a, 0x75, 0x6c, 0x68, 0x6f
+};
+
+static BYTE NLSALLOC(0416) rgbSMONTHNAME8[] = { /* "agosto" */
+ 0x61, 0x67, 0x6f, 0x73, 0x74, 0x6f
+};
+
+static BYTE NLSALLOC(0416) rgbSMONTHNAME9[] = { /* "setembro" */
+ 0x73, 0x65, 0x74, 0x65, 0x6d, 0x62, 0x72, 0x6f
+};
+
+static BYTE NLSALLOC(0416) rgbSMONTHNAME10[] = { /* "outubro" */
+ 0x6f, 0x75, 0x74, 0x75, 0x62, 0x72, 0x6f
+};
+
+static BYTE NLSALLOC(0416) rgbSMONTHNAME11[] = { /* "novembro" */
+ 0x6e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x72, 0x6f
+};
+
+static BYTE NLSALLOC(0416) rgbSMONTHNAME12[] = { /* "dezembro" */
+ 0x64, 0x65, 0x7a, 0x65, 0x6d, 0x62, 0x72, 0x6f
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVMONTHNAME1[] = { /* "jan" */
+ 0x6a, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVMONTHNAME2[] = { /* "fev" */
+ 0x66, 0x65, 0x76
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVMONTHNAME3[] = { /* "mar" */
+ 0x6d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVMONTHNAME4[] = { /* "abr" */
+ 0x61, 0x62, 0x72
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVMONTHNAME5[] = { /* "mai" */
+ 0x6d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVMONTHNAME6[] = { /* "jun" */
+ 0x6a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVMONTHNAME7[] = { /* "jul" */
+ 0x6a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVMONTHNAME8[] = { /* "ago" */
+ 0x61, 0x67, 0x6f
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVMONTHNAME9[] = { /* "set" */
+ 0x73, 0x65, 0x74
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVMONTHNAME10[] = { /* "out" */
+ 0x6f, 0x75, 0x74
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVMONTHNAME11[] = { /* "nov" */
+ 0x6e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(0416) rgbSABBREVMONTHNAME12[] = { /* "dez" */
+ 0x64, 0x65, 0x7a
+};
+
+static BYTE NLSALLOC(0416) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0416) rgbIPOSSIGNPOSN[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0416) rgbINEGSIGNPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0416) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0416) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0416) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0416) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0416) rgbSENGCOUNTRY[] = { /* "Brazil" */
+ 0x42, 0x72, 0x61, 0x7a, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(0416) rgbSENGLANGUAGE[] = { /* "Portuguese" */
+ 0x50, 0x6f, 0x72, 0x74, 0x75, 0x67, 0x75, 0x65
+ , 0x73, 0x65
+};
+
+static BYTE NLSALLOC(0416) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0416) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0416) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0416) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0416) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0416) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0416) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0416) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0416) g_rglcinfo0416[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 20, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 9, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 6, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 6, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 3, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 27, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 13, rgbSDAYNAME1 }
+ , { 11, rgbSDAYNAME2 }
+ , { 12, rgbSDAYNAME3 }
+ , { 12, rgbSDAYNAME4 }
+ , { 11, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 7, rgbSDAYNAME7 }
+ , { 3, rgbSABBREVDAYNAME1 }
+ , { 3, rgbSABBREVDAYNAME2 }
+ , { 3, rgbSABBREVDAYNAME3 }
+ , { 3, rgbSABBREVDAYNAME4 }
+ , { 3, rgbSABBREVDAYNAME5 }
+ , { 3, rgbSABBREVDAYNAME6 }
+ , { 3, rgbSABBREVDAYNAME7 }
+ , { 7, rgbSMONTHNAME1 }
+ , { 9, rgbSMONTHNAME2 }
+ , { 5, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 4, rgbSMONTHNAME5 }
+ , { 5, rgbSMONTHNAME6 }
+ , { 5, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 8, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 6, rgbSENGCOUNTRY }
+ , { 10, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0416) g_strinfo0416 = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0419.c b/private/oleauto/src/dispatch/win16/0419.c
new file mode 100644
index 000000000..2b58f931b
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0419.c
@@ -0,0 +1,690 @@
+/****************************************************************************
+* 0419.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Russian - Russia
+*
+* LCID = 0x0419
+*
+* CodePage = 1251
+*
+* Generated: Thu Dec 01 18:17:20 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+WORD NLSALLOC(0419) rgwSort_0419[256] = {
+ 0x0000, 0xc007, 0xc008, 0xc009, 0xc00a, 0xc00b, 0xc00c, 0xc00d
+ , 0xc00e, 0x402b, 0x402c, 0x402d, 0x402e, 0x402f, 0xc00f, 0xc010
+ , 0xc011, 0xc012, 0xc013, 0xc014, 0xc015, 0xc016, 0xc017, 0xc018
+ , 0xc019, 0xc01a, 0xc01b, 0xc01c, 0xc01d, 0xc01e, 0xc01f, 0xc020
+ , 0x4029, 0x4030, 0x4031, 0x4032, 0x4033, 0x4034, 0x4035, 0xc024
+ , 0x4036, 0x4037, 0x4038, 0x4053, 0x4039, 0xc025, 0x403a, 0x403b
+ , 0x0068, 0x0069, 0x006a, 0x006b, 0x006c, 0x006d, 0x006e, 0x006f
+ , 0x0070, 0x0071, 0x403c, 0x403d, 0x4054, 0x4055, 0x4056, 0x403e
+ , 0x403f, 0x0872, 0x0873, 0x0874, 0x0875, 0x0876, 0x0877, 0x0878
+ , 0x0879, 0x087a, 0x087b, 0x087c, 0x087d, 0x087e, 0x087f, 0x0881
+ , 0x0882, 0x0883, 0x0884, 0x0885, 0x0886, 0x0888, 0x0889, 0x088a
+ , 0x088b, 0x088c, 0x088d, 0x4040, 0x4041, 0x4042, 0x4043, 0x4044
+ , 0x4045, 0x0072, 0x0073, 0x0074, 0x0075, 0x0076, 0x0077, 0x0078
+ , 0x0079, 0x007a, 0x007b, 0x007c, 0x007d, 0x007e, 0x007f, 0x0081
+ , 0x0082, 0x0083, 0x0084, 0x0085, 0x0086, 0x0088, 0x0089, 0x008a
+ , 0x008b, 0x008c, 0x008d, 0x4046, 0x4047, 0x4048, 0x4049, 0xc021
+ , 0x0893, 0x0a91, 0x404d, 0x0291, 0x4050, 0x4066, 0x4063, 0x4064
+ , 0xc022, 0x4067, 0x08a0, 0x4051, 0x08a3, 0x099e, 0x08a9, 0x08b0
+ , 0x0093, 0x404b, 0x404c, 0x404e, 0x404f, 0x4065, 0xc027, 0xc028
+ , 0xc023, 0x0887, 0x00a0, 0x4052, 0x00a3, 0x019e, 0x00a9, 0x00b0
+ , 0x402a, 0x08ab, 0x00ab, 0x089d, 0x405a, 0x0991, 0x404a, 0x405b
+ , 0x0994, 0x405c, 0x0895, 0x4058, 0x405d, 0xc026, 0x405e, 0x089b
+ , 0x405f, 0x4057, 0x089a, 0x009a, 0x0191, 0x4060, 0x4061, 0x4062
+ , 0x0194, 0x0880, 0x0095, 0x4059, 0x009d, 0x0898, 0x0098, 0x009b
+ , 0x088e, 0x088f, 0x0890, 0x0891, 0x0892, 0x0894, 0x0896, 0x0897
+ , 0x0899, 0x089c, 0x089e, 0x089f, 0x08a1, 0x08a2, 0x08a4, 0x08a5
+ , 0x08a6, 0x08a7, 0x08a8, 0x08aa, 0x08ac, 0x08ad, 0x08ae, 0x08af
+ , 0x08b1, 0x08b2, 0x08b3, 0x08b4, 0x08b5, 0x08b6, 0x08b7, 0x08b8
+ , 0x008e, 0x008f, 0x0090, 0x0091, 0x0092, 0x0094, 0x0096, 0x0097
+ , 0x0099, 0x009c, 0x009e, 0x009f, 0x00a1, 0x00a2, 0x00a4, 0x00a5
+ , 0x00a6, 0x00a7, 0x00a8, 0x00aa, 0x00ac, 0x00ad, 0x00ae, 0x00af
+ , 0x00b1, 0x00b2, 0x00b3, 0x00b4, 0x00b5, 0x00b6, 0x00b7, 0x00b8
+};
+
+WORD NLSALLOC(0419) rgwCType12_0419[256] = {
+ 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x9068, 0x0028, 0x0028, 0x0028, 0x0028, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0xa048, 0xb010, 0xb010, 0x5010, 0x5010, 0x5010, 0x1010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0x5010, 0x7010, 0x5010, 0x4010, 0x4010
+ , 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084
+ , 0x3084, 0x3084, 0x7010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010, 0x0020
+ , 0x1101, 0x1101, 0xb010, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x0020, 0x5010, 0x1101, 0xb010, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1102, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x0020, 0xb010, 0x1102, 0xb010, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0xa048, 0x1101, 0x1102, 0x1101, 0x5010, 0x1101, 0xb010, 0xb010
+ , 0x1101, 0xb010, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0x1101
+ , 0x5010, 0x5010, 0x1101, 0x1102, 0x1102, 0xb010, 0xb010, 0xb010
+ , 0x1102, 0xb010, 0x1102, 0xb010, 0x1102, 0x1101, 0x1102, 0x1102
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+};
+
+WORD NLSALLOC(0419) rgwCType3_0419[256] = {
+ 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0008, 0x0008, 0x0008, 0x0008, 0x0008, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0048, 0x0048, 0x0448, 0x0048, 0x0448, 0x0048, 0x0048, 0x0440
+ , 0x0048, 0x0048, 0x0048, 0x0048, 0x0048, 0x0440, 0x0048, 0x0448
+ , 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040
+ , 0x0040, 0x0040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0048, 0x0048
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0448, 0x0048, 0x0448, 0x0448
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0000
+ , 0x8000, 0x8003, 0x0008, 0x8003, 0x0008, 0x0008, 0x0008, 0x0008
+ , 0x0000, 0x0008, 0x8000, 0x0008, 0x8000, 0x8003, 0x8000, 0x8000
+ , 0x8000, 0x0088, 0x0088, 0x0088, 0x0088, 0x0008, 0x0400, 0x0400
+ , 0x0000, 0x0000, 0x8000, 0x0008, 0x8000, 0x8003, 0x8000, 0x8000
+ , 0x0008, 0x8003, 0x8003, 0x8000, 0x0008, 0x8000, 0x0048, 0x0008
+ , 0x8003, 0x0008, 0x8000, 0x0008, 0x0048, 0x0408, 0x0008, 0x8003
+ , 0x0008, 0x0008, 0x8000, 0x8000, 0x8000, 0x0008, 0x0008, 0x0008
+ , 0x8003, 0x0000, 0x8000, 0x0008, 0x8000, 0x8000, 0x8000, 0x8003
+ , 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000
+ , 0x8000, 0x8003, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000
+ , 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000
+ , 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000
+ , 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000
+ , 0x8000, 0x8003, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000
+ , 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000
+ , 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000, 0x8000
+};
+
+BYTE NLSALLOC(0419) rgbUCase_0419[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x81, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0x80, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x8a, 0x9b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0xa0, 0xa1, 0xa1, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb2, 0xa5, 0xb5, 0xb6, 0xb7
+ , 0xa8, 0xb9, 0xaa, 0xbb, 0xa3, 0xbd, 0xbd, 0xaf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf
+};
+
+BYTE NLSALLOC(0419) rgbLCase_0419[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x90, 0x83, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x9a, 0x8b, 0x9c, 0x9d, 0x9e, 0x9f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f
+ , 0xa0, 0xa2, 0xa2, 0xbc, 0xa4, 0xb4, 0xa6, 0xa7
+ , 0xb8, 0xa9, 0xba, 0xab, 0xac, 0xad, 0xae, 0xbf
+ , 0xb0, 0xb1, 0xb3, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbe, 0xbe, 0xbf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
+};
+
+static BYTE NLSALLOC(0419) rgbILANGUAGE[] = { /* "0419" */
+ 0x30, 0x34, 0x31, 0x39
+};
+
+static BYTE NLSALLOC(0419) rgbSLANGUAGE[] = { /* "Russian" */
+ 0x52, 0x75, 0x73, 0x73, 0x69, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVLANGNAME[] = { /* "RUS" */
+ 0x52, 0x55, 0x53
+};
+
+static BYTE NLSALLOC(0419) rgbSNATIVELANGNAME[] = { /* "\x0440\x0443\x0441\x0441\x043a\x0438\x0439" */
+ 0xf0, 0xf3, 0xf1, 0xf1, 0xea, 0xe8, 0xe9
+};
+
+static BYTE NLSALLOC(0419) rgbICOUNTRY[] = { /* "7" */
+ 0x37
+};
+
+static BYTE NLSALLOC(0419) rgbSCOUNTRY[] = { /* "Russia" */
+ 0x52, 0x75, 0x73, 0x73, 0x69, 0x61
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVCTRYNAME[] = { /* "RUS" */
+ 0x52, 0x55, 0x53
+};
+
+static BYTE NLSALLOC(0419) rgbSNATIVECTRYNAME[] = { /* "\x0420\x043e\x0441\x0441\x0438\x044f" */
+ 0xd0, 0xee, 0xf1, 0xf1, 0xe8, 0xff
+};
+
+static BYTE NLSALLOC(0419) rgbIDEFAULTLANGUAGE[] = { /* "0419" */
+ 0x30, 0x34, 0x31, 0x39
+};
+
+static BYTE NLSALLOC(0419) rgbIDEFAULTCOUNTRY[] = { /* "7" */
+ 0x37
+};
+
+static BYTE NLSALLOC(0419) rgbIDEFAULTCODEPAGE[] = { /* "866" */
+ 0x38, 0x36, 0x36
+};
+
+static BYTE NLSALLOC(0419) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0419) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0419) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0419) rgbSTHOUSAND[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(0419) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0419) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0419) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0419) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0419) rgbSCURRENCY[] = { /* "\x0440." */
+ 0xf0, 0x2e
+};
+
+static BYTE NLSALLOC(0419) rgbSINTLSYMBOL[] = { /* "RUR" */
+ 0x52, 0x55, 0x52
+};
+
+static BYTE NLSALLOC(0419) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0419) rgbSMONTHOUSANDSEP[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(0419) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0419) rgbICURRDIGITS[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0419) rgbIINTLCURRDIGITS[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0419) rgbICURRENCY[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0419) rgbINEGCURR[] = { /* "5" */
+ 0x35
+};
+
+static BYTE NLSALLOC(0419) rgbSDATE[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0419) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0419) rgbSSHORTDATE[] = { /* "dd.MM.yy" */
+ 0x64, 0x64, 0x2e, 0x4d, 0x4d, 0x2e, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0419) rgbSLONGDATE[] = { /* "d MMMM yyyy \x0433." */
+ 0x64, 0x20, 0x4d, 0x4d, 0x4d, 0x4d, 0x20, 0x79
+ , 0x79, 0x79, 0x79, 0x20, 0xe3, 0x2e
+};
+
+static BYTE NLSALLOC(0419) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0419) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0419) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0419) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0419) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0419) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0419) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0419) rgbSDAYNAME1[] = { /* "\x043f\x043e\x043d\x0435\x0434\x0435\x043b\x044c\x043d\x0438\x043a" */
+ 0xef, 0xee, 0xed, 0xe5, 0xe4, 0xe5, 0xeb, 0xfc
+ , 0xed, 0xe8, 0xea
+};
+
+static BYTE NLSALLOC(0419) rgbSDAYNAME2[] = { /* "\x0432\x0442\x043e\x0440\x043d\x0438\x043a" */
+ 0xe2, 0xf2, 0xee, 0xf0, 0xed, 0xe8, 0xea
+};
+
+static BYTE NLSALLOC(0419) rgbSDAYNAME3[] = { /* "\x0441\x0440\x0435\x0434\x0430" */
+ 0xf1, 0xf0, 0xe5, 0xe4, 0xe0
+};
+
+static BYTE NLSALLOC(0419) rgbSDAYNAME4[] = { /* "\x0447\x0435\x0442\x0432\x0435\x0440\x0433" */
+ 0xf7, 0xe5, 0xf2, 0xe2, 0xe5, 0xf0, 0xe3
+};
+
+static BYTE NLSALLOC(0419) rgbSDAYNAME5[] = { /* "\x043f\x044f\x0442\x043d\x0438\x0446\x0430" */
+ 0xef, 0xff, 0xf2, 0xed, 0xe8, 0xf6, 0xe0
+};
+
+static BYTE NLSALLOC(0419) rgbSDAYNAME6[] = { /* "\x0441\x0443\x0431\x0431\x043e\x0442\x0430" */
+ 0xf1, 0xf3, 0xe1, 0xe1, 0xee, 0xf2, 0xe0
+};
+
+static BYTE NLSALLOC(0419) rgbSDAYNAME7[] = { /* "\x0432\x043e\x0441\x043a\x0440\x0435\x0441\x0435\x043d\x044c\x0435" */
+ 0xe2, 0xee, 0xf1, 0xea, 0xf0, 0xe5, 0xf1, 0xe5
+ , 0xed, 0xfc, 0xe5
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVDAYNAME1[] = { /* "\x041f\x043d" */
+ 0xcf, 0xed
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVDAYNAME2[] = { /* "\x0412\x0442" */
+ 0xc2, 0xf2
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVDAYNAME3[] = { /* "\x0421\x0440" */
+ 0xd1, 0xf0
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVDAYNAME4[] = { /* "\x0427\x0442" */
+ 0xd7, 0xf2
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVDAYNAME5[] = { /* "\x041f\x0442" */
+ 0xcf, 0xf2
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVDAYNAME6[] = { /* "\x0421\x0431" */
+ 0xd1, 0xe1
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVDAYNAME7[] = { /* "\x0412\x0441" */
+ 0xc2, 0xf1
+};
+
+static BYTE NLSALLOC(0419) rgbSMONTHNAME1[] = { /* "\x042f\x043d\x0432\x0430\x0440\x044c" */
+ 0xdf, 0xed, 0xe2, 0xe0, 0xf0, 0xfc
+};
+
+static BYTE NLSALLOC(0419) rgbSMONTHNAME2[] = { /* "\x0424\x0435\x0432\x0440\x0430\x043b\x044c" */
+ 0xd4, 0xe5, 0xe2, 0xf0, 0xe0, 0xeb, 0xfc
+};
+
+static BYTE NLSALLOC(0419) rgbSMONTHNAME3[] = { /* "\x041c\x0430\x0440\x0442" */
+ 0xcc, 0xe0, 0xf0, 0xf2
+};
+
+static BYTE NLSALLOC(0419) rgbSMONTHNAME4[] = { /* "\x0410\x043f\x0440\x0435\x043b\x044c" */
+ 0xc0, 0xef, 0xf0, 0xe5, 0xeb, 0xfc
+};
+
+static BYTE NLSALLOC(0419) rgbSMONTHNAME5[] = { /* "\x041c\x0430\x0439" */
+ 0xcc, 0xe0, 0xe9
+};
+
+static BYTE NLSALLOC(0419) rgbSMONTHNAME6[] = { /* "\x0418\x044e\x043d\x044c" */
+ 0xc8, 0xfe, 0xed, 0xfc
+};
+
+static BYTE NLSALLOC(0419) rgbSMONTHNAME7[] = { /* "\x0418\x044e\x043b\x044c" */
+ 0xc8, 0xfe, 0xeb, 0xfc
+};
+
+static BYTE NLSALLOC(0419) rgbSMONTHNAME8[] = { /* "\x0410\x0432\x0433\x0443\x0441\x0442" */
+ 0xc0, 0xe2, 0xe3, 0xf3, 0xf1, 0xf2
+};
+
+static BYTE NLSALLOC(0419) rgbSMONTHNAME9[] = { /* "\x0421\x0435\x043d\x0442\x044f\x0431\x0440\x044c" */
+ 0xd1, 0xe5, 0xed, 0xf2, 0xff, 0xe1, 0xf0, 0xfc
+};
+
+static BYTE NLSALLOC(0419) rgbSMONTHNAME10[] = { /* "\x041e\x043a\x0442\x044f\x0431\x0440\x044c" */
+ 0xce, 0xea, 0xf2, 0xff, 0xe1, 0xf0, 0xfc
+};
+
+static BYTE NLSALLOC(0419) rgbSMONTHNAME11[] = { /* "\x041d\x043e\x044f\x0431\x0440\x044c" */
+ 0xcd, 0xee, 0xff, 0xe1, 0xf0, 0xfc
+};
+
+static BYTE NLSALLOC(0419) rgbSMONTHNAME12[] = { /* "\x0414\x0435\x043a\x0430\x0431\x0440\x044c" */
+ 0xc4, 0xe5, 0xea, 0xe0, 0xe1, 0xf0, 0xfc
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVMONTHNAME1[] = { /* "\x042f\x043d\x0432" */
+ 0xdf, 0xed, 0xe2
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVMONTHNAME2[] = { /* "\x0424\x0435\x0432" */
+ 0xd4, 0xe5, 0xe2
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVMONTHNAME3[] = { /* "\x041c\x0430\x0440" */
+ 0xcc, 0xe0, 0xf0
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVMONTHNAME4[] = { /* "\x0410\x043f\x0440" */
+ 0xc0, 0xef, 0xf0
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVMONTHNAME5[] = { /* "\x041c\x0430\x044f" */
+ 0xcc, 0xe0, 0xff
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVMONTHNAME6[] = { /* "\x0418\x044e\x043d" */
+ 0xc8, 0xfe, 0xed
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVMONTHNAME7[] = { /* "\x0418\x044e\x043b" */
+ 0xc8, 0xfe, 0xeb
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVMONTHNAME8[] = { /* "\x0410\x0432\x0433" */
+ 0xc0, 0xe2, 0xe3
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVMONTHNAME9[] = { /* "\x0421\x0435\x043d" */
+ 0xd1, 0xe5, 0xed
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVMONTHNAME10[] = { /* "\x041e\x043a\x0442" */
+ 0xce, 0xea, 0xf2
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVMONTHNAME11[] = { /* "\x041d\x043e\x044f" */
+ 0xcd, 0xee, 0xff
+};
+
+static BYTE NLSALLOC(0419) rgbSABBREVMONTHNAME12[] = { /* "\x0414\x0435\x043a" */
+ 0xc4, 0xe5, 0xea
+};
+
+static BYTE NLSALLOC(0419) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0419) rgbIPOSSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0419) rgbINEGSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0419) rgbIPOSSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0419) rgbIPOSSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0419) rgbINEGSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0419) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0419) rgbSENGCOUNTRY[] = { /* "Russia" */
+ 0x52, 0x75, 0x73, 0x73, 0x69, 0x61
+};
+
+static BYTE NLSALLOC(0419) rgbSENGLANGUAGE[] = { /* "Russian" */
+ 0x52, 0x75, 0x73, 0x73, 0x69, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0419) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0419) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0419) rgbIDEFAULTANSICODEPAGE[] = { /* "1251" */
+ 0x31, 0x32, 0x35, 0x31
+};
+
+static BYTE NLSALLOC(0419) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0419) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0419) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0419) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0419) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0419) g_rglcinfo0419[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 7, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 1, rgbICOUNTRY }
+ , { 6, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 6, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 1, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 2, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 14, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 11, rgbSDAYNAME1 }
+ , { 7, rgbSDAYNAME2 }
+ , { 5, rgbSDAYNAME3 }
+ , { 7, rgbSDAYNAME4 }
+ , { 7, rgbSDAYNAME5 }
+ , { 7, rgbSDAYNAME6 }
+ , { 11, rgbSDAYNAME7 }
+ , { 2, rgbSABBREVDAYNAME1 }
+ , { 2, rgbSABBREVDAYNAME2 }
+ , { 2, rgbSABBREVDAYNAME3 }
+ , { 2, rgbSABBREVDAYNAME4 }
+ , { 2, rgbSABBREVDAYNAME5 }
+ , { 2, rgbSABBREVDAYNAME6 }
+ , { 2, rgbSABBREVDAYNAME7 }
+ , { 6, rgbSMONTHNAME1 }
+ , { 7, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 6, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 8, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 6, rgbSMONTHNAME11 }
+ , { 7, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 6, rgbSENGCOUNTRY }
+ , { 7, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0419) g_strinfo0419 = {
+ rgbUCase_0419
+ , rgbLCase_0419
+ , rgwCType12_0419
+ , rgwCType3_0419
+ , rgwSort_0419
+ , NULL
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/041b.c b/private/oleauto/src/dispatch/win16/041b.c
new file mode 100644
index 000000000..3c5633ac6
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/041b.c
@@ -0,0 +1,706 @@
+/****************************************************************************
+* 041b.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Slovak - Slovak Republic
+*
+* LCID = 0x041b
+*
+* CodePage = 1250
+*
+* Generated: Thu Dec 01 18:14:21 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+WORD NLSALLOC(041b) rgwSort_041b[256] = {
+ 0x0000, 0xc007, 0xc008, 0xc009, 0xc00a, 0xc00b, 0xc00c, 0xc00d
+ , 0xc00e, 0x402f, 0x4030, 0x4031, 0x4032, 0x4033, 0xc00f, 0xc010
+ , 0xc011, 0xc012, 0xc013, 0xc014, 0xc015, 0xc016, 0xc017, 0xc018
+ , 0xc019, 0xc01a, 0xc01b, 0xc01c, 0xc01d, 0xc01e, 0xc01f, 0xc020
+ , 0x402d, 0x4034, 0x4035, 0x4036, 0x4037, 0x4038, 0x4039, 0xc028
+ , 0x403a, 0x403b, 0x403c, 0x405e, 0x403d, 0xc029, 0x403e, 0x403f
+ , 0x0075, 0x0076, 0x0077, 0x0078, 0x0079, 0x007a, 0x007b, 0x007c
+ , 0x007d, 0x007e, 0x4040, 0x4041, 0x405f, 0x4060, 0x4061, 0x4042
+ , 0x4043, 0x087f, 0x0881, 0x0006, 0x0884, 0x0885, 0x0886, 0x0887
+ , 0x0888, 0x088a, 0x088b, 0x088c, 0x088d, 0x088e, 0x088f, 0x0890
+ , 0x0892, 0x0893, 0x0894, 0x0896, 0x0898, 0x089a, 0x089b, 0x089c
+ , 0x089d, 0x089e, 0x089f, 0x4044, 0x4045, 0x4046, 0x4047, 0x4048
+ , 0x4049, 0x007f, 0x0081, 0x0306, 0x0084, 0x0085, 0x0086, 0x0087
+ , 0x0088, 0x008a, 0x008b, 0x008c, 0x008d, 0x008e, 0x008f, 0x0090
+ , 0x0092, 0x0093, 0x0094, 0x0096, 0x0098, 0x009a, 0x009b, 0x009c
+ , 0x009d, 0x009e, 0x009f, 0x404a, 0x404b, 0x404c, 0x404d, 0xc021
+ , 0xc022, 0xc023, 0x4058, 0xc024, 0x405b, 0x4073, 0x4070, 0x4071
+ , 0xc025, 0x4074, 0x0897, 0x405c, 0x0896, 0x0998, 0x08a0, 0x0a9f
+ , 0xc026, 0x4056, 0x4057, 0x4059, 0x405a, 0x4072, 0xc02b, 0xc02c
+ , 0xc027, 0x0899, 0x0097, 0x405d, 0x0096, 0x0198, 0x00a0, 0x029f
+ , 0x402e, 0x4052, 0x4152, 0x0b8d, 0x4067, 0x0c7f, 0x404e, 0x4068
+ , 0x404f, 0x4069, 0x0996, 0x4063, 0x406a, 0xc02a, 0x406b, 0x099f
+ , 0x406c, 0x4062, 0x4054, 0x038d, 0x4050, 0x406d, 0x406e, 0x406f
+ , 0x4051, 0x047f, 0x0196, 0x4064, 0x0a8d, 0x4055, 0x028d, 0x019f
+ , 0x0994, 0x097f, 0x0a7f, 0x0b7f, 0x0880, 0x098d, 0x0982, 0x0a82
+ , 0x0883, 0x0a85, 0x0c85, 0x0985, 0x0b85, 0x098a, 0x0a8a, 0x0984
+ , 0x0a84, 0x098f, 0x0a8f, 0x0a90, 0x0891, 0x0b90, 0x0990, 0x4065
+ , 0x0895, 0x0b9a, 0x0a9a, 0x0c9a, 0x099a, 0x099e, 0x0a98, 0x0005
+ , 0x0194, 0x017f, 0x027f, 0x037f, 0x0080, 0x018d, 0x0182, 0x0282
+ , 0x0083, 0x0285, 0x0485, 0x0185, 0x0385, 0x018a, 0x028a, 0x0184
+ , 0x0284, 0x018f, 0x028f, 0x0290, 0x0091, 0x0390, 0x0190, 0x4066
+ , 0x0095, 0x039a, 0x029a, 0x049a, 0x019a, 0x019e, 0x0298, 0x4053
+};
+
+DIGRAPH NLSALLOC(041b) rgdig_041b[5] = {
+ { 0x0882, 0x02 }
+ , { 0x1089, 0x48 }
+ , { 0x0889, 0x68 }
+ , { 0x0082, 0x02 }
+ , { 0x0089, 0x68 }
+};
+
+EXPANSION NLSALLOC(041b) rgexp_041b[1] = {
+ { 0x0096, 0x0096 }
+};
+
+WORD NLSALLOC(041b) rgwCType12_041b[256] = {
+ 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x9068, 0x0028, 0x0028, 0x0028, 0x0028, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0xa048, 0xb010, 0xb010, 0x5010, 0x5010, 0x5010, 0x1010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0x5010, 0x7010, 0x5010, 0x4010, 0x4010
+ , 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084
+ , 0x3084, 0x3084, 0x7010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010, 0x0020
+ , 0x0020, 0x0020, 0xb010, 0x0020, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x0020, 0x5010, 0x1101, 0xb010, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x0020, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x0020, 0xb010, 0x1102, 0xb010, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0xa048, 0x1010, 0x1010, 0x1101, 0x5010, 0x1101, 0xb010, 0xb010
+ , 0xb010, 0xb010, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0x1101
+ , 0x5010, 0x5010, 0x1010, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x1102, 0x1102, 0xb010, 0x1101, 0x1010, 0x1102, 0x1102
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0xb010
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0xb010
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1010
+};
+
+WORD NLSALLOC(041b) rgwCType3_041b[256] = {
+ 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0008, 0x0008, 0x0008, 0x0008, 0x0008, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0048, 0x0048, 0x0448, 0x0048, 0x0448, 0x0048, 0x0048, 0x0440
+ , 0x0048, 0x0048, 0x0048, 0x0048, 0x0048, 0x0440, 0x0048, 0x0448
+ , 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040
+ , 0x0040, 0x0040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0048, 0x0048
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0448, 0x0048, 0x0448, 0x0448
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0000
+ , 0x0000, 0x0000, 0x0008, 0x0000, 0x0008, 0x0008, 0x0008, 0x0008
+ , 0x0000, 0x0008, 0x8003, 0x0008, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x0000, 0x0088, 0x0088, 0x0088, 0x0088, 0x0008, 0x0400, 0x0400
+ , 0x0000, 0x0000, 0x8003, 0x0008, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x0008, 0x0401, 0x0408, 0x8003, 0x0008, 0x8003, 0x0048, 0x0008
+ , 0x0408, 0x0008, 0x8003, 0x0008, 0x0048, 0x0408, 0x0008, 0x8003
+ , 0x0008, 0x0008, 0x0408, 0x8003, 0x0408, 0x0008, 0x0008, 0x0008
+ , 0x0408, 0x8003, 0x8003, 0x0008, 0x8003, 0x0408, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0408
+};
+
+BYTE NLSALLOC(041b) rgbUCase_041b[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x8a, 0x9b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xa3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xa5, 0xaa, 0xbb, 0xbc, 0xbd, 0xbc, 0xaf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xf7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xff
+};
+
+BYTE NLSALLOC(041b) rgbLCase_041b[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x9a, 0x8b, 0x9c, 0x9d, 0x9e, 0x9f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f
+ , 0xa0, 0xa1, 0xa2, 0xb3, 0xa4, 0xb9, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xba, 0xab, 0xac, 0xad, 0xae, 0xbf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbe, 0xbd, 0xbe, 0xbf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xd7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xdf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
+};
+
+static BYTE NLSALLOC(041b) rgbILANGUAGE[] = { /* "041b" */
+ 0x30, 0x34, 0x31, 0x62
+};
+
+static BYTE NLSALLOC(041b) rgbSLANGUAGE[] = { /* "Slovak" */
+ 0x53, 0x6c, 0x6f, 0x76, 0x61, 0x6b
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVLANGNAME[] = { /* "SKY" */
+ 0x53, 0x4b, 0x59
+};
+
+static BYTE NLSALLOC(041b) rgbSNATIVELANGNAME[] = { /* "sloven\x010dtina" */
+ 0x73, 0x6c, 0x6f, 0x76, 0x65, 0x6e, 0xe8, 0x74
+ , 0x69, 0x6e, 0x61
+};
+
+static BYTE NLSALLOC(041b) rgbICOUNTRY[] = { /* "42" */
+ 0x34, 0x32
+};
+
+static BYTE NLSALLOC(041b) rgbSCOUNTRY[] = { /* "Slovak Republic" */
+ 0x53, 0x6c, 0x6f, 0x76, 0x61, 0x6b, 0x20, 0x52
+ , 0x65, 0x70, 0x75, 0x62, 0x6c, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVCTRYNAME[] = { /* "SVK" */
+ 0x53, 0x56, 0x4b
+};
+
+static BYTE NLSALLOC(041b) rgbSNATIVECTRYNAME[] = { /* "Slovenská republika" */
+ 0x53, 0x6c, 0x6f, 0x76, 0x65, 0x6e, 0x73, 0x6b
+ , 0xe1, 0x20, 0x72, 0x65, 0x70, 0x75, 0x62, 0x6c
+ , 0x69, 0x6b, 0x61
+};
+
+static BYTE NLSALLOC(041b) rgbIDEFAULTLANGUAGE[] = { /* "041b" */
+ 0x30, 0x34, 0x31, 0x62
+};
+
+static BYTE NLSALLOC(041b) rgbIDEFAULTCOUNTRY[] = { /* "42" */
+ 0x34, 0x32
+};
+
+static BYTE NLSALLOC(041b) rgbIDEFAULTCODEPAGE[] = { /* "852" */
+ 0x38, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(041b) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(041b) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041b) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(041b) rgbSTHOUSAND[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(041b) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(041b) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(041b) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041b) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(041b) rgbSCURRENCY[] = { /* "Sk" */
+ 0x53, 0x6b
+};
+
+static BYTE NLSALLOC(041b) rgbSINTLSYMBOL[] = { /* "SKK" */
+ 0x53, 0x4b, 0x4b
+};
+
+static BYTE NLSALLOC(041b) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(041b) rgbSMONTHOUSANDSEP[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(041b) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(041b) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(041b) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(041b) rgbICURRENCY[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(041b) rgbINEGCURR[] = { /* "8" */
+ 0x38
+};
+
+static BYTE NLSALLOC(041b) rgbSDATE[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(041b) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(041b) rgbSSHORTDATE[] = { /* "d.M.yyyy" */
+ 0x64, 0x2e, 0x4d, 0x2e, 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(041b) rgbSLONGDATE[] = { /* "d. MMMM yyyy" */
+ 0x64, 0x2e, 0x20, 0x4d, 0x4d, 0x4d, 0x4d, 0x20
+ , 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(041b) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041b) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041b) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041b) rgbICENTURY[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041b) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041b) rgbIDAYLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041b) rgbIMONLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041b) rgbSDAYNAME1[] = { /* "pondelok" */
+ 0x70, 0x6f, 0x6e, 0x64, 0x65, 0x6c, 0x6f, 0x6b
+};
+
+static BYTE NLSALLOC(041b) rgbSDAYNAME2[] = { /* "utorok" */
+ 0x75, 0x74, 0x6f, 0x72, 0x6f, 0x6b
+};
+
+static BYTE NLSALLOC(041b) rgbSDAYNAME3[] = { /* "streda" */
+ 0x73, 0x74, 0x72, 0x65, 0x64, 0x61
+};
+
+static BYTE NLSALLOC(041b) rgbSDAYNAME4[] = { /* "\x0161tvrtok" */
+ 0x9a, 0x74, 0x76, 0x72, 0x74, 0x6f, 0x6b
+};
+
+static BYTE NLSALLOC(041b) rgbSDAYNAME5[] = { /* "piatok" */
+ 0x70, 0x69, 0x61, 0x74, 0x6f, 0x6b
+};
+
+static BYTE NLSALLOC(041b) rgbSDAYNAME6[] = { /* "sobota" */
+ 0x73, 0x6f, 0x62, 0x6f, 0x74, 0x61
+};
+
+static BYTE NLSALLOC(041b) rgbSDAYNAME7[] = { /* "nede\x013ea" */
+ 0x6e, 0x65, 0x64, 0x65, 0xbe, 0x61
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVDAYNAME1[] = { /* "po" */
+ 0x70, 0x6f
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVDAYNAME2[] = { /* "ut" */
+ 0x75, 0x74
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVDAYNAME3[] = { /* "st" */
+ 0x73, 0x74
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVDAYNAME4[] = { /* "\x0161t" */
+ 0x9a, 0x74
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVDAYNAME5[] = { /* "pi" */
+ 0x70, 0x69
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVDAYNAME6[] = { /* "so" */
+ 0x73, 0x6f
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVDAYNAME7[] = { /* "ne" */
+ 0x6e, 0x65
+};
+
+static BYTE NLSALLOC(041b) rgbSMONTHNAME1[] = { /* "január" */
+ 0x6a, 0x61, 0x6e, 0x75, 0xe1, 0x72
+};
+
+static BYTE NLSALLOC(041b) rgbSMONTHNAME2[] = { /* "február" */
+ 0x66, 0x65, 0x62, 0x72, 0x75, 0xe1, 0x72
+};
+
+static BYTE NLSALLOC(041b) rgbSMONTHNAME3[] = { /* "marec" */
+ 0x6d, 0x61, 0x72, 0x65, 0x63
+};
+
+static BYTE NLSALLOC(041b) rgbSMONTHNAME4[] = { /* "apríl" */
+ 0x61, 0x70, 0x72, 0xed, 0x6c
+};
+
+static BYTE NLSALLOC(041b) rgbSMONTHNAME5[] = { /* "máj" */
+ 0x6d, 0xe1, 0x6a
+};
+
+static BYTE NLSALLOC(041b) rgbSMONTHNAME6[] = { /* "jún" */
+ 0x6a, 0xfa, 0x6e
+};
+
+static BYTE NLSALLOC(041b) rgbSMONTHNAME7[] = { /* "júl" */
+ 0x6a, 0xfa, 0x6c
+};
+
+static BYTE NLSALLOC(041b) rgbSMONTHNAME8[] = { /* "august" */
+ 0x61, 0x75, 0x67, 0x75, 0x73, 0x74
+};
+
+static BYTE NLSALLOC(041b) rgbSMONTHNAME9[] = { /* "september" */
+ 0x73, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x65
+ , 0x72
+};
+
+static BYTE NLSALLOC(041b) rgbSMONTHNAME10[] = { /* "október" */
+ 0x6f, 0x6b, 0x74, 0xf3, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(041b) rgbSMONTHNAME11[] = { /* "november" */
+ 0x6e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(041b) rgbSMONTHNAME12[] = { /* "december" */
+ 0x64, 0x65, 0x63, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVMONTHNAME1[] = { /* "I" */
+ 0x49
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVMONTHNAME2[] = { /* "II" */
+ 0x49, 0x49
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVMONTHNAME3[] = { /* "III" */
+ 0x49, 0x49, 0x49
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVMONTHNAME4[] = { /* "IV" */
+ 0x49, 0x56
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVMONTHNAME5[] = { /* "V" */
+ 0x56
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVMONTHNAME6[] = { /* "VI" */
+ 0x56, 0x49
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVMONTHNAME7[] = { /* "VII" */
+ 0x56, 0x49, 0x49
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVMONTHNAME8[] = { /* "VIII" */
+ 0x56, 0x49, 0x49, 0x49
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVMONTHNAME9[] = { /* "IX" */
+ 0x49, 0x58
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVMONTHNAME10[] = { /* "X" */
+ 0x58
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVMONTHNAME11[] = { /* "XI" */
+ 0x58, 0x49
+};
+
+static BYTE NLSALLOC(041b) rgbSABBREVMONTHNAME12[] = { /* "XII" */
+ 0x58, 0x49, 0x49
+};
+
+static BYTE NLSALLOC(041b) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(041b) rgbIPOSSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041b) rgbINEGSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041b) rgbIPOSSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041b) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041b) rgbINEGSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041b) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041b) rgbSENGCOUNTRY[] = { /* "Slovak Republic" */
+ 0x53, 0x6c, 0x6f, 0x76, 0x61, 0x6b, 0x20, 0x52
+ , 0x65, 0x70, 0x75, 0x62, 0x6c, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(041b) rgbSENGLANGUAGE[] = { /* "Slovak" */
+ 0x53, 0x6c, 0x6f, 0x76, 0x61, 0x6b
+};
+
+static BYTE NLSALLOC(041b) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041b) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041b) rgbIDEFAULTANSICODEPAGE[] = { /* "1250" */
+ 0x31, 0x32, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(041b) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041b) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(041b) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041b) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041b) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(041b) g_rglcinfo041b[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 11, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 15, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 19, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 2, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 12, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 8, rgbSDAYNAME1 }
+ , { 6, rgbSDAYNAME2 }
+ , { 6, rgbSDAYNAME3 }
+ , { 7, rgbSDAYNAME4 }
+ , { 6, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 2, rgbSABBREVDAYNAME1 }
+ , { 2, rgbSABBREVDAYNAME2 }
+ , { 2, rgbSABBREVDAYNAME3 }
+ , { 2, rgbSABBREVDAYNAME4 }
+ , { 2, rgbSABBREVDAYNAME5 }
+ , { 2, rgbSABBREVDAYNAME6 }
+ , { 2, rgbSABBREVDAYNAME7 }
+ , { 6, rgbSMONTHNAME1 }
+ , { 7, rgbSMONTHNAME2 }
+ , { 5, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 3, rgbSMONTHNAME6 }
+ , { 3, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 1, rgbSABBREVMONTHNAME1 }
+ , { 2, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 2, rgbSABBREVMONTHNAME4 }
+ , { 1, rgbSABBREVMONTHNAME5 }
+ , { 2, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 4, rgbSABBREVMONTHNAME8 }
+ , { 2, rgbSABBREVMONTHNAME9 }
+ , { 1, rgbSABBREVMONTHNAME10 }
+ , { 2, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 15, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(041b) g_strinfo041b = {
+ rgbUCase_041b
+ , rgbLCase_041b
+ , rgwCType12_041b
+ , rgwCType3_041b
+ , rgwSort_041b
+ , rgexp_041b
+ , rgdig_041b
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/041d.c b/private/oleauto/src/dispatch/win16/041d.c
new file mode 100644
index 000000000..5626120b6
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/041d.c
@@ -0,0 +1,701 @@
+/****************************************************************************
+* 041d.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Swedish - Sweden
+*
+* LCID = 0x041d
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:59:57 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+WORD NLSALLOC(041d) rgwSort_041d[256] = {
+ 0x0000, 0xc007, 0xc008, 0xc009, 0xc00a, 0xc00b, 0xc00c, 0xc00d
+ , 0xc00e, 0x4031, 0x4032, 0x4033, 0x4034, 0x4035, 0xc00f, 0xc010
+ , 0xc011, 0xc012, 0xc013, 0xc014, 0xc015, 0xc016, 0xc017, 0xc018
+ , 0xc019, 0xc01a, 0xc01b, 0xc01c, 0xc01d, 0xc01e, 0xc01f, 0xc020
+ , 0x402f, 0x4036, 0x4037, 0x4038, 0x4039, 0x403a, 0x403b, 0xc02a
+ , 0x403c, 0x403d, 0x403e, 0x4060, 0x403f, 0xc02b, 0x4040, 0x4041
+ , 0x007a, 0x007e, 0x007f, 0x0080, 0x0081, 0x0082, 0x0083, 0x0084
+ , 0x0085, 0x0086, 0x4042, 0x4043, 0x4061, 0x4062, 0x4063, 0x4044
+ , 0x4045, 0x1087, 0x1088, 0x1089, 0x108a, 0x108b, 0x108c, 0x108d
+ , 0x108e, 0x108f, 0x1090, 0x1091, 0x1092, 0x1093, 0x1094, 0x1095
+ , 0x1096, 0x1097, 0x1098, 0x1099, 0x109a, 0x109c, 0x109d, 0x119d
+ , 0x109e, 0x109f, 0x10a0, 0x4046, 0x4047, 0x4048, 0x4049, 0x404a
+ , 0x404b, 0x0087, 0x0088, 0x0089, 0x008a, 0x008b, 0x008c, 0x008d
+ , 0x008e, 0x008f, 0x0090, 0x0091, 0x0092, 0x0093, 0x0094, 0x0095
+ , 0x0096, 0x0097, 0x0098, 0x0099, 0x009a, 0x009c, 0x009d, 0x019d
+ , 0x009e, 0x009f, 0x00a0, 0x404c, 0x404d, 0x404e, 0x404f, 0xc021
+ , 0xc022, 0xc023, 0x405a, 0x018c, 0x405d, 0x4078, 0x4075, 0x4076
+ , 0x4149, 0x4079, 0x1199, 0x405e, 0x0505, 0xc024, 0xc025, 0xc026
+ , 0xc027, 0x4058, 0x4059, 0x405b, 0x405c, 0x4077, 0xc02d, 0xc02e
+ , 0x4057, 0x109b, 0x0199, 0x405f, 0x0605, 0xc028, 0xc029, 0x129f
+ , 0x4030, 0x4050, 0x4069, 0x406a, 0x406b, 0x406c, 0x4051, 0x406d
+ , 0x4052, 0x406e, 0x0887, 0x4065, 0x406f, 0xc02c, 0x4070, 0x4053
+ , 0x4071, 0x4064, 0x087f, 0x0880, 0x4054, 0x4072, 0x4073, 0x4074
+ , 0x4055, 0x087e, 0x0995, 0x4066, 0x007b, 0x007c, 0x007d, 0x4056
+ , 0x1287, 0x1187, 0x1387, 0x1487, 0x10a2, 0x10a1, 0x0005, 0x1189
+ , 0x128b, 0x118b, 0x138b, 0x148b, 0x128f, 0x118f, 0x138f, 0x148f
+ , 0x118a, 0x1194, 0x1395, 0x1295, 0x1495, 0x1595, 0x10a3, 0x4067
+ , 0x11a3, 0x129c, 0x119c, 0x139c, 0x139f, 0x119f, 0x0105, 0x0205
+ , 0x0287, 0x0187, 0x0387, 0x0487, 0x00a2, 0x00a1, 0x0305, 0x0189
+ , 0x028b, 0x018b, 0x038b, 0x048b, 0x028f, 0x018f, 0x038f, 0x048f
+ , 0x018a, 0x0194, 0x0395, 0x0295, 0x0495, 0x0595, 0x00a3, 0x4068
+ , 0x01a3, 0x029c, 0x019c, 0x039c, 0x039f, 0x019f, 0x0405, 0x029f
+};
+
+EXPANSION NLSALLOC(041d) rgexp_041d[7] = {
+ { 0x1087, 0x108b }
+ , { 0x109a, 0x108e }
+ , { 0x0099, 0x0099 }
+ , { 0x0087, 0x008b }
+ , { 0x009a, 0x008e }
+ , { 0x1095, 0x108b }
+ , { 0x0095, 0x008b }
+};
+
+WORD NLSALLOC(041d) rgwCType12_041d[256] = {
+ 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x9068, 0x0028, 0x0028, 0x0028, 0x0028, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0xa048, 0xb010, 0xb010, 0x5010, 0x5010, 0x5010, 0x1010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0x5010, 0x7010, 0x5010, 0x4010, 0x4010
+ , 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084
+ , 0x3084, 0x3084, 0x7010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010, 0x0020
+ , 0x0020, 0x0020, 0xb010, 0x1112, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x5010, 0x1101, 0xb010, 0x1101, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0xb010, 0x1102, 0xb010, 0x1102, 0x0020, 0x0020, 0x1101
+ , 0xa048, 0xb010, 0x5010, 0x5010, 0x5010, 0x5010, 0xb010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x5010, 0x5010, 0x3014, 0x3014, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x3014, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0xb010
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0xb010
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+};
+
+WORD NLSALLOC(041d) rgwCType3_041d[256] = {
+ 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0008, 0x0008, 0x0008, 0x0008, 0x0008, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0048, 0x0048, 0x0448, 0x0048, 0x0448, 0x0048, 0x0048, 0x0440
+ , 0x0048, 0x0048, 0x0048, 0x0048, 0x0048, 0x0440, 0x0048, 0x0448
+ , 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040
+ , 0x0040, 0x0040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0048, 0x0048
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0448, 0x0048, 0x0448, 0x0448
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0000
+ , 0x0000, 0x0000, 0x0008, 0x8000, 0x0008, 0x0008, 0x0008, 0x0008
+ , 0x0001, 0x0008, 0x8003, 0x0008, 0x8000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0088, 0x0088, 0x0088, 0x0088, 0x0008, 0x0400, 0x0400
+ , 0x0408, 0x0000, 0x8003, 0x0008, 0x8000, 0x0000, 0x0000, 0x8003
+ , 0x0008, 0x0008, 0x0048, 0x0048, 0x0008, 0x0048, 0x0048, 0x0008
+ , 0x0408, 0x0008, 0x0400, 0x0008, 0x0048, 0x0408, 0x0008, 0x0448
+ , 0x0008, 0x0008, 0x0000, 0x0000, 0x0408, 0x0008, 0x0008, 0x0008
+ , 0x0408, 0x0000, 0x0400, 0x0008, 0x0000, 0x0000, 0x0000, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8000, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8000
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8000, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+};
+
+BYTE NLSALLOC(041d) rgbUCase_041d[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x8a, 0x9b, 0x8c, 0x9d, 0x9e, 0x9f
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xf7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0x9f
+};
+
+BYTE NLSALLOC(041d) rgbLCase_041d[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x9a, 0x8b, 0x9c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0xff
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xd7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xdf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
+};
+
+static BYTE NLSALLOC(041d) rgbILANGUAGE[] = { /* "041d" */
+ 0x30, 0x34, 0x31, 0x64
+};
+
+static BYTE NLSALLOC(041d) rgbSLANGUAGE[] = { /* "Swedish" */
+ 0x53, 0x77, 0x65, 0x64, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVLANGNAME[] = { /* "SVE" */
+ 0x53, 0x56, 0x45
+};
+
+static BYTE NLSALLOC(041d) rgbSNATIVELANGNAME[] = { /* "svenska" */
+ 0x73, 0x76, 0x65, 0x6e, 0x73, 0x6b, 0x61
+};
+
+static BYTE NLSALLOC(041d) rgbICOUNTRY[] = { /* "46" */
+ 0x34, 0x36
+};
+
+static BYTE NLSALLOC(041d) rgbSCOUNTRY[] = { /* "Sweden" */
+ 0x53, 0x77, 0x65, 0x64, 0x65, 0x6e
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVCTRYNAME[] = { /* "SWE" */
+ 0x53, 0x57, 0x45
+};
+
+static BYTE NLSALLOC(041d) rgbSNATIVECTRYNAME[] = { /* "Sverige" */
+ 0x53, 0x76, 0x65, 0x72, 0x69, 0x67, 0x65
+};
+
+static BYTE NLSALLOC(041d) rgbIDEFAULTLANGUAGE[] = { /* "041d" */
+ 0x30, 0x34, 0x31, 0x64
+};
+
+static BYTE NLSALLOC(041d) rgbIDEFAULTCOUNTRY[] = { /* "46" */
+ 0x34, 0x36
+};
+
+static BYTE NLSALLOC(041d) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(041d) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(041d) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041d) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(041d) rgbSTHOUSAND[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(041d) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(041d) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(041d) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041d) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(041d) rgbSCURRENCY[] = { /* "kr" */
+ 0x6b, 0x72
+};
+
+static BYTE NLSALLOC(041d) rgbSINTLSYMBOL[] = { /* "SEK" */
+ 0x53, 0x45, 0x4b
+};
+
+static BYTE NLSALLOC(041d) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(041d) rgbSMONTHOUSANDSEP[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(041d) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(041d) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(041d) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(041d) rgbICURRENCY[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(041d) rgbINEGCURR[] = { /* "8" */
+ 0x38
+};
+
+static BYTE NLSALLOC(041d) rgbSDATE[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(041d) rgbSTIME[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(041d) rgbSSHORTDATE[] = { /* "yyyy-MM-dd" */
+ 0x79, 0x79, 0x79, 0x79, 0x2d, 0x4d, 0x4d, 0x2d
+ , 0x64, 0x64
+};
+
+static BYTE NLSALLOC(041d) rgbSLONGDATE[] = { /* " den 'd MMMM yyyy" */
+ 0x20, 0x64, 0x65, 0x6e, 0x20, 0x27, 0x64, 0x20
+ , 0x4d, 0x4d, 0x4d, 0x4d, 0x20, 0x79, 0x79, 0x79
+ , 0x79
+};
+
+static BYTE NLSALLOC(041d) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(041d) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041d) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041d) rgbICENTURY[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041d) rgbITLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041d) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041d) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041d) rgbSDAYNAME1[] = { /* "måndag" */
+ 0x6d, 0xe5, 0x6e, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(041d) rgbSDAYNAME2[] = { /* "tisdag" */
+ 0x74, 0x69, 0x73, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(041d) rgbSDAYNAME3[] = { /* "onsdag" */
+ 0x6f, 0x6e, 0x73, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(041d) rgbSDAYNAME4[] = { /* "torsdag" */
+ 0x74, 0x6f, 0x72, 0x73, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(041d) rgbSDAYNAME5[] = { /* "fredag" */
+ 0x66, 0x72, 0x65, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(041d) rgbSDAYNAME6[] = { /* "lördag" */
+ 0x6c, 0xf6, 0x72, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(041d) rgbSDAYNAME7[] = { /* "söndag" */
+ 0x73, 0xf6, 0x6e, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVDAYNAME1[] = { /* "må" */
+ 0x6d, 0xe5
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVDAYNAME2[] = { /* "ti" */
+ 0x74, 0x69
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVDAYNAME3[] = { /* "on" */
+ 0x6f, 0x6e
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVDAYNAME4[] = { /* "to" */
+ 0x74, 0x6f
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVDAYNAME5[] = { /* "fr" */
+ 0x66, 0x72
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVDAYNAME6[] = { /* "lö" */
+ 0x6c, 0xf6
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVDAYNAME7[] = { /* "sö" */
+ 0x73, 0xf6
+};
+
+static BYTE NLSALLOC(041d) rgbSMONTHNAME1[] = { /* "januari" */
+ 0x6a, 0x61, 0x6e, 0x75, 0x61, 0x72, 0x69
+};
+
+static BYTE NLSALLOC(041d) rgbSMONTHNAME2[] = { /* "februari" */
+ 0x66, 0x65, 0x62, 0x72, 0x75, 0x61, 0x72, 0x69
+};
+
+static BYTE NLSALLOC(041d) rgbSMONTHNAME3[] = { /* "mars" */
+ 0x6d, 0x61, 0x72, 0x73
+};
+
+static BYTE NLSALLOC(041d) rgbSMONTHNAME4[] = { /* "april" */
+ 0x61, 0x70, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(041d) rgbSMONTHNAME5[] = { /* "maj" */
+ 0x6d, 0x61, 0x6a
+};
+
+static BYTE NLSALLOC(041d) rgbSMONTHNAME6[] = { /* "juni" */
+ 0x6a, 0x75, 0x6e, 0x69
+};
+
+static BYTE NLSALLOC(041d) rgbSMONTHNAME7[] = { /* "juli" */
+ 0x6a, 0x75, 0x6c, 0x69
+};
+
+static BYTE NLSALLOC(041d) rgbSMONTHNAME8[] = { /* "augusti" */
+ 0x61, 0x75, 0x67, 0x75, 0x73, 0x74, 0x69
+};
+
+static BYTE NLSALLOC(041d) rgbSMONTHNAME9[] = { /* "september" */
+ 0x73, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x65
+ , 0x72
+};
+
+static BYTE NLSALLOC(041d) rgbSMONTHNAME10[] = { /* "oktober" */
+ 0x6f, 0x6b, 0x74, 0x6f, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(041d) rgbSMONTHNAME11[] = { /* "november" */
+ 0x6e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(041d) rgbSMONTHNAME12[] = { /* "december" */
+ 0x64, 0x65, 0x63, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVMONTHNAME1[] = { /* "jan" */
+ 0x6a, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVMONTHNAME2[] = { /* "feb" */
+ 0x66, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVMONTHNAME3[] = { /* "mar" */
+ 0x6d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVMONTHNAME4[] = { /* "apr" */
+ 0x61, 0x70, 0x72
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVMONTHNAME5[] = { /* "maj" */
+ 0x6d, 0x61, 0x6a
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVMONTHNAME6[] = { /* "jun" */
+ 0x6a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVMONTHNAME7[] = { /* "jul" */
+ 0x6a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVMONTHNAME8[] = { /* "aug" */
+ 0x61, 0x75, 0x67
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVMONTHNAME9[] = { /* "sep" */
+ 0x73, 0x65, 0x70
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVMONTHNAME10[] = { /* "okt" */
+ 0x6f, 0x6b, 0x74
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVMONTHNAME11[] = { /* "nov" */
+ 0x6e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(041d) rgbSABBREVMONTHNAME12[] = { /* "dec" */
+ 0x64, 0x65, 0x63
+};
+
+static BYTE NLSALLOC(041d) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(041d) rgbIPOSSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041d) rgbINEGSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041d) rgbIPOSSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041d) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041d) rgbINEGSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041d) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041d) rgbSENGCOUNTRY[] = { /* "Sweden" */
+ 0x53, 0x77, 0x65, 0x64, 0x65, 0x6e
+};
+
+static BYTE NLSALLOC(041d) rgbSENGLANGUAGE[] = { /* "Swedish" */
+ 0x53, 0x77, 0x65, 0x64, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(041d) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041d) rgbIFIRSTWEEKOFYEAR[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(041d) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(041d) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041d) rgbSTIMEFORMAT[] = { /* "HH.mm.ss" */
+ 0x48, 0x48, 0x2e, 0x6d, 0x6d, 0x2e, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(041d) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041d) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041d) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(041d) g_rglcinfo041d[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 7, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 6, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 7, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 2, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 10, rgbSSHORTDATE }
+ , { 17, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 6, rgbSDAYNAME1 }
+ , { 6, rgbSDAYNAME2 }
+ , { 6, rgbSDAYNAME3 }
+ , { 7, rgbSDAYNAME4 }
+ , { 6, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 2, rgbSABBREVDAYNAME1 }
+ , { 2, rgbSABBREVDAYNAME2 }
+ , { 2, rgbSABBREVDAYNAME3 }
+ , { 2, rgbSABBREVDAYNAME4 }
+ , { 2, rgbSABBREVDAYNAME5 }
+ , { 2, rgbSABBREVDAYNAME6 }
+ , { 2, rgbSABBREVDAYNAME7 }
+ , { 7, rgbSMONTHNAME1 }
+ , { 8, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 7, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 6, rgbSENGCOUNTRY }
+ , { 7, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 8, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(041d) g_strinfo041d = {
+ rgbUCase_041d
+ , rgbLCase_041d
+ , rgwCType12_041d
+ , rgwCType3_041d
+ , rgwSort_041d
+ , rgexp_041d
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/041f.c b/private/oleauto/src/dispatch/win16/041f.c
new file mode 100644
index 000000000..53f39ed84
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/041f.c
@@ -0,0 +1,699 @@
+/****************************************************************************
+* 041f.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Turkish - Turkey
+*
+* LCID = 0x041f
+*
+* CodePage = 1254
+*
+* Generated: Thu Dec 01 18:23:53 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+WORD NLSALLOC(041f) rgwSort_041f[256] = {
+ 0x0000, 0xc007, 0xc008, 0xc009, 0xc00a, 0xc00b, 0xc00c, 0xc00d
+ , 0xc00e, 0x4031, 0x4032, 0x4033, 0x4034, 0x4035, 0xc00f, 0xc010
+ , 0xc011, 0xc012, 0xc013, 0xc014, 0xc015, 0xc016, 0xc017, 0xc018
+ , 0xc019, 0xc01a, 0xc01b, 0xc01c, 0xc01d, 0xc01e, 0xc01f, 0xc020
+ , 0x402f, 0x4036, 0x4037, 0x4038, 0x4039, 0x403a, 0x403b, 0xc02a
+ , 0x403c, 0x403d, 0x403e, 0x4060, 0x403f, 0xc02b, 0x4040, 0x4041
+ , 0x007a, 0x007e, 0x007f, 0x0080, 0x0081, 0x0082, 0x0083, 0x0084
+ , 0x0085, 0x0086, 0x4042, 0x4043, 0x4061, 0x4062, 0x4063, 0x4044
+ , 0x4045, 0x1887, 0x1888, 0x1889, 0x188b, 0x188c, 0x188d, 0x188e
+ , 0x1890, 0x0891, 0x1892, 0x1893, 0x1894, 0x1895, 0x1896, 0x1897
+ , 0x1899, 0x189a, 0x189b, 0x189c, 0x189e, 0x18a0, 0x18a2, 0x18a3
+ , 0x18a4, 0x18a5, 0x18a6, 0x4046, 0x4047, 0x4048, 0x4049, 0x404a
+ , 0x404b, 0x0087, 0x0088, 0x0089, 0x008b, 0x008c, 0x008d, 0x008e
+ , 0x0090, 0x1891, 0x0092, 0x0093, 0x0094, 0x0095, 0x0096, 0x0097
+ , 0x0099, 0x009a, 0x009b, 0x009c, 0x009e, 0x00a0, 0x00a2, 0x00a3
+ , 0x00a4, 0x00a5, 0x00a6, 0x404c, 0x404d, 0x404e, 0x404f, 0xc021
+ , 0xc022, 0xc023, 0x405a, 0x018d, 0x405d, 0x4078, 0x4075, 0x4076
+ , 0x4149, 0x4079, 0x199c, 0x405e, 0x0305, 0xc024, 0xc025, 0xc026
+ , 0xc027, 0x4058, 0x4059, 0x405b, 0x405c, 0x4077, 0xc02d, 0xc02e
+ , 0x4057, 0x189f, 0x019c, 0x405f, 0x0405, 0xc028, 0xc029, 0x19a5
+ , 0x4030, 0x4050, 0x4069, 0x406a, 0x406b, 0x406c, 0x4051, 0x406d
+ , 0x4052, 0x406e, 0x1087, 0x4065, 0x406f, 0xc02c, 0x4070, 0x4053
+ , 0x4071, 0x4064, 0x107f, 0x1080, 0x4054, 0x4072, 0x4073, 0x4074
+ , 0x4055, 0x107e, 0x1197, 0x4066, 0x007b, 0x007c, 0x007d, 0x4056
+ , 0x1a87, 0x1987, 0x1b87, 0x1d87, 0x1c87, 0x1e87, 0x0005, 0x188a
+ , 0x1a8c, 0x198c, 0x1b8c, 0x1c8c, 0x1a91, 0x1991, 0x1b91, 0x1c91
+ , 0x188f, 0x1996, 0x1b97, 0x1a97, 0x1c97, 0x1d97, 0x1898, 0x4067
+ , 0x1e97, 0x1aa0, 0x19a0, 0x1ba0, 0x18a1, 0x2091, 0x189d, 0x0105
+ , 0x0287, 0x0187, 0x0387, 0x0587, 0x0487, 0x0687, 0x0205, 0x008a
+ , 0x028c, 0x018c, 0x038c, 0x048c, 0x0291, 0x0191, 0x0391, 0x0491
+ , 0x008f, 0x0196, 0x0397, 0x0297, 0x0497, 0x0597, 0x0098, 0x4068
+ , 0x0697, 0x02a0, 0x01a0, 0x03a0, 0x00a1, 0x0091, 0x009d, 0x01a5
+};
+
+EXPANSION NLSALLOC(041f) rgexp_041f[5] = {
+ { 0x1887, 0x188c }
+ , { 0x009c, 0x009c }
+ , { 0x0087, 0x008c }
+ , { 0x1897, 0x188c }
+ , { 0x0097, 0x008c }
+};
+
+WORD NLSALLOC(041f) rgwCType12_041f[256] = {
+ 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x9068, 0x0028, 0x0028, 0x0028, 0x0028, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0xa048, 0xb010, 0xb010, 0x5010, 0x5010, 0x5010, 0x1010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0x5010, 0x7010, 0x5010, 0x4010, 0x4010
+ , 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084
+ , 0x3084, 0x3084, 0x7010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010, 0x0020
+ , 0x0020, 0x0020, 0xb010, 0x1112, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x5010, 0x1101, 0xb010, 0x1101, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0xb010, 0x1102, 0xb010, 0x1102, 0x0020, 0x0020, 0x1101
+ , 0xa048, 0xb010, 0x5010, 0x5010, 0x5010, 0x5010, 0xb010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x5010, 0x5010, 0x3014, 0x3014, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x3014, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0xb010
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0xb010
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+};
+
+WORD NLSALLOC(041f) rgwCType3_041f[256] = {
+ 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0008, 0x0008, 0x0008, 0x0008, 0x0008, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0048, 0x0048, 0x0448, 0x0048, 0x0448, 0x0048, 0x0048, 0x0440
+ , 0x0048, 0x0048, 0x0048, 0x0048, 0x0048, 0x0440, 0x0048, 0x0448
+ , 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040
+ , 0x0040, 0x0040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0048, 0x0048
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0448, 0x0048, 0x0448, 0x0448
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0000
+ , 0x0000, 0x0000, 0x0008, 0x8000, 0x0008, 0x0008, 0x0008, 0x0008
+ , 0x0001, 0x0008, 0x8003, 0x0008, 0x8000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0088, 0x0088, 0x0088, 0x0088, 0x0008, 0x0400, 0x0400
+ , 0x0408, 0x0000, 0x8003, 0x0008, 0x8000, 0x0000, 0x0000, 0x8003
+ , 0x0008, 0x0008, 0x0048, 0x0048, 0x0008, 0x0048, 0x0048, 0x0008
+ , 0x0408, 0x0008, 0x0400, 0x0008, 0x0048, 0x0408, 0x0008, 0x0448
+ , 0x0008, 0x0008, 0x0000, 0x0000, 0x0408, 0x0008, 0x0008, 0x0008
+ , 0x0408, 0x0000, 0x0400, 0x0008, 0x0000, 0x0000, 0x0000, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+};
+
+BYTE NLSALLOC(041f) rgbUCase_041f[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x8a, 0x9b, 0x8c, 0x9d, 0x9e, 0x9f
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xf7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xfd, 0xde, 0x9f
+};
+
+BYTE NLSALLOC(041f) rgbLCase_041f[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x9a, 0x8b, 0x9c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0xff
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xd7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xdd, 0xfe, 0xdf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
+};
+
+static BYTE NLSALLOC(041f) rgbILANGUAGE[] = { /* "041f" */
+ 0x30, 0x34, 0x31, 0x66
+};
+
+static BYTE NLSALLOC(041f) rgbSLANGUAGE[] = { /* "Turkish" */
+ 0x54, 0x75, 0x72, 0x6b, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVLANGNAME[] = { /* "TRK" */
+ 0x54, 0x52, 0x4b
+};
+
+static BYTE NLSALLOC(041f) rgbSNATIVELANGNAME[] = { /* "Türkçe" */
+ 0x54, 0xfc, 0x72, 0x6b, 0xe7, 0x65
+};
+
+static BYTE NLSALLOC(041f) rgbICOUNTRY[] = { /* "90" */
+ 0x39, 0x30
+};
+
+static BYTE NLSALLOC(041f) rgbSCOUNTRY[] = { /* "Turkey" */
+ 0x54, 0x75, 0x72, 0x6b, 0x65, 0x79
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVCTRYNAME[] = { /* "TUR" */
+ 0x54, 0x55, 0x52
+};
+
+static BYTE NLSALLOC(041f) rgbSNATIVECTRYNAME[] = { /* "Türkiye" */
+ 0x54, 0xfc, 0x72, 0x6b, 0x69, 0x79, 0x65
+};
+
+static BYTE NLSALLOC(041f) rgbIDEFAULTLANGUAGE[] = { /* "041f" */
+ 0x30, 0x34, 0x31, 0x66
+};
+
+static BYTE NLSALLOC(041f) rgbIDEFAULTCOUNTRY[] = { /* "90" */
+ 0x39, 0x30
+};
+
+static BYTE NLSALLOC(041f) rgbIDEFAULTCODEPAGE[] = { /* "857" */
+ 0x38, 0x35, 0x37
+};
+
+static BYTE NLSALLOC(041f) rgbSLIST[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(041f) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041f) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(041f) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(041f) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(041f) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(041f) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041f) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(041f) rgbSCURRENCY[] = { /* "TL" */
+ 0x54, 0x4c
+};
+
+static BYTE NLSALLOC(041f) rgbSINTLSYMBOL[] = { /* "TRL" */
+ 0x54, 0x52, 0x4c
+};
+
+static BYTE NLSALLOC(041f) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(041f) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(041f) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(041f) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(041f) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(041f) rgbICURRENCY[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(041f) rgbINEGCURR[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041f) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(041f) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(041f) rgbSSHORTDATE[] = { /* "d/M/yyyy" */
+ 0x64, 0x2f, 0x4d, 0x2f, 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(041f) rgbSLONGDATE[] = { /* "d MMMM yyyy, dddd" */
+ 0x64, 0x20, 0x4d, 0x4d, 0x4d, 0x4d, 0x20, 0x79
+ , 0x79, 0x79, 0x79, 0x2c, 0x20, 0x64, 0x64, 0x64
+ , 0x64
+};
+
+static BYTE NLSALLOC(041f) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041f) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041f) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041f) rgbICENTURY[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041f) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041f) rgbIDAYLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041f) rgbIMONLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041f) rgbSDAYNAME1[] = { /* "Pazartesi" */
+ 0x50, 0x61, 0x7a, 0x61, 0x72, 0x74, 0x65, 0x73
+ , 0x69
+};
+
+static BYTE NLSALLOC(041f) rgbSDAYNAME2[] = { /* "Sal\x0131" */
+ 0x53, 0x61, 0x6c, 0xfd
+};
+
+static BYTE NLSALLOC(041f) rgbSDAYNAME3[] = { /* "\x00c7ar\x015famba" */
+ 0xc7, 0x61, 0x72, 0xfe, 0x61, 0x6d, 0x62, 0x61
+};
+
+static BYTE NLSALLOC(041f) rgbSDAYNAME4[] = { /* "Per\x015fembe" */
+ 0x50, 0x65, 0x72, 0xfe, 0x65, 0x6d, 0x62, 0x65
+};
+
+static BYTE NLSALLOC(041f) rgbSDAYNAME5[] = { /* "Cuma" */
+ 0x43, 0x75, 0x6d, 0x61
+};
+
+static BYTE NLSALLOC(041f) rgbSDAYNAME6[] = { /* "Cumartesi" */
+ 0x43, 0x75, 0x6d, 0x61, 0x72, 0x74, 0x65, 0x73
+ , 0x69
+};
+
+static BYTE NLSALLOC(041f) rgbSDAYNAME7[] = { /* "Pazar" */
+ 0x50, 0x61, 0x7a, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVDAYNAME1[] = { /* "Pzt" */
+ 0x50, 0x7a, 0x74
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVDAYNAME2[] = { /* "Sal" */
+ 0x53, 0x61, 0x6c
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVDAYNAME3[] = { /* "\x00c7ar" */
+ 0xc7, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVDAYNAME4[] = { /* "Per" */
+ 0x50, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVDAYNAME5[] = { /* "Cum" */
+ 0x43, 0x75, 0x6d
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVDAYNAME6[] = { /* "Cmt" */
+ 0x43, 0x6d, 0x74
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVDAYNAME7[] = { /* "Paz" */
+ 0x50, 0x61, 0x7a
+};
+
+static BYTE NLSALLOC(041f) rgbSMONTHNAME1[] = { /* "Ocak" */
+ 0x4f, 0x63, 0x61, 0x6b
+};
+
+static BYTE NLSALLOC(041f) rgbSMONTHNAME2[] = { /* "\x015eubat" */
+ 0xde, 0x75, 0x62, 0x61, 0x74
+};
+
+static BYTE NLSALLOC(041f) rgbSMONTHNAME3[] = { /* "Mart" */
+ 0x4d, 0x61, 0x72, 0x74
+};
+
+static BYTE NLSALLOC(041f) rgbSMONTHNAME4[] = { /* "Nisan" */
+ 0x4e, 0x69, 0x73, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(041f) rgbSMONTHNAME5[] = { /* "May\x0131s" */
+ 0x4d, 0x61, 0x79, 0xfd, 0x73
+};
+
+static BYTE NLSALLOC(041f) rgbSMONTHNAME6[] = { /* "Haziran" */
+ 0x48, 0x61, 0x7a, 0x69, 0x72, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(041f) rgbSMONTHNAME7[] = { /* "Temmuz" */
+ 0x54, 0x65, 0x6d, 0x6d, 0x75, 0x7a
+};
+
+static BYTE NLSALLOC(041f) rgbSMONTHNAME8[] = { /* "A\x011fustos" */
+ 0x41, 0xf0, 0x75, 0x73, 0x74, 0x6f, 0x73
+};
+
+static BYTE NLSALLOC(041f) rgbSMONTHNAME9[] = { /* "Eylül" */
+ 0x45, 0x79, 0x6c, 0xfc, 0x6c
+};
+
+static BYTE NLSALLOC(041f) rgbSMONTHNAME10[] = { /* "Ekim" */
+ 0x45, 0x6b, 0x69, 0x6d
+};
+
+static BYTE NLSALLOC(041f) rgbSMONTHNAME11[] = { /* "Kas\x0131m" */
+ 0x4b, 0x61, 0x73, 0xfd, 0x6d
+};
+
+static BYTE NLSALLOC(041f) rgbSMONTHNAME12[] = { /* "Aral\x0131k" */
+ 0x41, 0x72, 0x61, 0x6c, 0xfd, 0x6b
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVMONTHNAME1[] = { /* "Oca" */
+ 0x4f, 0x63, 0x61
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVMONTHNAME2[] = { /* "\x015eub" */
+ 0xde, 0x75, 0x62
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVMONTHNAME3[] = { /* "Mar" */
+ 0x4d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVMONTHNAME4[] = { /* "Nis" */
+ 0x4e, 0x69, 0x73
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVMONTHNAME5[] = { /* "May" */
+ 0x4d, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVMONTHNAME6[] = { /* "Haz" */
+ 0x48, 0x61, 0x7a
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVMONTHNAME7[] = { /* "Tem" */
+ 0x54, 0x65, 0x6d
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVMONTHNAME8[] = { /* "A\x011fu" */
+ 0x41, 0xf0, 0x75
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVMONTHNAME9[] = { /* "Eyl" */
+ 0x45, 0x79, 0x6c
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVMONTHNAME10[] = { /* "Eki" */
+ 0x45, 0x6b, 0x69
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVMONTHNAME11[] = { /* "Kas" */
+ 0x4b, 0x61, 0x73
+};
+
+static BYTE NLSALLOC(041f) rgbSABBREVMONTHNAME12[] = { /* "Ara" */
+ 0x41, 0x72, 0x61
+};
+
+static BYTE NLSALLOC(041f) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(041f) rgbIPOSSIGNPOSN[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(041f) rgbINEGSIGNPOSN[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(041f) rgbIPOSSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041f) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041f) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041f) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041f) rgbSENGCOUNTRY[] = { /* "Turkey" */
+ 0x54, 0x75, 0x72, 0x6b, 0x65, 0x79
+};
+
+static BYTE NLSALLOC(041f) rgbSENGLANGUAGE[] = { /* "Turkish" */
+ 0x54, 0x75, 0x72, 0x6b, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(041f) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041f) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041f) rgbIDEFAULTANSICODEPAGE[] = { /* "1254" */
+ 0x31, 0x32, 0x35, 0x34
+};
+
+static BYTE NLSALLOC(041f) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041f) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(041f) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(041f) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(041f) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(041f) g_rglcinfo041f[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 7, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 6, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 6, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 7, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 2, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 17, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 9, rgbSDAYNAME1 }
+ , { 4, rgbSDAYNAME2 }
+ , { 8, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 4, rgbSDAYNAME5 }
+ , { 9, rgbSDAYNAME6 }
+ , { 5, rgbSDAYNAME7 }
+ , { 3, rgbSABBREVDAYNAME1 }
+ , { 3, rgbSABBREVDAYNAME2 }
+ , { 3, rgbSABBREVDAYNAME3 }
+ , { 3, rgbSABBREVDAYNAME4 }
+ , { 3, rgbSABBREVDAYNAME5 }
+ , { 3, rgbSABBREVDAYNAME6 }
+ , { 3, rgbSABBREVDAYNAME7 }
+ , { 4, rgbSMONTHNAME1 }
+ , { 5, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 5, rgbSMONTHNAME5 }
+ , { 7, rgbSMONTHNAME6 }
+ , { 6, rgbSMONTHNAME7 }
+ , { 7, rgbSMONTHNAME8 }
+ , { 5, rgbSMONTHNAME9 }
+ , { 4, rgbSMONTHNAME10 }
+ , { 5, rgbSMONTHNAME11 }
+ , { 6, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 6, rgbSENGCOUNTRY }
+ , { 7, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(041f) g_strinfo041f = {
+ rgbUCase_041f
+ , rgbLCase_041f
+ , rgwCType12_041f
+ , rgwCType3_041f
+ , rgwSort_041f
+ , rgexp_041f
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0429.c b/private/oleauto/src/dispatch/win16/0429.c
new file mode 100644
index 000000000..0ecfdbd67
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0429.c
@@ -0,0 +1,536 @@
+/****************************************************************************
+* 0429.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Arabic - Iran
+*
+* LCID = 0x0429
+*
+* CodePage = 1256
+*
+* Generated: Thu Dec 01 18:42:04 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0401[256]; // from 0401:Arabic - Saudi Arabia
+extern EXPANSION rgexp_0401[3];
+extern WORD rgwCType12_0401[256];
+extern WORD rgwCType3_0401[256];
+extern BYTE rgbUCase_0401[256];
+extern BYTE rgbLCase_0401[256];
+
+static BYTE NLSALLOC(0429) rgbILANGUAGE[] = { /* "0429" */
+ 0x30, 0x34, 0x32, 0x39
+};
+
+static BYTE NLSALLOC(0429) rgbSLANGUAGE[] = { /* "Farsi" */
+ 0x46, 0x61, 0x72, 0x73, 0x69
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVLANGNAME[] = { /* "FAR" */
+ 0x46, 0x41, 0x52
+};
+
+static BYTE NLSALLOC(0429) rgbSNATIVELANGNAME[] = { /* "\x0641\x0627\x0631\x0633\x0649" */
+ 0xdd, 0xc7, 0xd1, 0xd3, 0xec
+};
+
+static BYTE NLSALLOC(0429) rgbICOUNTRY[] = { /* "981" */
+ 0x39, 0x38, 0x31
+};
+
+static BYTE NLSALLOC(0429) rgbSCOUNTRY[] = { /* "Iran" */
+ 0x49, 0x72, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVCTRYNAME[] = { /* "IRN" */
+ 0x49, 0x52, 0x4e
+};
+
+static BYTE NLSALLOC(0429) rgbSNATIVECTRYNAME[] = { /* "Iran" */
+ 0x49, 0x72, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0429) rgbIDEFAULTLANGUAGE[] = { /* "0429" */
+ 0x30, 0x34, 0x32, 0x39
+};
+
+static BYTE NLSALLOC(0429) rgbIDEFAULTCOUNTRY[] = { /* "981" */
+ 0x39, 0x38, 0x31
+};
+
+static BYTE NLSALLOC(0429) rgbIDEFAULTCODEPAGE[] = { /* "708" */
+ 0x37, 0x30, 0x38
+};
+
+static BYTE NLSALLOC(0429) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0429) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0429) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0429) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0429) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0429) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0429) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0429) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0429) rgbSCURRENCY[] = { /* "\x0631\x0649\x0627\x0644" */
+ 0xd1, 0xec, 0xc7, 0xe1
+};
+
+static BYTE NLSALLOC(0429) rgbSINTLSYMBOL[] = { /* "IRR" */
+ 0x49, 0x52, 0x52
+};
+
+static BYTE NLSALLOC(0429) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0429) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0429) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0429) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0429) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0429) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0429) rgbINEGCURR[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0429) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(0429) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0429) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0429) rgbSLONGDATE[] = { /* "dd/MM/yyyy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0429) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0429) rgbILDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0429) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0429) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0429) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0429) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0429) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0429) rgbS1159[] = { /* "\x0642.\x0638" */
+ 0xde, 0x2e, 0xd9
+};
+
+static BYTE NLSALLOC(0429) rgbS2359[] = { /* "\x0628.\x0638" */
+ 0xc8, 0x2e, 0xd9
+};
+
+static BYTE NLSALLOC(0429) rgbSDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(0429) rgbSDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(0429) rgbSDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(0429) rgbSDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(0429) rgbSDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(0429) rgbSDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(0429) rgbSDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(0429) rgbSMONTHNAME1[] = { /* "\x0645\x062d\x0631\x0645" */
+ 0xe3, 0xcd, 0xd1, 0xe3
+};
+
+static BYTE NLSALLOC(0429) rgbSMONTHNAME2[] = { /* "\x0633\x0641\x0631" */
+ 0xd3, 0xdd, 0xd1
+};
+
+static BYTE NLSALLOC(0429) rgbSMONTHNAME3[] = { /* "\x0631\x0628\x064a\x0639 \x0623\x0648\x0644" */
+ 0xd1, 0xc8, 0xed, 0xda, 0x20, 0xc3, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(0429) rgbSMONTHNAME4[] = { /* "\x0631\x0628\x064a\x0639 \x062b\x0627\x0646\x064a" */
+ 0xd1, 0xc8, 0xed, 0xda, 0x20, 0xcb, 0xc7, 0xe4
+ , 0xed
+};
+
+static BYTE NLSALLOC(0429) rgbSMONTHNAME5[] = { /* "\x062c\x0645\x0627\x062f\x0649 \x0623\x0648\x0644" */
+ 0xcc, 0xe3, 0xc7, 0xcf, 0xec, 0x20, 0xc3, 0xe6
+ , 0xe1
+};
+
+static BYTE NLSALLOC(0429) rgbSMONTHNAME6[] = { /* "\x062c\x0645\x0627\x062f\x0649 \x062b\x0627\x0646\x064a" */
+ 0xcc, 0xe3, 0xc7, 0xcf, 0xec, 0x20, 0xcb, 0xc7
+ , 0xe4, 0xed
+};
+
+static BYTE NLSALLOC(0429) rgbSMONTHNAME7[] = { /* "\x0631\x062c\x0628" */
+ 0xd1, 0xcc, 0xc8
+};
+
+static BYTE NLSALLOC(0429) rgbSMONTHNAME8[] = { /* "\x0634\x0639\x0628\x0627\x0646" */
+ 0xd4, 0xda, 0xc8, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(0429) rgbSMONTHNAME9[] = { /* "\x0631\x0645\x0636\x0627\x0646" */
+ 0xd1, 0xe3, 0xd6, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(0429) rgbSMONTHNAME10[] = { /* "\x0634\x0648\x0627\x0644" */
+ 0xd4, 0xe6, 0xc7, 0xe1
+};
+
+static BYTE NLSALLOC(0429) rgbSMONTHNAME11[] = { /* "\x0630\x0648 \x0627\x0644\x0642\x0639\x062f\x0629" */
+ 0xd0, 0xe6, 0x20, 0xc7, 0xe1, 0xde, 0xda, 0xcf
+ , 0xc9
+};
+
+static BYTE NLSALLOC(0429) rgbSMONTHNAME12[] = { /* "\x0630\x0648 \x0627\x0644\x062d\x062c\x0629" */
+ 0xd0, 0xe6, 0x20, 0xc7, 0xe1, 0xcd, 0xcc, 0xc9
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVMONTHNAME1[] = { /* "\x0645\x062d\x0631\x0645" */
+ 0xe3, 0xcd, 0xd1, 0xe3
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVMONTHNAME2[] = { /* "\x0633\x0641\x0631" */
+ 0xd3, 0xdd, 0xd1
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVMONTHNAME3[] = { /* "\x0631\x0628\x064a\x0639 \x0623\x0648\x0644" */
+ 0xd1, 0xc8, 0xed, 0xda, 0x20, 0xc3, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVMONTHNAME4[] = { /* "\x0631\x0628\x064a\x0639 \x062b\x0627\x0646\x064a" */
+ 0xd1, 0xc8, 0xed, 0xda, 0x20, 0xcb, 0xc7, 0xe4
+ , 0xed
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVMONTHNAME5[] = { /* "\x062c\x0645\x0627\x062f\x0649 \x0623\x0648\x0644" */
+ 0xcc, 0xe3, 0xc7, 0xcf, 0xec, 0x20, 0xc3, 0xe6
+ , 0xe1
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVMONTHNAME6[] = { /* "\x062c\x0645\x0627\x062f\x0649 \x062b\x0627\x0646\x064a" */
+ 0xcc, 0xe3, 0xc7, 0xcf, 0xec, 0x20, 0xcb, 0xc7
+ , 0xe4, 0xed
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVMONTHNAME7[] = { /* "\x0631\x062c\x0628" */
+ 0xd1, 0xcc, 0xc8
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVMONTHNAME8[] = { /* "\x0634\x0639\x0628\x0627\x0646" */
+ 0xd4, 0xda, 0xc8, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVMONTHNAME9[] = { /* "\x0631\x0645\x0636\x0627\x0646" */
+ 0xd1, 0xe3, 0xd6, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVMONTHNAME10[] = { /* "\x0634\x0648\x0627\x0644" */
+ 0xd4, 0xe6, 0xc7, 0xe1
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVMONTHNAME11[] = { /* "\x0630\x0648 \x0627\x0644\x0642\x0639\x062f\x0629" */
+ 0xd0, 0xe6, 0x20, 0xc7, 0xe1, 0xde, 0xda, 0xcf
+ , 0xc9
+};
+
+static BYTE NLSALLOC(0429) rgbSABBREVMONTHNAME12[] = { /* "\x0630\x0648 \x0627\x0644\x062d\x062c\x0629" */
+ 0xd0, 0xe6, 0x20, 0xc7, 0xe1, 0xcd, 0xcc, 0xc9
+};
+
+static BYTE NLSALLOC(0429) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0429) rgbIPOSSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0429) rgbINEGSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0429) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0429) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0429) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0429) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0429) rgbSENGCOUNTRY[] = { /* "Iran" */
+ 0x49, 0x72, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0429) rgbSENGLANGUAGE[] = { /* "Farsi" */
+ 0x46, 0x61, 0x72, 0x73, 0x69
+};
+
+static BYTE NLSALLOC(0429) rgbIFIRSTDAYOFWEEK[] = { /* "5" */
+ 0x35
+};
+
+static BYTE NLSALLOC(0429) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0429) rgbIDEFAULTANSICODEPAGE[] = { /* "1256" */
+ 0x31, 0x32, 0x35, 0x36
+};
+
+static BYTE NLSALLOC(0429) rgbINEGNUMBER[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0429) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0429) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0429) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0429) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0429) g_rglcinfo0429[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 5, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 5, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 4, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 4, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 4, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 10, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 3, rgbS1159 }
+ , { 3, rgbS2359 }
+ , { 5, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 7, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 8, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 5, rgbSABBREVDAYNAME1 }
+ , { 5, rgbSABBREVDAYNAME2 }
+ , { 7, rgbSABBREVDAYNAME3 }
+ , { 8, rgbSABBREVDAYNAME4 }
+ , { 8, rgbSABBREVDAYNAME5 }
+ , { 6, rgbSABBREVDAYNAME6 }
+ , { 6, rgbSABBREVDAYNAME7 }
+ , { 4, rgbSMONTHNAME1 }
+ , { 3, rgbSMONTHNAME2 }
+ , { 8, rgbSMONTHNAME3 }
+ , { 9, rgbSMONTHNAME4 }
+ , { 9, rgbSMONTHNAME5 }
+ , { 10, rgbSMONTHNAME6 }
+ , { 3, rgbSMONTHNAME7 }
+ , { 5, rgbSMONTHNAME8 }
+ , { 5, rgbSMONTHNAME9 }
+ , { 4, rgbSMONTHNAME10 }
+ , { 9, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 4, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 8, rgbSABBREVMONTHNAME3 }
+ , { 9, rgbSABBREVMONTHNAME4 }
+ , { 9, rgbSABBREVMONTHNAME5 }
+ , { 10, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 5, rgbSABBREVMONTHNAME8 }
+ , { 5, rgbSABBREVMONTHNAME9 }
+ , { 4, rgbSABBREVMONTHNAME10 }
+ , { 9, rgbSABBREVMONTHNAME11 }
+ , { 8, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 4, rgbSENGCOUNTRY }
+ , { 5, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0429) g_strinfo0429 = {
+ rgbUCase_0401
+ , rgbLCase_0401
+ , rgwCType12_0401
+ , rgwCType3_0401
+ , rgwSort_0401
+ , rgexp_0401
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0801.c b/private/oleauto/src/dispatch/win16/0801.c
new file mode 100644
index 000000000..e427330ac
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0801.c
@@ -0,0 +1,536 @@
+/****************************************************************************
+* 0801.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Arabic - Iraq
+*
+* LCID = 0x0801
+*
+* CodePage = 1256
+*
+* Generated: Thu Dec 01 18:41:08 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0401[256]; // from 0401:Arabic - Saudi Arabia
+extern EXPANSION rgexp_0401[3];
+extern WORD rgwCType12_0401[256];
+extern WORD rgwCType3_0401[256];
+extern BYTE rgbUCase_0401[256];
+extern BYTE rgbLCase_0401[256];
+
+static BYTE NLSALLOC(0801) rgbILANGUAGE[] = { /* "0801" */
+ 0x30, 0x38, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(0801) rgbSLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVLANGNAME[] = { /* "ARI" */
+ 0x41, 0x52, 0x49
+};
+
+static BYTE NLSALLOC(0801) rgbSNATIVELANGNAME[] = { /* "\x0627\x0644\x0639\x0631\x0628\x064a\x0629" */
+ 0xc7, 0xe1, 0xda, 0xd1, 0xc8, 0xed, 0xc9
+};
+
+static BYTE NLSALLOC(0801) rgbICOUNTRY[] = { /* "964" */
+ 0x39, 0x36, 0x34
+};
+
+static BYTE NLSALLOC(0801) rgbSCOUNTRY[] = { /* "Iraq" */
+ 0x49, 0x72, 0x61, 0x71
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVCTRYNAME[] = { /* "IRQ" */
+ 0x49, 0x52, 0x51
+};
+
+static BYTE NLSALLOC(0801) rgbSNATIVECTRYNAME[] = { /* "Iraq" */
+ 0x49, 0x72, 0x61, 0x71
+};
+
+static BYTE NLSALLOC(0801) rgbIDEFAULTLANGUAGE[] = { /* "0801" */
+ 0x30, 0x38, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(0801) rgbIDEFAULTCOUNTRY[] = { /* "964" */
+ 0x39, 0x36, 0x34
+};
+
+static BYTE NLSALLOC(0801) rgbIDEFAULTCODEPAGE[] = { /* "708" */
+ 0x37, 0x30, 0x38
+};
+
+static BYTE NLSALLOC(0801) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0801) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0801) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0801) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0801) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0801) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0801) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0801) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0801) rgbSCURRENCY[] = { /* "dinar" */
+ 0x64, 0x69, 0x6e, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0801) rgbSINTLSYMBOL[] = { /* "IQD" */
+ 0x49, 0x51, 0x44
+};
+
+static BYTE NLSALLOC(0801) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0801) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0801) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0801) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0801) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0801) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0801) rgbINEGCURR[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0801) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(0801) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0801) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0801) rgbSLONGDATE[] = { /* "dd/MM/yyyy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0801) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0801) rgbILDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0801) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0801) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0801) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0801) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0801) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0801) rgbS1159[] = { /* "\x0635" */
+ 0xd5
+};
+
+static BYTE NLSALLOC(0801) rgbS2359[] = { /* "\x0645" */
+ 0xe3
+};
+
+static BYTE NLSALLOC(0801) rgbSDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(0801) rgbSDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(0801) rgbSDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(0801) rgbSDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(0801) rgbSDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(0801) rgbSDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(0801) rgbSDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(0801) rgbSMONTHNAME1[] = { /* "\x0645\x062d\x0631\x0645" */
+ 0xe3, 0xcd, 0xd1, 0xe3
+};
+
+static BYTE NLSALLOC(0801) rgbSMONTHNAME2[] = { /* "\x0633\x0641\x0631" */
+ 0xd3, 0xdd, 0xd1
+};
+
+static BYTE NLSALLOC(0801) rgbSMONTHNAME3[] = { /* "\x0631\x0628\x064a\x0639 \x0623\x0648\x0644" */
+ 0xd1, 0xc8, 0xed, 0xda, 0x20, 0xc3, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(0801) rgbSMONTHNAME4[] = { /* "\x0631\x0628\x064a\x0639 \x062b\x0627\x0646\x064a" */
+ 0xd1, 0xc8, 0xed, 0xda, 0x20, 0xcb, 0xc7, 0xe4
+ , 0xed
+};
+
+static BYTE NLSALLOC(0801) rgbSMONTHNAME5[] = { /* "\x062c\x0645\x0627\x062f\x0649 \x0623\x0648\x0644" */
+ 0xcc, 0xe3, 0xc7, 0xcf, 0xec, 0x20, 0xc3, 0xe6
+ , 0xe1
+};
+
+static BYTE NLSALLOC(0801) rgbSMONTHNAME6[] = { /* "\x062c\x0645\x0627\x062f\x0649 \x062b\x0627\x0646\x064a" */
+ 0xcc, 0xe3, 0xc7, 0xcf, 0xec, 0x20, 0xcb, 0xc7
+ , 0xe4, 0xed
+};
+
+static BYTE NLSALLOC(0801) rgbSMONTHNAME7[] = { /* "\x0631\x062c\x0628" */
+ 0xd1, 0xcc, 0xc8
+};
+
+static BYTE NLSALLOC(0801) rgbSMONTHNAME8[] = { /* "\x0634\x0639\x0628\x0627\x0646" */
+ 0xd4, 0xda, 0xc8, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(0801) rgbSMONTHNAME9[] = { /* "\x0631\x0645\x0636\x0627\x0646" */
+ 0xd1, 0xe3, 0xd6, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(0801) rgbSMONTHNAME10[] = { /* "\x0634\x0648\x0627\x0644" */
+ 0xd4, 0xe6, 0xc7, 0xe1
+};
+
+static BYTE NLSALLOC(0801) rgbSMONTHNAME11[] = { /* "\x0630\x0648 \x0627\x0644\x0642\x0639\x062f\x0629" */
+ 0xd0, 0xe6, 0x20, 0xc7, 0xe1, 0xde, 0xda, 0xcf
+ , 0xc9
+};
+
+static BYTE NLSALLOC(0801) rgbSMONTHNAME12[] = { /* "\x0630\x0648 \x0627\x0644\x062d\x062c\x0629" */
+ 0xd0, 0xe6, 0x20, 0xc7, 0xe1, 0xcd, 0xcc, 0xc9
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVMONTHNAME1[] = { /* "\x0645\x062d\x0631\x0645" */
+ 0xe3, 0xcd, 0xd1, 0xe3
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVMONTHNAME2[] = { /* "\x0633\x0641\x0631" */
+ 0xd3, 0xdd, 0xd1
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVMONTHNAME3[] = { /* "\x0631\x0628\x064a\x0639 \x0623\x0648\x0644" */
+ 0xd1, 0xc8, 0xed, 0xda, 0x20, 0xc3, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVMONTHNAME4[] = { /* "\x0631\x0628\x064a\x0639 \x062b\x0627\x0646\x064a" */
+ 0xd1, 0xc8, 0xed, 0xda, 0x20, 0xcb, 0xc7, 0xe4
+ , 0xed
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVMONTHNAME5[] = { /* "\x062c\x0645\x0627\x062f\x0649 \x0623\x0648\x0644" */
+ 0xcc, 0xe3, 0xc7, 0xcf, 0xec, 0x20, 0xc3, 0xe6
+ , 0xe1
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVMONTHNAME6[] = { /* "\x062c\x0645\x0627\x062f\x0649 \x062b\x0627\x0646\x064a" */
+ 0xcc, 0xe3, 0xc7, 0xcf, 0xec, 0x20, 0xcb, 0xc7
+ , 0xe4, 0xed
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVMONTHNAME7[] = { /* "\x0631\x062c\x0628" */
+ 0xd1, 0xcc, 0xc8
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVMONTHNAME8[] = { /* "\x0634\x0639\x0628\x0627\x0646" */
+ 0xd4, 0xda, 0xc8, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVMONTHNAME9[] = { /* "\x0631\x0645\x0636\x0627\x0646" */
+ 0xd1, 0xe3, 0xd6, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVMONTHNAME10[] = { /* "\x0634\x0648\x0627\x0644" */
+ 0xd4, 0xe6, 0xc7, 0xe1
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVMONTHNAME11[] = { /* "\x0630\x0648 \x0627\x0644\x0642\x0639\x062f\x0629" */
+ 0xd0, 0xe6, 0x20, 0xc7, 0xe1, 0xde, 0xda, 0xcf
+ , 0xc9
+};
+
+static BYTE NLSALLOC(0801) rgbSABBREVMONTHNAME12[] = { /* "\x0630\x0648 \x0627\x0644\x062d\x062c\x0629" */
+ 0xd0, 0xe6, 0x20, 0xc7, 0xe1, 0xcd, 0xcc, 0xc9
+};
+
+static BYTE NLSALLOC(0801) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0801) rgbIPOSSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0801) rgbINEGSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0801) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0801) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0801) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0801) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0801) rgbSENGCOUNTRY[] = { /* "Iraq" */
+ 0x49, 0x72, 0x61, 0x71
+};
+
+static BYTE NLSALLOC(0801) rgbSENGLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(0801) rgbIFIRSTDAYOFWEEK[] = { /* "5" */
+ 0x35
+};
+
+static BYTE NLSALLOC(0801) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0801) rgbIDEFAULTANSICODEPAGE[] = { /* "1256" */
+ 0x31, 0x32, 0x35, 0x36
+};
+
+static BYTE NLSALLOC(0801) rgbINEGNUMBER[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0801) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0801) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0801) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0801) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0801) g_rglcinfo0801[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 4, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 4, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 5, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 10, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 1, rgbS1159 }
+ , { 1, rgbS2359 }
+ , { 5, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 7, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 8, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 5, rgbSABBREVDAYNAME1 }
+ , { 5, rgbSABBREVDAYNAME2 }
+ , { 7, rgbSABBREVDAYNAME3 }
+ , { 8, rgbSABBREVDAYNAME4 }
+ , { 8, rgbSABBREVDAYNAME5 }
+ , { 6, rgbSABBREVDAYNAME6 }
+ , { 6, rgbSABBREVDAYNAME7 }
+ , { 4, rgbSMONTHNAME1 }
+ , { 3, rgbSMONTHNAME2 }
+ , { 8, rgbSMONTHNAME3 }
+ , { 9, rgbSMONTHNAME4 }
+ , { 9, rgbSMONTHNAME5 }
+ , { 10, rgbSMONTHNAME6 }
+ , { 3, rgbSMONTHNAME7 }
+ , { 5, rgbSMONTHNAME8 }
+ , { 5, rgbSMONTHNAME9 }
+ , { 4, rgbSMONTHNAME10 }
+ , { 9, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 4, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 8, rgbSABBREVMONTHNAME3 }
+ , { 9, rgbSABBREVMONTHNAME4 }
+ , { 9, rgbSABBREVMONTHNAME5 }
+ , { 10, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 5, rgbSABBREVMONTHNAME8 }
+ , { 5, rgbSABBREVMONTHNAME9 }
+ , { 4, rgbSABBREVMONTHNAME10 }
+ , { 9, rgbSABBREVMONTHNAME11 }
+ , { 8, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 4, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0801) g_strinfo0801 = {
+ rgbUCase_0401
+ , rgbLCase_0401
+ , rgwCType12_0401
+ , rgwCType3_0401
+ , rgwSort_0401
+ , rgexp_0401
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0804.c b/private/oleauto/src/dispatch/win16/0804.c
new file mode 100644
index 000000000..8e5066f09
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0804.c
@@ -0,0 +1,724 @@
+/***
+*0804.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+*
+* China, Chinese Simplified (People's Republic of China [PRC])
+*
+* LCID = 0x0804
+*
+*
+*Generated: 9/22/93 - by hand from lcid_chs.txt
+*
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+#include "nlsdbcs.h"
+
+
+#if 1
+static SORTWEIGHT NLSALLOC(0804) rgsortweight[] = {
+ { 0x0000, 0x0200, 0x00, 0x00 }
+ , { 0x0020, 0x1020, 0x00, 0x02 }
+ , { 0x0030, 0x5030, 0x00, 0x02 }
+ , { 0x003A, 0x103A, 0x00, 0x02 }
+ , { 0x0041, 0x6041, 0x00, 0x02 }
+ , { 0x005B, 0x105B, 0x00, 0x02 }
+ , { 0x0061, 0x6041, 0x02, 0x02 }
+ , { 0x007B, 0x107B, 0x00, 0x02 }
+ , { 0x007F, 0xFFFF, 0x00, 0xFF }
+ , { 0xA1A1, 0x1020, 0x01, 0x02 }
+ , { 0xA1A2, 0x20A2, 0x00, 0x00 }
+ , { 0xA3A1, 0x1021, 0x01, 0x02 }
+ , { 0xA3B0, 0x5030, 0x01, 0x02 }
+ , { 0xA3BA, 0x103A, 0x01, 0x02 }
+ , { 0xA3C1, 0x6041, 0x01, 0x02 }
+ , { 0xA3DB, 0x105B, 0x01, 0x02 }
+ , { 0xA3E1, 0x6041, 0x03, 0x02 }
+ , { 0xA3FB, 0x107B, 0x01, 0x02 }
+ , { 0xA4A1, 0x30A1, 0x00, 0x00 }
+ , { 0xA6A1, 0x32A1, 0x01, 0x02 }
+ , { 0xA6C1, 0x32A1, 0x03, 0x02 }
+ , { 0xA7A1, 0x33A1, 0x01, 0x02 }
+ , { 0xA7D1, 0x33A1, 0x03, 0x02 }
+ , { 0xA8A1, 0x34A1, 0x00, 0x00 }
+ , { 0xB0A1, 0xB0A1, 0x00, 0x00 }
+};
+static MAPTABLE NLSALLOC(0804) rgmaptable[] = {
+ { 0x1020, 0x0001, 0x0020, 0xA1A1, 0x0020, 0xA1A1 }
+ , { 0x1021, 0x005F, 0x0021, 0xA3A1, 0x0021, 0xA3A1 }
+ , { 0x32A1, 0x0018, 0xA6A1, 0xA6A1, 0xA6C1, 0xA6C1 }
+ , { 0x33A1, 0x0021, 0xA7A1, 0xA7A1, 0xA7D1, 0xA7D1 }
+ , { 0x5030, 0x000A, 0x0030, 0xA3B0, 0x0030, 0xA3B0 }
+ , { 0x6041, 0x001A, 0x0041, 0xA3C1, 0x0061, 0xA3E1 }
+};
+static TYPETABLE NLSALLOC(0804) rgtypetable[] = {
+ { 0x0000, 0x0020, 0x00, 0x00 }
+ , { 0x0009, 0x0068, 0x09, 0x00 }
+ , { 0x000A, 0x0028, 0x00, 0x00 }
+ , { 0x000E, 0x0020, 0x00, 0x00 }
+ , { 0x0020, 0x0048, 0x0A, 0x00 }
+ , { 0x0021, 0x0010, 0x0B, 0x08 }
+ , { 0x0024, 0x0010, 0x05, 0x08 }
+ , { 0x0026, 0x0010, 0x01, 0x08 }
+ , { 0x002B, 0x0010, 0x05, 0x08 }
+ , { 0x002C, 0x0010, 0x07, 0x08 }
+ , { 0x002D, 0x0010, 0x05, 0x08 }
+ , { 0x002E, 0x0010, 0x03, 0x08 }
+ , { 0x0030, 0x0084, 0x03, 0x00 }
+ , { 0x003A, 0x0010, 0x07, 0x08 }
+ , { 0x003B, 0x0010, 0x0B, 0x08 }
+ , { 0x0040, 0x0010, 0x01, 0x08 }
+ , { 0x0041, 0x0181, 0x01, 0x00 }
+ , { 0x0047, 0x0101, 0x01, 0x00 }
+ , { 0x005B, 0x0010, 0x0B, 0x08 }
+ , { 0x0061, 0x0182, 0x01, 0x00 }
+ , { 0x0067, 0x0102, 0x01, 0x00 }
+ , { 0x007B, 0x0010, 0x0B, 0x08 }
+ , { 0x007F, 0x0020, 0x00, 0x00 }
+ , { 0x0080, 0x0000, 0x0B, 0x08 }
+ , { 0xA1A1, 0x0048, 0x0A, 0x00 }
+ , { 0xA1A2, 0x0000, 0x0B, 0x08 }
+ , { 0xA3A1, 0x0010, 0x0B, 0x08 }
+ , { 0xA3A4, 0x0010, 0x05, 0x08 }
+ , { 0xA3A6, 0x0010, 0x01, 0x08 }
+ , { 0xA3AB, 0x0010, 0x05, 0x08 }
+ , { 0xA3AC, 0x0010, 0x07, 0x08 }
+ , { 0xA3AD, 0x0010, 0x05, 0x08 }
+ , { 0xA3AE, 0x0010, 0x03, 0x08 }
+ , { 0xA3B0, 0x0084, 0x03, 0x00 }
+ , { 0xA3BA, 0x0010, 0x07, 0x08 }
+ , { 0xA3BB, 0x0010, 0x0B, 0x08 }
+ , { 0xA3C0, 0x0010, 0x01, 0x08 }
+ , { 0xA3C1, 0x0181, 0x01, 0x00 }
+ , { 0xA3C7, 0x0101, 0x01, 0x00 }
+ , { 0xA3DB, 0x0010, 0x0B, 0x08 }
+ , { 0xA3E1, 0x0182, 0x01, 0x00 }
+ , { 0xA3E7, 0x0102, 0x01, 0x00 }
+ , { 0xA3FB, 0x0010, 0x0B, 0x08 }
+ , { 0xA4A1, 0x0010, 0x0B, 0x08 }
+ , { 0xB0A1, 0x0100, 0x01, 0x00 }
+};
+#else
+static unsigned char NLSALLOC(0804) rgsortweight[] = {
+ 0x00 ,0x00 ,0x00 ,0x02 ,0x00 ,0x00
+ , 0x20 ,0x00 ,0x20 ,0x10 ,0x00 ,0x02
+ , 0x30 ,0x00 ,0x30 ,0x50 ,0x00 ,0x02
+ , 0x3A ,0x00 ,0x3A ,0x10 ,0x00 ,0x02
+ , 0x41 ,0x00 ,0x41 ,0x60 ,0x00 ,0x02
+ , 0x5B ,0x00 ,0x5B ,0x10 ,0x00 ,0x02
+ , 0x61 ,0x00 ,0x41 ,0x60 ,0x02 ,0x02
+ , 0x7B ,0x00 ,0x7B ,0x10 ,0x00 ,0x02
+ , 0x7F ,0x00 ,0xFF ,0xFF ,0x00 ,0xFF
+ , 0xA1 ,0xA1 ,0x20 ,0x10 ,0x01 ,0x02
+ , 0xA2 ,0xA1 ,0xA2 ,0x20 ,0x00 ,0x00
+ , 0xA1 ,0xA3 ,0x21 ,0x10 ,0x01 ,0x02
+ , 0xB0 ,0xA3 ,0x30 ,0x50 ,0x01 ,0x02
+ , 0xBA ,0xA3 ,0x3A ,0x10 ,0x01 ,0x02
+ , 0xC1 ,0xA3 ,0x41 ,0x60 ,0x01 ,0x02
+ , 0xDB ,0xA3 ,0x5B ,0x10 ,0x01 ,0x02
+ , 0xE1 ,0xA3 ,0x41 ,0x60 ,0x03 ,0x02
+ , 0xFB ,0xA3 ,0x7B ,0x10 ,0x01 ,0x02
+ , 0xA1 ,0xA4 ,0xA1 ,0x30 ,0x00 ,0x00
+ , 0xA1 ,0xA6 ,0xA1 ,0x32 ,0x01 ,0x02
+ , 0xC1 ,0xA6 ,0xA1 ,0x32 ,0x03 ,0x02
+ , 0xA1 ,0xA7 ,0xA1 ,0x33 ,0x01 ,0x02
+ , 0xD1 ,0xA7 ,0xA1 ,0x33 ,0x03 ,0x02
+ , 0xA1 ,0xA8 ,0xA1 ,0x34 ,0x00 ,0x00
+ , 0xA1 ,0xB0 ,0xA1 ,0xB0 ,0x00 ,0x00
+};
+
+static unsigned char NLSALLOC(0804) rgmaptable[] = {
+ 0x20 ,0x10 ,0x01 ,0x00 ,0x20 ,0x00
+ , 0xA1 ,0xA1 ,0x20 ,0x00 ,0xA1 ,0xA1
+ , 0x21 ,0x10 ,0x5F ,0x00 ,0x21 ,0x00
+ , 0xA1 ,0xA3 ,0x21 ,0x00 ,0xA1 ,0xA3
+ , 0xA1 ,0x32 ,0x18 ,0x00 ,0xA1 ,0xA6
+ , 0xA1 ,0xA6 ,0xC1 ,0xA6 ,0xC1 ,0xA6
+ , 0xA1 ,0x33 ,0x21 ,0x00 ,0xA1 ,0xA7
+ , 0xA1 ,0xA7 ,0xD1 ,0xA7 ,0xD1 ,0xA7
+ , 0x30 ,0x50 ,0x0A ,0x00 ,0x30 ,0x00
+ , 0xB0 ,0xA3 ,0x30 ,0x00 ,0xB0 ,0xA3
+ , 0x41 ,0x60 ,0x1A ,0x00 ,0x41 ,0x00
+ , 0xC1 ,0xA3 ,0x61 ,0x00 ,0xE1 ,0xA3
+};
+
+static unsigned char NLSALLOC(0804) rgtypetable[] = {
+ 0x00 ,0x00 ,0x20 ,0x00 ,0x00 ,0x00
+ , 0x09 ,0x00 ,0x68 ,0x00 ,0x09 ,0x00
+ , 0x0A ,0x00 ,0x28 ,0x00 ,0x00 ,0x00
+ , 0x0E ,0x00 ,0x20 ,0x00 ,0x00 ,0x00
+ , 0x20 ,0x00 ,0x48 ,0x00 ,0x0A ,0x00
+ , 0x21 ,0x00 ,0x10 ,0x00 ,0x0B ,0x08
+ , 0x24 ,0x00 ,0x10 ,0x00 ,0x05 ,0x08
+ , 0x26 ,0x00 ,0x10 ,0x00 ,0x01 ,0x08
+ , 0x2B ,0x00 ,0x10 ,0x00 ,0x05 ,0x08
+ , 0x2C ,0x00 ,0x10 ,0x00 ,0x07 ,0x08
+ , 0x2D ,0x00 ,0x10 ,0x00 ,0x05 ,0x08
+ , 0x2E ,0x00 ,0x10 ,0x00 ,0x03 ,0x08
+ , 0x30 ,0x00 ,0x84 ,0x00 ,0x03 ,0x00
+ , 0x3A ,0x00 ,0x10 ,0x00 ,0x07 ,0x08
+ , 0x3B ,0x00 ,0x10 ,0x00 ,0x0B ,0x08
+ , 0x40 ,0x00 ,0x10 ,0x00 ,0x01 ,0x08
+ , 0x41 ,0x00 ,0x81 ,0x01 ,0x01 ,0x00
+ , 0x47 ,0x00 ,0x01 ,0x01 ,0x01 ,0x00
+ , 0x5B ,0x00 ,0x10 ,0x00 ,0x0B ,0x08
+ , 0x61 ,0x00 ,0x82 ,0x01 ,0x01 ,0x00
+ , 0x67 ,0x00 ,0x02 ,0x01 ,0x01 ,0x00
+ , 0x7B ,0x00 ,0x10 ,0x00 ,0x0B ,0x08
+ , 0x7F ,0x00 ,0x20 ,0x00 ,0x00 ,0x00
+ , 0x80 ,0x00 ,0x00 ,0x00 ,0x0B ,0x08
+ , 0xA1 ,0xA1 ,0x48 ,0x00 ,0x0A ,0x00
+ , 0xA2 ,0xA1 ,0x00 ,0x00 ,0x0B ,0x08
+ , 0xA1 ,0xA3 ,0x10 ,0x00 ,0x0B ,0x08
+ , 0xA4 ,0xA3 ,0x10 ,0x00 ,0x05 ,0x08
+ , 0xA6 ,0xA3 ,0x10 ,0x00 ,0x01 ,0x08
+ , 0xAB ,0xA3 ,0x10 ,0x00 ,0x05 ,0x08
+ , 0xAC ,0xA3 ,0x10 ,0x00 ,0x07 ,0x08
+ , 0xAD ,0xA3 ,0x10 ,0x00 ,0x05 ,0x08
+ , 0xAE ,0xA3 ,0x10 ,0x00 ,0x03 ,0x08
+ , 0xB0 ,0xA3 ,0x84 ,0x00 ,0x03 ,0x00
+ , 0xBA ,0xA3 ,0x10 ,0x00 ,0x07 ,0x08
+ , 0xBB ,0xA3 ,0x10 ,0x00 ,0x0B ,0x08
+ , 0xC0 ,0xA3 ,0x10 ,0x00 ,0x01 ,0x08
+ , 0xC1 ,0xA3 ,0x81 ,0x01 ,0x01 ,0x00
+ , 0xC7 ,0xA3 ,0x01 ,0x01 ,0x01 ,0x00
+ , 0xDB ,0xA3 ,0x10 ,0x00 ,0x0B ,0x08
+ , 0xE1 ,0xA3 ,0x82 ,0x01 ,0x01 ,0x00
+ , 0xE7 ,0xA3 ,0x02 ,0x01 ,0x01 ,0x00
+ , 0xFB ,0xA3 ,0x10 ,0x00 ,0x0B ,0x08
+ , 0xA1 ,0xA4 ,0x10 ,0x00 ,0x0B ,0x08
+ , 0xA1 ,0xB0 ,0x00 ,0x01 ,0x01 ,0x00
+};
+#endif
+
+
+static unsigned char NLSALLOC(0804) rgbSENGCOUNTRY[] = {
+ 'P', 'e', 'o', 'p', 'l', 'e', 's', '\'', ' ',
+ 'R', 'e', 'p', 'u', 'b', 'l', 'i', 'c', ' ',
+ 'o', 'f', ' ',
+ 'C', 'h', 'i', 'n', 'a'
+};
+
+static unsigned char NLSALLOC(0804) rgbSENGLANGUAGE[] = {
+ 'C', 'h', 'i', 'n', 'e', 's', 'e'
+};
+
+#if defined(VBA2) //hand-edited this locale info based on daytona [bassam]
+static BYTE NLSALLOC(0804) rgbIFIRSTDAYOFWEEK[] = { /* "6" */
+ 0x36
+};
+
+static BYTE NLSALLOC(0804) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0804) rgbIDEFAULTANSICODEPAGE[] = { /* "936" */
+ 0x39, 0x33, 0x36
+};
+
+static BYTE NLSALLOC(0804) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0804) rgbSTIMEFORMAT[] = { /* "tt h:mm:ss" */
+ 0x74, 0x74, 0x20, 0x68, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0804) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0804) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0804) rgbIOPTIONALCALENDAR[] = { /* "2" */
+ 0x32
+};
+#endif
+
+
+static unsigned char NLSALLOC(0804) rgbILANGUAGE[] = {
+ '0', '8', '0', '4'
+};
+
+static unsigned char NLSALLOC(0804) rgbSLANGUAGE[] = {
+ 0xd6, 0xd0, 0xce, 0xc4, '(', 'C', 'h', 'i', 'n', 'e', 's', 'e', ' ', 'S', 'i', 'm', 'p', 'l', 'i', 'f', 'i', 'e', 'd', ')'
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVLANGNAME[] = {
+ 'C', 'H', 'S'
+};
+
+static unsigned char NLSALLOC(0804) rgbSNATIVELANGNAME[] = {
+ 0xd6, 0xd0, 0xce, 0xc4
+};
+
+static unsigned char NLSALLOC(0804) rgbICOUNTRY[] = { /* "86" */
+ '8', '6'
+};
+
+static unsigned char NLSALLOC(0804) rgbSCOUNTRY[] = {
+ 0xd6, 0xd0, 0xbb, 0xaa, 0xc8, 0xcb, 0xc3, 0xf1,
+ 0xb9, 0xb2, 0xba, 0xcd, 0xb9, 0xfa,
+ '(', 'C', 'h', 'i', 'n', 'a', ')'
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVCTRYNAME[] = {
+ 'C', 'H', 'N'
+};
+
+static unsigned char NLSALLOC(0804) rgbSNATIVECTRYNAME[] = {
+ 0xd6, 0xd0, 0xbb, 0xaa, 0xc8, 0xcb, 0xc3, 0xf1,
+ 0xb9, 0xb2, 0xba, 0xcd, 0xb9, 0xfa
+};
+
+static unsigned char NLSALLOC(0804) rgbIDEFAULTLANGUAGE[] = {
+ '0', '8', '0', '4'
+};
+
+static unsigned char NLSALLOC(0804) rgbIDEFAULTCOUNTRY[] = {
+ '0', '8', '6'
+};
+
+static unsigned char NLSALLOC(0804) rgbIDEFAULTCODEPAGE[] = {
+ '9', '3', '6'
+};
+
+static unsigned char NLSALLOC(0804) rgbSLIST[] = {
+ ','
+};
+
+static unsigned char NLSALLOC(0804) rgbIMEASURE[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0804) rgbSDECIMAL[] = {
+ '.'
+};
+
+static unsigned char NLSALLOC(0804) rgbSTHOUSAND[] = {
+ ','
+};
+
+static unsigned char NLSALLOC(0804) rgbSGROUPING[] = {
+ '3', ';', '0'
+};
+
+static unsigned char NLSALLOC(0804) rgbIDIGITS[] = {
+ '2'
+};
+
+static unsigned char NLSALLOC(0804) rgbILZERO[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0804) rgbSNATIVEDIGITS[] = {
+ '0', '1', '2', '3', '4', '5', '6', '7', '8', '9'
+};
+
+static unsigned char NLSALLOC(0804) rgbSCURRENCY[] = {
+ 0xa3, 0xa4
+};
+
+static unsigned char NLSALLOC(0804) rgbSINTLSYMBOL[] = {
+ 'C', 'N', 'Y'
+};
+
+static unsigned char NLSALLOC(0804) rgbSMONDECIMALSEP[] = {
+ '.'
+};
+
+static unsigned char NLSALLOC(0804) rgbSMONTHOUSANDSEP[] = {
+ ','
+};
+
+static unsigned char NLSALLOC(0804) rgbSMONGROUPING[] = {
+ '3', ';', '0'
+};
+
+static unsigned char NLSALLOC(0804) rgbICURRDIGITS[] = {
+ '2'
+};
+
+static unsigned char NLSALLOC(0804) rgbIINTLCURRDIGITS[] = {
+ '2'
+};
+
+static unsigned char NLSALLOC(0804) rgbICURRENCY[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0804) rgbINEGCURR[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0804) rgbSDATE[] = {
+ '/'
+};
+
+static unsigned char NLSALLOC(0804) rgbSTIME[] = {
+ ':'
+};
+
+static unsigned char NLSALLOC(0804) rgbSSHORTDATE[] = {
+ 'y', 'y', 'y', 'y', '/', 'M', '/', 'd'
+};
+
+static unsigned char NLSALLOC(0804) rgbSLONGDATE[] = {
+ 'd', 'd', 'd', 'd', ',', ' ',
+ 'M', 'M', 'M', 'M', ' ',
+ 'd', ',', ' ',
+ 'y', 'y', 'y', 'y'
+};
+
+static unsigned char NLSALLOC(0804) rgbIDATE[] = {
+ '2'
+};
+
+static unsigned char NLSALLOC(0804) rgbILDATE[] = {
+ '2'
+};
+
+static unsigned char NLSALLOC(0804) rgbITIME[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0804) rgbICENTURY[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0804) rgbITLZERO[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0804) rgbIDAYLZERO[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0804) rgbIMONLZERO[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0804) rgbS1159[] = {
+ 0xc9, 0xcf, 0xce, 0xe7
+};
+
+static unsigned char NLSALLOC(0804) rgbS2359[] = {
+ 0xcf, 0xc2, 0xce, 0xe7
+};
+
+static unsigned char NLSALLOC(0804) rgbSDAYNAME1[] = {
+ 0xd0, 0xc7, 0xc6, 0xda, 0xd2, 0xbb
+};
+
+static unsigned char NLSALLOC(0804) rgbSDAYNAME2[] = {
+ 0xd0, 0xc7, 0xc6, 0xda, 0xb6, 0xfe
+};
+
+static unsigned char NLSALLOC(0804) rgbSDAYNAME3[] = {
+ 0xd0, 0xc7, 0xc6, 0xda, 0xc8, 0xfd
+};
+
+static unsigned char NLSALLOC(0804) rgbSDAYNAME4[] = {
+ 0xd0, 0xc7, 0xc6, 0xda, 0xcb, 0xc4
+};
+
+static unsigned char NLSALLOC(0804) rgbSDAYNAME5[] = {
+ 0xd0, 0xc7, 0xc6, 0xda, 0xce, 0xe5
+};
+
+static unsigned char NLSALLOC(0804) rgbSDAYNAME6[] = {
+ 0xd0, 0xc7, 0xc6, 0xda, 0xc1, 0xf9
+};
+
+static unsigned char NLSALLOC(0804) rgbSDAYNAME7[] = {
+ 0xd0, 0xc7, 0xc6, 0xda, 0xc8, 0xd5
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVDAYNAME1[] = {
+ 0xd0, 0xc7, 0xc6, 0xda, 0xd2, 0xbb
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVDAYNAME2[] = {
+ 0xd0, 0xc7, 0xc6, 0xda, 0xb6, 0xfe
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVDAYNAME3[] = {
+ 0xd0, 0xc7, 0xc6, 0xda, 0xc8, 0xfd
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVDAYNAME4[] = {
+ 0xd0, 0xc7, 0xc6, 0xda, 0xcb, 0xc4
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVDAYNAME5[] = {
+ 0xd0, 0xc7, 0xc6, 0xda, 0xce, 0xe5
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVDAYNAME6[] = {
+ 0xd0, 0xc7, 0xc6, 0xda, 0xc1, 0xf9
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVDAYNAME7[] = {
+ 0xd0, 0xc7, 0xc6, 0xda, 0xc8, 0xd5
+};
+
+static unsigned char NLSALLOC(0804) rgbSMONTHNAME1[] = {
+ 0xd2, 0xbb, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSMONTHNAME2[] = {
+ 0xb6, 0xfe, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSMONTHNAME3[] = {
+ 0xc8, 0xfd, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSMONTHNAME4[] = {
+ 0xcb, 0xc4, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSMONTHNAME5[] = {
+ 0xce, 0xe5, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSMONTHNAME6[] = {
+ 0xc1, 0xf9, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSMONTHNAME7[] = {
+ 0xc6, 0xdf, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSMONTHNAME8[] = {
+ 0xb0, 0xcb, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSMONTHNAME9[] = {
+ 0xbe, 0xc5, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSMONTHNAME10[] = {
+ 0xca, 0xae, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSMONTHNAME11[] = {
+ 0xca, 0xae, 0xd2, 0xbb, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSMONTHNAME12[] = {
+ 0xca, 0xae, 0xb6, 0xfe, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVMONTHNAME1[] = {
+ 0xd2, 0xbb, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVMONTHNAME2[] = {
+ 0xb6, 0xfe, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVMONTHNAME3[] = {
+ 0xc8, 0xfd, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVMONTHNAME4[] = {
+ 0xcb, 0xc4, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVMONTHNAME5[] = {
+ 0xce, 0xe5, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVMONTHNAME6[] = {
+ 0xc1, 0xf9, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVMONTHNAME7[] = {
+ 0xc6, 0xdf, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVMONTHNAME8[] = {
+ 0xb0, 0xcb, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVMONTHNAME9[] = {
+ 0xbe, 0xc5, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVMONTHNAME10[] = {
+ 0xca, 0xae, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVMONTHNAME11[] = {
+ 0xca, 0xae, 0xd2, 0xbb, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSABBREVMONTHNAME12[] = {
+ 0xca, 0xae, 0xb6, 0xfe, 0xd4, 0xc2
+};
+
+static unsigned char NLSALLOC(0804) rgbSNEGATIVESIGN[] = {
+ '-'
+};
+
+static unsigned char NLSALLOC(0804) rgbIPOSSIGNPOSN[] = {
+ '3'
+};
+
+static unsigned char NLSALLOC(0804) rgbINEGSIGNPOSN[] = {
+ '3'
+};
+
+static unsigned char NLSALLOC(0804) rgbIPOSSYMPRECEDES[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0804) rgbIPOSSEPBYSPACE[] = {
+ '0'
+};
+
+static unsigned char NLSALLOC(0804) rgbINEGSYMPRECEDES[] = {
+ '1'
+};
+
+static unsigned char NLSALLOC(0804) rgbINEGSEPBYSPACE[] = {
+ '0'
+};
+
+
+#define LCINFODAT(X) { DIM(X), (X) }
+LCINFO NLSALLOC(0804) g_rglcinfo0804[] = {
+ { 0, NULL}
+ , LCINFODAT(rgbILANGUAGE)
+ , LCINFODAT(rgbSLANGUAGE)
+ , LCINFODAT(rgbSABBREVLANGNAME)
+ , LCINFODAT(rgbSNATIVELANGNAME)
+ , LCINFODAT(rgbICOUNTRY)
+ , LCINFODAT(rgbSCOUNTRY)
+ , LCINFODAT(rgbSABBREVCTRYNAME)
+ , LCINFODAT(rgbSNATIVECTRYNAME)
+ , LCINFODAT(rgbIDEFAULTLANGUAGE)
+ , LCINFODAT(rgbIDEFAULTCOUNTRY)
+ , LCINFODAT(rgbIDEFAULTCODEPAGE)
+ , LCINFODAT(rgbSLIST)
+ , LCINFODAT(rgbIMEASURE)
+ , LCINFODAT(rgbSDECIMAL)
+ , LCINFODAT(rgbSTHOUSAND)
+ , LCINFODAT(rgbSGROUPING)
+ , LCINFODAT(rgbIDIGITS)
+ , LCINFODAT(rgbILZERO)
+ , LCINFODAT(rgbSNATIVEDIGITS)
+ , LCINFODAT(rgbSCURRENCY)
+ , LCINFODAT(rgbSINTLSYMBOL)
+ , LCINFODAT(rgbSMONDECIMALSEP)
+ , LCINFODAT(rgbSMONTHOUSANDSEP)
+ , LCINFODAT(rgbSMONGROUPING)
+ , LCINFODAT(rgbICURRDIGITS)
+ , LCINFODAT(rgbIINTLCURRDIGITS)
+ , LCINFODAT(rgbICURRENCY)
+ , LCINFODAT(rgbINEGCURR)
+ , LCINFODAT(rgbSDATE)
+ , LCINFODAT(rgbSTIME)
+ , LCINFODAT(rgbSSHORTDATE)
+ , LCINFODAT(rgbSLONGDATE)
+ , LCINFODAT(rgbIDATE)
+ , LCINFODAT(rgbILDATE)
+ , LCINFODAT(rgbITIME)
+ , LCINFODAT(rgbICENTURY)
+ , LCINFODAT(rgbITLZERO)
+ , LCINFODAT(rgbIDAYLZERO)
+ , LCINFODAT(rgbIMONLZERO)
+ , LCINFODAT(rgbS1159)
+ , LCINFODAT(rgbS2359)
+ , LCINFODAT(rgbSDAYNAME1)
+ , LCINFODAT(rgbSDAYNAME2)
+ , LCINFODAT(rgbSDAYNAME3)
+ , LCINFODAT(rgbSDAYNAME4)
+ , LCINFODAT(rgbSDAYNAME5)
+ , LCINFODAT(rgbSDAYNAME6)
+ , LCINFODAT(rgbSDAYNAME7)
+ , LCINFODAT(rgbSABBREVDAYNAME1)
+ , LCINFODAT(rgbSABBREVDAYNAME2)
+ , LCINFODAT(rgbSABBREVDAYNAME3)
+ , LCINFODAT(rgbSABBREVDAYNAME4)
+ , LCINFODAT(rgbSABBREVDAYNAME5)
+ , LCINFODAT(rgbSABBREVDAYNAME6)
+ , LCINFODAT(rgbSABBREVDAYNAME7)
+ , LCINFODAT(rgbSMONTHNAME1)
+ , LCINFODAT(rgbSMONTHNAME2)
+ , LCINFODAT(rgbSMONTHNAME3)
+ , LCINFODAT(rgbSMONTHNAME4)
+ , LCINFODAT(rgbSMONTHNAME5)
+ , LCINFODAT(rgbSMONTHNAME6)
+ , LCINFODAT(rgbSMONTHNAME7)
+ , LCINFODAT(rgbSMONTHNAME8)
+ , LCINFODAT(rgbSMONTHNAME9)
+ , LCINFODAT(rgbSMONTHNAME10)
+ , LCINFODAT(rgbSMONTHNAME11)
+ , LCINFODAT(rgbSMONTHNAME12)
+ , LCINFODAT(rgbSABBREVMONTHNAME1)
+ , LCINFODAT(rgbSABBREVMONTHNAME2)
+ , LCINFODAT(rgbSABBREVMONTHNAME3)
+ , LCINFODAT(rgbSABBREVMONTHNAME4)
+ , LCINFODAT(rgbSABBREVMONTHNAME5)
+ , LCINFODAT(rgbSABBREVMONTHNAME6)
+ , LCINFODAT(rgbSABBREVMONTHNAME7)
+ , LCINFODAT(rgbSABBREVMONTHNAME8)
+ , LCINFODAT(rgbSABBREVMONTHNAME9)
+ , LCINFODAT(rgbSABBREVMONTHNAME10)
+ , LCINFODAT(rgbSABBREVMONTHNAME11)
+ , LCINFODAT(rgbSABBREVMONTHNAME12)
+ , { 0, NULL }
+ , LCINFODAT(rgbSNEGATIVESIGN)
+ , LCINFODAT(rgbIPOSSIGNPOSN)
+ , LCINFODAT(rgbINEGSIGNPOSN)
+ , LCINFODAT(rgbIPOSSYMPRECEDES)
+ , LCINFODAT(rgbIPOSSEPBYSPACE)
+ , LCINFODAT(rgbINEGSYMPRECEDES)
+ , LCINFODAT(rgbINEGSEPBYSPACE)
+ , LCINFODAT(rgbSENGCOUNTRY)
+ , LCINFODAT(rgbSENGLANGUAGE)
+#if defined(VBA2)
+ , LCINFODAT(rgbIFIRSTDAYOFWEEK)
+ , LCINFODAT(rgbIFIRSTWEEKOFYEAR)
+ , LCINFODAT(rgbIDEFAULTANSICODEPAGE)
+ , LCINFODAT(rgbINEGNUMBER)
+ , LCINFODAT(rgbSTIMEFORMAT)
+ , LCINFODAT(rgbITIMEMARKPOSN)
+ , LCINFODAT(rgbICALENDARTYPE)
+ , LCINFODAT(rgbIOPTIONALCALENDAR)
+ , { 0, NULL }
+ , { 0, NULL }
+#endif
+};
+#undef LCINFODAT
+
+
+#if 1
+STRINFO_KTP NLSALLOC(0804) g_strinfo0804 = {
+ rgsortweight
+ , rgmaptable
+ , rgtypetable
+ , DIM(rgsortweight)
+ , DIM(rgmaptable)
+ , DIM(rgtypetable)
+};
+#else
+STRINFO_KTP NLSALLOC(0804) g_strinfo0804 = {
+ (SORTWEIGHT FAR*) rgsortweight
+ , (MAPTABLE FAR*) rgmaptable
+ , (TYPETABLE FAR*) rgtypetable
+ , DIM(rgsortweight)
+ , DIM(rgmaptable)
+ , DIM(rgtypetable)
+};
+#endif
diff --git a/private/oleauto/src/dispatch/win16/0807.c b/private/oleauto/src/dispatch/win16/0807.c
new file mode 100644
index 000000000..49e483d8d
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0807.c
@@ -0,0 +1,518 @@
+/****************************************************************************
+* 0807.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* German - Switzerland
+*
+* LCID = 0x0807
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:40:13 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0409[256]; // from 0409:English - United States
+extern EXPANSION rgexp_0409[7];
+extern WORD rgwCType12_0409[256];
+extern WORD rgwCType3_0409[256];
+extern BYTE rgbUCase_0409[256];
+extern BYTE rgbLCase_0409[256];
+
+static BYTE NLSALLOC(0807) rgbILANGUAGE[] = { /* "0807" */
+ 0x30, 0x38, 0x30, 0x37
+};
+
+static BYTE NLSALLOC(0807) rgbSLANGUAGE[] = { /* "Swiss German" */
+ 0x53, 0x77, 0x69, 0x73, 0x73, 0x20, 0x47, 0x65
+ , 0x72, 0x6d, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVLANGNAME[] = { /* "DES" */
+ 0x44, 0x45, 0x53
+};
+
+static BYTE NLSALLOC(0807) rgbSNATIVELANGNAME[] = { /* "Deutsch" */
+ 0x44, 0x65, 0x75, 0x74, 0x73, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(0807) rgbICOUNTRY[] = { /* "41" */
+ 0x34, 0x31
+};
+
+static BYTE NLSALLOC(0807) rgbSCOUNTRY[] = { /* "Switzerland" */
+ 0x53, 0x77, 0x69, 0x74, 0x7a, 0x65, 0x72, 0x6c
+ , 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVCTRYNAME[] = { /* "CHE" */
+ 0x43, 0x48, 0x45
+};
+
+static BYTE NLSALLOC(0807) rgbSNATIVECTRYNAME[] = { /* "Schweiz" */
+ 0x53, 0x63, 0x68, 0x77, 0x65, 0x69, 0x7a
+};
+
+static BYTE NLSALLOC(0807) rgbIDEFAULTLANGUAGE[] = { /* "0807" */
+ 0x30, 0x38, 0x30, 0x37
+};
+
+static BYTE NLSALLOC(0807) rgbIDEFAULTCOUNTRY[] = { /* "41" */
+ 0x34, 0x31
+};
+
+static BYTE NLSALLOC(0807) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0807) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0807) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0807) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0807) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0807) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0807) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0807) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0807) rgbSCURRENCY[] = { /* "CHF" */
+ 0x43, 0x48, 0x46
+};
+
+static BYTE NLSALLOC(0807) rgbSINTLSYMBOL[] = { /* "CHF" */
+ 0x43, 0x48, 0x46
+};
+
+static BYTE NLSALLOC(0807) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0807) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0807) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0807) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0807) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0807) rgbINEGCURR[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0807) rgbSDATE[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0807) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0807) rgbSSHORTDATE[] = { /* "dd.MM.yy" */
+ 0x64, 0x64, 0x2e, 0x4d, 0x4d, 0x2e, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0807) rgbSLONGDATE[] = { /* "dddd, d. MMMM yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x2c, 0x20, 0x64, 0x2e
+ , 0x20, 0x4d, 0x4d, 0x4d, 0x4d, 0x20, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0807) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0807) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0807) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0807) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0807) rgbITLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0807) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0807) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0807) rgbSDAYNAME1[] = { /* "Montag" */
+ 0x4d, 0x6f, 0x6e, 0x74, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0807) rgbSDAYNAME2[] = { /* "Dienstag" */
+ 0x44, 0x69, 0x65, 0x6e, 0x73, 0x74, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0807) rgbSDAYNAME3[] = { /* "Mittwoch" */
+ 0x4d, 0x69, 0x74, 0x74, 0x77, 0x6f, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(0807) rgbSDAYNAME4[] = { /* "Donnerstag" */
+ 0x44, 0x6f, 0x6e, 0x6e, 0x65, 0x72, 0x73, 0x74
+ , 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0807) rgbSDAYNAME5[] = { /* "Freitag" */
+ 0x46, 0x72, 0x65, 0x69, 0x74, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0807) rgbSDAYNAME6[] = { /* "Samstag" */
+ 0x53, 0x61, 0x6d, 0x73, 0x74, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0807) rgbSDAYNAME7[] = { /* "Sonntag" */
+ 0x53, 0x6f, 0x6e, 0x6e, 0x74, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVDAYNAME1[] = { /* "Mo" */
+ 0x4d, 0x6f
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVDAYNAME2[] = { /* "Di" */
+ 0x44, 0x69
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVDAYNAME3[] = { /* "Mi" */
+ 0x4d, 0x69
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVDAYNAME4[] = { /* "Do" */
+ 0x44, 0x6f
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVDAYNAME5[] = { /* "Fr" */
+ 0x46, 0x72
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVDAYNAME6[] = { /* "Sa" */
+ 0x53, 0x61
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVDAYNAME7[] = { /* "So" */
+ 0x53, 0x6f
+};
+
+static BYTE NLSALLOC(0807) rgbSMONTHNAME1[] = { /* "Januar" */
+ 0x4a, 0x61, 0x6e, 0x75, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0807) rgbSMONTHNAME2[] = { /* "Februar" */
+ 0x46, 0x65, 0x62, 0x72, 0x75, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0807) rgbSMONTHNAME3[] = { /* "März" */
+ 0x4d, 0xe4, 0x72, 0x7a
+};
+
+static BYTE NLSALLOC(0807) rgbSMONTHNAME4[] = { /* "April" */
+ 0x41, 0x70, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(0807) rgbSMONTHNAME5[] = { /* "Mai" */
+ 0x4d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(0807) rgbSMONTHNAME6[] = { /* "Juni" */
+ 0x4a, 0x75, 0x6e, 0x69
+};
+
+static BYTE NLSALLOC(0807) rgbSMONTHNAME7[] = { /* "Juli" */
+ 0x4a, 0x75, 0x6c, 0x69
+};
+
+static BYTE NLSALLOC(0807) rgbSMONTHNAME8[] = { /* "August" */
+ 0x41, 0x75, 0x67, 0x75, 0x73, 0x74
+};
+
+static BYTE NLSALLOC(0807) rgbSMONTHNAME9[] = { /* "September" */
+ 0x53, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x65
+ , 0x72
+};
+
+static BYTE NLSALLOC(0807) rgbSMONTHNAME10[] = { /* "Oktober" */
+ 0x4f, 0x6b, 0x74, 0x6f, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0807) rgbSMONTHNAME11[] = { /* "November" */
+ 0x4e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0807) rgbSMONTHNAME12[] = { /* "Dezember" */
+ 0x44, 0x65, 0x7a, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVMONTHNAME1[] = { /* "Jan" */
+ 0x4a, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVMONTHNAME2[] = { /* "Feb" */
+ 0x46, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVMONTHNAME3[] = { /* "Mrz" */
+ 0x4d, 0x72, 0x7a
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVMONTHNAME4[] = { /* "Apr" */
+ 0x41, 0x70, 0x72
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVMONTHNAME5[] = { /* "Mai" */
+ 0x4d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVMONTHNAME6[] = { /* "Jun" */
+ 0x4a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVMONTHNAME7[] = { /* "Jul" */
+ 0x4a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVMONTHNAME8[] = { /* "Aug" */
+ 0x41, 0x75, 0x67
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVMONTHNAME9[] = { /* "Sep" */
+ 0x53, 0x65, 0x70
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVMONTHNAME10[] = { /* "Okt" */
+ 0x4f, 0x6b, 0x74
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVMONTHNAME11[] = { /* "Nov" */
+ 0x4e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(0807) rgbSABBREVMONTHNAME12[] = { /* "Dez" */
+ 0x44, 0x65, 0x7a
+};
+
+static BYTE NLSALLOC(0807) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0807) rgbIPOSSIGNPOSN[] = { /* "4" */
+ 0x34
+};
+
+static BYTE NLSALLOC(0807) rgbINEGSIGNPOSN[] = { /* "4" */
+ 0x34
+};
+
+static BYTE NLSALLOC(0807) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0807) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0807) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0807) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0807) rgbSENGCOUNTRY[] = { /* "Switzerland" */
+ 0x53, 0x77, 0x69, 0x74, 0x7a, 0x65, 0x72, 0x6c
+ , 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(0807) rgbSENGLANGUAGE[] = { /* "German" */
+ 0x47, 0x65, 0x72, 0x6d, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0807) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0807) rgbIFIRSTWEEKOFYEAR[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0807) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0807) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0807) rgbSTIMEFORMAT[] = { /* "HH:mm:ss" */
+ 0x48, 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0807) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0807) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0807) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0807) g_rglcinfo0807[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 12, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 11, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 7, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 0, NULL } /* STHOUSAND */
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 3, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 0, NULL } /* SMONTHOUSANDSEP */
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 18, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 6, rgbSDAYNAME1 }
+ , { 8, rgbSDAYNAME2 }
+ , { 8, rgbSDAYNAME3 }
+ , { 10, rgbSDAYNAME4 }
+ , { 7, rgbSDAYNAME5 }
+ , { 7, rgbSDAYNAME6 }
+ , { 7, rgbSDAYNAME7 }
+ , { 2, rgbSABBREVDAYNAME1 }
+ , { 2, rgbSABBREVDAYNAME2 }
+ , { 2, rgbSABBREVDAYNAME3 }
+ , { 2, rgbSABBREVDAYNAME4 }
+ , { 2, rgbSABBREVDAYNAME5 }
+ , { 2, rgbSABBREVDAYNAME6 }
+ , { 2, rgbSABBREVDAYNAME7 }
+ , { 6, rgbSMONTHNAME1 }
+ , { 7, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 11, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 8, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0807) g_strinfo0807 = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0809.c b/private/oleauto/src/dispatch/win16/0809.c
new file mode 100644
index 000000000..717035ac0
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0809.c
@@ -0,0 +1,525 @@
+/****************************************************************************
+* 0809.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* English - United Kingdom
+*
+* LCID = 0x0809
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:40:48 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0409[256]; // from 0409:English - United States
+extern EXPANSION rgexp_0409[7];
+extern WORD rgwCType12_0409[256];
+extern WORD rgwCType3_0409[256];
+extern BYTE rgbUCase_0409[256];
+extern BYTE rgbLCase_0409[256];
+
+static BYTE NLSALLOC(0809) rgbILANGUAGE[] = { /* "0809" */
+ 0x30, 0x38, 0x30, 0x39
+};
+
+static BYTE NLSALLOC(0809) rgbSLANGUAGE[] = { /* "U.K. English" */
+ 0x55, 0x2e, 0x4b, 0x2e, 0x20, 0x45, 0x6e, 0x67
+ , 0x6c, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVLANGNAME[] = { /* "ENG" */
+ 0x45, 0x4e, 0x47
+};
+
+static BYTE NLSALLOC(0809) rgbSNATIVELANGNAME[] = { /* "English" */
+ 0x45, 0x6e, 0x67, 0x6c, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(0809) rgbICOUNTRY[] = { /* "44" */
+ 0x34, 0x34
+};
+
+static BYTE NLSALLOC(0809) rgbSCOUNTRY[] = { /* "United Kingdom" */
+ 0x55, 0x6e, 0x69, 0x74, 0x65, 0x64, 0x20, 0x4b
+ , 0x69, 0x6e, 0x67, 0x64, 0x6f, 0x6d
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVCTRYNAME[] = { /* "GBR" */
+ 0x47, 0x42, 0x52
+};
+
+static BYTE NLSALLOC(0809) rgbSNATIVECTRYNAME[] = { /* "England" */
+ 0x45, 0x6e, 0x67, 0x6c, 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(0809) rgbIDEFAULTLANGUAGE[] = { /* "0809" */
+ 0x30, 0x38, 0x30, 0x39
+};
+
+static BYTE NLSALLOC(0809) rgbIDEFAULTCOUNTRY[] = { /* "44" */
+ 0x34, 0x34
+};
+
+static BYTE NLSALLOC(0809) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0809) rgbSLIST[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0809) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0809) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0809) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0809) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0809) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0809) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0809) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0809) rgbSCURRENCY[] = { /* "£" */
+ 0xa3
+};
+
+static BYTE NLSALLOC(0809) rgbSINTLSYMBOL[] = { /* "GBP" */
+ 0x47, 0x42, 0x50
+};
+
+static BYTE NLSALLOC(0809) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0809) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0809) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0809) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0809) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0809) rgbICURRENCY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0809) rgbINEGCURR[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0809) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(0809) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0809) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0809) rgbSLONGDATE[] = { /* "dd MMMM yyyy" */
+ 0x64, 0x64, 0x20, 0x4d, 0x4d, 0x4d, 0x4d, 0x20
+ , 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0809) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0809) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0809) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0809) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0809) rgbITLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0809) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0809) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0809) rgbSDAYNAME1[] = { /* "Monday" */
+ 0x4d, 0x6f, 0x6e, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0809) rgbSDAYNAME2[] = { /* "Tuesday" */
+ 0x54, 0x75, 0x65, 0x73, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0809) rgbSDAYNAME3[] = { /* "Wednesday" */
+ 0x57, 0x65, 0x64, 0x6e, 0x65, 0x73, 0x64, 0x61
+ , 0x79
+};
+
+static BYTE NLSALLOC(0809) rgbSDAYNAME4[] = { /* "Thursday" */
+ 0x54, 0x68, 0x75, 0x72, 0x73, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0809) rgbSDAYNAME5[] = { /* "Friday" */
+ 0x46, 0x72, 0x69, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0809) rgbSDAYNAME6[] = { /* "Saturday" */
+ 0x53, 0x61, 0x74, 0x75, 0x72, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0809) rgbSDAYNAME7[] = { /* "Sunday" */
+ 0x53, 0x75, 0x6e, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVDAYNAME1[] = { /* "Mon" */
+ 0x4d, 0x6f, 0x6e
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVDAYNAME2[] = { /* "Tue" */
+ 0x54, 0x75, 0x65
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVDAYNAME3[] = { /* "Wed" */
+ 0x57, 0x65, 0x64
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVDAYNAME4[] = { /* "Thu" */
+ 0x54, 0x68, 0x75
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVDAYNAME5[] = { /* "Fri" */
+ 0x46, 0x72, 0x69
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVDAYNAME6[] = { /* "Sat" */
+ 0x53, 0x61, 0x74
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVDAYNAME7[] = { /* "Sun" */
+ 0x53, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0809) rgbSMONTHNAME1[] = { /* "January" */
+ 0x4a, 0x61, 0x6e, 0x75, 0x61, 0x72, 0x79
+};
+
+static BYTE NLSALLOC(0809) rgbSMONTHNAME2[] = { /* "February" */
+ 0x46, 0x65, 0x62, 0x72, 0x75, 0x61, 0x72, 0x79
+};
+
+static BYTE NLSALLOC(0809) rgbSMONTHNAME3[] = { /* "March" */
+ 0x4d, 0x61, 0x72, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(0809) rgbSMONTHNAME4[] = { /* "April" */
+ 0x41, 0x70, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(0809) rgbSMONTHNAME5[] = { /* "May" */
+ 0x4d, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0809) rgbSMONTHNAME6[] = { /* "June" */
+ 0x4a, 0x75, 0x6e, 0x65
+};
+
+static BYTE NLSALLOC(0809) rgbSMONTHNAME7[] = { /* "July" */
+ 0x4a, 0x75, 0x6c, 0x79
+};
+
+static BYTE NLSALLOC(0809) rgbSMONTHNAME8[] = { /* "August" */
+ 0x41, 0x75, 0x67, 0x75, 0x73, 0x74
+};
+
+static BYTE NLSALLOC(0809) rgbSMONTHNAME9[] = { /* "September" */
+ 0x53, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x65
+ , 0x72
+};
+
+static BYTE NLSALLOC(0809) rgbSMONTHNAME10[] = { /* "October" */
+ 0x4f, 0x63, 0x74, 0x6f, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0809) rgbSMONTHNAME11[] = { /* "November" */
+ 0x4e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0809) rgbSMONTHNAME12[] = { /* "December" */
+ 0x44, 0x65, 0x63, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVMONTHNAME1[] = { /* "Jan" */
+ 0x4a, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVMONTHNAME2[] = { /* "Feb" */
+ 0x46, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVMONTHNAME3[] = { /* "Mar" */
+ 0x4d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVMONTHNAME4[] = { /* "Apr" */
+ 0x41, 0x70, 0x72
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVMONTHNAME5[] = { /* "May" */
+ 0x4d, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVMONTHNAME6[] = { /* "Jun" */
+ 0x4a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVMONTHNAME7[] = { /* "Jul" */
+ 0x4a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVMONTHNAME8[] = { /* "Aug" */
+ 0x41, 0x75, 0x67
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVMONTHNAME9[] = { /* "Sep" */
+ 0x53, 0x65, 0x70
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVMONTHNAME10[] = { /* "Oct" */
+ 0x4f, 0x63, 0x74
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVMONTHNAME11[] = { /* "Nov" */
+ 0x4e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(0809) rgbSABBREVMONTHNAME12[] = { /* "Dec" */
+ 0x44, 0x65, 0x63
+};
+
+static BYTE NLSALLOC(0809) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0809) rgbIPOSSIGNPOSN[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0809) rgbINEGSIGNPOSN[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0809) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0809) rgbIPOSSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0809) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0809) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0809) rgbSENGCOUNTRY[] = { /* "United Kingdom" */
+ 0x55, 0x6e, 0x69, 0x74, 0x65, 0x64, 0x20, 0x4b
+ , 0x69, 0x6e, 0x67, 0x64, 0x6f, 0x6d
+};
+
+static BYTE NLSALLOC(0809) rgbSENGLANGUAGE[] = { /* "English" */
+ 0x45, 0x6e, 0x67, 0x6c, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(0809) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0809) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0809) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0809) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0809) rgbSTIMEFORMAT[] = { /* "HH:mm:ss" */
+ 0x48, 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0809) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0809) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0809) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0809) g_rglcinfo0809[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 12, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 14, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 7, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 1, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 12, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 6, rgbSDAYNAME1 }
+ , { 7, rgbSDAYNAME2 }
+ , { 9, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 6, rgbSDAYNAME5 }
+ , { 8, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 3, rgbSABBREVDAYNAME1 }
+ , { 3, rgbSABBREVDAYNAME2 }
+ , { 3, rgbSABBREVDAYNAME3 }
+ , { 3, rgbSABBREVDAYNAME4 }
+ , { 3, rgbSABBREVDAYNAME5 }
+ , { 3, rgbSABBREVDAYNAME6 }
+ , { 3, rgbSABBREVDAYNAME7 }
+ , { 7, rgbSMONTHNAME1 }
+ , { 8, rgbSMONTHNAME2 }
+ , { 5, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 14, rgbSENGCOUNTRY }
+ , { 7, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 8, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0809) g_strinfo0809 = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/080a.c b/private/oleauto/src/dispatch/win16/080a.c
new file mode 100644
index 000000000..e237d4a6f
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/080a.c
@@ -0,0 +1,537 @@
+/****************************************************************************
+* 080a.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Spanish - Mexico
+*
+* LCID = 0x080a
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:53:00 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_040a[256]; // from 040a:Spanish - Spain (Traditional Sort)
+extern EXPANSION rgexp_040a[7];
+extern DIGRAPH rgdig_040a[10];
+extern WORD rgwCType12_040a[256];
+extern WORD rgwCType3_040a[256];
+extern BYTE rgbUCase_040a[256];
+extern BYTE rgbLCase_040a[256];
+
+static BYTE NLSALLOC(080a) rgbILANGUAGE[] = { /* "080a" */
+ 0x30, 0x38, 0x30, 0x61
+};
+
+static BYTE NLSALLOC(080a) rgbSLANGUAGE[] = { /* "Mexican Spanish" */
+ 0x4d, 0x65, 0x78, 0x69, 0x63, 0x61, 0x6e, 0x20
+ , 0x53, 0x70, 0x61, 0x6e, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVLANGNAME[] = { /* "ESM" */
+ 0x45, 0x53, 0x4d
+};
+
+static BYTE NLSALLOC(080a) rgbSNATIVELANGNAME[] = { /* "Español" */
+ 0x45, 0x73, 0x70, 0x61, 0xf1, 0x6f, 0x6c
+};
+
+static BYTE NLSALLOC(080a) rgbICOUNTRY[] = { /* "52" */
+ 0x35, 0x32
+};
+
+static BYTE NLSALLOC(080a) rgbSCOUNTRY[] = { /* "Mexico" */
+ 0x4d, 0x65, 0x78, 0x69, 0x63, 0x6f
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVCTRYNAME[] = { /* "MEX" */
+ 0x4d, 0x45, 0x58
+};
+
+static BYTE NLSALLOC(080a) rgbSNATIVECTRYNAME[] = { /* "México" */
+ 0x4d, 0xe9, 0x78, 0x69, 0x63, 0x6f
+};
+
+static BYTE NLSALLOC(080a) rgbIDEFAULTLANGUAGE[] = { /* "080a" */
+ 0x30, 0x38, 0x30, 0x61
+};
+
+static BYTE NLSALLOC(080a) rgbIDEFAULTCOUNTRY[] = { /* "52" */
+ 0x35, 0x32
+};
+
+static BYTE NLSALLOC(080a) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(080a) rgbSLIST[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(080a) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080a) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(080a) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(080a) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(080a) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(080a) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(080a) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(080a) rgbSCURRENCY[] = { /* "N$" */
+ 0x4e, 0x24
+};
+
+static BYTE NLSALLOC(080a) rgbSINTLSYMBOL[] = { /* "MXN" */
+ 0x4d, 0x58, 0x4e
+};
+
+static BYTE NLSALLOC(080a) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(080a) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(080a) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(080a) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(080a) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(080a) rgbICURRENCY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080a) rgbINEGCURR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080a) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(080a) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(080a) rgbSSHORTDATE[] = { /* "d/MM/yy" */
+ 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(080a) rgbSLONGDATE[] = { /* "dddd d' de 'MMMM' de 'yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x20, 0x64, 0x27, 0x20
+ , 0x64, 0x65, 0x20, 0x27, 0x4d, 0x4d, 0x4d, 0x4d
+ , 0x27, 0x20, 0x64, 0x65, 0x20, 0x27, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(080a) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(080a) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(080a) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080a) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080a) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080a) rgbIDAYLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080a) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(080a) rgbS1159[] = { /* "AM" */
+ 0x41, 0x4d
+};
+
+static BYTE NLSALLOC(080a) rgbS2359[] = { /* "PM" */
+ 0x50, 0x4d
+};
+
+static BYTE NLSALLOC(080a) rgbSDAYNAME1[] = { /* "lunes" */
+ 0x6c, 0x75, 0x6e, 0x65, 0x73
+};
+
+static BYTE NLSALLOC(080a) rgbSDAYNAME2[] = { /* "martes" */
+ 0x6d, 0x61, 0x72, 0x74, 0x65, 0x73
+};
+
+static BYTE NLSALLOC(080a) rgbSDAYNAME3[] = { /* "miércoles" */
+ 0x6d, 0x69, 0xe9, 0x72, 0x63, 0x6f, 0x6c, 0x65
+ , 0x73
+};
+
+static BYTE NLSALLOC(080a) rgbSDAYNAME4[] = { /* "jueves" */
+ 0x6a, 0x75, 0x65, 0x76, 0x65, 0x73
+};
+
+static BYTE NLSALLOC(080a) rgbSDAYNAME5[] = { /* "viernes" */
+ 0x76, 0x69, 0x65, 0x72, 0x6e, 0x65, 0x73
+};
+
+static BYTE NLSALLOC(080a) rgbSDAYNAME6[] = { /* "sábado" */
+ 0x73, 0xe1, 0x62, 0x61, 0x64, 0x6f
+};
+
+static BYTE NLSALLOC(080a) rgbSDAYNAME7[] = { /* "domingo" */
+ 0x64, 0x6f, 0x6d, 0x69, 0x6e, 0x67, 0x6f
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVDAYNAME1[] = { /* "lun" */
+ 0x6c, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVDAYNAME2[] = { /* "mar" */
+ 0x6d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVDAYNAME3[] = { /* "mié" */
+ 0x6d, 0x69, 0xe9
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVDAYNAME4[] = { /* "jue" */
+ 0x6a, 0x75, 0x65
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVDAYNAME5[] = { /* "vie" */
+ 0x76, 0x69, 0x65
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVDAYNAME6[] = { /* "sáb" */
+ 0x73, 0xe1, 0x62
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVDAYNAME7[] = { /* "dom" */
+ 0x64, 0x6f, 0x6d
+};
+
+static BYTE NLSALLOC(080a) rgbSMONTHNAME1[] = { /* "enero" */
+ 0x65, 0x6e, 0x65, 0x72, 0x6f
+};
+
+static BYTE NLSALLOC(080a) rgbSMONTHNAME2[] = { /* "febrero" */
+ 0x66, 0x65, 0x62, 0x72, 0x65, 0x72, 0x6f
+};
+
+static BYTE NLSALLOC(080a) rgbSMONTHNAME3[] = { /* "marzo" */
+ 0x6d, 0x61, 0x72, 0x7a, 0x6f
+};
+
+static BYTE NLSALLOC(080a) rgbSMONTHNAME4[] = { /* "abril" */
+ 0x61, 0x62, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(080a) rgbSMONTHNAME5[] = { /* "mayo" */
+ 0x6d, 0x61, 0x79, 0x6f
+};
+
+static BYTE NLSALLOC(080a) rgbSMONTHNAME6[] = { /* "junio" */
+ 0x6a, 0x75, 0x6e, 0x69, 0x6f
+};
+
+static BYTE NLSALLOC(080a) rgbSMONTHNAME7[] = { /* "julio" */
+ 0x6a, 0x75, 0x6c, 0x69, 0x6f
+};
+
+static BYTE NLSALLOC(080a) rgbSMONTHNAME8[] = { /* "agosto" */
+ 0x61, 0x67, 0x6f, 0x73, 0x74, 0x6f
+};
+
+static BYTE NLSALLOC(080a) rgbSMONTHNAME9[] = { /* "septiembre" */
+ 0x73, 0x65, 0x70, 0x74, 0x69, 0x65, 0x6d, 0x62
+ , 0x72, 0x65
+};
+
+static BYTE NLSALLOC(080a) rgbSMONTHNAME10[] = { /* "octubre" */
+ 0x6f, 0x63, 0x74, 0x75, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(080a) rgbSMONTHNAME11[] = { /* "noviembre" */
+ 0x6e, 0x6f, 0x76, 0x69, 0x65, 0x6d, 0x62, 0x72
+ , 0x65
+};
+
+static BYTE NLSALLOC(080a) rgbSMONTHNAME12[] = { /* "diciembre" */
+ 0x64, 0x69, 0x63, 0x69, 0x65, 0x6d, 0x62, 0x72
+ , 0x65
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVMONTHNAME1[] = { /* "ene" */
+ 0x65, 0x6e, 0x65
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVMONTHNAME2[] = { /* "feb" */
+ 0x66, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVMONTHNAME3[] = { /* "mar" */
+ 0x6d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVMONTHNAME4[] = { /* "abr" */
+ 0x61, 0x62, 0x72
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVMONTHNAME5[] = { /* "may" */
+ 0x6d, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVMONTHNAME6[] = { /* "jun" */
+ 0x6a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVMONTHNAME7[] = { /* "jul" */
+ 0x6a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVMONTHNAME8[] = { /* "ago" */
+ 0x61, 0x67, 0x6f
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVMONTHNAME9[] = { /* "sep" */
+ 0x73, 0x65, 0x70
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVMONTHNAME10[] = { /* "oct" */
+ 0x6f, 0x63, 0x74
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVMONTHNAME11[] = { /* "nov" */
+ 0x6e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(080a) rgbSABBREVMONTHNAME12[] = { /* "dic" */
+ 0x64, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(080a) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(080a) rgbIPOSSIGNPOSN[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(080a) rgbINEGSIGNPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080a) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(080a) rgbIPOSSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080a) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(080a) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080a) rgbSENGCOUNTRY[] = { /* "Mexico" */
+ 0x4d, 0x65, 0x78, 0x69, 0x63, 0x6f
+};
+
+static BYTE NLSALLOC(080a) rgbSENGLANGUAGE[] = { /* "Spanish" */
+ 0x53, 0x70, 0x61, 0x6e, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(080a) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080a) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080a) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(080a) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(080a) rgbSTIMEFORMAT[] = { /* "h:mm:ss tt" */
+ 0x68, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73, 0x20
+ , 0x74, 0x74
+};
+
+static BYTE NLSALLOC(080a) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080a) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(080a) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(080a) g_rglcinfo080a[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 15, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 6, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 6, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 2, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 7, rgbSSHORTDATE }
+ , { 26, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 2, rgbS1159 }
+ , { 2, rgbS2359 }
+ , { 5, rgbSDAYNAME1 }
+ , { 6, rgbSDAYNAME2 }
+ , { 9, rgbSDAYNAME3 }
+ , { 6, rgbSDAYNAME4 }
+ , { 7, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 7, rgbSDAYNAME7 }
+ , { 3, rgbSABBREVDAYNAME1 }
+ , { 3, rgbSABBREVDAYNAME2 }
+ , { 3, rgbSABBREVDAYNAME3 }
+ , { 3, rgbSABBREVDAYNAME4 }
+ , { 3, rgbSABBREVDAYNAME5 }
+ , { 3, rgbSABBREVDAYNAME6 }
+ , { 3, rgbSABBREVDAYNAME7 }
+ , { 5, rgbSMONTHNAME1 }
+ , { 7, rgbSMONTHNAME2 }
+ , { 5, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 4, rgbSMONTHNAME5 }
+ , { 5, rgbSMONTHNAME6 }
+ , { 5, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 10, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 9, rgbSMONTHNAME11 }
+ , { 9, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 6, rgbSENGCOUNTRY }
+ , { 7, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 10, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(080a) g_strinfo080a = {
+ rgbUCase_040a
+ , rgbLCase_040a
+ , rgwCType12_040a
+ , rgwCType3_040a
+ , rgwSort_040a
+ , rgexp_040a
+ , rgdig_040a
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/080c.c b/private/oleauto/src/dispatch/win16/080c.c
new file mode 100644
index 000000000..22610e3a3
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/080c.c
@@ -0,0 +1,522 @@
+/****************************************************************************
+* 080c.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* French - Belgium
+*
+* LCID = 0x080c
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:41:24 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0409[256]; // from 0409:English - United States
+extern EXPANSION rgexp_0409[7];
+extern WORD rgwCType12_0409[256];
+extern WORD rgwCType3_0409[256];
+extern BYTE rgbUCase_0409[256];
+extern BYTE rgbLCase_0409[256];
+
+static BYTE NLSALLOC(080c) rgbILANGUAGE[] = { /* "080c" */
+ 0x30, 0x38, 0x30, 0x63
+};
+
+static BYTE NLSALLOC(080c) rgbSLANGUAGE[] = { /* "Belgian French" */
+ 0x42, 0x65, 0x6c, 0x67, 0x69, 0x61, 0x6e, 0x20
+ , 0x46, 0x72, 0x65, 0x6e, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVLANGNAME[] = { /* "FRB" */
+ 0x46, 0x52, 0x42
+};
+
+static BYTE NLSALLOC(080c) rgbSNATIVELANGNAME[] = { /* "français" */
+ 0x66, 0x72, 0x61, 0x6e, 0xe7, 0x61, 0x69, 0x73
+};
+
+static BYTE NLSALLOC(080c) rgbICOUNTRY[] = { /* "32" */
+ 0x33, 0x32
+};
+
+static BYTE NLSALLOC(080c) rgbSCOUNTRY[] = { /* "Belgium" */
+ 0x42, 0x65, 0x6c, 0x67, 0x69, 0x75, 0x6d
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVCTRYNAME[] = { /* "BEL" */
+ 0x42, 0x45, 0x4c
+};
+
+static BYTE NLSALLOC(080c) rgbSNATIVECTRYNAME[] = { /* "Belgique" */
+ 0x42, 0x65, 0x6c, 0x67, 0x69, 0x71, 0x75, 0x65
+};
+
+static BYTE NLSALLOC(080c) rgbIDEFAULTLANGUAGE[] = { /* "080c" */
+ 0x30, 0x38, 0x30, 0x63
+};
+
+static BYTE NLSALLOC(080c) rgbIDEFAULTCOUNTRY[] = { /* "32" */
+ 0x33, 0x32
+};
+
+static BYTE NLSALLOC(080c) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(080c) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(080c) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080c) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(080c) rgbSTHOUSAND[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(080c) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(080c) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(080c) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(080c) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(080c) rgbSCURRENCY[] = { /* "FB" */
+ 0x46, 0x42
+};
+
+static BYTE NLSALLOC(080c) rgbSINTLSYMBOL[] = { /* "BEF" */
+ 0x42, 0x45, 0x46
+};
+
+static BYTE NLSALLOC(080c) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(080c) rgbSMONTHOUSANDSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(080c) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(080c) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(080c) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(080c) rgbICURRENCY[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(080c) rgbINEGCURR[] = { /* "8" */
+ 0x38
+};
+
+static BYTE NLSALLOC(080c) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(080c) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(080c) rgbSSHORTDATE[] = { /* "d/MM/yy" */
+ 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(080c) rgbSLONGDATE[] = { /* "dddd d MMMM yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x20, 0x64, 0x20, 0x4d
+ , 0x4d, 0x4d, 0x4d, 0x20, 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(080c) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(080c) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(080c) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(080c) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080c) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080c) rgbIDAYLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080c) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(080c) rgbSDAYNAME1[] = { /* "lundi" */
+ 0x6c, 0x75, 0x6e, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(080c) rgbSDAYNAME2[] = { /* "mardi" */
+ 0x6d, 0x61, 0x72, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(080c) rgbSDAYNAME3[] = { /* "mercredi" */
+ 0x6d, 0x65, 0x72, 0x63, 0x72, 0x65, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(080c) rgbSDAYNAME4[] = { /* "jeudi" */
+ 0x6a, 0x65, 0x75, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(080c) rgbSDAYNAME5[] = { /* "vendredi" */
+ 0x76, 0x65, 0x6e, 0x64, 0x72, 0x65, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(080c) rgbSDAYNAME6[] = { /* "samedi" */
+ 0x73, 0x61, 0x6d, 0x65, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(080c) rgbSDAYNAME7[] = { /* "dimanche" */
+ 0x64, 0x69, 0x6d, 0x61, 0x6e, 0x63, 0x68, 0x65
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVDAYNAME1[] = { /* "lun." */
+ 0x6c, 0x75, 0x6e, 0x2e
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVDAYNAME2[] = { /* "mar." */
+ 0x6d, 0x61, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVDAYNAME3[] = { /* "mer." */
+ 0x6d, 0x65, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVDAYNAME4[] = { /* "jeu." */
+ 0x6a, 0x65, 0x75, 0x2e
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVDAYNAME5[] = { /* "ven." */
+ 0x76, 0x65, 0x6e, 0x2e
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVDAYNAME6[] = { /* "sam." */
+ 0x73, 0x61, 0x6d, 0x2e
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVDAYNAME7[] = { /* "dim." */
+ 0x64, 0x69, 0x6d, 0x2e
+};
+
+static BYTE NLSALLOC(080c) rgbSMONTHNAME1[] = { /* "janvier" */
+ 0x6a, 0x61, 0x6e, 0x76, 0x69, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(080c) rgbSMONTHNAME2[] = { /* "février" */
+ 0x66, 0xe9, 0x76, 0x72, 0x69, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(080c) rgbSMONTHNAME3[] = { /* "mars" */
+ 0x6d, 0x61, 0x72, 0x73
+};
+
+static BYTE NLSALLOC(080c) rgbSMONTHNAME4[] = { /* "avril" */
+ 0x61, 0x76, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(080c) rgbSMONTHNAME5[] = { /* "mai" */
+ 0x6d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(080c) rgbSMONTHNAME6[] = { /* "juin" */
+ 0x6a, 0x75, 0x69, 0x6e
+};
+
+static BYTE NLSALLOC(080c) rgbSMONTHNAME7[] = { /* "juillet" */
+ 0x6a, 0x75, 0x69, 0x6c, 0x6c, 0x65, 0x74
+};
+
+static BYTE NLSALLOC(080c) rgbSMONTHNAME8[] = { /* "août" */
+ 0x61, 0x6f, 0xfb, 0x74
+};
+
+static BYTE NLSALLOC(080c) rgbSMONTHNAME9[] = { /* "septembre" */
+ 0x73, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x72
+ , 0x65
+};
+
+static BYTE NLSALLOC(080c) rgbSMONTHNAME10[] = { /* "octobre" */
+ 0x6f, 0x63, 0x74, 0x6f, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(080c) rgbSMONTHNAME11[] = { /* "novembre" */
+ 0x6e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(080c) rgbSMONTHNAME12[] = { /* "décembre" */
+ 0x64, 0xe9, 0x63, 0x65, 0x6d, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVMONTHNAME1[] = { /* "janv." */
+ 0x6a, 0x61, 0x6e, 0x76, 0x2e
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVMONTHNAME2[] = { /* "févr." */
+ 0x66, 0xe9, 0x76, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVMONTHNAME3[] = { /* "mars" */
+ 0x6d, 0x61, 0x72, 0x73
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVMONTHNAME4[] = { /* "avr." */
+ 0x61, 0x76, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVMONTHNAME5[] = { /* "mai" */
+ 0x6d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVMONTHNAME6[] = { /* "juin" */
+ 0x6a, 0x75, 0x69, 0x6e
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVMONTHNAME7[] = { /* "juil." */
+ 0x6a, 0x75, 0x69, 0x6c, 0x2e
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVMONTHNAME8[] = { /* "août" */
+ 0x61, 0x6f, 0xfb, 0x74
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVMONTHNAME9[] = { /* "sept." */
+ 0x73, 0x65, 0x70, 0x74, 0x2e
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVMONTHNAME10[] = { /* "oct." */
+ 0x6f, 0x63, 0x74, 0x2e
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVMONTHNAME11[] = { /* "nov." */
+ 0x6e, 0x6f, 0x76, 0x2e
+};
+
+static BYTE NLSALLOC(080c) rgbSABBREVMONTHNAME12[] = { /* "déc." */
+ 0x64, 0xe9, 0x63, 0x2e
+};
+
+static BYTE NLSALLOC(080c) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(080c) rgbIPOSSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(080c) rgbINEGSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(080c) rgbIPOSSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080c) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(080c) rgbINEGSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080c) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(080c) rgbSENGCOUNTRY[] = { /* "Belgium" */
+ 0x42, 0x65, 0x6c, 0x67, 0x69, 0x75, 0x6d
+};
+
+static BYTE NLSALLOC(080c) rgbSENGLANGUAGE[] = { /* "French" */
+ 0x46, 0x72, 0x65, 0x6e, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(080c) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080c) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080c) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(080c) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(080c) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(080c) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(080c) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(080c) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(080c) g_rglcinfo080c[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 14, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 8, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 7, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 8, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 2, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 7, rgbSSHORTDATE }
+ , { 16, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 5, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 8, rgbSDAYNAME3 }
+ , { 5, rgbSDAYNAME4 }
+ , { 8, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 8, rgbSDAYNAME7 }
+ , { 4, rgbSABBREVDAYNAME1 }
+ , { 4, rgbSABBREVDAYNAME2 }
+ , { 4, rgbSABBREVDAYNAME3 }
+ , { 4, rgbSABBREVDAYNAME4 }
+ , { 4, rgbSABBREVDAYNAME5 }
+ , { 4, rgbSABBREVDAYNAME6 }
+ , { 4, rgbSABBREVDAYNAME7 }
+ , { 7, rgbSMONTHNAME1 }
+ , { 7, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 7, rgbSMONTHNAME7 }
+ , { 4, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 5, rgbSABBREVMONTHNAME1 }
+ , { 5, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 4, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 4, rgbSABBREVMONTHNAME6 }
+ , { 5, rgbSABBREVMONTHNAME7 }
+ , { 4, rgbSABBREVMONTHNAME8 }
+ , { 5, rgbSABBREVMONTHNAME9 }
+ , { 4, rgbSABBREVMONTHNAME10 }
+ , { 4, rgbSABBREVMONTHNAME11 }
+ , { 4, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 7, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(080c) g_strinfo080c = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0810.c b/private/oleauto/src/dispatch/win16/0810.c
new file mode 100644
index 000000000..ec820a87e
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0810.c
@@ -0,0 +1,518 @@
+/****************************************************************************
+* 0810.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Italian - Switzerland
+*
+* LCID = 0x0810
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:42:00 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0409[256]; // from 0409:English - United States
+extern EXPANSION rgexp_0409[7];
+extern WORD rgwCType12_0409[256];
+extern WORD rgwCType3_0409[256];
+extern BYTE rgbUCase_0409[256];
+extern BYTE rgbLCase_0409[256];
+
+static BYTE NLSALLOC(0810) rgbILANGUAGE[] = { /* "0810" */
+ 0x30, 0x38, 0x31, 0x30
+};
+
+static BYTE NLSALLOC(0810) rgbSLANGUAGE[] = { /* "Swiss Italian" */
+ 0x53, 0x77, 0x69, 0x73, 0x73, 0x20, 0x49, 0x74
+ , 0x61, 0x6c, 0x69, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVLANGNAME[] = { /* "ITS" */
+ 0x49, 0x54, 0x53
+};
+
+static BYTE NLSALLOC(0810) rgbSNATIVELANGNAME[] = { /* "Italiano" */
+ 0x49, 0x74, 0x61, 0x6c, 0x69, 0x61, 0x6e, 0x6f
+};
+
+static BYTE NLSALLOC(0810) rgbICOUNTRY[] = { /* "41" */
+ 0x34, 0x31
+};
+
+static BYTE NLSALLOC(0810) rgbSCOUNTRY[] = { /* "Switzerland" */
+ 0x53, 0x77, 0x69, 0x74, 0x7a, 0x65, 0x72, 0x6c
+ , 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVCTRYNAME[] = { /* "CHE" */
+ 0x43, 0x48, 0x45
+};
+
+static BYTE NLSALLOC(0810) rgbSNATIVECTRYNAME[] = { /* "Svizzera" */
+ 0x53, 0x76, 0x69, 0x7a, 0x7a, 0x65, 0x72, 0x61
+};
+
+static BYTE NLSALLOC(0810) rgbIDEFAULTLANGUAGE[] = { /* "0810" */
+ 0x30, 0x38, 0x31, 0x30
+};
+
+static BYTE NLSALLOC(0810) rgbIDEFAULTCOUNTRY[] = { /* "41" */
+ 0x34, 0x31
+};
+
+static BYTE NLSALLOC(0810) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0810) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0810) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0810) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0810) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0810) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0810) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0810) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0810) rgbSCURRENCY[] = { /* "CHF" */
+ 0x43, 0x48, 0x46
+};
+
+static BYTE NLSALLOC(0810) rgbSINTLSYMBOL[] = { /* "CHF" */
+ 0x43, 0x48, 0x46
+};
+
+static BYTE NLSALLOC(0810) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0810) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0810) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0810) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0810) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0810) rgbINEGCURR[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0810) rgbSDATE[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0810) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0810) rgbSSHORTDATE[] = { /* "dd.MM.yy" */
+ 0x64, 0x64, 0x2e, 0x4d, 0x4d, 0x2e, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0810) rgbSLONGDATE[] = { /* "dddd, d. MMMM yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x2c, 0x20, 0x64, 0x2e
+ , 0x20, 0x4d, 0x4d, 0x4d, 0x4d, 0x20, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0810) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0810) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0810) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0810) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0810) rgbITLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0810) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0810) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0810) rgbSDAYNAME1[] = { /* "lunedì" */
+ 0x6c, 0x75, 0x6e, 0x65, 0x64, 0xec
+};
+
+static BYTE NLSALLOC(0810) rgbSDAYNAME2[] = { /* "martedì" */
+ 0x6d, 0x61, 0x72, 0x74, 0x65, 0x64, 0xec
+};
+
+static BYTE NLSALLOC(0810) rgbSDAYNAME3[] = { /* "mercoledì" */
+ 0x6d, 0x65, 0x72, 0x63, 0x6f, 0x6c, 0x65, 0x64
+ , 0xec
+};
+
+static BYTE NLSALLOC(0810) rgbSDAYNAME4[] = { /* "giovedì" */
+ 0x67, 0x69, 0x6f, 0x76, 0x65, 0x64, 0xec
+};
+
+static BYTE NLSALLOC(0810) rgbSDAYNAME5[] = { /* "venerdì" */
+ 0x76, 0x65, 0x6e, 0x65, 0x72, 0x64, 0xec
+};
+
+static BYTE NLSALLOC(0810) rgbSDAYNAME6[] = { /* "sabato" */
+ 0x73, 0x61, 0x62, 0x61, 0x74, 0x6f
+};
+
+static BYTE NLSALLOC(0810) rgbSDAYNAME7[] = { /* "domenica" */
+ 0x64, 0x6f, 0x6d, 0x65, 0x6e, 0x69, 0x63, 0x61
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVDAYNAME1[] = { /* "lun" */
+ 0x6c, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVDAYNAME2[] = { /* "mar" */
+ 0x6d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVDAYNAME3[] = { /* "mer" */
+ 0x6d, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVDAYNAME4[] = { /* "gio" */
+ 0x67, 0x69, 0x6f
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVDAYNAME5[] = { /* "ven" */
+ 0x76, 0x65, 0x6e
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVDAYNAME6[] = { /* "sab" */
+ 0x73, 0x61, 0x62
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVDAYNAME7[] = { /* "dom" */
+ 0x64, 0x6f, 0x6d
+};
+
+static BYTE NLSALLOC(0810) rgbSMONTHNAME1[] = { /* "gennaio" */
+ 0x67, 0x65, 0x6e, 0x6e, 0x61, 0x69, 0x6f
+};
+
+static BYTE NLSALLOC(0810) rgbSMONTHNAME2[] = { /* "febbraio" */
+ 0x66, 0x65, 0x62, 0x62, 0x72, 0x61, 0x69, 0x6f
+};
+
+static BYTE NLSALLOC(0810) rgbSMONTHNAME3[] = { /* "marzo" */
+ 0x6d, 0x61, 0x72, 0x7a, 0x6f
+};
+
+static BYTE NLSALLOC(0810) rgbSMONTHNAME4[] = { /* "aprile" */
+ 0x61, 0x70, 0x72, 0x69, 0x6c, 0x65
+};
+
+static BYTE NLSALLOC(0810) rgbSMONTHNAME5[] = { /* "maggio" */
+ 0x6d, 0x61, 0x67, 0x67, 0x69, 0x6f
+};
+
+static BYTE NLSALLOC(0810) rgbSMONTHNAME6[] = { /* "giugno" */
+ 0x67, 0x69, 0x75, 0x67, 0x6e, 0x6f
+};
+
+static BYTE NLSALLOC(0810) rgbSMONTHNAME7[] = { /* "luglio" */
+ 0x6c, 0x75, 0x67, 0x6c, 0x69, 0x6f
+};
+
+static BYTE NLSALLOC(0810) rgbSMONTHNAME8[] = { /* "agosto" */
+ 0x61, 0x67, 0x6f, 0x73, 0x74, 0x6f
+};
+
+static BYTE NLSALLOC(0810) rgbSMONTHNAME9[] = { /* "settembre" */
+ 0x73, 0x65, 0x74, 0x74, 0x65, 0x6d, 0x62, 0x72
+ , 0x65
+};
+
+static BYTE NLSALLOC(0810) rgbSMONTHNAME10[] = { /* "ottobre" */
+ 0x6f, 0x74, 0x74, 0x6f, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(0810) rgbSMONTHNAME11[] = { /* "novembre" */
+ 0x6e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(0810) rgbSMONTHNAME12[] = { /* "dicembre" */
+ 0x64, 0x69, 0x63, 0x65, 0x6d, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVMONTHNAME1[] = { /* "gen" */
+ 0x67, 0x65, 0x6e
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVMONTHNAME2[] = { /* "feb" */
+ 0x66, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVMONTHNAME3[] = { /* "mar" */
+ 0x6d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVMONTHNAME4[] = { /* "apr" */
+ 0x61, 0x70, 0x72
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVMONTHNAME5[] = { /* "mag" */
+ 0x6d, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVMONTHNAME6[] = { /* "gio" */
+ 0x67, 0x69, 0x6f
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVMONTHNAME7[] = { /* "lug" */
+ 0x6c, 0x75, 0x67
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVMONTHNAME8[] = { /* "ago" */
+ 0x61, 0x67, 0x6f
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVMONTHNAME9[] = { /* "set" */
+ 0x73, 0x65, 0x74
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVMONTHNAME10[] = { /* "ott" */
+ 0x6f, 0x74, 0x74
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVMONTHNAME11[] = { /* "nov" */
+ 0x6e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(0810) rgbSABBREVMONTHNAME12[] = { /* "dic" */
+ 0x64, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(0810) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0810) rgbIPOSSIGNPOSN[] = { /* "4" */
+ 0x34
+};
+
+static BYTE NLSALLOC(0810) rgbINEGSIGNPOSN[] = { /* "4" */
+ 0x34
+};
+
+static BYTE NLSALLOC(0810) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0810) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0810) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0810) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0810) rgbSENGCOUNTRY[] = { /* "Switzerland" */
+ 0x53, 0x77, 0x69, 0x74, 0x7a, 0x65, 0x72, 0x6c
+ , 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(0810) rgbSENGLANGUAGE[] = { /* "Italian" */
+ 0x49, 0x74, 0x61, 0x6c, 0x69, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0810) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0810) rgbIFIRSTWEEKOFYEAR[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0810) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0810) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0810) rgbSTIMEFORMAT[] = { /* "HH:mm:ss" */
+ 0x48, 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0810) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0810) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0810) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0810) g_rglcinfo0810[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 13, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 8, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 11, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 8, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 0, NULL } /* STHOUSAND */
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 3, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 0, NULL } /* SMONTHOUSANDSEP */
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 18, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 6, rgbSDAYNAME1 }
+ , { 7, rgbSDAYNAME2 }
+ , { 9, rgbSDAYNAME3 }
+ , { 7, rgbSDAYNAME4 }
+ , { 7, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 8, rgbSDAYNAME7 }
+ , { 3, rgbSABBREVDAYNAME1 }
+ , { 3, rgbSABBREVDAYNAME2 }
+ , { 3, rgbSABBREVDAYNAME3 }
+ , { 3, rgbSABBREVDAYNAME4 }
+ , { 3, rgbSABBREVDAYNAME5 }
+ , { 3, rgbSABBREVDAYNAME6 }
+ , { 3, rgbSABBREVDAYNAME7 }
+ , { 7, rgbSMONTHNAME1 }
+ , { 8, rgbSMONTHNAME2 }
+ , { 5, rgbSMONTHNAME3 }
+ , { 6, rgbSMONTHNAME4 }
+ , { 6, rgbSMONTHNAME5 }
+ , { 6, rgbSMONTHNAME6 }
+ , { 6, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 11, rgbSENGCOUNTRY }
+ , { 7, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 8, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0810) g_strinfo0810 = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0813.c b/private/oleauto/src/dispatch/win16/0813.c
new file mode 100644
index 000000000..17439365b
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0813.c
@@ -0,0 +1,524 @@
+/****************************************************************************
+* 0813.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Dutch - Belgium
+*
+* LCID = 0x0813
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:42:39 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0409[256]; // from 0409:English - United States
+extern EXPANSION rgexp_0409[7];
+extern WORD rgwCType12_0409[256];
+extern WORD rgwCType3_0409[256];
+extern BYTE rgbUCase_0409[256];
+extern BYTE rgbLCase_0409[256];
+
+static BYTE NLSALLOC(0813) rgbILANGUAGE[] = { /* "0813" */
+ 0x30, 0x38, 0x31, 0x33
+};
+
+static BYTE NLSALLOC(0813) rgbSLANGUAGE[] = { /* "Belgian Dutch" */
+ 0x42, 0x65, 0x6c, 0x67, 0x69, 0x61, 0x6e, 0x20
+ , 0x44, 0x75, 0x74, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVLANGNAME[] = { /* "NLB" */
+ 0x4e, 0x4c, 0x42
+};
+
+static BYTE NLSALLOC(0813) rgbSNATIVELANGNAME[] = { /* "Nederlands" */
+ 0x4e, 0x65, 0x64, 0x65, 0x72, 0x6c, 0x61, 0x6e
+ , 0x64, 0x73
+};
+
+static BYTE NLSALLOC(0813) rgbICOUNTRY[] = { /* "32" */
+ 0x33, 0x32
+};
+
+static BYTE NLSALLOC(0813) rgbSCOUNTRY[] = { /* "Belgium" */
+ 0x42, 0x65, 0x6c, 0x67, 0x69, 0x75, 0x6d
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVCTRYNAME[] = { /* "BEL" */
+ 0x42, 0x45, 0x4c
+};
+
+static BYTE NLSALLOC(0813) rgbSNATIVECTRYNAME[] = { /* "België" */
+ 0x42, 0x65, 0x6c, 0x67, 0x69, 0xeb
+};
+
+static BYTE NLSALLOC(0813) rgbIDEFAULTLANGUAGE[] = { /* "0813" */
+ 0x30, 0x38, 0x31, 0x33
+};
+
+static BYTE NLSALLOC(0813) rgbIDEFAULTCOUNTRY[] = { /* "32" */
+ 0x33, 0x32
+};
+
+static BYTE NLSALLOC(0813) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0813) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0813) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0813) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0813) rgbSTHOUSAND[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0813) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0813) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0813) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0813) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0813) rgbSCURRENCY[] = { /* "BF" */
+ 0x42, 0x46
+};
+
+static BYTE NLSALLOC(0813) rgbSINTLSYMBOL[] = { /* "BEF" */
+ 0x42, 0x45, 0x46
+};
+
+static BYTE NLSALLOC(0813) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0813) rgbSMONTHOUSANDSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0813) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0813) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0813) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0813) rgbICURRENCY[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0813) rgbINEGCURR[] = { /* "8" */
+ 0x38
+};
+
+static BYTE NLSALLOC(0813) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(0813) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0813) rgbSSHORTDATE[] = { /* "d/MM/yy" */
+ 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0813) rgbSLONGDATE[] = { /* "dddd d MMMM yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x20, 0x64, 0x20, 0x4d
+ , 0x4d, 0x4d, 0x4d, 0x20, 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0813) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0813) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0813) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0813) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0813) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0813) rgbIDAYLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0813) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0813) rgbSDAYNAME1[] = { /* "maandag" */
+ 0x6d, 0x61, 0x61, 0x6e, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0813) rgbSDAYNAME2[] = { /* "dinsdag" */
+ 0x64, 0x69, 0x6e, 0x73, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0813) rgbSDAYNAME3[] = { /* "woensdag" */
+ 0x77, 0x6f, 0x65, 0x6e, 0x73, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0813) rgbSDAYNAME4[] = { /* "donderdag" */
+ 0x64, 0x6f, 0x6e, 0x64, 0x65, 0x72, 0x64, 0x61
+ , 0x67
+};
+
+static BYTE NLSALLOC(0813) rgbSDAYNAME5[] = { /* "vrijdag" */
+ 0x76, 0x72, 0x69, 0x6a, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0813) rgbSDAYNAME6[] = { /* "zaterdag" */
+ 0x7a, 0x61, 0x74, 0x65, 0x72, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0813) rgbSDAYNAME7[] = { /* "zondag" */
+ 0x7a, 0x6f, 0x6e, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVDAYNAME1[] = { /* "ma" */
+ 0x6d, 0x61
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVDAYNAME2[] = { /* "di" */
+ 0x64, 0x69
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVDAYNAME3[] = { /* "wo" */
+ 0x77, 0x6f
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVDAYNAME4[] = { /* "do" */
+ 0x64, 0x6f
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVDAYNAME5[] = { /* "vr" */
+ 0x76, 0x72
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVDAYNAME6[] = { /* "za" */
+ 0x7a, 0x61
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVDAYNAME7[] = { /* "zo" */
+ 0x7a, 0x6f
+};
+
+static BYTE NLSALLOC(0813) rgbSMONTHNAME1[] = { /* "januari" */
+ 0x6a, 0x61, 0x6e, 0x75, 0x61, 0x72, 0x69
+};
+
+static BYTE NLSALLOC(0813) rgbSMONTHNAME2[] = { /* "februari" */
+ 0x66, 0x65, 0x62, 0x72, 0x75, 0x61, 0x72, 0x69
+};
+
+static BYTE NLSALLOC(0813) rgbSMONTHNAME3[] = { /* "maart" */
+ 0x6d, 0x61, 0x61, 0x72, 0x74
+};
+
+static BYTE NLSALLOC(0813) rgbSMONTHNAME4[] = { /* "april" */
+ 0x61, 0x70, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(0813) rgbSMONTHNAME5[] = { /* "mei" */
+ 0x6d, 0x65, 0x69
+};
+
+static BYTE NLSALLOC(0813) rgbSMONTHNAME6[] = { /* "juni" */
+ 0x6a, 0x75, 0x6e, 0x69
+};
+
+static BYTE NLSALLOC(0813) rgbSMONTHNAME7[] = { /* "juli" */
+ 0x6a, 0x75, 0x6c, 0x69
+};
+
+static BYTE NLSALLOC(0813) rgbSMONTHNAME8[] = { /* "augustus" */
+ 0x61, 0x75, 0x67, 0x75, 0x73, 0x74, 0x75, 0x73
+};
+
+static BYTE NLSALLOC(0813) rgbSMONTHNAME9[] = { /* "september" */
+ 0x73, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x65
+ , 0x72
+};
+
+static BYTE NLSALLOC(0813) rgbSMONTHNAME10[] = { /* "oktober" */
+ 0x6f, 0x6b, 0x74, 0x6f, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0813) rgbSMONTHNAME11[] = { /* "november" */
+ 0x6e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0813) rgbSMONTHNAME12[] = { /* "december" */
+ 0x64, 0x65, 0x63, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVMONTHNAME1[] = { /* "jan" */
+ 0x6a, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVMONTHNAME2[] = { /* "feb" */
+ 0x66, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVMONTHNAME3[] = { /* "mrt" */
+ 0x6d, 0x72, 0x74
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVMONTHNAME4[] = { /* "apr" */
+ 0x61, 0x70, 0x72
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVMONTHNAME5[] = { /* "mei" */
+ 0x6d, 0x65, 0x69
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVMONTHNAME6[] = { /* "jun" */
+ 0x6a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVMONTHNAME7[] = { /* "jul" */
+ 0x6a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVMONTHNAME8[] = { /* "aug" */
+ 0x61, 0x75, 0x67
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVMONTHNAME9[] = { /* "sep" */
+ 0x73, 0x65, 0x70
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVMONTHNAME10[] = { /* "okt" */
+ 0x6f, 0x6b, 0x74
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVMONTHNAME11[] = { /* "nov" */
+ 0x6e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(0813) rgbSABBREVMONTHNAME12[] = { /* "dec" */
+ 0x64, 0x65, 0x63
+};
+
+static BYTE NLSALLOC(0813) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0813) rgbIPOSSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0813) rgbINEGSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0813) rgbIPOSSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0813) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0813) rgbINEGSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0813) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0813) rgbSENGCOUNTRY[] = { /* "Belgium" */
+ 0x42, 0x65, 0x6c, 0x67, 0x69, 0x75, 0x6d
+};
+
+static BYTE NLSALLOC(0813) rgbSENGLANGUAGE[] = { /* "Dutch" */
+ 0x44, 0x75, 0x74, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(0813) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0813) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0813) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0813) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0813) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0813) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0813) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0813) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0813) g_rglcinfo0813[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 13, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 10, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 7, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 6, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 2, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 7, rgbSSHORTDATE }
+ , { 16, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 7, rgbSDAYNAME1 }
+ , { 7, rgbSDAYNAME2 }
+ , { 8, rgbSDAYNAME3 }
+ , { 9, rgbSDAYNAME4 }
+ , { 7, rgbSDAYNAME5 }
+ , { 8, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 2, rgbSABBREVDAYNAME1 }
+ , { 2, rgbSABBREVDAYNAME2 }
+ , { 2, rgbSABBREVDAYNAME3 }
+ , { 2, rgbSABBREVDAYNAME4 }
+ , { 2, rgbSABBREVDAYNAME5 }
+ , { 2, rgbSABBREVDAYNAME6 }
+ , { 2, rgbSABBREVDAYNAME7 }
+ , { 7, rgbSMONTHNAME1 }
+ , { 8, rgbSMONTHNAME2 }
+ , { 5, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 8, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 7, rgbSENGCOUNTRY }
+ , { 5, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0813) g_strinfo0813 = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0814.c b/private/oleauto/src/dispatch/win16/0814.c
new file mode 100644
index 000000000..891bce127
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0814.c
@@ -0,0 +1,526 @@
+/****************************************************************************
+* 0814.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Norwegian - Norway (Nynorsk)
+*
+* LCID = 0x0814
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:58:50 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0406[256]; // from 0406:Danish - Denmark
+extern EXPANSION rgexp_0406[5];
+extern DIGRAPH rgdig_0406[5];
+extern WORD rgwCType12_0406[256];
+extern WORD rgwCType3_0406[256];
+extern BYTE rgbUCase_0406[256];
+extern BYTE rgbLCase_0406[256];
+
+static BYTE NLSALLOC(0814) rgbILANGUAGE[] = { /* "0814" */
+ 0x30, 0x38, 0x31, 0x34
+};
+
+static BYTE NLSALLOC(0814) rgbSLANGUAGE[] = { /* "Norwegian - Nynorsk" */
+ 0x4e, 0x6f, 0x72, 0x77, 0x65, 0x67, 0x69, 0x61
+ , 0x6e, 0x20, 0x2d, 0x20, 0x4e, 0x79, 0x6e, 0x6f
+ , 0x72, 0x73, 0x6b
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVLANGNAME[] = { /* "NON" */
+ 0x4e, 0x4f, 0x4e
+};
+
+static BYTE NLSALLOC(0814) rgbSNATIVELANGNAME[] = { /* "nynorsk" */
+ 0x6e, 0x79, 0x6e, 0x6f, 0x72, 0x73, 0x6b
+};
+
+static BYTE NLSALLOC(0814) rgbICOUNTRY[] = { /* "47" */
+ 0x34, 0x37
+};
+
+static BYTE NLSALLOC(0814) rgbSCOUNTRY[] = { /* "Norway" */
+ 0x4e, 0x6f, 0x72, 0x77, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVCTRYNAME[] = { /* "NOR" */
+ 0x4e, 0x4f, 0x52
+};
+
+static BYTE NLSALLOC(0814) rgbSNATIVECTRYNAME[] = { /* "Noreg" */
+ 0x4e, 0x6f, 0x72, 0x65, 0x67
+};
+
+static BYTE NLSALLOC(0814) rgbIDEFAULTLANGUAGE[] = { /* "0814" */
+ 0x30, 0x38, 0x31, 0x34
+};
+
+static BYTE NLSALLOC(0814) rgbIDEFAULTCOUNTRY[] = { /* "47" */
+ 0x34, 0x37
+};
+
+static BYTE NLSALLOC(0814) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0814) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0814) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0814) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0814) rgbSTHOUSAND[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(0814) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0814) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0814) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0814) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0814) rgbSCURRENCY[] = { /* "kr" */
+ 0x6b, 0x72
+};
+
+static BYTE NLSALLOC(0814) rgbSINTLSYMBOL[] = { /* "NOK" */
+ 0x4e, 0x4f, 0x4b
+};
+
+static BYTE NLSALLOC(0814) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0814) rgbSMONTHOUSANDSEP[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(0814) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0814) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0814) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0814) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0814) rgbINEGCURR[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0814) rgbSDATE[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0814) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0814) rgbSSHORTDATE[] = { /* "dd.MM.yy" */
+ 0x64, 0x64, 0x2e, 0x4d, 0x4d, 0x2e, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0814) rgbSLONGDATE[] = { /* "d. MMMM yyyy" */
+ 0x64, 0x2e, 0x20, 0x4d, 0x4d, 0x4d, 0x4d, 0x20
+ , 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0814) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0814) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0814) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0814) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0814) rgbITLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0814) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0814) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0814) rgbSDAYNAME1[] = { /* "måndag" */
+ 0x6d, 0xe5, 0x6e, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0814) rgbSDAYNAME2[] = { /* "tysdag" */
+ 0x74, 0x79, 0x73, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0814) rgbSDAYNAME3[] = { /* "onsdag" */
+ 0x6f, 0x6e, 0x73, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0814) rgbSDAYNAME4[] = { /* "torsdag" */
+ 0x74, 0x6f, 0x72, 0x73, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0814) rgbSDAYNAME5[] = { /* "fredag" */
+ 0x66, 0x72, 0x65, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0814) rgbSDAYNAME6[] = { /* "laurdag" */
+ 0x6c, 0x61, 0x75, 0x72, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0814) rgbSDAYNAME7[] = { /* "sundag" */
+ 0x73, 0x75, 0x6e, 0x64, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVDAYNAME1[] = { /* "må" */
+ 0x6d, 0xe5
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVDAYNAME2[] = { /* "ty" */
+ 0x74, 0x79
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVDAYNAME3[] = { /* "on" */
+ 0x6f, 0x6e
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVDAYNAME4[] = { /* "to" */
+ 0x74, 0x6f
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVDAYNAME5[] = { /* "fr" */
+ 0x66, 0x72
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVDAYNAME6[] = { /* "lau" */
+ 0x6c, 0x61, 0x75
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVDAYNAME7[] = { /* "su" */
+ 0x73, 0x75
+};
+
+static BYTE NLSALLOC(0814) rgbSMONTHNAME1[] = { /* "januar" */
+ 0x6a, 0x61, 0x6e, 0x75, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0814) rgbSMONTHNAME2[] = { /* "februar" */
+ 0x66, 0x65, 0x62, 0x72, 0x75, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0814) rgbSMONTHNAME3[] = { /* "mars" */
+ 0x6d, 0x61, 0x72, 0x73
+};
+
+static BYTE NLSALLOC(0814) rgbSMONTHNAME4[] = { /* "april" */
+ 0x61, 0x70, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(0814) rgbSMONTHNAME5[] = { /* "mai" */
+ 0x6d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(0814) rgbSMONTHNAME6[] = { /* "juni" */
+ 0x6a, 0x75, 0x6e, 0x69
+};
+
+static BYTE NLSALLOC(0814) rgbSMONTHNAME7[] = { /* "juli" */
+ 0x6a, 0x75, 0x6c, 0x69
+};
+
+static BYTE NLSALLOC(0814) rgbSMONTHNAME8[] = { /* "august" */
+ 0x61, 0x75, 0x67, 0x75, 0x73, 0x74
+};
+
+static BYTE NLSALLOC(0814) rgbSMONTHNAME9[] = { /* "september" */
+ 0x73, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x65
+ , 0x72
+};
+
+static BYTE NLSALLOC(0814) rgbSMONTHNAME10[] = { /* "oktober" */
+ 0x6f, 0x6b, 0x74, 0x6f, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0814) rgbSMONTHNAME11[] = { /* "november" */
+ 0x6e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0814) rgbSMONTHNAME12[] = { /* "desember" */
+ 0x64, 0x65, 0x73, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVMONTHNAME1[] = { /* "jan" */
+ 0x6a, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVMONTHNAME2[] = { /* "feb" */
+ 0x66, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVMONTHNAME3[] = { /* "mar" */
+ 0x6d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVMONTHNAME4[] = { /* "apr" */
+ 0x61, 0x70, 0x72
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVMONTHNAME5[] = { /* "mai" */
+ 0x6d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVMONTHNAME6[] = { /* "jun" */
+ 0x6a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVMONTHNAME7[] = { /* "jul" */
+ 0x6a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVMONTHNAME8[] = { /* "aug" */
+ 0x61, 0x75, 0x67
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVMONTHNAME9[] = { /* "sep" */
+ 0x73, 0x65, 0x70
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVMONTHNAME10[] = { /* "okt" */
+ 0x6f, 0x6b, 0x74
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVMONTHNAME11[] = { /* "nov" */
+ 0x6e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(0814) rgbSABBREVMONTHNAME12[] = { /* "des" */
+ 0x64, 0x65, 0x73
+};
+
+static BYTE NLSALLOC(0814) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0814) rgbIPOSSIGNPOSN[] = { /* "4" */
+ 0x34
+};
+
+static BYTE NLSALLOC(0814) rgbINEGSIGNPOSN[] = { /* "4" */
+ 0x34
+};
+
+static BYTE NLSALLOC(0814) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0814) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0814) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0814) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0814) rgbSENGCOUNTRY[] = { /* "Norway" */
+ 0x4e, 0x6f, 0x72, 0x77, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0814) rgbSENGLANGUAGE[] = { /* "Norwegian (Nynorsk)" */
+ 0x4e, 0x6f, 0x72, 0x77, 0x65, 0x67, 0x69, 0x61
+ , 0x6e, 0x20, 0x28, 0x4e, 0x79, 0x6e, 0x6f, 0x72
+ , 0x73, 0x6b, 0x29
+};
+
+static BYTE NLSALLOC(0814) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0814) rgbIFIRSTWEEKOFYEAR[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0814) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0814) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0814) rgbSTIMEFORMAT[] = { /* "HH:mm:ss" */
+ 0x48, 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0814) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0814) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0814) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0814) g_rglcinfo0814[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 19, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 6, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 5, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 2, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 12, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 6, rgbSDAYNAME1 }
+ , { 6, rgbSDAYNAME2 }
+ , { 6, rgbSDAYNAME3 }
+ , { 7, rgbSDAYNAME4 }
+ , { 6, rgbSDAYNAME5 }
+ , { 7, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 2, rgbSABBREVDAYNAME1 }
+ , { 2, rgbSABBREVDAYNAME2 }
+ , { 2, rgbSABBREVDAYNAME3 }
+ , { 2, rgbSABBREVDAYNAME4 }
+ , { 2, rgbSABBREVDAYNAME5 }
+ , { 3, rgbSABBREVDAYNAME6 }
+ , { 2, rgbSABBREVDAYNAME7 }
+ , { 6, rgbSMONTHNAME1 }
+ , { 7, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 6, rgbSENGCOUNTRY }
+ , { 19, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 8, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0814) g_strinfo0814 = {
+ rgbUCase_0406
+ , rgbLCase_0406
+ , rgwCType12_0406
+ , rgwCType3_0406
+ , rgwSort_0406
+ , rgexp_0406
+ , rgdig_0406
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0816.c b/private/oleauto/src/dispatch/win16/0816.c
new file mode 100644
index 000000000..a408aee7e
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0816.c
@@ -0,0 +1,532 @@
+/****************************************************************************
+* 0816.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Portuguese - Portugal
+*
+* LCID = 0x0816
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:43:20 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0409[256]; // from 0409:English - United States
+extern EXPANSION rgexp_0409[7];
+extern WORD rgwCType12_0409[256];
+extern WORD rgwCType3_0409[256];
+extern BYTE rgbUCase_0409[256];
+extern BYTE rgbLCase_0409[256];
+
+static BYTE NLSALLOC(0816) rgbILANGUAGE[] = { /* "0816" */
+ 0x30, 0x38, 0x31, 0x36
+};
+
+static BYTE NLSALLOC(0816) rgbSLANGUAGE[] = { /* "Portuguese" */
+ 0x50, 0x6f, 0x72, 0x74, 0x75, 0x67, 0x75, 0x65
+ , 0x73, 0x65
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVLANGNAME[] = { /* "PTG" */
+ 0x50, 0x54, 0x47
+};
+
+static BYTE NLSALLOC(0816) rgbSNATIVELANGNAME[] = { /* "Português" */
+ 0x50, 0x6f, 0x72, 0x74, 0x75, 0x67, 0x75, 0xea
+ , 0x73
+};
+
+static BYTE NLSALLOC(0816) rgbICOUNTRY[] = { /* "351" */
+ 0x33, 0x35, 0x31
+};
+
+static BYTE NLSALLOC(0816) rgbSCOUNTRY[] = { /* "Portugal" */
+ 0x50, 0x6f, 0x72, 0x74, 0x75, 0x67, 0x61, 0x6c
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVCTRYNAME[] = { /* "PRT" */
+ 0x50, 0x52, 0x54
+};
+
+static BYTE NLSALLOC(0816) rgbSNATIVECTRYNAME[] = { /* "Portugal" */
+ 0x50, 0x6f, 0x72, 0x74, 0x75, 0x67, 0x61, 0x6c
+};
+
+static BYTE NLSALLOC(0816) rgbIDEFAULTLANGUAGE[] = { /* "0816" */
+ 0x30, 0x38, 0x31, 0x36
+};
+
+static BYTE NLSALLOC(0816) rgbIDEFAULTCOUNTRY[] = { /* "351" */
+ 0x33, 0x35, 0x31
+};
+
+static BYTE NLSALLOC(0816) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0816) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0816) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0816) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0816) rgbSTHOUSAND[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0816) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0816) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0816) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0816) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0816) rgbSCURRENCY[] = { /* "Esc." */
+ 0x45, 0x73, 0x63, 0x2e
+};
+
+static BYTE NLSALLOC(0816) rgbSINTLSYMBOL[] = { /* "PTE" */
+ 0x50, 0x54, 0x45
+};
+
+static BYTE NLSALLOC(0816) rgbSMONDECIMALSEP[] = { /* "$" */
+ 0x24
+};
+
+static BYTE NLSALLOC(0816) rgbSMONTHOUSANDSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0816) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0816) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0816) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0816) rgbICURRENCY[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0816) rgbINEGCURR[] = { /* "8" */
+ 0x38
+};
+
+static BYTE NLSALLOC(0816) rgbSDATE[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0816) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0816) rgbSSHORTDATE[] = { /* "dd-MM-yyyy" */
+ 0x64, 0x64, 0x2d, 0x4d, 0x4d, 0x2d, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0816) rgbSLONGDATE[] = { /* "dddd, d' de 'MMMM' de 'yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x2c, 0x20, 0x64, 0x27
+ , 0x20, 0x64, 0x65, 0x20, 0x27, 0x4d, 0x4d, 0x4d
+ , 0x4d, 0x27, 0x20, 0x64, 0x65, 0x20, 0x27, 0x79
+ , 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0816) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0816) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0816) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0816) rgbICENTURY[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0816) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0816) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0816) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0816) rgbSDAYNAME1[] = { /* "segunda-feira" */
+ 0x73, 0x65, 0x67, 0x75, 0x6e, 0x64, 0x61, 0x2d
+ , 0x66, 0x65, 0x69, 0x72, 0x61
+};
+
+static BYTE NLSALLOC(0816) rgbSDAYNAME2[] = { /* "terça-feira" */
+ 0x74, 0x65, 0x72, 0xe7, 0x61, 0x2d, 0x66, 0x65
+ , 0x69, 0x72, 0x61
+};
+
+static BYTE NLSALLOC(0816) rgbSDAYNAME3[] = { /* "quarta-feira" */
+ 0x71, 0x75, 0x61, 0x72, 0x74, 0x61, 0x2d, 0x66
+ , 0x65, 0x69, 0x72, 0x61
+};
+
+static BYTE NLSALLOC(0816) rgbSDAYNAME4[] = { /* "quinta-feira" */
+ 0x71, 0x75, 0x69, 0x6e, 0x74, 0x61, 0x2d, 0x66
+ , 0x65, 0x69, 0x72, 0x61
+};
+
+static BYTE NLSALLOC(0816) rgbSDAYNAME5[] = { /* "sexta-feira" */
+ 0x73, 0x65, 0x78, 0x74, 0x61, 0x2d, 0x66, 0x65
+ , 0x69, 0x72, 0x61
+};
+
+static BYTE NLSALLOC(0816) rgbSDAYNAME6[] = { /* "sábado" */
+ 0x73, 0xe1, 0x62, 0x61, 0x64, 0x6f
+};
+
+static BYTE NLSALLOC(0816) rgbSDAYNAME7[] = { /* "domingo" */
+ 0x64, 0x6f, 0x6d, 0x69, 0x6e, 0x67, 0x6f
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVDAYNAME1[] = { /* "seg" */
+ 0x73, 0x65, 0x67
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVDAYNAME2[] = { /* "ter" */
+ 0x74, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVDAYNAME3[] = { /* "qua" */
+ 0x71, 0x75, 0x61
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVDAYNAME4[] = { /* "qui" */
+ 0x71, 0x75, 0x69
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVDAYNAME5[] = { /* "sex" */
+ 0x73, 0x65, 0x78
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVDAYNAME6[] = { /* "sáb" */
+ 0x73, 0xe1, 0x62
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVDAYNAME7[] = { /* "dom" */
+ 0x64, 0x6f, 0x6d
+};
+
+static BYTE NLSALLOC(0816) rgbSMONTHNAME1[] = { /* "janeiro" */
+ 0x6a, 0x61, 0x6e, 0x65, 0x69, 0x72, 0x6f
+};
+
+static BYTE NLSALLOC(0816) rgbSMONTHNAME2[] = { /* "fevereiro" */
+ 0x66, 0x65, 0x76, 0x65, 0x72, 0x65, 0x69, 0x72
+ , 0x6f
+};
+
+static BYTE NLSALLOC(0816) rgbSMONTHNAME3[] = { /* "março" */
+ 0x6d, 0x61, 0x72, 0xe7, 0x6f
+};
+
+static BYTE NLSALLOC(0816) rgbSMONTHNAME4[] = { /* "abril" */
+ 0x61, 0x62, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(0816) rgbSMONTHNAME5[] = { /* "maio" */
+ 0x6d, 0x61, 0x69, 0x6f
+};
+
+static BYTE NLSALLOC(0816) rgbSMONTHNAME6[] = { /* "junho" */
+ 0x6a, 0x75, 0x6e, 0x68, 0x6f
+};
+
+static BYTE NLSALLOC(0816) rgbSMONTHNAME7[] = { /* "julho" */
+ 0x6a, 0x75, 0x6c, 0x68, 0x6f
+};
+
+static BYTE NLSALLOC(0816) rgbSMONTHNAME8[] = { /* "agosto" */
+ 0x61, 0x67, 0x6f, 0x73, 0x74, 0x6f
+};
+
+static BYTE NLSALLOC(0816) rgbSMONTHNAME9[] = { /* "setembro" */
+ 0x73, 0x65, 0x74, 0x65, 0x6d, 0x62, 0x72, 0x6f
+};
+
+static BYTE NLSALLOC(0816) rgbSMONTHNAME10[] = { /* "outubro" */
+ 0x6f, 0x75, 0x74, 0x75, 0x62, 0x72, 0x6f
+};
+
+static BYTE NLSALLOC(0816) rgbSMONTHNAME11[] = { /* "novembro" */
+ 0x6e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x72, 0x6f
+};
+
+static BYTE NLSALLOC(0816) rgbSMONTHNAME12[] = { /* "dezembro" */
+ 0x64, 0x65, 0x7a, 0x65, 0x6d, 0x62, 0x72, 0x6f
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVMONTHNAME1[] = { /* "jan" */
+ 0x6a, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVMONTHNAME2[] = { /* "fev" */
+ 0x66, 0x65, 0x76
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVMONTHNAME3[] = { /* "mar" */
+ 0x6d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVMONTHNAME4[] = { /* "abr" */
+ 0x61, 0x62, 0x72
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVMONTHNAME5[] = { /* "mai" */
+ 0x6d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVMONTHNAME6[] = { /* "jun" */
+ 0x6a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVMONTHNAME7[] = { /* "jul" */
+ 0x6a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVMONTHNAME8[] = { /* "ago" */
+ 0x61, 0x67, 0x6f
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVMONTHNAME9[] = { /* "set" */
+ 0x73, 0x65, 0x74
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVMONTHNAME10[] = { /* "out" */
+ 0x6f, 0x75, 0x74
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVMONTHNAME11[] = { /* "nov" */
+ 0x6e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(0816) rgbSABBREVMONTHNAME12[] = { /* "dez" */
+ 0x64, 0x65, 0x7a
+};
+
+static BYTE NLSALLOC(0816) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0816) rgbIPOSSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0816) rgbINEGSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0816) rgbIPOSSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0816) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0816) rgbINEGSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0816) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0816) rgbSENGCOUNTRY[] = { /* "Portugal" */
+ 0x50, 0x6f, 0x72, 0x74, 0x75, 0x67, 0x61, 0x6c
+};
+
+static BYTE NLSALLOC(0816) rgbSENGLANGUAGE[] = { /* "Portuguese" */
+ 0x50, 0x6f, 0x72, 0x74, 0x75, 0x67, 0x75, 0x65
+ , 0x73, 0x65
+};
+
+static BYTE NLSALLOC(0816) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0816) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0816) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0816) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0816) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0816) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0816) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0816) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0816) g_rglcinfo0816[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 10, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 9, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 8, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 8, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 4, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 10, rgbSSHORTDATE }
+ , { 27, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 13, rgbSDAYNAME1 }
+ , { 11, rgbSDAYNAME2 }
+ , { 12, rgbSDAYNAME3 }
+ , { 12, rgbSDAYNAME4 }
+ , { 11, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 7, rgbSDAYNAME7 }
+ , { 3, rgbSABBREVDAYNAME1 }
+ , { 3, rgbSABBREVDAYNAME2 }
+ , { 3, rgbSABBREVDAYNAME3 }
+ , { 3, rgbSABBREVDAYNAME4 }
+ , { 3, rgbSABBREVDAYNAME5 }
+ , { 3, rgbSABBREVDAYNAME6 }
+ , { 3, rgbSABBREVDAYNAME7 }
+ , { 7, rgbSMONTHNAME1 }
+ , { 9, rgbSMONTHNAME2 }
+ , { 5, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 4, rgbSMONTHNAME5 }
+ , { 5, rgbSMONTHNAME6 }
+ , { 5, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 8, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 8, rgbSENGCOUNTRY }
+ , { 10, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0816) g_strinfo0816 = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0c01.c b/private/oleauto/src/dispatch/win16/0c01.c
new file mode 100644
index 000000000..44e738fa5
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0c01.c
@@ -0,0 +1,528 @@
+/****************************************************************************
+* 0c01.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Arabic - Egypt
+*
+* LCID = 0x0c01
+*
+* CodePage = 1256
+*
+* Generated: Thu Dec 01 18:28:06 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0401[256]; // from 0401:Arabic - Saudi Arabia
+extern EXPANSION rgexp_0401[3];
+extern WORD rgwCType12_0401[256];
+extern WORD rgwCType3_0401[256];
+extern BYTE rgbUCase_0401[256];
+extern BYTE rgbLCase_0401[256];
+
+static BYTE NLSALLOC(0c01) rgbILANGUAGE[] = { /* "0c01" */
+ 0x30, 0x63, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(0c01) rgbSLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVLANGNAME[] = { /* "ARE" */
+ 0x41, 0x52, 0x45
+};
+
+static BYTE NLSALLOC(0c01) rgbSNATIVELANGNAME[] = { /* "\x0627\x0644\x0639\x0631\x0628\x064a\x0629" */
+ 0xc7, 0xe1, 0xda, 0xd1, 0xc8, 0xed, 0xc9
+};
+
+static BYTE NLSALLOC(0c01) rgbICOUNTRY[] = { /* "20" */
+ 0x32, 0x30
+};
+
+static BYTE NLSALLOC(0c01) rgbSCOUNTRY[] = { /* "Egypt" */
+ 0x45, 0x67, 0x79, 0x70, 0x74
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVCTRYNAME[] = { /* "EGY" */
+ 0x45, 0x47, 0x59
+};
+
+static BYTE NLSALLOC(0c01) rgbSNATIVECTRYNAME[] = { /* "\x0645\x0635\x0631" */
+ 0xe3, 0xd5, 0xd1
+};
+
+static BYTE NLSALLOC(0c01) rgbIDEFAULTLANGUAGE[] = { /* "0c01" */
+ 0x30, 0x63, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(0c01) rgbIDEFAULTCOUNTRY[] = { /* "20" */
+ 0x32, 0x30
+};
+
+static BYTE NLSALLOC(0c01) rgbIDEFAULTCODEPAGE[] = { /* "708" */
+ 0x37, 0x30, 0x38
+};
+
+static BYTE NLSALLOC(0c01) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0c01) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c01) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0c01) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0c01) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0c01) rgbIDIGITS[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0c01) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c01) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0c01) rgbSCURRENCY[] = { /* "\x062c.\x0645.\x200f" */
+ 0xcc, 0x2e, 0xe3, 0x2e, 0xfe
+};
+
+static BYTE NLSALLOC(0c01) rgbSINTLSYMBOL[] = { /* "EGP" */
+ 0x45, 0x47, 0x50
+};
+
+static BYTE NLSALLOC(0c01) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0c01) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0c01) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0c01) rgbICURRDIGITS[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0c01) rgbIINTLCURRDIGITS[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0c01) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0c01) rgbINEGCURR[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0c01) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(0c01) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0c01) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0c01) rgbSLONGDATE[] = { /* "dd/MM/yyyy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0c01) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0c01) rgbILDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0c01) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c01) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c01) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c01) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c01) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c01) rgbS1159[] = { /* "\x0635" */
+ 0xd5
+};
+
+static BYTE NLSALLOC(0c01) rgbS2359[] = { /* "\x0645" */
+ 0xe3
+};
+
+static BYTE NLSALLOC(0c01) rgbSDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(0c01) rgbSDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(0c01) rgbSDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(0c01) rgbSDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(0c01) rgbSDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(0c01) rgbSDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(0c01) rgbSDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(0c01) rgbSMONTHNAME1[] = { /* "\x064a\x0646\x0627\x064a\x0631" */
+ 0xed, 0xe4, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(0c01) rgbSMONTHNAME2[] = { /* "\x0641\x0628\x0631\x0627\x064a\x0631" */
+ 0xdd, 0xc8, 0xd1, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(0c01) rgbSMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(0c01) rgbSMONTHNAME4[] = { /* "\x0627\x0628\x0631\x064a\x0644" */
+ 0xc7, 0xc8, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(0c01) rgbSMONTHNAME5[] = { /* "\x0645\x0627\x064a\x0648" */
+ 0xe3, 0xc7, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(0c01) rgbSMONTHNAME6[] = { /* "\x064a\x0648\x0646\x064a\x0648" */
+ 0xed, 0xe6, 0xe4, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(0c01) rgbSMONTHNAME7[] = { /* "\x064a\x0648\x0644\x064a\x0648" */
+ 0xed, 0xe6, 0xe1, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(0c01) rgbSMONTHNAME8[] = { /* "\x0623\x063a\x0633\x0637\x0633" */
+ 0xc3, 0xdb, 0xd3, 0xd8, 0xd3
+};
+
+static BYTE NLSALLOC(0c01) rgbSMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(0c01) rgbSMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(0c01) rgbSMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(0c01) rgbSMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVMONTHNAME1[] = { /* "\x064a\x0646\x0627\x064a\x0631" */
+ 0xed, 0xe4, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVMONTHNAME2[] = { /* "\x0641\x0628\x0631\x0627\x064a\x0631" */
+ 0xdd, 0xc8, 0xd1, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVMONTHNAME4[] = { /* "\x0627\x0628\x0631\x064a\x0644" */
+ 0xc7, 0xc8, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVMONTHNAME5[] = { /* "\x0645\x0627\x064a\x0648" */
+ 0xe3, 0xc7, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVMONTHNAME6[] = { /* "\x064a\x0648\x0646\x064a\x0648" */
+ 0xed, 0xe6, 0xe4, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVMONTHNAME7[] = { /* "\x064a\x0648\x0644\x064a\x0648" */
+ 0xed, 0xe6, 0xe1, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVMONTHNAME8[] = { /* "\x0623\x063a\x0633\x0637\x0633" */
+ 0xc3, 0xdb, 0xd3, 0xd8, 0xd3
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(0c01) rgbSABBREVMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(0c01) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0c01) rgbIPOSSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0c01) rgbINEGSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0c01) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c01) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c01) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c01) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c01) rgbSENGCOUNTRY[] = { /* "Egypt" */
+ 0x45, 0x67, 0x79, 0x70, 0x74
+};
+
+static BYTE NLSALLOC(0c01) rgbSENGLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(0c01) rgbIFIRSTDAYOFWEEK[] = { /* "5" */
+ 0x35
+};
+
+static BYTE NLSALLOC(0c01) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c01) rgbIDEFAULTANSICODEPAGE[] = { /* "1256" */
+ 0x31, 0x32, 0x35, 0x36
+};
+
+static BYTE NLSALLOC(0c01) rgbINEGNUMBER[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0c01) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0c01) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c01) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c01) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0c01) g_rglcinfo0c01[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 5, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 3, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 5, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 10, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 1, rgbS1159 }
+ , { 1, rgbS2359 }
+ , { 5, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 7, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 8, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 5, rgbSABBREVDAYNAME1 }
+ , { 5, rgbSABBREVDAYNAME2 }
+ , { 7, rgbSABBREVDAYNAME3 }
+ , { 8, rgbSABBREVDAYNAME4 }
+ , { 8, rgbSABBREVDAYNAME5 }
+ , { 6, rgbSABBREVDAYNAME6 }
+ , { 6, rgbSABBREVDAYNAME7 }
+ , { 5, rgbSMONTHNAME1 }
+ , { 6, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 4, rgbSMONTHNAME5 }
+ , { 5, rgbSMONTHNAME6 }
+ , { 5, rgbSMONTHNAME7 }
+ , { 5, rgbSMONTHNAME8 }
+ , { 6, rgbSMONTHNAME9 }
+ , { 6, rgbSMONTHNAME10 }
+ , { 6, rgbSMONTHNAME11 }
+ , { 6, rgbSMONTHNAME12 }
+ , { 5, rgbSABBREVMONTHNAME1 }
+ , { 6, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 5, rgbSABBREVMONTHNAME4 }
+ , { 4, rgbSABBREVMONTHNAME5 }
+ , { 5, rgbSABBREVMONTHNAME6 }
+ , { 5, rgbSABBREVMONTHNAME7 }
+ , { 5, rgbSABBREVMONTHNAME8 }
+ , { 6, rgbSABBREVMONTHNAME9 }
+ , { 6, rgbSABBREVMONTHNAME10 }
+ , { 6, rgbSABBREVMONTHNAME11 }
+ , { 6, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 5, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0c01) g_strinfo0c01 = {
+ rgbUCase_0401
+ , rgbLCase_0401
+ , rgwCType12_0401
+ , rgwCType3_0401
+ , rgwSort_0401
+ , rgexp_0401
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0c07.c b/private/oleauto/src/dispatch/win16/0c07.c
new file mode 100644
index 000000000..daab4a455
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0c07.c
@@ -0,0 +1,525 @@
+/****************************************************************************
+* 0c07.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* German - Austria
+*
+* LCID = 0x0c07
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:44:00 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0409[256]; // from 0409:English - United States
+extern EXPANSION rgexp_0409[7];
+extern WORD rgwCType12_0409[256];
+extern WORD rgwCType3_0409[256];
+extern BYTE rgbUCase_0409[256];
+extern BYTE rgbLCase_0409[256];
+
+static BYTE NLSALLOC(0c07) rgbILANGUAGE[] = { /* "0c07" */
+ 0x30, 0x63, 0x30, 0x37
+};
+
+static BYTE NLSALLOC(0c07) rgbSLANGUAGE[] = { /* "Austrian German" */
+ 0x41, 0x75, 0x73, 0x74, 0x72, 0x69, 0x61, 0x6e
+ , 0x20, 0x47, 0x65, 0x72, 0x6d, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVLANGNAME[] = { /* "DEA" */
+ 0x44, 0x45, 0x41
+};
+
+static BYTE NLSALLOC(0c07) rgbSNATIVELANGNAME[] = { /* "Deutsch" */
+ 0x44, 0x65, 0x75, 0x74, 0x73, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(0c07) rgbICOUNTRY[] = { /* "43" */
+ 0x34, 0x33
+};
+
+static BYTE NLSALLOC(0c07) rgbSCOUNTRY[] = { /* "Austria" */
+ 0x41, 0x75, 0x73, 0x74, 0x72, 0x69, 0x61
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVCTRYNAME[] = { /* "AUT" */
+ 0x41, 0x55, 0x54
+};
+
+static BYTE NLSALLOC(0c07) rgbSNATIVECTRYNAME[] = { /* "Österreich" */
+ 0xd6, 0x73, 0x74, 0x65, 0x72, 0x72, 0x65, 0x69
+ , 0x63, 0x68
+};
+
+static BYTE NLSALLOC(0c07) rgbIDEFAULTLANGUAGE[] = { /* "0c07" */
+ 0x30, 0x63, 0x30, 0x37
+};
+
+static BYTE NLSALLOC(0c07) rgbIDEFAULTCOUNTRY[] = { /* "43" */
+ 0x34, 0x33
+};
+
+static BYTE NLSALLOC(0c07) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0c07) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0c07) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c07) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0c07) rgbSTHOUSAND[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0c07) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0c07) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0c07) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c07) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0c07) rgbSCURRENCY[] = { /* "S" */
+ 0x53
+};
+
+static BYTE NLSALLOC(0c07) rgbSINTLSYMBOL[] = { /* "ATS" */
+ 0x41, 0x54, 0x53
+};
+
+static BYTE NLSALLOC(0c07) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0c07) rgbSMONTHOUSANDSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0c07) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0c07) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0c07) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0c07) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0c07) rgbINEGCURR[] = { /* "9" */
+ 0x39
+};
+
+static BYTE NLSALLOC(0c07) rgbSDATE[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0c07) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0c07) rgbSSHORTDATE[] = { /* "dd.MM.yy" */
+ 0x64, 0x64, 0x2e, 0x4d, 0x4d, 0x2e, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0c07) rgbSLONGDATE[] = { /* "dddd, dd. MMMM yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x2c, 0x20, 0x64, 0x64
+ , 0x2e, 0x20, 0x4d, 0x4d, 0x4d, 0x4d, 0x20, 0x79
+ , 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0c07) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c07) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c07) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c07) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c07) rgbITLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c07) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c07) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c07) rgbSDAYNAME1[] = { /* "Montag" */
+ 0x4d, 0x6f, 0x6e, 0x74, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0c07) rgbSDAYNAME2[] = { /* "Dienstag" */
+ 0x44, 0x69, 0x65, 0x6e, 0x73, 0x74, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0c07) rgbSDAYNAME3[] = { /* "Mittwoch" */
+ 0x4d, 0x69, 0x74, 0x74, 0x77, 0x6f, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(0c07) rgbSDAYNAME4[] = { /* "Donnerstag" */
+ 0x44, 0x6f, 0x6e, 0x6e, 0x65, 0x72, 0x73, 0x74
+ , 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0c07) rgbSDAYNAME5[] = { /* "Freitag" */
+ 0x46, 0x72, 0x65, 0x69, 0x74, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0c07) rgbSDAYNAME6[] = { /* "Samstag" */
+ 0x53, 0x61, 0x6d, 0x73, 0x74, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0c07) rgbSDAYNAME7[] = { /* "Sonntag" */
+ 0x53, 0x6f, 0x6e, 0x6e, 0x74, 0x61, 0x67
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVDAYNAME1[] = { /* "Mo" */
+ 0x4d, 0x6f
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVDAYNAME2[] = { /* "Di" */
+ 0x44, 0x69
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVDAYNAME3[] = { /* "Mi" */
+ 0x4d, 0x69
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVDAYNAME4[] = { /* "Do" */
+ 0x44, 0x6f
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVDAYNAME5[] = { /* "Fr" */
+ 0x46, 0x72
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVDAYNAME6[] = { /* "Sa" */
+ 0x53, 0x61
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVDAYNAME7[] = { /* "So" */
+ 0x53, 0x6f
+};
+
+static BYTE NLSALLOC(0c07) rgbSMONTHNAME1[] = { /* "Januar" */
+ 0x4a, 0x61, 0x6e, 0x75, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0c07) rgbSMONTHNAME2[] = { /* "Februar" */
+ 0x46, 0x65, 0x62, 0x72, 0x75, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0c07) rgbSMONTHNAME3[] = { /* "März" */
+ 0x4d, 0xe4, 0x72, 0x7a
+};
+
+static BYTE NLSALLOC(0c07) rgbSMONTHNAME4[] = { /* "April" */
+ 0x41, 0x70, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(0c07) rgbSMONTHNAME5[] = { /* "Mai" */
+ 0x4d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(0c07) rgbSMONTHNAME6[] = { /* "Juni" */
+ 0x4a, 0x75, 0x6e, 0x69
+};
+
+static BYTE NLSALLOC(0c07) rgbSMONTHNAME7[] = { /* "Juli" */
+ 0x4a, 0x75, 0x6c, 0x69
+};
+
+static BYTE NLSALLOC(0c07) rgbSMONTHNAME8[] = { /* "August" */
+ 0x41, 0x75, 0x67, 0x75, 0x73, 0x74
+};
+
+static BYTE NLSALLOC(0c07) rgbSMONTHNAME9[] = { /* "September" */
+ 0x53, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x65
+ , 0x72
+};
+
+static BYTE NLSALLOC(0c07) rgbSMONTHNAME10[] = { /* "Oktober" */
+ 0x4f, 0x6b, 0x74, 0x6f, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0c07) rgbSMONTHNAME11[] = { /* "November" */
+ 0x4e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0c07) rgbSMONTHNAME12[] = { /* "Dezember" */
+ 0x44, 0x65, 0x7a, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVMONTHNAME1[] = { /* "Jan" */
+ 0x4a, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVMONTHNAME2[] = { /* "Feb" */
+ 0x46, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVMONTHNAME3[] = { /* "Mär" */
+ 0x4d, 0xe4, 0x72
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVMONTHNAME4[] = { /* "Apr" */
+ 0x41, 0x70, 0x72
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVMONTHNAME5[] = { /* "Mai" */
+ 0x4d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVMONTHNAME6[] = { /* "Jun" */
+ 0x4a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVMONTHNAME7[] = { /* "Jul" */
+ 0x4a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVMONTHNAME8[] = { /* "Aug" */
+ 0x41, 0x75, 0x67
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVMONTHNAME9[] = { /* "Sep" */
+ 0x53, 0x65, 0x70
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVMONTHNAME10[] = { /* "Okt" */
+ 0x4f, 0x6b, 0x74
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVMONTHNAME11[] = { /* "Nov" */
+ 0x4e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(0c07) rgbSABBREVMONTHNAME12[] = { /* "Dez" */
+ 0x44, 0x65, 0x7a
+};
+
+static BYTE NLSALLOC(0c07) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0c07) rgbIPOSSIGNPOSN[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0c07) rgbINEGSIGNPOSN[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0c07) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c07) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c07) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c07) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c07) rgbSENGCOUNTRY[] = { /* "Austria" */
+ 0x41, 0x75, 0x73, 0x74, 0x72, 0x69, 0x61
+};
+
+static BYTE NLSALLOC(0c07) rgbSENGLANGUAGE[] = { /* "German" */
+ 0x47, 0x65, 0x72, 0x6d, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0c07) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c07) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c07) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0c07) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c07) rgbSTIMEFORMAT[] = { /* "HH:mm:ss" */
+ 0x48, 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0c07) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c07) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c07) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0c07) g_rglcinfo0c07[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 15, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 7, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 10, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 1, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 19, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 6, rgbSDAYNAME1 }
+ , { 8, rgbSDAYNAME2 }
+ , { 8, rgbSDAYNAME3 }
+ , { 10, rgbSDAYNAME4 }
+ , { 7, rgbSDAYNAME5 }
+ , { 7, rgbSDAYNAME6 }
+ , { 7, rgbSDAYNAME7 }
+ , { 2, rgbSABBREVDAYNAME1 }
+ , { 2, rgbSABBREVDAYNAME2 }
+ , { 2, rgbSABBREVDAYNAME3 }
+ , { 2, rgbSABBREVDAYNAME4 }
+ , { 2, rgbSABBREVDAYNAME5 }
+ , { 2, rgbSABBREVDAYNAME6 }
+ , { 2, rgbSABBREVDAYNAME7 }
+ , { 6, rgbSMONTHNAME1 }
+ , { 7, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 7, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 8, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0c07) g_strinfo0c07 = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0c09.c b/private/oleauto/src/dispatch/win16/0c09.c
new file mode 100644
index 000000000..67faddba4
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0c09.c
@@ -0,0 +1,528 @@
+/****************************************************************************
+* 0c09.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* English - Australia
+*
+* LCID = 0x0c09
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:44:37 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0409[256]; // from 0409:English - United States
+extern EXPANSION rgexp_0409[7];
+extern WORD rgwCType12_0409[256];
+extern WORD rgwCType3_0409[256];
+extern BYTE rgbUCase_0409[256];
+extern BYTE rgbLCase_0409[256];
+
+static BYTE NLSALLOC(0c09) rgbILANGUAGE[] = { /* "0c09" */
+ 0x30, 0x63, 0x30, 0x39
+};
+
+static BYTE NLSALLOC(0c09) rgbSLANGUAGE[] = { /* "Australian English" */
+ 0x41, 0x75, 0x73, 0x74, 0x72, 0x61, 0x6c, 0x69
+ , 0x61, 0x6e, 0x20, 0x45, 0x6e, 0x67, 0x6c, 0x69
+ , 0x73, 0x68
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVLANGNAME[] = { /* "ENA" */
+ 0x45, 0x4e, 0x41
+};
+
+static BYTE NLSALLOC(0c09) rgbSNATIVELANGNAME[] = { /* "English" */
+ 0x45, 0x6e, 0x67, 0x6c, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(0c09) rgbICOUNTRY[] = { /* "61" */
+ 0x36, 0x31
+};
+
+static BYTE NLSALLOC(0c09) rgbSCOUNTRY[] = { /* "Australia" */
+ 0x41, 0x75, 0x73, 0x74, 0x72, 0x61, 0x6c, 0x69
+ , 0x61
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVCTRYNAME[] = { /* "AUS" */
+ 0x41, 0x55, 0x53
+};
+
+static BYTE NLSALLOC(0c09) rgbSNATIVECTRYNAME[] = { /* "Australia" */
+ 0x41, 0x75, 0x73, 0x74, 0x72, 0x61, 0x6c, 0x69
+ , 0x61
+};
+
+static BYTE NLSALLOC(0c09) rgbIDEFAULTLANGUAGE[] = { /* "0c09" */
+ 0x30, 0x63, 0x30, 0x39
+};
+
+static BYTE NLSALLOC(0c09) rgbIDEFAULTCOUNTRY[] = { /* "61" */
+ 0x36, 0x31
+};
+
+static BYTE NLSALLOC(0c09) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0c09) rgbSLIST[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0c09) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c09) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0c09) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0c09) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0c09) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0c09) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c09) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0c09) rgbSCURRENCY[] = { /* "$" */
+ 0x24
+};
+
+static BYTE NLSALLOC(0c09) rgbSINTLSYMBOL[] = { /* "AUD" */
+ 0x41, 0x55, 0x44
+};
+
+static BYTE NLSALLOC(0c09) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0c09) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0c09) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0c09) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0c09) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0c09) rgbICURRENCY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c09) rgbINEGCURR[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c09) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(0c09) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0c09) rgbSSHORTDATE[] = { /* "d/MM/yy" */
+ 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0c09) rgbSLONGDATE[] = { /* "dddd, d MMMM yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x2c, 0x20, 0x64, 0x20
+ , 0x4d, 0x4d, 0x4d, 0x4d, 0x20, 0x79, 0x79, 0x79
+ , 0x79
+};
+
+static BYTE NLSALLOC(0c09) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c09) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c09) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c09) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c09) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c09) rgbIDAYLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c09) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c09) rgbSDAYNAME1[] = { /* "Monday" */
+ 0x4d, 0x6f, 0x6e, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0c09) rgbSDAYNAME2[] = { /* "Tuesday" */
+ 0x54, 0x75, 0x65, 0x73, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0c09) rgbSDAYNAME3[] = { /* "Wednesday" */
+ 0x57, 0x65, 0x64, 0x6e, 0x65, 0x73, 0x64, 0x61
+ , 0x79
+};
+
+static BYTE NLSALLOC(0c09) rgbSDAYNAME4[] = { /* "Thursday" */
+ 0x54, 0x68, 0x75, 0x72, 0x73, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0c09) rgbSDAYNAME5[] = { /* "Friday" */
+ 0x46, 0x72, 0x69, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0c09) rgbSDAYNAME6[] = { /* "Saturday" */
+ 0x53, 0x61, 0x74, 0x75, 0x72, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0c09) rgbSDAYNAME7[] = { /* "Sunday" */
+ 0x53, 0x75, 0x6e, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVDAYNAME1[] = { /* "Mon" */
+ 0x4d, 0x6f, 0x6e
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVDAYNAME2[] = { /* "Tue" */
+ 0x54, 0x75, 0x65
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVDAYNAME3[] = { /* "Wed" */
+ 0x57, 0x65, 0x64
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVDAYNAME4[] = { /* "Thu" */
+ 0x54, 0x68, 0x75
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVDAYNAME5[] = { /* "Fri" */
+ 0x46, 0x72, 0x69
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVDAYNAME6[] = { /* "Sat" */
+ 0x53, 0x61, 0x74
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVDAYNAME7[] = { /* "Sun" */
+ 0x53, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0c09) rgbSMONTHNAME1[] = { /* "January" */
+ 0x4a, 0x61, 0x6e, 0x75, 0x61, 0x72, 0x79
+};
+
+static BYTE NLSALLOC(0c09) rgbSMONTHNAME2[] = { /* "February" */
+ 0x46, 0x65, 0x62, 0x72, 0x75, 0x61, 0x72, 0x79
+};
+
+static BYTE NLSALLOC(0c09) rgbSMONTHNAME3[] = { /* "March" */
+ 0x4d, 0x61, 0x72, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(0c09) rgbSMONTHNAME4[] = { /* "April" */
+ 0x41, 0x70, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(0c09) rgbSMONTHNAME5[] = { /* "May" */
+ 0x4d, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0c09) rgbSMONTHNAME6[] = { /* "June" */
+ 0x4a, 0x75, 0x6e, 0x65
+};
+
+static BYTE NLSALLOC(0c09) rgbSMONTHNAME7[] = { /* "July" */
+ 0x4a, 0x75, 0x6c, 0x79
+};
+
+static BYTE NLSALLOC(0c09) rgbSMONTHNAME8[] = { /* "August" */
+ 0x41, 0x75, 0x67, 0x75, 0x73, 0x74
+};
+
+static BYTE NLSALLOC(0c09) rgbSMONTHNAME9[] = { /* "September" */
+ 0x53, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x65
+ , 0x72
+};
+
+static BYTE NLSALLOC(0c09) rgbSMONTHNAME10[] = { /* "October" */
+ 0x4f, 0x63, 0x74, 0x6f, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0c09) rgbSMONTHNAME11[] = { /* "November" */
+ 0x4e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0c09) rgbSMONTHNAME12[] = { /* "December" */
+ 0x44, 0x65, 0x63, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVMONTHNAME1[] = { /* "Jan" */
+ 0x4a, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVMONTHNAME2[] = { /* "Feb" */
+ 0x46, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVMONTHNAME3[] = { /* "Mar" */
+ 0x4d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVMONTHNAME4[] = { /* "Apr" */
+ 0x41, 0x70, 0x72
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVMONTHNAME5[] = { /* "May" */
+ 0x4d, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVMONTHNAME6[] = { /* "Jun" */
+ 0x4a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVMONTHNAME7[] = { /* "Jul" */
+ 0x4a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVMONTHNAME8[] = { /* "Aug" */
+ 0x41, 0x75, 0x67
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVMONTHNAME9[] = { /* "Sep" */
+ 0x53, 0x65, 0x70
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVMONTHNAME10[] = { /* "Oct" */
+ 0x4f, 0x63, 0x74
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVMONTHNAME11[] = { /* "Nov" */
+ 0x4e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(0c09) rgbSABBREVMONTHNAME12[] = { /* "Dec" */
+ 0x44, 0x65, 0x63
+};
+
+static BYTE NLSALLOC(0c09) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0c09) rgbIPOSSIGNPOSN[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0c09) rgbINEGSIGNPOSN[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0c09) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c09) rgbIPOSSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c09) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c09) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c09) rgbSENGCOUNTRY[] = { /* "Australia" */
+ 0x41, 0x75, 0x73, 0x74, 0x72, 0x61, 0x6c, 0x69
+ , 0x61
+};
+
+static BYTE NLSALLOC(0c09) rgbSENGLANGUAGE[] = { /* "English" */
+ 0x45, 0x6e, 0x67, 0x6c, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(0c09) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c09) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c09) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0c09) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c09) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0c09) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c09) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c09) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0c09) g_rglcinfo0c09[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 18, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 9, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 9, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 1, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 7, rgbSSHORTDATE }
+ , { 17, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 6, rgbSDAYNAME1 }
+ , { 7, rgbSDAYNAME2 }
+ , { 9, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 6, rgbSDAYNAME5 }
+ , { 8, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 3, rgbSABBREVDAYNAME1 }
+ , { 3, rgbSABBREVDAYNAME2 }
+ , { 3, rgbSABBREVDAYNAME3 }
+ , { 3, rgbSABBREVDAYNAME4 }
+ , { 3, rgbSABBREVDAYNAME5 }
+ , { 3, rgbSABBREVDAYNAME6 }
+ , { 3, rgbSABBREVDAYNAME7 }
+ , { 7, rgbSMONTHNAME1 }
+ , { 8, rgbSMONTHNAME2 }
+ , { 5, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 9, rgbSENGCOUNTRY }
+ , { 7, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0c09) g_strinfo0c09 = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0c0a.c b/private/oleauto/src/dispatch/win16/0c0a.c
new file mode 100644
index 000000000..18f06eb41
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0c0a.c
@@ -0,0 +1,708 @@
+/****************************************************************************
+* 0c0a.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Spanish - Spain (Modern Sort)
+*
+* LCID = 0x0c0a
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:54:28 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+WORD NLSALLOC(0c0a) rgwSort_0c0a[256] = {
+ 0x0000, 0xc007, 0xc008, 0xc009, 0xc00a, 0xc00b, 0xc00c, 0xc00d
+ , 0xc00e, 0x4031, 0x4032, 0x4033, 0x4034, 0x4035, 0xc00f, 0xc010
+ , 0xc011, 0xc012, 0xc013, 0xc014, 0xc015, 0xc016, 0xc017, 0xc018
+ , 0xc019, 0xc01a, 0xc01b, 0xc01c, 0xc01d, 0xc01e, 0xc01f, 0xc020
+ , 0x402f, 0x4036, 0x4037, 0x4038, 0x4039, 0x403a, 0x403b, 0xc02a
+ , 0x403c, 0x403d, 0x403e, 0x4060, 0x403f, 0xc02b, 0x4040, 0x4041
+ , 0x007a, 0x007e, 0x007f, 0x0080, 0x0081, 0x0082, 0x0083, 0x0084
+ , 0x0085, 0x0086, 0x4042, 0x4043, 0x4061, 0x4062, 0x4063, 0x4044
+ , 0x4045, 0x1087, 0x1088, 0x1089, 0x108a, 0x108b, 0x108c, 0x108d
+ , 0x108e, 0x108f, 0x1090, 0x1091, 0x1092, 0x1093, 0x1094, 0x1096
+ , 0x1097, 0x1098, 0x1099, 0x109a, 0x109b, 0x109d, 0x109e, 0x109f
+ , 0x10a0, 0x10a1, 0x10a2, 0x4046, 0x4047, 0x4048, 0x4049, 0x404a
+ , 0x404b, 0x0087, 0x0088, 0x0089, 0x008a, 0x008b, 0x008c, 0x008d
+ , 0x008e, 0x008f, 0x0090, 0x0091, 0x0092, 0x0093, 0x0094, 0x0096
+ , 0x0097, 0x0098, 0x0099, 0x009a, 0x009b, 0x009d, 0x009e, 0x009f
+ , 0x00a0, 0x00a1, 0x00a2, 0x404c, 0x404d, 0x404e, 0x404f, 0xc021
+ , 0xc022, 0xc023, 0x405a, 0x018c, 0x405d, 0x4078, 0x4075, 0x4076
+ , 0x4149, 0x4079, 0x119a, 0x405e, 0x0505, 0xc024, 0xc025, 0xc026
+ , 0xc027, 0x4058, 0x4059, 0x405b, 0x405c, 0x4077, 0xc02d, 0xc02e
+ , 0x4057, 0x109c, 0x019a, 0x405f, 0x0605, 0xc028, 0xc029, 0x12a1
+ , 0x4030, 0x4050, 0x4069, 0x406a, 0x406b, 0x406c, 0x4051, 0x406d
+ , 0x4052, 0x406e, 0x0887, 0x4065, 0x406f, 0xc02c, 0x4070, 0x4053
+ , 0x4071, 0x4064, 0x087f, 0x0880, 0x4054, 0x4072, 0x4073, 0x4074
+ , 0x4055, 0x087e, 0x0996, 0x4066, 0x007b, 0x007c, 0x007d, 0x4056
+ , 0x1287, 0x1187, 0x1387, 0x1587, 0x1487, 0x1687, 0x0005, 0x1189
+ , 0x128b, 0x118b, 0x138b, 0x148b, 0x128f, 0x118f, 0x138f, 0x148f
+ , 0x118a, 0x1095, 0x1396, 0x1296, 0x1496, 0x1696, 0x1596, 0x4067
+ , 0x1796, 0x129d, 0x119d, 0x139d, 0x149d, 0x11a1, 0x0105, 0x0205
+ , 0x0287, 0x0187, 0x0387, 0x0587, 0x0487, 0x0687, 0x0305, 0x0189
+ , 0x028b, 0x018b, 0x038b, 0x048b, 0x028f, 0x018f, 0x038f, 0x048f
+ , 0x018a, 0x0095, 0x0396, 0x0296, 0x0496, 0x0696, 0x0596, 0x4068
+ , 0x0796, 0x029d, 0x019d, 0x039d, 0x049d, 0x01a1, 0x0405, 0x02a1
+};
+
+EXPANSION NLSALLOC(0c0a) rgexp_0c0a[7] = {
+ { 0x1087, 0x108b }
+ , { 0x109b, 0x108e }
+ , { 0x009a, 0x009a }
+ , { 0x0087, 0x008b }
+ , { 0x009b, 0x008e }
+ , { 0x1096, 0x108b }
+ , { 0x0096, 0x008b }
+};
+
+WORD NLSALLOC(0c0a) rgwCType12_0c0a[256] = {
+ 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x9068, 0x0028, 0x0028, 0x0028, 0x0028, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020, 0x0020
+ , 0xa048, 0xb010, 0xb010, 0x5010, 0x5010, 0x5010, 0x1010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0x5010, 0x7010, 0x5010, 0x4010, 0x4010
+ , 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084, 0x3084
+ , 0x3084, 0x3084, 0x7010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1181, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1182, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0xb010, 0xb010, 0xb010, 0xb010, 0x0020
+ , 0x0020, 0x0020, 0xb010, 0x1112, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0x5010, 0x1101, 0xb010, 0x1101, 0x0020, 0x0020, 0x0020
+ , 0x0020, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1010, 0xb010, 0x1102, 0xb010, 0x1102, 0x0020, 0x0020, 0x1101
+ , 0xa048, 0xb010, 0x5010, 0x5010, 0x5010, 0x5010, 0xb010, 0xb010
+ , 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x5010, 0x5010, 0x3014, 0x3014, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0xb010, 0x3014, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010, 0xb010
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0xb010
+ , 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1101, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0xb010
+ , 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102, 0x1102
+};
+
+WORD NLSALLOC(0c0a) rgwCType3_0c0a[256] = {
+ 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0008, 0x0008, 0x0008, 0x0008, 0x0008, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000
+ , 0x0048, 0x0048, 0x0448, 0x0048, 0x0448, 0x0048, 0x0048, 0x0440
+ , 0x0048, 0x0048, 0x0048, 0x0048, 0x0048, 0x0440, 0x0048, 0x0448
+ , 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040, 0x0040
+ , 0x0040, 0x0040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0048, 0x0048
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0448, 0x0048, 0x0448, 0x0448
+ , 0x0448, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040, 0x8040
+ , 0x8040, 0x8040, 0x8040, 0x0048, 0x0048, 0x0048, 0x0448, 0x0000
+ , 0x0000, 0x0000, 0x0008, 0x8000, 0x0008, 0x0008, 0x0008, 0x0008
+ , 0x0001, 0x0008, 0x8003, 0x0008, 0x8000, 0x0000, 0x0000, 0x0000
+ , 0x0000, 0x0088, 0x0088, 0x0088, 0x0088, 0x0008, 0x0400, 0x0400
+ , 0x0408, 0x0000, 0x8003, 0x0008, 0x8000, 0x0000, 0x0000, 0x8003
+ , 0x0008, 0x0008, 0x0048, 0x0048, 0x0008, 0x0048, 0x0048, 0x0008
+ , 0x0408, 0x0008, 0x0400, 0x0008, 0x0048, 0x0408, 0x0008, 0x0448
+ , 0x0008, 0x0008, 0x0000, 0x0000, 0x0408, 0x0008, 0x0008, 0x0008
+ , 0x0408, 0x0000, 0x0400, 0x0008, 0x0000, 0x0000, 0x0000, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8000, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8000
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003
+ , 0x8000, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x0008
+ , 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8003, 0x8000, 0x8003
+};
+
+BYTE NLSALLOC(0c0a) rgbUCase_0c0a[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47
+ , 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f
+ , 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57
+ , 0x58, 0x59, 0x5a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x8a, 0x9b, 0x8c, 0x9d, 0x9e, 0x9f
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf
+ , 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7
+ , 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf
+ , 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xf7
+ , 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0x9f
+};
+
+BYTE NLSALLOC(0c0a) rgbLCase_0c0a[256] = {
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07
+ , 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f
+ , 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17
+ , 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
+ , 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27
+ , 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f
+ , 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f
+ , 0x40, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f
+ , 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67
+ , 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f
+ , 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77
+ , 0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f
+ , 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87
+ , 0x88, 0x89, 0x9a, 0x8b, 0x9c, 0x8d, 0x8e, 0x8f
+ , 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97
+ , 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0xff
+ , 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7
+ , 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf
+ , 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7
+ , 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xd7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xdf
+ , 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7
+ , 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef
+ , 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7
+ , 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
+};
+
+static BYTE NLSALLOC(0c0a) rgbILANGUAGE[] = { /* "0c0a" */
+ 0x30, 0x63, 0x30, 0x61
+};
+
+static BYTE NLSALLOC(0c0a) rgbSLANGUAGE[] = { /* "Spanish - Modern Sort" */
+ 0x53, 0x70, 0x61, 0x6e, 0x69, 0x73, 0x68, 0x20
+ , 0x2d, 0x20, 0x4d, 0x6f, 0x64, 0x65, 0x72, 0x6e
+ , 0x20, 0x53, 0x6f, 0x72, 0x74
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVLANGNAME[] = { /* "ESN" */
+ 0x45, 0x53, 0x4e
+};
+
+static BYTE NLSALLOC(0c0a) rgbSNATIVELANGNAME[] = { /* "Español" */
+ 0x45, 0x73, 0x70, 0x61, 0xf1, 0x6f, 0x6c
+};
+
+static BYTE NLSALLOC(0c0a) rgbICOUNTRY[] = { /* "34" */
+ 0x33, 0x34
+};
+
+static BYTE NLSALLOC(0c0a) rgbSCOUNTRY[] = { /* "Spain" */
+ 0x53, 0x70, 0x61, 0x69, 0x6e
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVCTRYNAME[] = { /* "ESP" */
+ 0x45, 0x53, 0x50
+};
+
+static BYTE NLSALLOC(0c0a) rgbSNATIVECTRYNAME[] = { /* "España" */
+ 0x45, 0x73, 0x70, 0x61, 0xf1, 0x61
+};
+
+static BYTE NLSALLOC(0c0a) rgbIDEFAULTLANGUAGE[] = { /* "0c0a" */
+ 0x30, 0x63, 0x30, 0x61
+};
+
+static BYTE NLSALLOC(0c0a) rgbIDEFAULTCOUNTRY[] = { /* "34" */
+ 0x33, 0x34
+};
+
+static BYTE NLSALLOC(0c0a) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0c0a) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0c0a) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c0a) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0c0a) rgbSTHOUSAND[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0c0a) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0c0a) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0c0a) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0a) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0c0a) rgbSCURRENCY[] = { /* "Pts" */
+ 0x50, 0x74, 0x73
+};
+
+static BYTE NLSALLOC(0c0a) rgbSINTLSYMBOL[] = { /* "ESP" */
+ 0x45, 0x53, 0x50
+};
+
+static BYTE NLSALLOC(0c0a) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0c0a) rgbSMONTHOUSANDSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(0c0a) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0c0a) rgbICURRDIGITS[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c0a) rgbIINTLCURRDIGITS[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c0a) rgbICURRENCY[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0c0a) rgbINEGCURR[] = { /* "8" */
+ 0x38
+};
+
+static BYTE NLSALLOC(0c0a) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(0c0a) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0c0a) rgbSSHORTDATE[] = { /* "d/MM/yy" */
+ 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0c0a) rgbSLONGDATE[] = { /* "dddd d' de 'MMMM' de 'yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x20, 0x64, 0x27, 0x20
+ , 0x64, 0x65, 0x20, 0x27, 0x4d, 0x4d, 0x4d, 0x4d
+ , 0x27, 0x20, 0x64, 0x65, 0x20, 0x27, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0c0a) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0a) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0a) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0a) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c0a) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c0a) rgbIDAYLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c0a) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0a) rgbSDAYNAME1[] = { /* "lunes" */
+ 0x6c, 0x75, 0x6e, 0x65, 0x73
+};
+
+static BYTE NLSALLOC(0c0a) rgbSDAYNAME2[] = { /* "martes" */
+ 0x6d, 0x61, 0x72, 0x74, 0x65, 0x73
+};
+
+static BYTE NLSALLOC(0c0a) rgbSDAYNAME3[] = { /* "miércoles" */
+ 0x6d, 0x69, 0xe9, 0x72, 0x63, 0x6f, 0x6c, 0x65
+ , 0x73
+};
+
+static BYTE NLSALLOC(0c0a) rgbSDAYNAME4[] = { /* "jueves" */
+ 0x6a, 0x75, 0x65, 0x76, 0x65, 0x73
+};
+
+static BYTE NLSALLOC(0c0a) rgbSDAYNAME5[] = { /* "viernes" */
+ 0x76, 0x69, 0x65, 0x72, 0x6e, 0x65, 0x73
+};
+
+static BYTE NLSALLOC(0c0a) rgbSDAYNAME6[] = { /* "sábado" */
+ 0x73, 0xe1, 0x62, 0x61, 0x64, 0x6f
+};
+
+static BYTE NLSALLOC(0c0a) rgbSDAYNAME7[] = { /* "domingo" */
+ 0x64, 0x6f, 0x6d, 0x69, 0x6e, 0x67, 0x6f
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVDAYNAME1[] = { /* "lun" */
+ 0x6c, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVDAYNAME2[] = { /* "mar" */
+ 0x6d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVDAYNAME3[] = { /* "mié" */
+ 0x6d, 0x69, 0xe9
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVDAYNAME4[] = { /* "jue" */
+ 0x6a, 0x75, 0x65
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVDAYNAME5[] = { /* "vie" */
+ 0x76, 0x69, 0x65
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVDAYNAME6[] = { /* "sáb" */
+ 0x73, 0xe1, 0x62
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVDAYNAME7[] = { /* "dom" */
+ 0x64, 0x6f, 0x6d
+};
+
+static BYTE NLSALLOC(0c0a) rgbSMONTHNAME1[] = { /* "enero" */
+ 0x65, 0x6e, 0x65, 0x72, 0x6f
+};
+
+static BYTE NLSALLOC(0c0a) rgbSMONTHNAME2[] = { /* "febrero" */
+ 0x66, 0x65, 0x62, 0x72, 0x65, 0x72, 0x6f
+};
+
+static BYTE NLSALLOC(0c0a) rgbSMONTHNAME3[] = { /* "marzo" */
+ 0x6d, 0x61, 0x72, 0x7a, 0x6f
+};
+
+static BYTE NLSALLOC(0c0a) rgbSMONTHNAME4[] = { /* "abril" */
+ 0x61, 0x62, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(0c0a) rgbSMONTHNAME5[] = { /* "mayo" */
+ 0x6d, 0x61, 0x79, 0x6f
+};
+
+static BYTE NLSALLOC(0c0a) rgbSMONTHNAME6[] = { /* "junio" */
+ 0x6a, 0x75, 0x6e, 0x69, 0x6f
+};
+
+static BYTE NLSALLOC(0c0a) rgbSMONTHNAME7[] = { /* "julio" */
+ 0x6a, 0x75, 0x6c, 0x69, 0x6f
+};
+
+static BYTE NLSALLOC(0c0a) rgbSMONTHNAME8[] = { /* "agosto" */
+ 0x61, 0x67, 0x6f, 0x73, 0x74, 0x6f
+};
+
+static BYTE NLSALLOC(0c0a) rgbSMONTHNAME9[] = { /* "septiembre" */
+ 0x73, 0x65, 0x70, 0x74, 0x69, 0x65, 0x6d, 0x62
+ , 0x72, 0x65
+};
+
+static BYTE NLSALLOC(0c0a) rgbSMONTHNAME10[] = { /* "octubre" */
+ 0x6f, 0x63, 0x74, 0x75, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(0c0a) rgbSMONTHNAME11[] = { /* "noviembre" */
+ 0x6e, 0x6f, 0x76, 0x69, 0x65, 0x6d, 0x62, 0x72
+ , 0x65
+};
+
+static BYTE NLSALLOC(0c0a) rgbSMONTHNAME12[] = { /* "diciembre" */
+ 0x64, 0x69, 0x63, 0x69, 0x65, 0x6d, 0x62, 0x72
+ , 0x65
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVMONTHNAME1[] = { /* "ene" */
+ 0x65, 0x6e, 0x65
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVMONTHNAME2[] = { /* "feb" */
+ 0x66, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVMONTHNAME3[] = { /* "mar" */
+ 0x6d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVMONTHNAME4[] = { /* "abr" */
+ 0x61, 0x62, 0x72
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVMONTHNAME5[] = { /* "may" */
+ 0x6d, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVMONTHNAME6[] = { /* "jun" */
+ 0x6a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVMONTHNAME7[] = { /* "jul" */
+ 0x6a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVMONTHNAME8[] = { /* "ago" */
+ 0x61, 0x67, 0x6f
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVMONTHNAME9[] = { /* "sep" */
+ 0x73, 0x65, 0x70
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVMONTHNAME10[] = { /* "oct" */
+ 0x6f, 0x63, 0x74
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVMONTHNAME11[] = { /* "nov" */
+ 0x6e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(0c0a) rgbSABBREVMONTHNAME12[] = { /* "dic" */
+ 0x64, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(0c0a) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0c0a) rgbIPOSSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0a) rgbINEGSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0a) rgbIPOSSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c0a) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0a) rgbINEGSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c0a) rgbINEGSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0a) rgbSENGCOUNTRY[] = { /* "Spain" */
+ 0x53, 0x70, 0x61, 0x69, 0x6e
+};
+
+static BYTE NLSALLOC(0c0a) rgbSENGLANGUAGE[] = { /* "Spanish - Modern Sort" */
+ 0x53, 0x70, 0x61, 0x6e, 0x69, 0x73, 0x68, 0x20
+ , 0x2d, 0x20, 0x4d, 0x6f, 0x64, 0x65, 0x72, 0x6e
+ , 0x20, 0x53, 0x6f, 0x72, 0x74
+};
+
+static BYTE NLSALLOC(0c0a) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c0a) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c0a) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0c0a) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0a) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0c0a) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c0a) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0a) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0c0a) g_rglcinfo0c0a[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 21, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 5, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 6, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 3, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 7, rgbSSHORTDATE }
+ , { 26, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 5, rgbSDAYNAME1 }
+ , { 6, rgbSDAYNAME2 }
+ , { 9, rgbSDAYNAME3 }
+ , { 6, rgbSDAYNAME4 }
+ , { 7, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 7, rgbSDAYNAME7 }
+ , { 3, rgbSABBREVDAYNAME1 }
+ , { 3, rgbSABBREVDAYNAME2 }
+ , { 3, rgbSABBREVDAYNAME3 }
+ , { 3, rgbSABBREVDAYNAME4 }
+ , { 3, rgbSABBREVDAYNAME5 }
+ , { 3, rgbSABBREVDAYNAME6 }
+ , { 3, rgbSABBREVDAYNAME7 }
+ , { 5, rgbSMONTHNAME1 }
+ , { 7, rgbSMONTHNAME2 }
+ , { 5, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 4, rgbSMONTHNAME5 }
+ , { 5, rgbSMONTHNAME6 }
+ , { 5, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 10, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 9, rgbSMONTHNAME11 }
+ , { 9, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 5, rgbSENGCOUNTRY }
+ , { 21, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0c0a) g_strinfo0c0a = {
+ rgbUCase_0c0a
+ , rgbLCase_0c0a
+ , rgwCType12_0c0a
+ , rgwCType3_0c0a
+ , rgwSort_0c0a
+ , rgexp_0c0a
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/0c0c.c b/private/oleauto/src/dispatch/win16/0c0c.c
new file mode 100644
index 000000000..8f1955398
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/0c0c.c
@@ -0,0 +1,522 @@
+/****************************************************************************
+* 0c0c.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* French - Canada
+*
+* LCID = 0x0c0c
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:45:11 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0409[256]; // from 0409:English - United States
+extern EXPANSION rgexp_0409[7];
+extern WORD rgwCType12_0409[256];
+extern WORD rgwCType3_0409[256];
+extern BYTE rgbUCase_0409[256];
+extern BYTE rgbLCase_0409[256];
+
+static BYTE NLSALLOC(0c0c) rgbILANGUAGE[] = { /* "0c0c" */
+ 0x30, 0x63, 0x30, 0x63
+};
+
+static BYTE NLSALLOC(0c0c) rgbSLANGUAGE[] = { /* "Canadian French" */
+ 0x43, 0x61, 0x6e, 0x61, 0x64, 0x69, 0x61, 0x6e
+ , 0x20, 0x46, 0x72, 0x65, 0x6e, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVLANGNAME[] = { /* "FRC" */
+ 0x46, 0x52, 0x43
+};
+
+static BYTE NLSALLOC(0c0c) rgbSNATIVELANGNAME[] = { /* "français" */
+ 0x66, 0x72, 0x61, 0x6e, 0xe7, 0x61, 0x69, 0x73
+};
+
+static BYTE NLSALLOC(0c0c) rgbICOUNTRY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0c0c) rgbSCOUNTRY[] = { /* "Canada" */
+ 0x43, 0x61, 0x6e, 0x61, 0x64, 0x61
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVCTRYNAME[] = { /* "CAN" */
+ 0x43, 0x41, 0x4e
+};
+
+static BYTE NLSALLOC(0c0c) rgbSNATIVECTRYNAME[] = { /* "Canada" */
+ 0x43, 0x61, 0x6e, 0x61, 0x64, 0x61
+};
+
+static BYTE NLSALLOC(0c0c) rgbIDEFAULTLANGUAGE[] = { /* "0c0c" */
+ 0x30, 0x63, 0x30, 0x63
+};
+
+static BYTE NLSALLOC(0c0c) rgbIDEFAULTCOUNTRY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0c0c) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(0c0c) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(0c0c) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c0c) rgbSDECIMAL[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0c0c) rgbSTHOUSAND[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(0c0c) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0c0c) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0c0c) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0c) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(0c0c) rgbSCURRENCY[] = { /* "$" */
+ 0x24
+};
+
+static BYTE NLSALLOC(0c0c) rgbSINTLSYMBOL[] = { /* "CAD" */
+ 0x43, 0x41, 0x44
+};
+
+static BYTE NLSALLOC(0c0c) rgbSMONDECIMALSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(0c0c) rgbSMONTHOUSANDSEP[] = { /* "\x00a0" */
+ 0xa0
+};
+
+static BYTE NLSALLOC(0c0c) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(0c0c) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0c0c) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0c0c) rgbICURRENCY[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(0c0c) rgbINEGCURR[] = { /* "4" */
+ 0x34
+};
+
+static BYTE NLSALLOC(0c0c) rgbSDATE[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0c0c) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(0c0c) rgbSSHORTDATE[] = { /* "yy-MM-dd" */
+ 0x79, 0x79, 0x2d, 0x4d, 0x4d, 0x2d, 0x64, 0x64
+};
+
+static BYTE NLSALLOC(0c0c) rgbSLONGDATE[] = { /* "d MMMM, yyyy" */
+ 0x64, 0x20, 0x4d, 0x4d, 0x4d, 0x4d, 0x2c, 0x20
+ , 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(0c0c) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(0c0c) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0c) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0c) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c0c) rgbITLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0c) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0c) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0c) rgbSDAYNAME1[] = { /* "lundi" */
+ 0x6c, 0x75, 0x6e, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(0c0c) rgbSDAYNAME2[] = { /* "mardi" */
+ 0x6d, 0x61, 0x72, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(0c0c) rgbSDAYNAME3[] = { /* "mercredi" */
+ 0x6d, 0x65, 0x72, 0x63, 0x72, 0x65, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(0c0c) rgbSDAYNAME4[] = { /* "jeudi" */
+ 0x6a, 0x65, 0x75, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(0c0c) rgbSDAYNAME5[] = { /* "vendredi" */
+ 0x76, 0x65, 0x6e, 0x64, 0x72, 0x65, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(0c0c) rgbSDAYNAME6[] = { /* "samedi" */
+ 0x73, 0x61, 0x6d, 0x65, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(0c0c) rgbSDAYNAME7[] = { /* "dimanche" */
+ 0x64, 0x69, 0x6d, 0x61, 0x6e, 0x63, 0x68, 0x65
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVDAYNAME1[] = { /* "lun." */
+ 0x6c, 0x75, 0x6e, 0x2e
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVDAYNAME2[] = { /* "mar." */
+ 0x6d, 0x61, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVDAYNAME3[] = { /* "mer." */
+ 0x6d, 0x65, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVDAYNAME4[] = { /* "jeu." */
+ 0x6a, 0x65, 0x75, 0x2e
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVDAYNAME5[] = { /* "ven." */
+ 0x76, 0x65, 0x6e, 0x2e
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVDAYNAME6[] = { /* "sam." */
+ 0x73, 0x61, 0x6d, 0x2e
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVDAYNAME7[] = { /* "dim." */
+ 0x64, 0x69, 0x6d, 0x2e
+};
+
+static BYTE NLSALLOC(0c0c) rgbSMONTHNAME1[] = { /* "janvier" */
+ 0x6a, 0x61, 0x6e, 0x76, 0x69, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0c0c) rgbSMONTHNAME2[] = { /* "février" */
+ 0x66, 0xe9, 0x76, 0x72, 0x69, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(0c0c) rgbSMONTHNAME3[] = { /* "mars" */
+ 0x6d, 0x61, 0x72, 0x73
+};
+
+static BYTE NLSALLOC(0c0c) rgbSMONTHNAME4[] = { /* "avril" */
+ 0x61, 0x76, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(0c0c) rgbSMONTHNAME5[] = { /* "mai" */
+ 0x6d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(0c0c) rgbSMONTHNAME6[] = { /* "juin" */
+ 0x6a, 0x75, 0x69, 0x6e
+};
+
+static BYTE NLSALLOC(0c0c) rgbSMONTHNAME7[] = { /* "juillet" */
+ 0x6a, 0x75, 0x69, 0x6c, 0x6c, 0x65, 0x74
+};
+
+static BYTE NLSALLOC(0c0c) rgbSMONTHNAME8[] = { /* "août" */
+ 0x61, 0x6f, 0xfb, 0x74
+};
+
+static BYTE NLSALLOC(0c0c) rgbSMONTHNAME9[] = { /* "septembre" */
+ 0x73, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x72
+ , 0x65
+};
+
+static BYTE NLSALLOC(0c0c) rgbSMONTHNAME10[] = { /* "octobre" */
+ 0x6f, 0x63, 0x74, 0x6f, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(0c0c) rgbSMONTHNAME11[] = { /* "novembre" */
+ 0x6e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(0c0c) rgbSMONTHNAME12[] = { /* "décembre" */
+ 0x64, 0xe9, 0x63, 0x65, 0x6d, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVMONTHNAME1[] = { /* "janv." */
+ 0x6a, 0x61, 0x6e, 0x76, 0x2e
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVMONTHNAME2[] = { /* "févr." */
+ 0x66, 0xe9, 0x76, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVMONTHNAME3[] = { /* "mars" */
+ 0x6d, 0x61, 0x72, 0x73
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVMONTHNAME4[] = { /* "avr." */
+ 0x61, 0x76, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVMONTHNAME5[] = { /* "mai" */
+ 0x6d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVMONTHNAME6[] = { /* "juin" */
+ 0x6a, 0x75, 0x69, 0x6e
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVMONTHNAME7[] = { /* "juil." */
+ 0x6a, 0x75, 0x69, 0x6c, 0x2e
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVMONTHNAME8[] = { /* "août" */
+ 0x61, 0x6f, 0xfb, 0x74
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVMONTHNAME9[] = { /* "sept." */
+ 0x73, 0x65, 0x70, 0x74, 0x2e
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVMONTHNAME10[] = { /* "oct." */
+ 0x6f, 0x63, 0x74, 0x2e
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVMONTHNAME11[] = { /* "nov." */
+ 0x6e, 0x6f, 0x76, 0x2e
+};
+
+static BYTE NLSALLOC(0c0c) rgbSABBREVMONTHNAME12[] = { /* "déc." */
+ 0x64, 0xe9, 0x63, 0x2e
+};
+
+static BYTE NLSALLOC(0c0c) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(0c0c) rgbIPOSSIGNPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0c) rgbINEGSIGNPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c0c) rgbIPOSSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c0c) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0c) rgbINEGSYMPRECEDES[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c0c) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c0c) rgbSENGCOUNTRY[] = { /* "Canada" */
+ 0x43, 0x61, 0x6e, 0x61, 0x64, 0x61
+};
+
+static BYTE NLSALLOC(0c0c) rgbSENGLANGUAGE[] = { /* "French" */
+ 0x46, 0x72, 0x65, 0x6e, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(0c0c) rgbIFIRSTDAYOFWEEK[] = { /* "6" */
+ 0x36
+};
+
+static BYTE NLSALLOC(0c0c) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c0c) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(0c0c) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0c) rgbSTIMEFORMAT[] = { /* "HH:mm:ss" */
+ 0x48, 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(0c0c) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(0c0c) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(0c0c) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(0c0c) g_rglcinfo0c0c[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 15, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 8, rgbSNATIVELANGNAME }
+ , { 1, rgbICOUNTRY }
+ , { 6, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 6, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 1, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 1, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 12, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 5, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 8, rgbSDAYNAME3 }
+ , { 5, rgbSDAYNAME4 }
+ , { 8, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 8, rgbSDAYNAME7 }
+ , { 4, rgbSABBREVDAYNAME1 }
+ , { 4, rgbSABBREVDAYNAME2 }
+ , { 4, rgbSABBREVDAYNAME3 }
+ , { 4, rgbSABBREVDAYNAME4 }
+ , { 4, rgbSABBREVDAYNAME5 }
+ , { 4, rgbSABBREVDAYNAME6 }
+ , { 4, rgbSABBREVDAYNAME7 }
+ , { 7, rgbSMONTHNAME1 }
+ , { 7, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 7, rgbSMONTHNAME7 }
+ , { 4, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 5, rgbSABBREVMONTHNAME1 }
+ , { 5, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 4, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 4, rgbSABBREVMONTHNAME6 }
+ , { 5, rgbSABBREVMONTHNAME7 }
+ , { 4, rgbSABBREVMONTHNAME8 }
+ , { 5, rgbSABBREVMONTHNAME9 }
+ , { 4, rgbSABBREVMONTHNAME10 }
+ , { 4, rgbSABBREVMONTHNAME11 }
+ , { 4, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 6, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 8, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(0c0c) g_strinfo0c0c = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/1001.c b/private/oleauto/src/dispatch/win16/1001.c
new file mode 100644
index 000000000..6f52ded33
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/1001.c
@@ -0,0 +1,528 @@
+/****************************************************************************
+* 1001.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Arabic - Libya
+*
+* LCID = 0x1001
+*
+* CodePage = 1256
+*
+* Generated: Thu Dec 01 18:28:59 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0401[256]; // from 0401:Arabic - Saudi Arabia
+extern EXPANSION rgexp_0401[3];
+extern WORD rgwCType12_0401[256];
+extern WORD rgwCType3_0401[256];
+extern BYTE rgbUCase_0401[256];
+extern BYTE rgbLCase_0401[256];
+
+static BYTE NLSALLOC(1001) rgbILANGUAGE[] = { /* "1001" */
+ 0x31, 0x30, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(1001) rgbSLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVLANGNAME[] = { /* "ARL" */
+ 0x41, 0x52, 0x4c
+};
+
+static BYTE NLSALLOC(1001) rgbSNATIVELANGNAME[] = { /* "\x0627\x0644\x0639\x0631\x0628\x064a\x0629" */
+ 0xc7, 0xe1, 0xda, 0xd1, 0xc8, 0xed, 0xc9
+};
+
+static BYTE NLSALLOC(1001) rgbICOUNTRY[] = { /* "218" */
+ 0x32, 0x31, 0x38
+};
+
+static BYTE NLSALLOC(1001) rgbSCOUNTRY[] = { /* "Libya" */
+ 0x4c, 0x69, 0x62, 0x79, 0x61
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVCTRYNAME[] = { /* "LBY" */
+ 0x4c, 0x42, 0x59
+};
+
+static BYTE NLSALLOC(1001) rgbSNATIVECTRYNAME[] = { /* "\x0644\x064a\x0628\x064a\x0627" */
+ 0xe1, 0xed, 0xc8, 0xed, 0xc7
+};
+
+static BYTE NLSALLOC(1001) rgbIDEFAULTLANGUAGE[] = { /* "1001" */
+ 0x31, 0x30, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(1001) rgbIDEFAULTCOUNTRY[] = { /* "218" */
+ 0x32, 0x31, 0x38
+};
+
+static BYTE NLSALLOC(1001) rgbIDEFAULTCODEPAGE[] = { /* "708" */
+ 0x37, 0x30, 0x38
+};
+
+static BYTE NLSALLOC(1001) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(1001) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1001) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(1001) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(1001) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(1001) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1001) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1001) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(1001) rgbSCURRENCY[] = { /* "\x062f.\x0644.\x200f" */
+ 0xcf, 0x2e, 0xe1, 0x2e, 0xfe
+};
+
+static BYTE NLSALLOC(1001) rgbSINTLSYMBOL[] = { /* "LYD" */
+ 0x4c, 0x59, 0x44
+};
+
+static BYTE NLSALLOC(1001) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(1001) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(1001) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(1001) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1001) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1001) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1001) rgbINEGCURR[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(1001) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(1001) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(1001) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(1001) rgbSLONGDATE[] = { /* "dd/MM/yyyy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(1001) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1001) rgbILDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1001) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1001) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1001) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1001) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1001) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1001) rgbS1159[] = { /* "\x0635" */
+ 0xd5
+};
+
+static BYTE NLSALLOC(1001) rgbS2359[] = { /* "\x0645" */
+ 0xe3
+};
+
+static BYTE NLSALLOC(1001) rgbSDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(1001) rgbSDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(1001) rgbSDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(1001) rgbSDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(1001) rgbSDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(1001) rgbSDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(1001) rgbSDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(1001) rgbSMONTHNAME1[] = { /* "\x064a\x0646\x0627\x064a\x0631" */
+ 0xed, 0xe4, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(1001) rgbSMONTHNAME2[] = { /* "\x0641\x0628\x0631\x0627\x064a\x0631" */
+ 0xdd, 0xc8, 0xd1, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(1001) rgbSMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(1001) rgbSMONTHNAME4[] = { /* "\x0627\x0628\x0631\x064a\x0644" */
+ 0xc7, 0xc8, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(1001) rgbSMONTHNAME5[] = { /* "\x0645\x0627\x064a\x0648" */
+ 0xe3, 0xc7, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(1001) rgbSMONTHNAME6[] = { /* "\x064a\x0648\x0646\x064a\x0648" */
+ 0xed, 0xe6, 0xe4, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(1001) rgbSMONTHNAME7[] = { /* "\x064a\x0648\x0644\x064a\x0648" */
+ 0xed, 0xe6, 0xe1, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(1001) rgbSMONTHNAME8[] = { /* "\x0623\x063a\x0633\x0637\x0633" */
+ 0xc3, 0xdb, 0xd3, 0xd8, 0xd3
+};
+
+static BYTE NLSALLOC(1001) rgbSMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1001) rgbSMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1001) rgbSMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1001) rgbSMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVMONTHNAME1[] = { /* "\x064a\x0646\x0627\x064a\x0631" */
+ 0xed, 0xe4, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVMONTHNAME2[] = { /* "\x0641\x0628\x0631\x0627\x064a\x0631" */
+ 0xdd, 0xc8, 0xd1, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVMONTHNAME4[] = { /* "\x0627\x0628\x0631\x064a\x0644" */
+ 0xc7, 0xc8, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVMONTHNAME5[] = { /* "\x0645\x0627\x064a\x0648" */
+ 0xe3, 0xc7, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVMONTHNAME6[] = { /* "\x064a\x0648\x0646\x064a\x0648" */
+ 0xed, 0xe6, 0xe4, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVMONTHNAME7[] = { /* "\x064a\x0648\x0644\x064a\x0648" */
+ 0xed, 0xe6, 0xe1, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVMONTHNAME8[] = { /* "\x0623\x063a\x0633\x0637\x0633" */
+ 0xc3, 0xdb, 0xd3, 0xd8, 0xd3
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1001) rgbSABBREVMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1001) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(1001) rgbIPOSSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1001) rgbINEGSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1001) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1001) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1001) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1001) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1001) rgbSENGCOUNTRY[] = { /* "Libya" */
+ 0x4c, 0x69, 0x62, 0x79, 0x61
+};
+
+static BYTE NLSALLOC(1001) rgbSENGLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(1001) rgbIFIRSTDAYOFWEEK[] = { /* "5" */
+ 0x35
+};
+
+static BYTE NLSALLOC(1001) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1001) rgbIDEFAULTANSICODEPAGE[] = { /* "1256" */
+ 0x31, 0x32, 0x35, 0x36
+};
+
+static BYTE NLSALLOC(1001) rgbINEGNUMBER[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(1001) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(1001) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1001) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1001) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(1001) g_rglcinfo1001[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 5, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 5, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 5, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 10, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 1, rgbS1159 }
+ , { 1, rgbS2359 }
+ , { 5, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 7, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 8, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 5, rgbSABBREVDAYNAME1 }
+ , { 5, rgbSABBREVDAYNAME2 }
+ , { 7, rgbSABBREVDAYNAME3 }
+ , { 8, rgbSABBREVDAYNAME4 }
+ , { 8, rgbSABBREVDAYNAME5 }
+ , { 6, rgbSABBREVDAYNAME6 }
+ , { 6, rgbSABBREVDAYNAME7 }
+ , { 5, rgbSMONTHNAME1 }
+ , { 6, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 4, rgbSMONTHNAME5 }
+ , { 5, rgbSMONTHNAME6 }
+ , { 5, rgbSMONTHNAME7 }
+ , { 5, rgbSMONTHNAME8 }
+ , { 6, rgbSMONTHNAME9 }
+ , { 6, rgbSMONTHNAME10 }
+ , { 6, rgbSMONTHNAME11 }
+ , { 6, rgbSMONTHNAME12 }
+ , { 5, rgbSABBREVMONTHNAME1 }
+ , { 6, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 5, rgbSABBREVMONTHNAME4 }
+ , { 4, rgbSABBREVMONTHNAME5 }
+ , { 5, rgbSABBREVMONTHNAME6 }
+ , { 5, rgbSABBREVMONTHNAME7 }
+ , { 5, rgbSABBREVMONTHNAME8 }
+ , { 6, rgbSABBREVMONTHNAME9 }
+ , { 6, rgbSABBREVMONTHNAME10 }
+ , { 6, rgbSABBREVMONTHNAME11 }
+ , { 6, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 5, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(1001) g_strinfo1001 = {
+ rgbUCase_0401
+ , rgbLCase_0401
+ , rgwCType12_0401
+ , rgwCType3_0401
+ , rgwSort_0401
+ , rgexp_0401
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/1009.c b/private/oleauto/src/dispatch/win16/1009.c
new file mode 100644
index 000000000..94c88122a
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/1009.c
@@ -0,0 +1,523 @@
+/****************************************************************************
+* 1009.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* English - Canada
+*
+* LCID = 0x1009
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:46:28 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0409[256]; // from 0409:English - United States
+extern EXPANSION rgexp_0409[7];
+extern WORD rgwCType12_0409[256];
+extern WORD rgwCType3_0409[256];
+extern BYTE rgbUCase_0409[256];
+extern BYTE rgbLCase_0409[256];
+
+static BYTE NLSALLOC(1009) rgbILANGUAGE[] = { /* "1009" */
+ 0x31, 0x30, 0x30, 0x39
+};
+
+static BYTE NLSALLOC(1009) rgbSLANGUAGE[] = { /* "Canadian English" */
+ 0x43, 0x61, 0x6e, 0x61, 0x64, 0x69, 0x61, 0x6e
+ , 0x20, 0x45, 0x6e, 0x67, 0x6c, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVLANGNAME[] = { /* "ENC" */
+ 0x45, 0x4e, 0x43
+};
+
+static BYTE NLSALLOC(1009) rgbSNATIVELANGNAME[] = { /* "English" */
+ 0x45, 0x6e, 0x67, 0x6c, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(1009) rgbICOUNTRY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1009) rgbSCOUNTRY[] = { /* "Canada" */
+ 0x43, 0x61, 0x6e, 0x61, 0x64, 0x61
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVCTRYNAME[] = { /* "CAN" */
+ 0x43, 0x41, 0x4e
+};
+
+static BYTE NLSALLOC(1009) rgbSNATIVECTRYNAME[] = { /* "Canada" */
+ 0x43, 0x61, 0x6e, 0x61, 0x64, 0x61
+};
+
+static BYTE NLSALLOC(1009) rgbIDEFAULTLANGUAGE[] = { /* "1009" */
+ 0x31, 0x30, 0x30, 0x39
+};
+
+static BYTE NLSALLOC(1009) rgbIDEFAULTCOUNTRY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1009) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(1009) rgbSLIST[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(1009) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1009) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(1009) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(1009) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(1009) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1009) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1009) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(1009) rgbSCURRENCY[] = { /* "$" */
+ 0x24
+};
+
+static BYTE NLSALLOC(1009) rgbSINTLSYMBOL[] = { /* "CAD" */
+ 0x43, 0x41, 0x44
+};
+
+static BYTE NLSALLOC(1009) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(1009) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(1009) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(1009) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1009) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1009) rgbICURRENCY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1009) rgbINEGCURR[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1009) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(1009) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(1009) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(1009) rgbSLONGDATE[] = { /* "MMMM d, yyyy" */
+ 0x4d, 0x4d, 0x4d, 0x4d, 0x20, 0x64, 0x2c, 0x20
+ , 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(1009) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1009) rgbILDATE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1009) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1009) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1009) rgbITLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1009) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1009) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1009) rgbSDAYNAME1[] = { /* "Monday" */
+ 0x4d, 0x6f, 0x6e, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1009) rgbSDAYNAME2[] = { /* "Tuesday" */
+ 0x54, 0x75, 0x65, 0x73, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1009) rgbSDAYNAME3[] = { /* "Wednesday" */
+ 0x57, 0x65, 0x64, 0x6e, 0x65, 0x73, 0x64, 0x61
+ , 0x79
+};
+
+static BYTE NLSALLOC(1009) rgbSDAYNAME4[] = { /* "Thursday" */
+ 0x54, 0x68, 0x75, 0x72, 0x73, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1009) rgbSDAYNAME5[] = { /* "Friday" */
+ 0x46, 0x72, 0x69, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1009) rgbSDAYNAME6[] = { /* "Saturday" */
+ 0x53, 0x61, 0x74, 0x75, 0x72, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1009) rgbSDAYNAME7[] = { /* "Sunday" */
+ 0x53, 0x75, 0x6e, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVDAYNAME1[] = { /* "Mon" */
+ 0x4d, 0x6f, 0x6e
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVDAYNAME2[] = { /* "Tue" */
+ 0x54, 0x75, 0x65
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVDAYNAME3[] = { /* "Wed" */
+ 0x57, 0x65, 0x64
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVDAYNAME4[] = { /* "Thu" */
+ 0x54, 0x68, 0x75
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVDAYNAME5[] = { /* "Fri" */
+ 0x46, 0x72, 0x69
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVDAYNAME6[] = { /* "Sat" */
+ 0x53, 0x61, 0x74
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVDAYNAME7[] = { /* "Sun" */
+ 0x53, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(1009) rgbSMONTHNAME1[] = { /* "January" */
+ 0x4a, 0x61, 0x6e, 0x75, 0x61, 0x72, 0x79
+};
+
+static BYTE NLSALLOC(1009) rgbSMONTHNAME2[] = { /* "February" */
+ 0x46, 0x65, 0x62, 0x72, 0x75, 0x61, 0x72, 0x79
+};
+
+static BYTE NLSALLOC(1009) rgbSMONTHNAME3[] = { /* "March" */
+ 0x4d, 0x61, 0x72, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(1009) rgbSMONTHNAME4[] = { /* "April" */
+ 0x41, 0x70, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(1009) rgbSMONTHNAME5[] = { /* "May" */
+ 0x4d, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1009) rgbSMONTHNAME6[] = { /* "June" */
+ 0x4a, 0x75, 0x6e, 0x65
+};
+
+static BYTE NLSALLOC(1009) rgbSMONTHNAME7[] = { /* "July" */
+ 0x4a, 0x75, 0x6c, 0x79
+};
+
+static BYTE NLSALLOC(1009) rgbSMONTHNAME8[] = { /* "August" */
+ 0x41, 0x75, 0x67, 0x75, 0x73, 0x74
+};
+
+static BYTE NLSALLOC(1009) rgbSMONTHNAME9[] = { /* "September" */
+ 0x53, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x65
+ , 0x72
+};
+
+static BYTE NLSALLOC(1009) rgbSMONTHNAME10[] = { /* "October" */
+ 0x4f, 0x63, 0x74, 0x6f, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(1009) rgbSMONTHNAME11[] = { /* "November" */
+ 0x4e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(1009) rgbSMONTHNAME12[] = { /* "December" */
+ 0x44, 0x65, 0x63, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVMONTHNAME1[] = { /* "Jan" */
+ 0x4a, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVMONTHNAME2[] = { /* "Feb" */
+ 0x46, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVMONTHNAME3[] = { /* "Mar" */
+ 0x4d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVMONTHNAME4[] = { /* "Apr" */
+ 0x41, 0x70, 0x72
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVMONTHNAME5[] = { /* "May" */
+ 0x4d, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVMONTHNAME6[] = { /* "Jun" */
+ 0x4a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVMONTHNAME7[] = { /* "Jul" */
+ 0x4a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVMONTHNAME8[] = { /* "Aug" */
+ 0x41, 0x75, 0x67
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVMONTHNAME9[] = { /* "Sep" */
+ 0x53, 0x65, 0x70
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVMONTHNAME10[] = { /* "Oct" */
+ 0x4f, 0x63, 0x74
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVMONTHNAME11[] = { /* "Nov" */
+ 0x4e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(1009) rgbSABBREVMONTHNAME12[] = { /* "Dec" */
+ 0x44, 0x65, 0x63
+};
+
+static BYTE NLSALLOC(1009) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(1009) rgbIPOSSIGNPOSN[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(1009) rgbINEGSIGNPOSN[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(1009) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1009) rgbIPOSSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1009) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1009) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1009) rgbSENGCOUNTRY[] = { /* "Canada" */
+ 0x43, 0x61, 0x6e, 0x61, 0x64, 0x61
+};
+
+static BYTE NLSALLOC(1009) rgbSENGLANGUAGE[] = { /* "English" */
+ 0x45, 0x6e, 0x67, 0x6c, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(1009) rgbIFIRSTDAYOFWEEK[] = { /* "6" */
+ 0x36
+};
+
+static BYTE NLSALLOC(1009) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1009) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(1009) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1009) rgbSTIMEFORMAT[] = { /* "HH:mm:ss" */
+ 0x48, 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(1009) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1009) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1009) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(1009) g_rglcinfo1009[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 16, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 1, rgbICOUNTRY }
+ , { 6, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 6, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 1, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 1, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 12, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 6, rgbSDAYNAME1 }
+ , { 7, rgbSDAYNAME2 }
+ , { 9, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 6, rgbSDAYNAME5 }
+ , { 8, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 3, rgbSABBREVDAYNAME1 }
+ , { 3, rgbSABBREVDAYNAME2 }
+ , { 3, rgbSABBREVDAYNAME3 }
+ , { 3, rgbSABBREVDAYNAME4 }
+ , { 3, rgbSABBREVDAYNAME5 }
+ , { 3, rgbSABBREVDAYNAME6 }
+ , { 3, rgbSABBREVDAYNAME7 }
+ , { 7, rgbSMONTHNAME1 }
+ , { 8, rgbSMONTHNAME2 }
+ , { 5, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 6, rgbSENGCOUNTRY }
+ , { 7, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 8, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(1009) g_strinfo1009 = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/100c.c b/private/oleauto/src/dispatch/win16/100c.c
new file mode 100644
index 000000000..5644accc0
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/100c.c
@@ -0,0 +1,517 @@
+/****************************************************************************
+* 100c.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* French - Switzerland
+*
+* LCID = 0x100c
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:47:06 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0409[256]; // from 0409:English - United States
+extern EXPANSION rgexp_0409[7];
+extern WORD rgwCType12_0409[256];
+extern WORD rgwCType3_0409[256];
+extern BYTE rgbUCase_0409[256];
+extern BYTE rgbLCase_0409[256];
+
+static BYTE NLSALLOC(100c) rgbILANGUAGE[] = { /* "100c" */
+ 0x31, 0x30, 0x30, 0x63
+};
+
+static BYTE NLSALLOC(100c) rgbSLANGUAGE[] = { /* "Swiss French" */
+ 0x53, 0x77, 0x69, 0x73, 0x73, 0x20, 0x46, 0x72
+ , 0x65, 0x6e, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVLANGNAME[] = { /* "FRS" */
+ 0x46, 0x52, 0x53
+};
+
+static BYTE NLSALLOC(100c) rgbSNATIVELANGNAME[] = { /* "français" */
+ 0x66, 0x72, 0x61, 0x6e, 0xe7, 0x61, 0x69, 0x73
+};
+
+static BYTE NLSALLOC(100c) rgbICOUNTRY[] = { /* "41" */
+ 0x34, 0x31
+};
+
+static BYTE NLSALLOC(100c) rgbSCOUNTRY[] = { /* "Switzerland" */
+ 0x53, 0x77, 0x69, 0x74, 0x7a, 0x65, 0x72, 0x6c
+ , 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVCTRYNAME[] = { /* "CHE" */
+ 0x43, 0x48, 0x45
+};
+
+static BYTE NLSALLOC(100c) rgbSNATIVECTRYNAME[] = { /* "Suisse" */
+ 0x53, 0x75, 0x69, 0x73, 0x73, 0x65
+};
+
+static BYTE NLSALLOC(100c) rgbIDEFAULTLANGUAGE[] = { /* "100c" */
+ 0x31, 0x30, 0x30, 0x63
+};
+
+static BYTE NLSALLOC(100c) rgbIDEFAULTCOUNTRY[] = { /* "41" */
+ 0x34, 0x31
+};
+
+static BYTE NLSALLOC(100c) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(100c) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(100c) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(100c) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(100c) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(100c) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(100c) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(100c) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(100c) rgbSCURRENCY[] = { /* "CHF" */
+ 0x43, 0x48, 0x46
+};
+
+static BYTE NLSALLOC(100c) rgbSINTLSYMBOL[] = { /* "CHF" */
+ 0x43, 0x48, 0x46
+};
+
+static BYTE NLSALLOC(100c) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(100c) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(100c) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(100c) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(100c) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(100c) rgbINEGCURR[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(100c) rgbSDATE[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(100c) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(100c) rgbSSHORTDATE[] = { /* "dd.MM.yy" */
+ 0x64, 0x64, 0x2e, 0x4d, 0x4d, 0x2e, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(100c) rgbSLONGDATE[] = { /* "dddd, d. MMMM yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x2c, 0x20, 0x64, 0x2e
+ , 0x20, 0x4d, 0x4d, 0x4d, 0x4d, 0x20, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(100c) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(100c) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(100c) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(100c) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(100c) rgbITLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(100c) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(100c) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(100c) rgbSDAYNAME1[] = { /* "lundi" */
+ 0x6c, 0x75, 0x6e, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(100c) rgbSDAYNAME2[] = { /* "mardi" */
+ 0x6d, 0x61, 0x72, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(100c) rgbSDAYNAME3[] = { /* "mercredi" */
+ 0x6d, 0x65, 0x72, 0x63, 0x72, 0x65, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(100c) rgbSDAYNAME4[] = { /* "jeudi" */
+ 0x6a, 0x65, 0x75, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(100c) rgbSDAYNAME5[] = { /* "vendredi" */
+ 0x76, 0x65, 0x6e, 0x64, 0x72, 0x65, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(100c) rgbSDAYNAME6[] = { /* "samedi" */
+ 0x73, 0x61, 0x6d, 0x65, 0x64, 0x69
+};
+
+static BYTE NLSALLOC(100c) rgbSDAYNAME7[] = { /* "dimanche" */
+ 0x64, 0x69, 0x6d, 0x61, 0x6e, 0x63, 0x68, 0x65
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVDAYNAME1[] = { /* "lun." */
+ 0x6c, 0x75, 0x6e, 0x2e
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVDAYNAME2[] = { /* "mar." */
+ 0x6d, 0x61, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVDAYNAME3[] = { /* "mer." */
+ 0x6d, 0x65, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVDAYNAME4[] = { /* "jeu." */
+ 0x6a, 0x65, 0x75, 0x2e
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVDAYNAME5[] = { /* "ven." */
+ 0x76, 0x65, 0x6e, 0x2e
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVDAYNAME6[] = { /* "sam." */
+ 0x73, 0x61, 0x6d, 0x2e
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVDAYNAME7[] = { /* "dim." */
+ 0x64, 0x69, 0x6d, 0x2e
+};
+
+static BYTE NLSALLOC(100c) rgbSMONTHNAME1[] = { /* "janvier" */
+ 0x6a, 0x61, 0x6e, 0x76, 0x69, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(100c) rgbSMONTHNAME2[] = { /* "février" */
+ 0x66, 0xe9, 0x76, 0x72, 0x69, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(100c) rgbSMONTHNAME3[] = { /* "mars" */
+ 0x6d, 0x61, 0x72, 0x73
+};
+
+static BYTE NLSALLOC(100c) rgbSMONTHNAME4[] = { /* "avril" */
+ 0x61, 0x76, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(100c) rgbSMONTHNAME5[] = { /* "mai" */
+ 0x6d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(100c) rgbSMONTHNAME6[] = { /* "juin" */
+ 0x6a, 0x75, 0x69, 0x6e
+};
+
+static BYTE NLSALLOC(100c) rgbSMONTHNAME7[] = { /* "juillet" */
+ 0x6a, 0x75, 0x69, 0x6c, 0x6c, 0x65, 0x74
+};
+
+static BYTE NLSALLOC(100c) rgbSMONTHNAME8[] = { /* "août" */
+ 0x61, 0x6f, 0xfb, 0x74
+};
+
+static BYTE NLSALLOC(100c) rgbSMONTHNAME9[] = { /* "septembre" */
+ 0x73, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x72
+ , 0x65
+};
+
+static BYTE NLSALLOC(100c) rgbSMONTHNAME10[] = { /* "octobre" */
+ 0x6f, 0x63, 0x74, 0x6f, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(100c) rgbSMONTHNAME11[] = { /* "novembre" */
+ 0x6e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(100c) rgbSMONTHNAME12[] = { /* "décembre" */
+ 0x64, 0xe9, 0x63, 0x65, 0x6d, 0x62, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVMONTHNAME1[] = { /* "janv." */
+ 0x6a, 0x61, 0x6e, 0x76, 0x2e
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVMONTHNAME2[] = { /* "févr." */
+ 0x66, 0xe9, 0x76, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVMONTHNAME3[] = { /* "mars" */
+ 0x6d, 0x61, 0x72, 0x73
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVMONTHNAME4[] = { /* "avr." */
+ 0x61, 0x76, 0x72, 0x2e
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVMONTHNAME5[] = { /* "mai" */
+ 0x6d, 0x61, 0x69
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVMONTHNAME6[] = { /* "juin" */
+ 0x6a, 0x75, 0x69, 0x6e
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVMONTHNAME7[] = { /* "juil." */
+ 0x6a, 0x75, 0x69, 0x6c, 0x2e
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVMONTHNAME8[] = { /* "août" */
+ 0x61, 0x6f, 0xfb, 0x74
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVMONTHNAME9[] = { /* "sept." */
+ 0x73, 0x65, 0x70, 0x74, 0x2e
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVMONTHNAME10[] = { /* "oct." */
+ 0x6f, 0x63, 0x74, 0x2e
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVMONTHNAME11[] = { /* "nov." */
+ 0x6e, 0x6f, 0x76, 0x2e
+};
+
+static BYTE NLSALLOC(100c) rgbSABBREVMONTHNAME12[] = { /* "déc." */
+ 0x64, 0xe9, 0x63, 0x2e
+};
+
+static BYTE NLSALLOC(100c) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(100c) rgbIPOSSIGNPOSN[] = { /* "4" */
+ 0x34
+};
+
+static BYTE NLSALLOC(100c) rgbINEGSIGNPOSN[] = { /* "4" */
+ 0x34
+};
+
+static BYTE NLSALLOC(100c) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(100c) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(100c) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(100c) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(100c) rgbSENGCOUNTRY[] = { /* "Switzerland" */
+ 0x53, 0x77, 0x69, 0x74, 0x7a, 0x65, 0x72, 0x6c
+ , 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(100c) rgbSENGLANGUAGE[] = { /* "French" */
+ 0x46, 0x72, 0x65, 0x6e, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(100c) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(100c) rgbIFIRSTWEEKOFYEAR[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(100c) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(100c) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(100c) rgbSTIMEFORMAT[] = { /* "HH:mm:ss" */
+ 0x48, 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(100c) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(100c) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(100c) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(100c) g_rglcinfo100c[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 12, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 8, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 11, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 6, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 0, NULL } /* STHOUSAND */
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 3, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 0, NULL } /* SMONTHOUSANDSEP */
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 18, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 5, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 8, rgbSDAYNAME3 }
+ , { 5, rgbSDAYNAME4 }
+ , { 8, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 8, rgbSDAYNAME7 }
+ , { 4, rgbSABBREVDAYNAME1 }
+ , { 4, rgbSABBREVDAYNAME2 }
+ , { 4, rgbSABBREVDAYNAME3 }
+ , { 4, rgbSABBREVDAYNAME4 }
+ , { 4, rgbSABBREVDAYNAME5 }
+ , { 4, rgbSABBREVDAYNAME6 }
+ , { 4, rgbSABBREVDAYNAME7 }
+ , { 7, rgbSMONTHNAME1 }
+ , { 7, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 7, rgbSMONTHNAME7 }
+ , { 4, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 5, rgbSABBREVMONTHNAME1 }
+ , { 5, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 4, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 4, rgbSABBREVMONTHNAME6 }
+ , { 5, rgbSABBREVMONTHNAME7 }
+ , { 4, rgbSABBREVMONTHNAME8 }
+ , { 5, rgbSABBREVMONTHNAME9 }
+ , { 4, rgbSABBREVMONTHNAME10 }
+ , { 4, rgbSABBREVMONTHNAME11 }
+ , { 4, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 11, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 8, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(100c) g_strinfo100c = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/1401.c b/private/oleauto/src/dispatch/win16/1401.c
new file mode 100644
index 000000000..6607c108b
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/1401.c
@@ -0,0 +1,528 @@
+/****************************************************************************
+* 1401.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Arabic - Algeria
+*
+* LCID = 0x1401
+*
+* CodePage = 1256
+*
+* Generated: Thu Dec 01 18:30:05 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0401[256]; // from 0401:Arabic - Saudi Arabia
+extern EXPANSION rgexp_0401[3];
+extern WORD rgwCType12_0401[256];
+extern WORD rgwCType3_0401[256];
+extern BYTE rgbUCase_0401[256];
+extern BYTE rgbLCase_0401[256];
+
+static BYTE NLSALLOC(1401) rgbILANGUAGE[] = { /* "1401" */
+ 0x31, 0x34, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(1401) rgbSLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVLANGNAME[] = { /* "ARG" */
+ 0x41, 0x52, 0x47
+};
+
+static BYTE NLSALLOC(1401) rgbSNATIVELANGNAME[] = { /* "\x0627\x0644\x0639\x0631\x0628\x064a\x0629" */
+ 0xc7, 0xe1, 0xda, 0xd1, 0xc8, 0xed, 0xc9
+};
+
+static BYTE NLSALLOC(1401) rgbICOUNTRY[] = { /* "213" */
+ 0x32, 0x31, 0x33
+};
+
+static BYTE NLSALLOC(1401) rgbSCOUNTRY[] = { /* "Algeria" */
+ 0x41, 0x6c, 0x67, 0x65, 0x72, 0x69, 0x61
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVCTRYNAME[] = { /* "DZA" */
+ 0x44, 0x5a, 0x41
+};
+
+static BYTE NLSALLOC(1401) rgbSNATIVECTRYNAME[] = { /* "\x0627\x0644\x062c\x0632\x0627\x0626\x0631" */
+ 0xc7, 0xe1, 0xcc, 0xd2, 0xc7, 0xc6, 0xd1
+};
+
+static BYTE NLSALLOC(1401) rgbIDEFAULTLANGUAGE[] = { /* "1401" */
+ 0x31, 0x34, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(1401) rgbIDEFAULTCOUNTRY[] = { /* "213" */
+ 0x32, 0x31, 0x33
+};
+
+static BYTE NLSALLOC(1401) rgbIDEFAULTCODEPAGE[] = { /* "708" */
+ 0x37, 0x30, 0x38
+};
+
+static BYTE NLSALLOC(1401) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(1401) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1401) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(1401) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(1401) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(1401) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1401) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1401) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(1401) rgbSCURRENCY[] = { /* "\x062f.\x062c.\x200f" */
+ 0xcf, 0x2e, 0xcc, 0x2e, 0xfe
+};
+
+static BYTE NLSALLOC(1401) rgbSINTLSYMBOL[] = { /* "DZD" */
+ 0x44, 0x5a, 0x44
+};
+
+static BYTE NLSALLOC(1401) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(1401) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(1401) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(1401) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1401) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1401) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1401) rgbINEGCURR[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(1401) rgbSDATE[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(1401) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(1401) rgbSSHORTDATE[] = { /* "dd-MM-yy" */
+ 0x64, 0x64, 0x2d, 0x4d, 0x4d, 0x2d, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(1401) rgbSLONGDATE[] = { /* "dd-MM-yyyy" */
+ 0x64, 0x64, 0x2d, 0x4d, 0x4d, 0x2d, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(1401) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1401) rgbILDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1401) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1401) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1401) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1401) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1401) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1401) rgbS1159[] = { /* "\x0635" */
+ 0xd5
+};
+
+static BYTE NLSALLOC(1401) rgbS2359[] = { /* "\x0645" */
+ 0xe3
+};
+
+static BYTE NLSALLOC(1401) rgbSDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(1401) rgbSDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(1401) rgbSDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(1401) rgbSDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(1401) rgbSDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(1401) rgbSDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(1401) rgbSDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(1401) rgbSMONTHNAME1[] = { /* "\x062c\x0627\x0646\x0641\x064a" */
+ 0xcc, 0xc7, 0xe4, 0xdd, 0xed
+};
+
+static BYTE NLSALLOC(1401) rgbSMONTHNAME2[] = { /* "\x0641\x064a\x0641\x0631\x064a" */
+ 0xdd, 0xed, 0xdd, 0xd1, 0xed
+};
+
+static BYTE NLSALLOC(1401) rgbSMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(1401) rgbSMONTHNAME4[] = { /* "\x0627\x0641\x0631\x064a\x0644" */
+ 0xc7, 0xdd, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(1401) rgbSMONTHNAME5[] = { /* "\x0645\x0627\x064a" */
+ 0xe3, 0xc7, 0xed
+};
+
+static BYTE NLSALLOC(1401) rgbSMONTHNAME6[] = { /* "\x062c\x0648\x0627\x0646" */
+ 0xcc, 0xe6, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(1401) rgbSMONTHNAME7[] = { /* "\x062c\x0648\x064a\x0644\x064a\x0647" */
+ 0xcc, 0xe6, 0xed, 0xe1, 0xed, 0xe5
+};
+
+static BYTE NLSALLOC(1401) rgbSMONTHNAME8[] = { /* "\x0623\x0648\x062a" */
+ 0xc3, 0xe6, 0xca
+};
+
+static BYTE NLSALLOC(1401) rgbSMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1401) rgbSMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1401) rgbSMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1401) rgbSMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVMONTHNAME1[] = { /* "\x062c\x0627\x0646\x0641\x064a" */
+ 0xcc, 0xc7, 0xe4, 0xdd, 0xed
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVMONTHNAME2[] = { /* "\x0641\x064a\x0641\x0631\x064a" */
+ 0xdd, 0xed, 0xdd, 0xd1, 0xed
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVMONTHNAME4[] = { /* "\x0627\x0641\x0631\x064a\x0644" */
+ 0xc7, 0xdd, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVMONTHNAME5[] = { /* "\x0645\x0627\x064a" */
+ 0xe3, 0xc7, 0xed
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVMONTHNAME6[] = { /* "\x062c\x0648\x0627\x0646" */
+ 0xcc, 0xe6, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVMONTHNAME7[] = { /* "\x062c\x0648\x064a\x0644\x064a\x0647" */
+ 0xcc, 0xe6, 0xed, 0xe1, 0xed, 0xe5
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVMONTHNAME8[] = { /* "\x0623\x0648\x062a" */
+ 0xc3, 0xe6, 0xca
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1401) rgbSABBREVMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1401) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(1401) rgbIPOSSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1401) rgbINEGSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1401) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1401) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1401) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1401) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1401) rgbSENGCOUNTRY[] = { /* "Algeria" */
+ 0x41, 0x6c, 0x67, 0x65, 0x72, 0x69, 0x61
+};
+
+static BYTE NLSALLOC(1401) rgbSENGLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(1401) rgbIFIRSTDAYOFWEEK[] = { /* "5" */
+ 0x35
+};
+
+static BYTE NLSALLOC(1401) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1401) rgbIDEFAULTANSICODEPAGE[] = { /* "1256" */
+ 0x31, 0x32, 0x35, 0x36
+};
+
+static BYTE NLSALLOC(1401) rgbINEGNUMBER[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(1401) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(1401) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1401) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1401) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(1401) g_rglcinfo1401[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 7, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 7, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 5, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 10, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 1, rgbS1159 }
+ , { 1, rgbS2359 }
+ , { 5, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 7, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 8, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 5, rgbSABBREVDAYNAME1 }
+ , { 5, rgbSABBREVDAYNAME2 }
+ , { 7, rgbSABBREVDAYNAME3 }
+ , { 8, rgbSABBREVDAYNAME4 }
+ , { 8, rgbSABBREVDAYNAME5 }
+ , { 6, rgbSABBREVDAYNAME6 }
+ , { 6, rgbSABBREVDAYNAME7 }
+ , { 5, rgbSMONTHNAME1 }
+ , { 5, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 6, rgbSMONTHNAME7 }
+ , { 3, rgbSMONTHNAME8 }
+ , { 6, rgbSMONTHNAME9 }
+ , { 6, rgbSMONTHNAME10 }
+ , { 6, rgbSMONTHNAME11 }
+ , { 6, rgbSMONTHNAME12 }
+ , { 5, rgbSABBREVMONTHNAME1 }
+ , { 5, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 5, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 4, rgbSABBREVMONTHNAME6 }
+ , { 6, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 6, rgbSABBREVMONTHNAME9 }
+ , { 6, rgbSABBREVMONTHNAME10 }
+ , { 6, rgbSABBREVMONTHNAME11 }
+ , { 6, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 7, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(1401) g_strinfo1401 = {
+ rgbUCase_0401
+ , rgbLCase_0401
+ , rgwCType12_0401
+ , rgwCType3_0401
+ , rgwSort_0401
+ , rgexp_0401
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/1409.c b/private/oleauto/src/dispatch/win16/1409.c
new file mode 100644
index 000000000..642564187
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/1409.c
@@ -0,0 +1,528 @@
+/****************************************************************************
+* 1409.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* English - New Zealand
+*
+* LCID = 0x1409
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:48:25 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0409[256]; // from 0409:English - United States
+extern EXPANSION rgexp_0409[7];
+extern WORD rgwCType12_0409[256];
+extern WORD rgwCType3_0409[256];
+extern BYTE rgbUCase_0409[256];
+extern BYTE rgbLCase_0409[256];
+
+static BYTE NLSALLOC(1409) rgbILANGUAGE[] = { /* "1409" */
+ 0x31, 0x34, 0x30, 0x39
+};
+
+static BYTE NLSALLOC(1409) rgbSLANGUAGE[] = { /* "New Zealand English" */
+ 0x4e, 0x65, 0x77, 0x20, 0x5a, 0x65, 0x61, 0x6c
+ , 0x61, 0x6e, 0x64, 0x20, 0x45, 0x6e, 0x67, 0x6c
+ , 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVLANGNAME[] = { /* "ENZ" */
+ 0x45, 0x4e, 0x5a
+};
+
+static BYTE NLSALLOC(1409) rgbSNATIVELANGNAME[] = { /* "English" */
+ 0x45, 0x6e, 0x67, 0x6c, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(1409) rgbICOUNTRY[] = { /* "64" */
+ 0x36, 0x34
+};
+
+static BYTE NLSALLOC(1409) rgbSCOUNTRY[] = { /* "New Zealand" */
+ 0x4e, 0x65, 0x77, 0x20, 0x5a, 0x65, 0x61, 0x6c
+ , 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVCTRYNAME[] = { /* "NZL" */
+ 0x4e, 0x5a, 0x4c
+};
+
+static BYTE NLSALLOC(1409) rgbSNATIVECTRYNAME[] = { /* "New Zealand" */
+ 0x4e, 0x65, 0x77, 0x20, 0x5a, 0x65, 0x61, 0x6c
+ , 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(1409) rgbIDEFAULTLANGUAGE[] = { /* "1409" */
+ 0x31, 0x34, 0x30, 0x39
+};
+
+static BYTE NLSALLOC(1409) rgbIDEFAULTCOUNTRY[] = { /* "64" */
+ 0x36, 0x34
+};
+
+static BYTE NLSALLOC(1409) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(1409) rgbSLIST[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(1409) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1409) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(1409) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(1409) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(1409) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1409) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1409) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(1409) rgbSCURRENCY[] = { /* "$" */
+ 0x24
+};
+
+static BYTE NLSALLOC(1409) rgbSINTLSYMBOL[] = { /* "NZD" */
+ 0x4e, 0x5a, 0x44
+};
+
+static BYTE NLSALLOC(1409) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(1409) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(1409) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(1409) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1409) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1409) rgbICURRENCY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1409) rgbINEGCURR[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1409) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(1409) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(1409) rgbSSHORTDATE[] = { /* "d/MM/yy" */
+ 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(1409) rgbSLONGDATE[] = { /* "dddd, d MMMM yyyy" */
+ 0x64, 0x64, 0x64, 0x64, 0x2c, 0x20, 0x64, 0x20
+ , 0x4d, 0x4d, 0x4d, 0x4d, 0x20, 0x79, 0x79, 0x79
+ , 0x79
+};
+
+static BYTE NLSALLOC(1409) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1409) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1409) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1409) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1409) rgbITLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1409) rgbIDAYLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1409) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1409) rgbSDAYNAME1[] = { /* "Monday" */
+ 0x4d, 0x6f, 0x6e, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1409) rgbSDAYNAME2[] = { /* "Tuesday" */
+ 0x54, 0x75, 0x65, 0x73, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1409) rgbSDAYNAME3[] = { /* "Wednesday" */
+ 0x57, 0x65, 0x64, 0x6e, 0x65, 0x73, 0x64, 0x61
+ , 0x79
+};
+
+static BYTE NLSALLOC(1409) rgbSDAYNAME4[] = { /* "Thursday" */
+ 0x54, 0x68, 0x75, 0x72, 0x73, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1409) rgbSDAYNAME5[] = { /* "Friday" */
+ 0x46, 0x72, 0x69, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1409) rgbSDAYNAME6[] = { /* "Saturday" */
+ 0x53, 0x61, 0x74, 0x75, 0x72, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1409) rgbSDAYNAME7[] = { /* "Sunday" */
+ 0x53, 0x75, 0x6e, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVDAYNAME1[] = { /* "Mon" */
+ 0x4d, 0x6f, 0x6e
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVDAYNAME2[] = { /* "Tue" */
+ 0x54, 0x75, 0x65
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVDAYNAME3[] = { /* "Wed" */
+ 0x57, 0x65, 0x64
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVDAYNAME4[] = { /* "Thu" */
+ 0x54, 0x68, 0x75
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVDAYNAME5[] = { /* "Fri" */
+ 0x46, 0x72, 0x69
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVDAYNAME6[] = { /* "Sat" */
+ 0x53, 0x61, 0x74
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVDAYNAME7[] = { /* "Sun" */
+ 0x53, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(1409) rgbSMONTHNAME1[] = { /* "January" */
+ 0x4a, 0x61, 0x6e, 0x75, 0x61, 0x72, 0x79
+};
+
+static BYTE NLSALLOC(1409) rgbSMONTHNAME2[] = { /* "February" */
+ 0x46, 0x65, 0x62, 0x72, 0x75, 0x61, 0x72, 0x79
+};
+
+static BYTE NLSALLOC(1409) rgbSMONTHNAME3[] = { /* "March" */
+ 0x4d, 0x61, 0x72, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(1409) rgbSMONTHNAME4[] = { /* "April" */
+ 0x41, 0x70, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(1409) rgbSMONTHNAME5[] = { /* "May" */
+ 0x4d, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1409) rgbSMONTHNAME6[] = { /* "June" */
+ 0x4a, 0x75, 0x6e, 0x65
+};
+
+static BYTE NLSALLOC(1409) rgbSMONTHNAME7[] = { /* "July" */
+ 0x4a, 0x75, 0x6c, 0x79
+};
+
+static BYTE NLSALLOC(1409) rgbSMONTHNAME8[] = { /* "August" */
+ 0x41, 0x75, 0x67, 0x75, 0x73, 0x74
+};
+
+static BYTE NLSALLOC(1409) rgbSMONTHNAME9[] = { /* "September" */
+ 0x53, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x65
+ , 0x72
+};
+
+static BYTE NLSALLOC(1409) rgbSMONTHNAME10[] = { /* "October" */
+ 0x4f, 0x63, 0x74, 0x6f, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(1409) rgbSMONTHNAME11[] = { /* "November" */
+ 0x4e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(1409) rgbSMONTHNAME12[] = { /* "December" */
+ 0x44, 0x65, 0x63, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVMONTHNAME1[] = { /* "Jan" */
+ 0x4a, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVMONTHNAME2[] = { /* "Feb" */
+ 0x46, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVMONTHNAME3[] = { /* "Mar" */
+ 0x4d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVMONTHNAME4[] = { /* "Apr" */
+ 0x41, 0x70, 0x72
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVMONTHNAME5[] = { /* "May" */
+ 0x4d, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVMONTHNAME6[] = { /* "Jun" */
+ 0x4a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVMONTHNAME7[] = { /* "Jul" */
+ 0x4a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVMONTHNAME8[] = { /* "Aug" */
+ 0x41, 0x75, 0x67
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVMONTHNAME9[] = { /* "Sep" */
+ 0x53, 0x65, 0x70
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVMONTHNAME10[] = { /* "Oct" */
+ 0x4f, 0x63, 0x74
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVMONTHNAME11[] = { /* "Nov" */
+ 0x4e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(1409) rgbSABBREVMONTHNAME12[] = { /* "Dec" */
+ 0x44, 0x65, 0x63
+};
+
+static BYTE NLSALLOC(1409) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(1409) rgbIPOSSIGNPOSN[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(1409) rgbINEGSIGNPOSN[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(1409) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1409) rgbIPOSSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1409) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1409) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1409) rgbSENGCOUNTRY[] = { /* "New Zealand" */
+ 0x4e, 0x65, 0x77, 0x20, 0x5a, 0x65, 0x61, 0x6c
+ , 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(1409) rgbSENGLANGUAGE[] = { /* "English" */
+ 0x45, 0x6e, 0x67, 0x6c, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(1409) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1409) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1409) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(1409) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1409) rgbSTIMEFORMAT[] = { /* "HH:mm:ss" */
+ 0x48, 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(1409) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1409) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1409) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(1409) g_rglcinfo1409[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 19, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 2, rgbICOUNTRY }
+ , { 11, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 11, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 2, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 1, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 7, rgbSSHORTDATE }
+ , { 17, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 6, rgbSDAYNAME1 }
+ , { 7, rgbSDAYNAME2 }
+ , { 9, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 6, rgbSDAYNAME5 }
+ , { 8, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 3, rgbSABBREVDAYNAME1 }
+ , { 3, rgbSABBREVDAYNAME2 }
+ , { 3, rgbSABBREVDAYNAME3 }
+ , { 3, rgbSABBREVDAYNAME4 }
+ , { 3, rgbSABBREVDAYNAME5 }
+ , { 3, rgbSABBREVDAYNAME6 }
+ , { 3, rgbSABBREVDAYNAME7 }
+ , { 7, rgbSMONTHNAME1 }
+ , { 8, rgbSMONTHNAME2 }
+ , { 5, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 11, rgbSENGCOUNTRY }
+ , { 7, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 8, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(1409) g_strinfo1409 = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/1801.c b/private/oleauto/src/dispatch/win16/1801.c
new file mode 100644
index 000000000..9d0009641
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/1801.c
@@ -0,0 +1,521 @@
+/****************************************************************************
+* 1801.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Arabic - Morocco
+*
+* LCID = 0x1801
+*
+* CodePage = 1256
+*
+* Generated: Thu Dec 01 18:31:09 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0401[256]; // from 0401:Arabic - Saudi Arabia
+extern EXPANSION rgexp_0401[3];
+extern WORD rgwCType12_0401[256];
+extern WORD rgwCType3_0401[256];
+extern BYTE rgbUCase_0401[256];
+extern BYTE rgbLCase_0401[256];
+
+static BYTE NLSALLOC(1801) rgbILANGUAGE[] = { /* "1801" */
+ 0x31, 0x38, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(1801) rgbSLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVLANGNAME[] = { /* "ARM" */
+ 0x41, 0x52, 0x4d
+};
+
+static BYTE NLSALLOC(1801) rgbSNATIVELANGNAME[] = { /* "\x0627\x0644\x0639\x0631\x0628\x064a\x0629" */
+ 0xc7, 0xe1, 0xda, 0xd1, 0xc8, 0xed, 0xc9
+};
+
+static BYTE NLSALLOC(1801) rgbICOUNTRY[] = { /* "212" */
+ 0x32, 0x31, 0x32
+};
+
+static BYTE NLSALLOC(1801) rgbSCOUNTRY[] = { /* "Morocco" */
+ 0x4d, 0x6f, 0x72, 0x6f, 0x63, 0x63, 0x6f
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVCTRYNAME[] = { /* "MAR" */
+ 0x4d, 0x41, 0x52
+};
+
+static BYTE NLSALLOC(1801) rgbSNATIVECTRYNAME[] = { /* "\x0627\x0644\x0645\x0645\x0644\x0643\x0629 \x0627\x0644\x0645\x063a\x0631\x0628\x064a\x0629" */
+ 0xc7, 0xe1, 0xe3, 0xe3, 0xe1, 0xdf, 0xc9, 0x20
+ , 0xc7, 0xe1, 0xe3, 0xdb, 0xd1, 0xc8, 0xed, 0xc9
+};
+
+static BYTE NLSALLOC(1801) rgbIDEFAULTLANGUAGE[] = { /* "1801" */
+ 0x31, 0x38, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(1801) rgbIDEFAULTCOUNTRY[] = { /* "212" */
+ 0x32, 0x31, 0x32
+};
+
+static BYTE NLSALLOC(1801) rgbIDEFAULTCODEPAGE[] = { /* "708" */
+ 0x37, 0x30, 0x38
+};
+
+static BYTE NLSALLOC(1801) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(1801) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1801) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(1801) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(1801) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(1801) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1801) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1801) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(1801) rgbSCURRENCY[] = { /* "\x062f.\x0645." */
+ 0xcf, 0x2e, 0xe3, 0x2e
+};
+
+static BYTE NLSALLOC(1801) rgbSINTLSYMBOL[] = { /* "MAD" */
+ 0x4d, 0x41, 0x44
+};
+
+static BYTE NLSALLOC(1801) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(1801) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(1801) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(1801) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1801) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1801) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1801) rgbINEGCURR[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(1801) rgbSDATE[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(1801) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(1801) rgbSSHORTDATE[] = { /* "dd-MM-yy" */
+ 0x64, 0x64, 0x2d, 0x4d, 0x4d, 0x2d, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(1801) rgbSLONGDATE[] = { /* "dd-MM-yyyy" */
+ 0x64, 0x64, 0x2d, 0x4d, 0x4d, 0x2d, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(1801) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1801) rgbILDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1801) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1801) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1801) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1801) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1801) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1801) rgbSDAYNAME1[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(1801) rgbSDAYNAME2[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(1801) rgbSDAYNAME3[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(1801) rgbSDAYNAME4[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(1801) rgbSDAYNAME5[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(1801) rgbSDAYNAME6[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(1801) rgbSDAYNAME7[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVDAYNAME1[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVDAYNAME2[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVDAYNAME3[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVDAYNAME4[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVDAYNAME5[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVDAYNAME6[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVDAYNAME7[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(1801) rgbSMONTHNAME1[] = { /* "\x064a\x0646\x0627\x064a\x0631" */
+ 0xed, 0xe4, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(1801) rgbSMONTHNAME2[] = { /* "\x0641\x0628\x0631\x0627\x064a\x0631" */
+ 0xdd, 0xc8, 0xd1, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(1801) rgbSMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(1801) rgbSMONTHNAME4[] = { /* "\x0627\x0628\x0631\x064a\x0644" */
+ 0xc7, 0xc8, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(1801) rgbSMONTHNAME5[] = { /* "\x0645\x0627\x064a\x0648" */
+ 0xe3, 0xc7, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(1801) rgbSMONTHNAME6[] = { /* "\x064a\x0648\x0646\x064a\x0648" */
+ 0xed, 0xe6, 0xe4, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(1801) rgbSMONTHNAME7[] = { /* "\x064a\x0648\x0644\x064a\x0648" */
+ 0xed, 0xe6, 0xe1, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(1801) rgbSMONTHNAME8[] = { /* "\x063a\x0634\x062a" */
+ 0xdb, 0xd4, 0xca
+};
+
+static BYTE NLSALLOC(1801) rgbSMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1801) rgbSMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1801) rgbSMONTHNAME11[] = { /* "\x0646\x0648\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1801) rgbSMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVMONTHNAME1[] = { /* "\x064a\x0646\x0627\x064a\x0631" */
+ 0xed, 0xe4, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVMONTHNAME2[] = { /* "\x0641\x0628\x0631\x0627\x064a\x0631" */
+ 0xdd, 0xc8, 0xd1, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVMONTHNAME4[] = { /* "\x0627\x0628\x0631\x064a\x0644" */
+ 0xc7, 0xc8, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVMONTHNAME5[] = { /* "\x0645\x0627\x064a\x0648" */
+ 0xe3, 0xc7, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVMONTHNAME6[] = { /* "\x064a\x0648\x0646\x064a\x0648" */
+ 0xed, 0xe6, 0xe4, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVMONTHNAME7[] = { /* "\x064a\x0648\x0644\x064a\x0648" */
+ 0xed, 0xe6, 0xe1, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVMONTHNAME8[] = { /* "\x063a\x0634\x062a" */
+ 0xdb, 0xd4, 0xca
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVMONTHNAME11[] = { /* "\x0646\x0648\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1801) rgbSABBREVMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1801) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(1801) rgbIPOSSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1801) rgbINEGSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1801) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1801) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1801) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1801) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1801) rgbSENGCOUNTRY[] = { /* "Morocco" */
+ 0x4d, 0x6f, 0x72, 0x6f, 0x63, 0x63, 0x6f
+};
+
+static BYTE NLSALLOC(1801) rgbSENGLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(1801) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1801) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1801) rgbIDEFAULTANSICODEPAGE[] = { /* "1256" */
+ 0x31, 0x32, 0x35, 0x36
+};
+
+static BYTE NLSALLOC(1801) rgbINEGNUMBER[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(1801) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(1801) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1801) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1801) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(1801) g_rglcinfo1801[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 7, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 16, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 4, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 10, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 7, rgbSDAYNAME1 }
+ , { 8, rgbSDAYNAME2 }
+ , { 8, rgbSDAYNAME3 }
+ , { 6, rgbSDAYNAME4 }
+ , { 6, rgbSDAYNAME5 }
+ , { 5, rgbSDAYNAME6 }
+ , { 5, rgbSDAYNAME7 }
+ , { 7, rgbSABBREVDAYNAME1 }
+ , { 8, rgbSABBREVDAYNAME2 }
+ , { 8, rgbSABBREVDAYNAME3 }
+ , { 6, rgbSABBREVDAYNAME4 }
+ , { 6, rgbSABBREVDAYNAME5 }
+ , { 5, rgbSABBREVDAYNAME6 }
+ , { 5, rgbSABBREVDAYNAME7 }
+ , { 5, rgbSMONTHNAME1 }
+ , { 6, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 4, rgbSMONTHNAME5 }
+ , { 5, rgbSMONTHNAME6 }
+ , { 5, rgbSMONTHNAME7 }
+ , { 3, rgbSMONTHNAME8 }
+ , { 6, rgbSMONTHNAME9 }
+ , { 6, rgbSMONTHNAME10 }
+ , { 5, rgbSMONTHNAME11 }
+ , { 6, rgbSMONTHNAME12 }
+ , { 5, rgbSABBREVMONTHNAME1 }
+ , { 6, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 5, rgbSABBREVMONTHNAME4 }
+ , { 4, rgbSABBREVMONTHNAME5 }
+ , { 5, rgbSABBREVMONTHNAME6 }
+ , { 5, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 6, rgbSABBREVMONTHNAME9 }
+ , { 6, rgbSABBREVMONTHNAME10 }
+ , { 5, rgbSABBREVMONTHNAME11 }
+ , { 6, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 7, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(1801) g_strinfo1801 = {
+ rgbUCase_0401
+ , rgbLCase_0401
+ , rgwCType12_0401
+ , rgwCType3_0401
+ , rgwSort_0401
+ , rgexp_0401
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/1809.c b/private/oleauto/src/dispatch/win16/1809.c
new file mode 100644
index 000000000..14913074e
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/1809.c
@@ -0,0 +1,523 @@
+/****************************************************************************
+* 1809.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* English - Ireland
+*
+* LCID = 0x1809
+*
+* CodePage = 1252
+*
+* Generated: Thu Dec 01 17:49:44 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0409[256]; // from 0409:English - United States
+extern EXPANSION rgexp_0409[7];
+extern WORD rgwCType12_0409[256];
+extern WORD rgwCType3_0409[256];
+extern BYTE rgbUCase_0409[256];
+extern BYTE rgbLCase_0409[256];
+
+static BYTE NLSALLOC(1809) rgbILANGUAGE[] = { /* "1809" */
+ 0x31, 0x38, 0x30, 0x39
+};
+
+static BYTE NLSALLOC(1809) rgbSLANGUAGE[] = { /* "Irish English" */
+ 0x49, 0x72, 0x69, 0x73, 0x68, 0x20, 0x45, 0x6e
+ , 0x67, 0x6c, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVLANGNAME[] = { /* "ENI" */
+ 0x45, 0x4e, 0x49
+};
+
+static BYTE NLSALLOC(1809) rgbSNATIVELANGNAME[] = { /* "English" */
+ 0x45, 0x6e, 0x67, 0x6c, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(1809) rgbICOUNTRY[] = { /* "353" */
+ 0x33, 0x35, 0x33
+};
+
+static BYTE NLSALLOC(1809) rgbSCOUNTRY[] = { /* "Ireland" */
+ 0x49, 0x72, 0x65, 0x6c, 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVCTRYNAME[] = { /* "IRL" */
+ 0x49, 0x52, 0x4c
+};
+
+static BYTE NLSALLOC(1809) rgbSNATIVECTRYNAME[] = { /* "Eire" */
+ 0x45, 0x69, 0x72, 0x65
+};
+
+static BYTE NLSALLOC(1809) rgbIDEFAULTLANGUAGE[] = { /* "1809" */
+ 0x31, 0x38, 0x30, 0x39
+};
+
+static BYTE NLSALLOC(1809) rgbIDEFAULTCOUNTRY[] = { /* "353" */
+ 0x33, 0x35, 0x33
+};
+
+static BYTE NLSALLOC(1809) rgbIDEFAULTCODEPAGE[] = { /* "850" */
+ 0x38, 0x35, 0x30
+};
+
+static BYTE NLSALLOC(1809) rgbSLIST[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(1809) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1809) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(1809) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(1809) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(1809) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1809) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1809) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(1809) rgbSCURRENCY[] = { /* "IR£" */
+ 0x49, 0x52, 0xa3
+};
+
+static BYTE NLSALLOC(1809) rgbSINTLSYMBOL[] = { /* "IEP" */
+ 0x49, 0x45, 0x50
+};
+
+static BYTE NLSALLOC(1809) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(1809) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(1809) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(1809) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1809) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1809) rgbICURRENCY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1809) rgbINEGCURR[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1809) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(1809) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(1809) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(1809) rgbSLONGDATE[] = { /* "dd MMMM yyyy" */
+ 0x64, 0x64, 0x20, 0x4d, 0x4d, 0x4d, 0x4d, 0x20
+ , 0x79, 0x79, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(1809) rgbIDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1809) rgbILDATE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1809) rgbITIME[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1809) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1809) rgbITLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1809) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1809) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1809) rgbSDAYNAME1[] = { /* "Monday" */
+ 0x4d, 0x6f, 0x6e, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1809) rgbSDAYNAME2[] = { /* "Tuesday" */
+ 0x54, 0x75, 0x65, 0x73, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1809) rgbSDAYNAME3[] = { /* "Wednesday" */
+ 0x57, 0x65, 0x64, 0x6e, 0x65, 0x73, 0x64, 0x61
+ , 0x79
+};
+
+static BYTE NLSALLOC(1809) rgbSDAYNAME4[] = { /* "Thursday" */
+ 0x54, 0x68, 0x75, 0x72, 0x73, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1809) rgbSDAYNAME5[] = { /* "Friday" */
+ 0x46, 0x72, 0x69, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1809) rgbSDAYNAME6[] = { /* "Saturday" */
+ 0x53, 0x61, 0x74, 0x75, 0x72, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1809) rgbSDAYNAME7[] = { /* "Sunday" */
+ 0x53, 0x75, 0x6e, 0x64, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVDAYNAME1[] = { /* "Mon" */
+ 0x4d, 0x6f, 0x6e
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVDAYNAME2[] = { /* "Tue" */
+ 0x54, 0x75, 0x65
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVDAYNAME3[] = { /* "Wed" */
+ 0x57, 0x65, 0x64
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVDAYNAME4[] = { /* "Thu" */
+ 0x54, 0x68, 0x75
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVDAYNAME5[] = { /* "Fri" */
+ 0x46, 0x72, 0x69
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVDAYNAME6[] = { /* "Sat" */
+ 0x53, 0x61, 0x74
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVDAYNAME7[] = { /* "Sun" */
+ 0x53, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(1809) rgbSMONTHNAME1[] = { /* "January" */
+ 0x4a, 0x61, 0x6e, 0x75, 0x61, 0x72, 0x79
+};
+
+static BYTE NLSALLOC(1809) rgbSMONTHNAME2[] = { /* "February" */
+ 0x46, 0x65, 0x62, 0x72, 0x75, 0x61, 0x72, 0x79
+};
+
+static BYTE NLSALLOC(1809) rgbSMONTHNAME3[] = { /* "March" */
+ 0x4d, 0x61, 0x72, 0x63, 0x68
+};
+
+static BYTE NLSALLOC(1809) rgbSMONTHNAME4[] = { /* "April" */
+ 0x41, 0x70, 0x72, 0x69, 0x6c
+};
+
+static BYTE NLSALLOC(1809) rgbSMONTHNAME5[] = { /* "May" */
+ 0x4d, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1809) rgbSMONTHNAME6[] = { /* "June" */
+ 0x4a, 0x75, 0x6e, 0x65
+};
+
+static BYTE NLSALLOC(1809) rgbSMONTHNAME7[] = { /* "July" */
+ 0x4a, 0x75, 0x6c, 0x79
+};
+
+static BYTE NLSALLOC(1809) rgbSMONTHNAME8[] = { /* "August" */
+ 0x41, 0x75, 0x67, 0x75, 0x73, 0x74
+};
+
+static BYTE NLSALLOC(1809) rgbSMONTHNAME9[] = { /* "September" */
+ 0x53, 0x65, 0x70, 0x74, 0x65, 0x6d, 0x62, 0x65
+ , 0x72
+};
+
+static BYTE NLSALLOC(1809) rgbSMONTHNAME10[] = { /* "October" */
+ 0x4f, 0x63, 0x74, 0x6f, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(1809) rgbSMONTHNAME11[] = { /* "November" */
+ 0x4e, 0x6f, 0x76, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(1809) rgbSMONTHNAME12[] = { /* "December" */
+ 0x44, 0x65, 0x63, 0x65, 0x6d, 0x62, 0x65, 0x72
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVMONTHNAME1[] = { /* "Jan" */
+ 0x4a, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVMONTHNAME2[] = { /* "Feb" */
+ 0x46, 0x65, 0x62
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVMONTHNAME3[] = { /* "Mar" */
+ 0x4d, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVMONTHNAME4[] = { /* "Apr" */
+ 0x41, 0x70, 0x72
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVMONTHNAME5[] = { /* "May" */
+ 0x4d, 0x61, 0x79
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVMONTHNAME6[] = { /* "Jun" */
+ 0x4a, 0x75, 0x6e
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVMONTHNAME7[] = { /* "Jul" */
+ 0x4a, 0x75, 0x6c
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVMONTHNAME8[] = { /* "Aug" */
+ 0x41, 0x75, 0x67
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVMONTHNAME9[] = { /* "Sep" */
+ 0x53, 0x65, 0x70
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVMONTHNAME10[] = { /* "Oct" */
+ 0x4f, 0x63, 0x74
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVMONTHNAME11[] = { /* "Nov" */
+ 0x4e, 0x6f, 0x76
+};
+
+static BYTE NLSALLOC(1809) rgbSABBREVMONTHNAME12[] = { /* "Dec" */
+ 0x44, 0x65, 0x63
+};
+
+static BYTE NLSALLOC(1809) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(1809) rgbIPOSSIGNPOSN[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(1809) rgbINEGSIGNPOSN[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(1809) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1809) rgbIPOSSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1809) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1809) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1809) rgbSENGCOUNTRY[] = { /* "Ireland" */
+ 0x49, 0x72, 0x65, 0x6c, 0x61, 0x6e, 0x64
+};
+
+static BYTE NLSALLOC(1809) rgbSENGLANGUAGE[] = { /* "English" */
+ 0x45, 0x6e, 0x67, 0x6c, 0x69, 0x73, 0x68
+};
+
+static BYTE NLSALLOC(1809) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1809) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1809) rgbIDEFAULTANSICODEPAGE[] = { /* "1252" */
+ 0x31, 0x32, 0x35, 0x32
+};
+
+static BYTE NLSALLOC(1809) rgbINEGNUMBER[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1809) rgbSTIMEFORMAT[] = { /* "HH:mm:ss" */
+ 0x48, 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(1809) rgbITIMEMARKPOSN[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1809) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1809) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(1809) g_rglcinfo1809[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 13, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 7, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 4, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 3, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 12, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 6, rgbSDAYNAME1 }
+ , { 7, rgbSDAYNAME2 }
+ , { 9, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 6, rgbSDAYNAME5 }
+ , { 8, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 3, rgbSABBREVDAYNAME1 }
+ , { 3, rgbSABBREVDAYNAME2 }
+ , { 3, rgbSABBREVDAYNAME3 }
+ , { 3, rgbSABBREVDAYNAME4 }
+ , { 3, rgbSABBREVDAYNAME5 }
+ , { 3, rgbSABBREVDAYNAME6 }
+ , { 3, rgbSABBREVDAYNAME7 }
+ , { 7, rgbSMONTHNAME1 }
+ , { 8, rgbSMONTHNAME2 }
+ , { 5, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 6, rgbSMONTHNAME8 }
+ , { 9, rgbSMONTHNAME9 }
+ , { 7, rgbSMONTHNAME10 }
+ , { 8, rgbSMONTHNAME11 }
+ , { 8, rgbSMONTHNAME12 }
+ , { 3, rgbSABBREVMONTHNAME1 }
+ , { 3, rgbSABBREVMONTHNAME2 }
+ , { 3, rgbSABBREVMONTHNAME3 }
+ , { 3, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 3, rgbSABBREVMONTHNAME6 }
+ , { 3, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 3, rgbSABBREVMONTHNAME9 }
+ , { 3, rgbSABBREVMONTHNAME10 }
+ , { 3, rgbSABBREVMONTHNAME11 }
+ , { 3, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 7, rgbSENGCOUNTRY }
+ , { 7, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 8, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(1809) g_strinfo1809 = {
+ rgbUCase_0409
+ , rgbLCase_0409
+ , rgwCType12_0409
+ , rgwCType3_0409
+ , rgwSort_0409
+ , rgexp_0409
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/1c01.c b/private/oleauto/src/dispatch/win16/1c01.c
new file mode 100644
index 000000000..a0bb5d519
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/1c01.c
@@ -0,0 +1,520 @@
+/****************************************************************************
+* 1c01.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Arabic - Tunisia
+*
+* LCID = 0x1c01
+*
+* CodePage = 1256
+*
+* Generated: Thu Dec 01 18:32:04 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0401[256]; // from 0401:Arabic - Saudi Arabia
+extern EXPANSION rgexp_0401[3];
+extern WORD rgwCType12_0401[256];
+extern WORD rgwCType3_0401[256];
+extern BYTE rgbUCase_0401[256];
+extern BYTE rgbLCase_0401[256];
+
+static BYTE NLSALLOC(1c01) rgbILANGUAGE[] = { /* "1c01" */
+ 0x31, 0x63, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(1c01) rgbSLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVLANGNAME[] = { /* "ART" */
+ 0x41, 0x52, 0x54
+};
+
+static BYTE NLSALLOC(1c01) rgbSNATIVELANGNAME[] = { /* "\x0627\x0644\x0639\x0631\x0628\x064a\x0629" */
+ 0xc7, 0xe1, 0xda, 0xd1, 0xc8, 0xed, 0xc9
+};
+
+static BYTE NLSALLOC(1c01) rgbICOUNTRY[] = { /* "216" */
+ 0x32, 0x31, 0x36
+};
+
+static BYTE NLSALLOC(1c01) rgbSCOUNTRY[] = { /* "Tunisia" */
+ 0x54, 0x75, 0x6e, 0x69, 0x73, 0x69, 0x61
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVCTRYNAME[] = { /* "TUN" */
+ 0x54, 0x55, 0x4e
+};
+
+static BYTE NLSALLOC(1c01) rgbSNATIVECTRYNAME[] = { /* "\x062a\x0648\x0646\x0633" */
+ 0xca, 0xe6, 0xe4, 0xd3
+};
+
+static BYTE NLSALLOC(1c01) rgbIDEFAULTLANGUAGE[] = { /* "1c01" */
+ 0x31, 0x63, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(1c01) rgbIDEFAULTCOUNTRY[] = { /* "216" */
+ 0x32, 0x31, 0x36
+};
+
+static BYTE NLSALLOC(1c01) rgbIDEFAULTCODEPAGE[] = { /* "708" */
+ 0x37, 0x30, 0x38
+};
+
+static BYTE NLSALLOC(1c01) rgbSLIST[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(1c01) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1c01) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(1c01) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(1c01) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(1c01) rgbIDIGITS[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(1c01) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1c01) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(1c01) rgbSCURRENCY[] = { /* "\x062f.\x062a.\x200f" */
+ 0xcf, 0x2e, 0xca, 0x2e, 0xfe
+};
+
+static BYTE NLSALLOC(1c01) rgbSINTLSYMBOL[] = { /* "TND" */
+ 0x54, 0x4e, 0x44
+};
+
+static BYTE NLSALLOC(1c01) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(1c01) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(1c01) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(1c01) rgbICURRDIGITS[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(1c01) rgbIINTLCURRDIGITS[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(1c01) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1c01) rgbINEGCURR[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(1c01) rgbSDATE[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(1c01) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(1c01) rgbSSHORTDATE[] = { /* "dd-MM-yy" */
+ 0x64, 0x64, 0x2d, 0x4d, 0x4d, 0x2d, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(1c01) rgbSLONGDATE[] = { /* "dd-MM-yyyy" */
+ 0x64, 0x64, 0x2d, 0x4d, 0x4d, 0x2d, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(1c01) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1c01) rgbILDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1c01) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1c01) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1c01) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1c01) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1c01) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1c01) rgbSDAYNAME1[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(1c01) rgbSDAYNAME2[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(1c01) rgbSDAYNAME3[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(1c01) rgbSDAYNAME4[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(1c01) rgbSDAYNAME5[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(1c01) rgbSDAYNAME6[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(1c01) rgbSDAYNAME7[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVDAYNAME1[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVDAYNAME2[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVDAYNAME3[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVDAYNAME4[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVDAYNAME5[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVDAYNAME6[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVDAYNAME7[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(1c01) rgbSMONTHNAME1[] = { /* "\x062c\x0627\x0646\x0641\x064a" */
+ 0xcc, 0xc7, 0xe4, 0xdd, 0xed
+};
+
+static BYTE NLSALLOC(1c01) rgbSMONTHNAME2[] = { /* "\x0641\x064a\x0641\x0631\x064a" */
+ 0xdd, 0xed, 0xdd, 0xd1, 0xed
+};
+
+static BYTE NLSALLOC(1c01) rgbSMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(1c01) rgbSMONTHNAME4[] = { /* "\x0627\x0641\x0631\x064a\x0644" */
+ 0xc7, 0xdd, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(1c01) rgbSMONTHNAME5[] = { /* "\x0645\x0627\x064a" */
+ 0xe3, 0xc7, 0xed
+};
+
+static BYTE NLSALLOC(1c01) rgbSMONTHNAME6[] = { /* "\x062c\x0648\x0627\x0646" */
+ 0xcc, 0xe6, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(1c01) rgbSMONTHNAME7[] = { /* "\x062c\x0648\x064a\x0644\x064a\x0647" */
+ 0xcc, 0xe6, 0xed, 0xe1, 0xed, 0xe5
+};
+
+static BYTE NLSALLOC(1c01) rgbSMONTHNAME8[] = { /* "\x0623\x0648\x062a" */
+ 0xc3, 0xe6, 0xca
+};
+
+static BYTE NLSALLOC(1c01) rgbSMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1c01) rgbSMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1c01) rgbSMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1c01) rgbSMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVMONTHNAME1[] = { /* "\x062c\x0627\x0646\x0641\x064a" */
+ 0xcc, 0xc7, 0xe4, 0xdd, 0xed
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVMONTHNAME2[] = { /* "\x0641\x064a\x0641\x0631\x064a" */
+ 0xdd, 0xed, 0xdd, 0xd1, 0xed
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVMONTHNAME4[] = { /* "\x0627\x0641\x0631\x064a\x0644" */
+ 0xc7, 0xdd, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVMONTHNAME5[] = { /* "\x0645\x0627\x064a" */
+ 0xe3, 0xc7, 0xed
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVMONTHNAME6[] = { /* "\x062c\x0648\x0627\x0646" */
+ 0xcc, 0xe6, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVMONTHNAME7[] = { /* "\x062c\x0648\x064a\x0644\x064a\x0647" */
+ 0xcc, 0xe6, 0xed, 0xe1, 0xed, 0xe5
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVMONTHNAME8[] = { /* "\x0623\x0648\x062a" */
+ 0xc3, 0xe6, 0xca
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1c01) rgbSABBREVMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(1c01) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(1c01) rgbIPOSSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1c01) rgbINEGSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(1c01) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1c01) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1c01) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1c01) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1c01) rgbSENGCOUNTRY[] = { /* "Tunisia" */
+ 0x54, 0x75, 0x6e, 0x69, 0x73, 0x69, 0x61
+};
+
+static BYTE NLSALLOC(1c01) rgbSENGLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(1c01) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1c01) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(1c01) rgbIDEFAULTANSICODEPAGE[] = { /* "1256" */
+ 0x31, 0x32, 0x35, 0x36
+};
+
+static BYTE NLSALLOC(1c01) rgbINEGNUMBER[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(1c01) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(1c01) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1c01) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(1c01) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(1c01) g_rglcinfo1c01[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 7, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 4, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 5, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 10, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 0, NULL } /* S1159 */
+ , { 0, NULL } /* S2359 */
+ , { 7, rgbSDAYNAME1 }
+ , { 8, rgbSDAYNAME2 }
+ , { 8, rgbSDAYNAME3 }
+ , { 6, rgbSDAYNAME4 }
+ , { 6, rgbSDAYNAME5 }
+ , { 5, rgbSDAYNAME6 }
+ , { 5, rgbSDAYNAME7 }
+ , { 7, rgbSABBREVDAYNAME1 }
+ , { 8, rgbSABBREVDAYNAME2 }
+ , { 8, rgbSABBREVDAYNAME3 }
+ , { 6, rgbSABBREVDAYNAME4 }
+ , { 6, rgbSABBREVDAYNAME5 }
+ , { 5, rgbSABBREVDAYNAME6 }
+ , { 5, rgbSABBREVDAYNAME7 }
+ , { 5, rgbSMONTHNAME1 }
+ , { 5, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 3, rgbSMONTHNAME5 }
+ , { 4, rgbSMONTHNAME6 }
+ , { 6, rgbSMONTHNAME7 }
+ , { 3, rgbSMONTHNAME8 }
+ , { 6, rgbSMONTHNAME9 }
+ , { 6, rgbSMONTHNAME10 }
+ , { 6, rgbSMONTHNAME11 }
+ , { 6, rgbSMONTHNAME12 }
+ , { 5, rgbSABBREVMONTHNAME1 }
+ , { 5, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 5, rgbSABBREVMONTHNAME4 }
+ , { 3, rgbSABBREVMONTHNAME5 }
+ , { 4, rgbSABBREVMONTHNAME6 }
+ , { 6, rgbSABBREVMONTHNAME7 }
+ , { 3, rgbSABBREVMONTHNAME8 }
+ , { 6, rgbSABBREVMONTHNAME9 }
+ , { 6, rgbSABBREVMONTHNAME10 }
+ , { 6, rgbSABBREVMONTHNAME11 }
+ , { 6, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 7, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(1c01) g_strinfo1c01 = {
+ rgbUCase_0401
+ , rgbLCase_0401
+ , rgwCType12_0401
+ , rgwCType3_0401
+ , rgwSort_0401
+ , rgexp_0401
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/2001.c b/private/oleauto/src/dispatch/win16/2001.c
new file mode 100644
index 000000000..c88b1d265
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/2001.c
@@ -0,0 +1,528 @@
+/****************************************************************************
+* 2001.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Arabic - Oman
+*
+* LCID = 0x2001
+*
+* CodePage = 1256
+*
+* Generated: Thu Dec 01 18:32:57 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0401[256]; // from 0401:Arabic - Saudi Arabia
+extern EXPANSION rgexp_0401[3];
+extern WORD rgwCType12_0401[256];
+extern WORD rgwCType3_0401[256];
+extern BYTE rgbUCase_0401[256];
+extern BYTE rgbLCase_0401[256];
+
+static BYTE NLSALLOC(2001) rgbILANGUAGE[] = { /* "2001" */
+ 0x32, 0x30, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(2001) rgbSLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVLANGNAME[] = { /* "ARO" */
+ 0x41, 0x52, 0x4f
+};
+
+static BYTE NLSALLOC(2001) rgbSNATIVELANGNAME[] = { /* "\x0627\x0644\x0639\x0631\x0628\x064a\x0629" */
+ 0xc7, 0xe1, 0xda, 0xd1, 0xc8, 0xed, 0xc9
+};
+
+static BYTE NLSALLOC(2001) rgbICOUNTRY[] = { /* "968" */
+ 0x39, 0x36, 0x38
+};
+
+static BYTE NLSALLOC(2001) rgbSCOUNTRY[] = { /* "Oman" */
+ 0x4f, 0x6d, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVCTRYNAME[] = { /* "OMN" */
+ 0x4f, 0x4d, 0x4e
+};
+
+static BYTE NLSALLOC(2001) rgbSNATIVECTRYNAME[] = { /* "\x0639\x0645\x0627\x0646" */
+ 0xda, 0xe3, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(2001) rgbIDEFAULTLANGUAGE[] = { /* "2001" */
+ 0x32, 0x30, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(2001) rgbIDEFAULTCOUNTRY[] = { /* "968" */
+ 0x39, 0x36, 0x38
+};
+
+static BYTE NLSALLOC(2001) rgbIDEFAULTCODEPAGE[] = { /* "708" */
+ 0x37, 0x30, 0x38
+};
+
+static BYTE NLSALLOC(2001) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(2001) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2001) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(2001) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(2001) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(2001) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2001) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2001) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(2001) rgbSCURRENCY[] = { /* "\x0631.\x0639.\x200f" */
+ 0xd1, 0x2e, 0xda, 0x2e, 0xfe
+};
+
+static BYTE NLSALLOC(2001) rgbSINTLSYMBOL[] = { /* "OMR" */
+ 0x4f, 0x4d, 0x52
+};
+
+static BYTE NLSALLOC(2001) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(2001) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(2001) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(2001) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2001) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2001) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2001) rgbINEGCURR[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(2001) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(2001) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(2001) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(2001) rgbSLONGDATE[] = { /* "dd/MM/yyyy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(2001) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2001) rgbILDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2001) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2001) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2001) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2001) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2001) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2001) rgbS1159[] = { /* "\x0635" */
+ 0xd5
+};
+
+static BYTE NLSALLOC(2001) rgbS2359[] = { /* "\x0645" */
+ 0xe3
+};
+
+static BYTE NLSALLOC(2001) rgbSDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(2001) rgbSDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(2001) rgbSDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(2001) rgbSDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(2001) rgbSDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(2001) rgbSDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(2001) rgbSDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(2001) rgbSMONTHNAME1[] = { /* "\x064a\x0646\x0627\x064a\x0631" */
+ 0xed, 0xe4, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(2001) rgbSMONTHNAME2[] = { /* "\x0641\x0628\x0631\x0627\x064a\x0631" */
+ 0xdd, 0xc8, 0xd1, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(2001) rgbSMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(2001) rgbSMONTHNAME4[] = { /* "\x0627\x0628\x0631\x064a\x0644" */
+ 0xc7, 0xc8, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(2001) rgbSMONTHNAME5[] = { /* "\x0645\x0627\x064a\x0648" */
+ 0xe3, 0xc7, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(2001) rgbSMONTHNAME6[] = { /* "\x064a\x0648\x0646\x064a\x0648" */
+ 0xed, 0xe6, 0xe4, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(2001) rgbSMONTHNAME7[] = { /* "\x064a\x0648\x0644\x064a\x0648" */
+ 0xed, 0xe6, 0xe1, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(2001) rgbSMONTHNAME8[] = { /* "\x0623\x063a\x0633\x0637\x0633" */
+ 0xc3, 0xdb, 0xd3, 0xd8, 0xd3
+};
+
+static BYTE NLSALLOC(2001) rgbSMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(2001) rgbSMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(2001) rgbSMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(2001) rgbSMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVMONTHNAME1[] = { /* "\x064a\x0646\x0627\x064a\x0631" */
+ 0xed, 0xe4, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVMONTHNAME2[] = { /* "\x0641\x0628\x0631\x0627\x064a\x0631" */
+ 0xdd, 0xc8, 0xd1, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVMONTHNAME4[] = { /* "\x0627\x0628\x0631\x064a\x0644" */
+ 0xc7, 0xc8, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVMONTHNAME5[] = { /* "\x0645\x0627\x064a\x0648" */
+ 0xe3, 0xc7, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVMONTHNAME6[] = { /* "\x064a\x0648\x0646\x064a\x0648" */
+ 0xed, 0xe6, 0xe4, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVMONTHNAME7[] = { /* "\x064a\x0648\x0644\x064a\x0648" */
+ 0xed, 0xe6, 0xe1, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVMONTHNAME8[] = { /* "\x0623\x063a\x0633\x0637\x0633" */
+ 0xc3, 0xdb, 0xd3, 0xd8, 0xd3
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(2001) rgbSABBREVMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(2001) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(2001) rgbIPOSSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2001) rgbINEGSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2001) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2001) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2001) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2001) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2001) rgbSENGCOUNTRY[] = { /* "Oman" */
+ 0x4f, 0x6d, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(2001) rgbSENGLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(2001) rgbIFIRSTDAYOFWEEK[] = { /* "5" */
+ 0x35
+};
+
+static BYTE NLSALLOC(2001) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2001) rgbIDEFAULTANSICODEPAGE[] = { /* "1256" */
+ 0x31, 0x32, 0x35, 0x36
+};
+
+static BYTE NLSALLOC(2001) rgbINEGNUMBER[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(2001) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(2001) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2001) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2001) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(2001) g_rglcinfo2001[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 4, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 4, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 5, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 10, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 1, rgbS1159 }
+ , { 1, rgbS2359 }
+ , { 5, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 7, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 8, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 5, rgbSABBREVDAYNAME1 }
+ , { 5, rgbSABBREVDAYNAME2 }
+ , { 7, rgbSABBREVDAYNAME3 }
+ , { 8, rgbSABBREVDAYNAME4 }
+ , { 8, rgbSABBREVDAYNAME5 }
+ , { 6, rgbSABBREVDAYNAME6 }
+ , { 6, rgbSABBREVDAYNAME7 }
+ , { 5, rgbSMONTHNAME1 }
+ , { 6, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 4, rgbSMONTHNAME5 }
+ , { 5, rgbSMONTHNAME6 }
+ , { 5, rgbSMONTHNAME7 }
+ , { 5, rgbSMONTHNAME8 }
+ , { 6, rgbSMONTHNAME9 }
+ , { 6, rgbSMONTHNAME10 }
+ , { 6, rgbSMONTHNAME11 }
+ , { 6, rgbSMONTHNAME12 }
+ , { 5, rgbSABBREVMONTHNAME1 }
+ , { 6, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 5, rgbSABBREVMONTHNAME4 }
+ , { 4, rgbSABBREVMONTHNAME5 }
+ , { 5, rgbSABBREVMONTHNAME6 }
+ , { 5, rgbSABBREVMONTHNAME7 }
+ , { 5, rgbSABBREVMONTHNAME8 }
+ , { 6, rgbSABBREVMONTHNAME9 }
+ , { 6, rgbSABBREVMONTHNAME10 }
+ , { 6, rgbSABBREVMONTHNAME11 }
+ , { 6, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 4, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(2001) g_strinfo2001 = {
+ rgbUCase_0401
+ , rgbLCase_0401
+ , rgwCType12_0401
+ , rgwCType3_0401
+ , rgwSort_0401
+ , rgexp_0401
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/2401.c b/private/oleauto/src/dispatch/win16/2401.c
new file mode 100644
index 000000000..cb1dfae48
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/2401.c
@@ -0,0 +1,528 @@
+/****************************************************************************
+* 2401.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Arabic - Yemen
+*
+* LCID = 0x2401
+*
+* CodePage = 1256
+*
+* Generated: Thu Dec 01 18:33:50 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0401[256]; // from 0401:Arabic - Saudi Arabia
+extern EXPANSION rgexp_0401[3];
+extern WORD rgwCType12_0401[256];
+extern WORD rgwCType3_0401[256];
+extern BYTE rgbUCase_0401[256];
+extern BYTE rgbLCase_0401[256];
+
+static BYTE NLSALLOC(2401) rgbILANGUAGE[] = { /* "2401" */
+ 0x32, 0x34, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(2401) rgbSLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVLANGNAME[] = { /* "ARY" */
+ 0x41, 0x52, 0x59
+};
+
+static BYTE NLSALLOC(2401) rgbSNATIVELANGNAME[] = { /* "\x0627\x0644\x0639\x0631\x0628\x064a\x0629" */
+ 0xc7, 0xe1, 0xda, 0xd1, 0xc8, 0xed, 0xc9
+};
+
+static BYTE NLSALLOC(2401) rgbICOUNTRY[] = { /* "967" */
+ 0x39, 0x36, 0x37
+};
+
+static BYTE NLSALLOC(2401) rgbSCOUNTRY[] = { /* "Yemen" */
+ 0x59, 0x65, 0x6d, 0x65, 0x6e
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVCTRYNAME[] = { /* "YEM" */
+ 0x59, 0x45, 0x4d
+};
+
+static BYTE NLSALLOC(2401) rgbSNATIVECTRYNAME[] = { /* "\x0627\x0644\x064a\x0645\x0646" */
+ 0xc7, 0xe1, 0xed, 0xe3, 0xe4
+};
+
+static BYTE NLSALLOC(2401) rgbIDEFAULTLANGUAGE[] = { /* "2401" */
+ 0x32, 0x34, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(2401) rgbIDEFAULTCOUNTRY[] = { /* "967" */
+ 0x39, 0x36, 0x37
+};
+
+static BYTE NLSALLOC(2401) rgbIDEFAULTCODEPAGE[] = { /* "708" */
+ 0x37, 0x30, 0x38
+};
+
+static BYTE NLSALLOC(2401) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(2401) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2401) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(2401) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(2401) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(2401) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2401) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2401) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(2401) rgbSCURRENCY[] = { /* "\x0631.\x064a.\x200f" */
+ 0xd1, 0x2e, 0xed, 0x2e, 0xfe
+};
+
+static BYTE NLSALLOC(2401) rgbSINTLSYMBOL[] = { /* "YER" */
+ 0x59, 0x45, 0x52
+};
+
+static BYTE NLSALLOC(2401) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(2401) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(2401) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(2401) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2401) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2401) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2401) rgbINEGCURR[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(2401) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(2401) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(2401) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(2401) rgbSLONGDATE[] = { /* "dd/MM/yyyy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(2401) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2401) rgbILDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2401) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2401) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2401) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2401) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2401) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2401) rgbS1159[] = { /* "\x0635" */
+ 0xd5
+};
+
+static BYTE NLSALLOC(2401) rgbS2359[] = { /* "\x0645" */
+ 0xe3
+};
+
+static BYTE NLSALLOC(2401) rgbSDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(2401) rgbSDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(2401) rgbSDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(2401) rgbSDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(2401) rgbSDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(2401) rgbSDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(2401) rgbSDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(2401) rgbSMONTHNAME1[] = { /* "\x064a\x0646\x0627\x064a\x0631" */
+ 0xed, 0xe4, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(2401) rgbSMONTHNAME2[] = { /* "\x0641\x0628\x0631\x0627\x064a\x0631" */
+ 0xdd, 0xc8, 0xd1, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(2401) rgbSMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(2401) rgbSMONTHNAME4[] = { /* "\x0627\x0628\x0631\x064a\x0644" */
+ 0xc7, 0xc8, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(2401) rgbSMONTHNAME5[] = { /* "\x0645\x0627\x064a\x0648" */
+ 0xe3, 0xc7, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(2401) rgbSMONTHNAME6[] = { /* "\x064a\x0648\x0646\x064a\x0648" */
+ 0xed, 0xe6, 0xe4, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(2401) rgbSMONTHNAME7[] = { /* "\x064a\x0648\x0644\x064a\x0648" */
+ 0xed, 0xe6, 0xe1, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(2401) rgbSMONTHNAME8[] = { /* "\x0623\x063a\x0633\x0637\x0633" */
+ 0xc3, 0xdb, 0xd3, 0xd8, 0xd3
+};
+
+static BYTE NLSALLOC(2401) rgbSMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(2401) rgbSMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(2401) rgbSMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(2401) rgbSMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVMONTHNAME1[] = { /* "\x064a\x0646\x0627\x064a\x0631" */
+ 0xed, 0xe4, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVMONTHNAME2[] = { /* "\x0641\x0628\x0631\x0627\x064a\x0631" */
+ 0xdd, 0xc8, 0xd1, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVMONTHNAME4[] = { /* "\x0627\x0628\x0631\x064a\x0644" */
+ 0xc7, 0xc8, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVMONTHNAME5[] = { /* "\x0645\x0627\x064a\x0648" */
+ 0xe3, 0xc7, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVMONTHNAME6[] = { /* "\x064a\x0648\x0646\x064a\x0648" */
+ 0xed, 0xe6, 0xe4, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVMONTHNAME7[] = { /* "\x064a\x0648\x0644\x064a\x0648" */
+ 0xed, 0xe6, 0xe1, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVMONTHNAME8[] = { /* "\x0623\x063a\x0633\x0637\x0633" */
+ 0xc3, 0xdb, 0xd3, 0xd8, 0xd3
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(2401) rgbSABBREVMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(2401) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(2401) rgbIPOSSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2401) rgbINEGSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2401) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2401) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2401) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2401) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2401) rgbSENGCOUNTRY[] = { /* "Yemen" */
+ 0x59, 0x65, 0x6d, 0x65, 0x6e
+};
+
+static BYTE NLSALLOC(2401) rgbSENGLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(2401) rgbIFIRSTDAYOFWEEK[] = { /* "5" */
+ 0x35
+};
+
+static BYTE NLSALLOC(2401) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2401) rgbIDEFAULTANSICODEPAGE[] = { /* "1256" */
+ 0x31, 0x32, 0x35, 0x36
+};
+
+static BYTE NLSALLOC(2401) rgbINEGNUMBER[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(2401) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(2401) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2401) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2401) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(2401) g_rglcinfo2401[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 5, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 5, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 5, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 10, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 1, rgbS1159 }
+ , { 1, rgbS2359 }
+ , { 5, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 7, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 8, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 5, rgbSABBREVDAYNAME1 }
+ , { 5, rgbSABBREVDAYNAME2 }
+ , { 7, rgbSABBREVDAYNAME3 }
+ , { 8, rgbSABBREVDAYNAME4 }
+ , { 8, rgbSABBREVDAYNAME5 }
+ , { 6, rgbSABBREVDAYNAME6 }
+ , { 6, rgbSABBREVDAYNAME7 }
+ , { 5, rgbSMONTHNAME1 }
+ , { 6, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 4, rgbSMONTHNAME5 }
+ , { 5, rgbSMONTHNAME6 }
+ , { 5, rgbSMONTHNAME7 }
+ , { 5, rgbSMONTHNAME8 }
+ , { 6, rgbSMONTHNAME9 }
+ , { 6, rgbSMONTHNAME10 }
+ , { 6, rgbSMONTHNAME11 }
+ , { 6, rgbSMONTHNAME12 }
+ , { 5, rgbSABBREVMONTHNAME1 }
+ , { 6, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 5, rgbSABBREVMONTHNAME4 }
+ , { 4, rgbSABBREVMONTHNAME5 }
+ , { 5, rgbSABBREVMONTHNAME6 }
+ , { 5, rgbSABBREVMONTHNAME7 }
+ , { 5, rgbSABBREVMONTHNAME8 }
+ , { 6, rgbSABBREVMONTHNAME9 }
+ , { 6, rgbSABBREVMONTHNAME10 }
+ , { 6, rgbSABBREVMONTHNAME11 }
+ , { 6, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 5, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(2401) g_strinfo2401 = {
+ rgbUCase_0401
+ , rgbLCase_0401
+ , rgwCType12_0401
+ , rgwCType3_0401
+ , rgwSort_0401
+ , rgexp_0401
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/2801.c b/private/oleauto/src/dispatch/win16/2801.c
new file mode 100644
index 000000000..caa3f8c21
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/2801.c
@@ -0,0 +1,536 @@
+/****************************************************************************
+* 2801.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Arabic - Syria
+*
+* LCID = 0x2801
+*
+* CodePage = 1256
+*
+* Generated: Thu Dec 01 18:34:45 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0401[256]; // from 0401:Arabic - Saudi Arabia
+extern EXPANSION rgexp_0401[3];
+extern WORD rgwCType12_0401[256];
+extern WORD rgwCType3_0401[256];
+extern BYTE rgbUCase_0401[256];
+extern BYTE rgbLCase_0401[256];
+
+static BYTE NLSALLOC(2801) rgbILANGUAGE[] = { /* "2801" */
+ 0x32, 0x38, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(2801) rgbSLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVLANGNAME[] = { /* "ARS" */
+ 0x41, 0x52, 0x53
+};
+
+static BYTE NLSALLOC(2801) rgbSNATIVELANGNAME[] = { /* "\x0627\x0644\x0639\x0631\x0628\x064a\x0629" */
+ 0xc7, 0xe1, 0xda, 0xd1, 0xc8, 0xed, 0xc9
+};
+
+static BYTE NLSALLOC(2801) rgbICOUNTRY[] = { /* "963" */
+ 0x39, 0x36, 0x33
+};
+
+static BYTE NLSALLOC(2801) rgbSCOUNTRY[] = { /* "Syria" */
+ 0x53, 0x79, 0x72, 0x69, 0x61
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVCTRYNAME[] = { /* "SYR" */
+ 0x53, 0x59, 0x52
+};
+
+static BYTE NLSALLOC(2801) rgbSNATIVECTRYNAME[] = { /* "\x0633\x0648\x0631\x064a\x0627" */
+ 0xd3, 0xe6, 0xd1, 0xed, 0xc7
+};
+
+static BYTE NLSALLOC(2801) rgbIDEFAULTLANGUAGE[] = { /* "2801" */
+ 0x32, 0x38, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(2801) rgbIDEFAULTCOUNTRY[] = { /* "963" */
+ 0x39, 0x36, 0x33
+};
+
+static BYTE NLSALLOC(2801) rgbIDEFAULTCODEPAGE[] = { /* "708" */
+ 0x37, 0x30, 0x38
+};
+
+static BYTE NLSALLOC(2801) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(2801) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2801) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(2801) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(2801) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(2801) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2801) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2801) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(2801) rgbSCURRENCY[] = { /* "\x0644.\x0633.\x200f" */
+ 0xe1, 0x2e, 0xd3, 0x2e, 0xfe
+};
+
+static BYTE NLSALLOC(2801) rgbSINTLSYMBOL[] = { /* "SYP" */
+ 0x53, 0x59, 0x50
+};
+
+static BYTE NLSALLOC(2801) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(2801) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(2801) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(2801) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2801) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2801) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2801) rgbINEGCURR[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(2801) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(2801) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(2801) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(2801) rgbSLONGDATE[] = { /* "dd/MM/yyyy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(2801) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2801) rgbILDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2801) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2801) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2801) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2801) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2801) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2801) rgbS1159[] = { /* "\x0635" */
+ 0xd5
+};
+
+static BYTE NLSALLOC(2801) rgbS2359[] = { /* "\x0645" */
+ 0xe3
+};
+
+static BYTE NLSALLOC(2801) rgbSDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(2801) rgbSDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(2801) rgbSDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(2801) rgbSDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(2801) rgbSDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(2801) rgbSDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(2801) rgbSDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(2801) rgbSMONTHNAME1[] = { /* "\x0643\x0627\x0646\x0648\x0646 \x0627\x0644\x062b\x0627\x0646\x064a" */
+ 0xdf, 0xc7, 0xe4, 0xe6, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xcb, 0xc7, 0xe4, 0xed
+};
+
+static BYTE NLSALLOC(2801) rgbSMONTHNAME2[] = { /* "\x0634\x0628\x0627\x0637" */
+ 0xd4, 0xc8, 0xc7, 0xd8
+};
+
+static BYTE NLSALLOC(2801) rgbSMONTHNAME3[] = { /* "\x0622\x0630\x0627\x0631" */
+ 0xc2, 0xd0, 0xc7, 0xd1
+};
+
+static BYTE NLSALLOC(2801) rgbSMONTHNAME4[] = { /* "\x0646\x064a\x0633\x0627\x0646" */
+ 0xe4, 0xed, 0xd3, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(2801) rgbSMONTHNAME5[] = { /* "\x0623\x064a\x0627\x0631" */
+ 0xc3, 0xed, 0xc7, 0xd1
+};
+
+static BYTE NLSALLOC(2801) rgbSMONTHNAME6[] = { /* "\x062d\x0632\x064a\x0631\x0627\x0646" */
+ 0xcd, 0xd2, 0xed, 0xd1, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(2801) rgbSMONTHNAME7[] = { /* "\x062a\x0645\x0648\x0632" */
+ 0xca, 0xe3, 0xe6, 0xd2
+};
+
+static BYTE NLSALLOC(2801) rgbSMONTHNAME8[] = { /* "\x0622\x0628" */
+ 0xc2, 0xc8
+};
+
+static BYTE NLSALLOC(2801) rgbSMONTHNAME9[] = { /* "\x0623\x064a\x0644\x0648\x0644" */
+ 0xc3, 0xed, 0xe1, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(2801) rgbSMONTHNAME10[] = { /* "\x062a\x0634\x0631\x064a\x0646 \x0627\x0644\x0623\x0648\x0644" */
+ 0xca, 0xd4, 0xd1, 0xed, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xc3, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(2801) rgbSMONTHNAME11[] = { /* "\x062a\x0634\x0631\x064a\x0646 \x0627\x0644\x062b\x0627\x0646\x064a" */
+ 0xca, 0xd4, 0xd1, 0xed, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xcb, 0xc7, 0xe4, 0xed
+};
+
+static BYTE NLSALLOC(2801) rgbSMONTHNAME12[] = { /* "\x0643\x0627\x0646\x0648\x0646 \x0627\x0644\x0623\x0648\x0644" */
+ 0xdf, 0xc7, 0xe4, 0xe6, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xc3, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVMONTHNAME1[] = { /* "\x0643\x0627\x0646\x0648\x0646 \x0627\x0644\x062b\x0627\x0646\x064a" */
+ 0xdf, 0xc7, 0xe4, 0xe6, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xcb, 0xc7, 0xe4, 0xed
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVMONTHNAME2[] = { /* "\x0634\x0628\x0627\x0637" */
+ 0xd4, 0xc8, 0xc7, 0xd8
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVMONTHNAME3[] = { /* "\x0622\x0630\x0627\x0631" */
+ 0xc2, 0xd0, 0xc7, 0xd1
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVMONTHNAME4[] = { /* "\x0646\x064a\x0633\x0627\x0646" */
+ 0xe4, 0xed, 0xd3, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVMONTHNAME5[] = { /* "\x0623\x064a\x0627\x0631" */
+ 0xc3, 0xed, 0xc7, 0xd1
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVMONTHNAME6[] = { /* "\x062d\x0632\x064a\x0631\x0627\x0646" */
+ 0xcd, 0xd2, 0xed, 0xd1, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVMONTHNAME7[] = { /* "\x062a\x0645\x0648\x0632" */
+ 0xca, 0xe3, 0xe6, 0xd2
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVMONTHNAME8[] = { /* "\x0622\x0628" */
+ 0xc2, 0xc8
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVMONTHNAME9[] = { /* "\x0623\x064a\x0644\x0648\x0644" */
+ 0xc3, 0xed, 0xe1, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVMONTHNAME10[] = { /* "\x062a\x0634\x0631\x064a\x0646 \x0627\x0644\x0623\x0648\x0644" */
+ 0xca, 0xd4, 0xd1, 0xed, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xc3, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVMONTHNAME11[] = { /* "\x062a\x0634\x0631\x064a\x0646 \x0627\x0644\x062b\x0627\x0646\x064a" */
+ 0xca, 0xd4, 0xd1, 0xed, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xcb, 0xc7, 0xe4, 0xed
+};
+
+static BYTE NLSALLOC(2801) rgbSABBREVMONTHNAME12[] = { /* "\x0643\x0627\x0646\x0648\x0646 \x0627\x0644\x0623\x0648\x0644" */
+ 0xdf, 0xc7, 0xe4, 0xe6, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xc3, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(2801) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(2801) rgbIPOSSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2801) rgbINEGSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2801) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2801) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2801) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2801) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2801) rgbSENGCOUNTRY[] = { /* "Syria" */
+ 0x53, 0x79, 0x72, 0x69, 0x61
+};
+
+static BYTE NLSALLOC(2801) rgbSENGLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(2801) rgbIFIRSTDAYOFWEEK[] = { /* "5" */
+ 0x35
+};
+
+static BYTE NLSALLOC(2801) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2801) rgbIDEFAULTANSICODEPAGE[] = { /* "1256" */
+ 0x31, 0x32, 0x35, 0x36
+};
+
+static BYTE NLSALLOC(2801) rgbINEGNUMBER[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(2801) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(2801) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2801) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2801) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(2801) g_rglcinfo2801[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 5, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 5, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 5, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 10, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 1, rgbS1159 }
+ , { 1, rgbS2359 }
+ , { 5, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 7, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 8, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 5, rgbSABBREVDAYNAME1 }
+ , { 5, rgbSABBREVDAYNAME2 }
+ , { 7, rgbSABBREVDAYNAME3 }
+ , { 8, rgbSABBREVDAYNAME4 }
+ , { 8, rgbSABBREVDAYNAME5 }
+ , { 6, rgbSABBREVDAYNAME6 }
+ , { 6, rgbSABBREVDAYNAME7 }
+ , { 12, rgbSMONTHNAME1 }
+ , { 4, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 4, rgbSMONTHNAME5 }
+ , { 6, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 2, rgbSMONTHNAME8 }
+ , { 5, rgbSMONTHNAME9 }
+ , { 11, rgbSMONTHNAME10 }
+ , { 12, rgbSMONTHNAME11 }
+ , { 11, rgbSMONTHNAME12 }
+ , { 12, rgbSABBREVMONTHNAME1 }
+ , { 4, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 5, rgbSABBREVMONTHNAME4 }
+ , { 4, rgbSABBREVMONTHNAME5 }
+ , { 6, rgbSABBREVMONTHNAME6 }
+ , { 4, rgbSABBREVMONTHNAME7 }
+ , { 2, rgbSABBREVMONTHNAME8 }
+ , { 5, rgbSABBREVMONTHNAME9 }
+ , { 11, rgbSABBREVMONTHNAME10 }
+ , { 12, rgbSABBREVMONTHNAME11 }
+ , { 11, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 5, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(2801) g_strinfo2801 = {
+ rgbUCase_0401
+ , rgbLCase_0401
+ , rgwCType12_0401
+ , rgwCType3_0401
+ , rgwSort_0401
+ , rgexp_0401
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/2c01.c b/private/oleauto/src/dispatch/win16/2c01.c
new file mode 100644
index 000000000..973645885
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/2c01.c
@@ -0,0 +1,536 @@
+/****************************************************************************
+* 2c01.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Arabic - Jordan
+*
+* LCID = 0x2c01
+*
+* CodePage = 1256
+*
+* Generated: Thu Dec 01 18:35:38 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0401[256]; // from 0401:Arabic - Saudi Arabia
+extern EXPANSION rgexp_0401[3];
+extern WORD rgwCType12_0401[256];
+extern WORD rgwCType3_0401[256];
+extern BYTE rgbUCase_0401[256];
+extern BYTE rgbLCase_0401[256];
+
+static BYTE NLSALLOC(2c01) rgbILANGUAGE[] = { /* "2c01" */
+ 0x32, 0x63, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(2c01) rgbSLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVLANGNAME[] = { /* "ARJ" */
+ 0x41, 0x52, 0x4a
+};
+
+static BYTE NLSALLOC(2c01) rgbSNATIVELANGNAME[] = { /* "\x0627\x0644\x0639\x0631\x0628\x064a\x0629" */
+ 0xc7, 0xe1, 0xda, 0xd1, 0xc8, 0xed, 0xc9
+};
+
+static BYTE NLSALLOC(2c01) rgbICOUNTRY[] = { /* "962" */
+ 0x39, 0x36, 0x32
+};
+
+static BYTE NLSALLOC(2c01) rgbSCOUNTRY[] = { /* "Jordan" */
+ 0x4a, 0x6f, 0x72, 0x64, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVCTRYNAME[] = { /* "JOR" */
+ 0x4a, 0x4f, 0x52
+};
+
+static BYTE NLSALLOC(2c01) rgbSNATIVECTRYNAME[] = { /* "\x0627\x0644\x0623\x0631\x062f\x0646" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xcf, 0xe4
+};
+
+static BYTE NLSALLOC(2c01) rgbIDEFAULTLANGUAGE[] = { /* "2c01" */
+ 0x32, 0x63, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(2c01) rgbIDEFAULTCOUNTRY[] = { /* "962" */
+ 0x39, 0x36, 0x32
+};
+
+static BYTE NLSALLOC(2c01) rgbIDEFAULTCODEPAGE[] = { /* "708" */
+ 0x37, 0x30, 0x38
+};
+
+static BYTE NLSALLOC(2c01) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(2c01) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2c01) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(2c01) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(2c01) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(2c01) rgbIDIGITS[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(2c01) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2c01) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(2c01) rgbSCURRENCY[] = { /* "\x062f.\x0627.\x200f" */
+ 0xcf, 0x2e, 0xc7, 0x2e, 0xfe
+};
+
+static BYTE NLSALLOC(2c01) rgbSINTLSYMBOL[] = { /* "JOD" */
+ 0x4a, 0x4f, 0x44
+};
+
+static BYTE NLSALLOC(2c01) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(2c01) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(2c01) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(2c01) rgbICURRDIGITS[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(2c01) rgbIINTLCURRDIGITS[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(2c01) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2c01) rgbINEGCURR[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(2c01) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(2c01) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(2c01) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(2c01) rgbSLONGDATE[] = { /* "dd/MM/yyyy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(2c01) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2c01) rgbILDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2c01) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2c01) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2c01) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2c01) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2c01) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2c01) rgbS1159[] = { /* "\x0635" */
+ 0xd5
+};
+
+static BYTE NLSALLOC(2c01) rgbS2359[] = { /* "\x0645" */
+ 0xe3
+};
+
+static BYTE NLSALLOC(2c01) rgbSDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(2c01) rgbSDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(2c01) rgbSDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(2c01) rgbSDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(2c01) rgbSDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(2c01) rgbSDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(2c01) rgbSDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(2c01) rgbSMONTHNAME1[] = { /* "\x0643\x0627\x0646\x0648\x0646 \x0627\x0644\x062b\x0627\x0646\x064a" */
+ 0xdf, 0xc7, 0xe4, 0xe6, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xcb, 0xc7, 0xe4, 0xed
+};
+
+static BYTE NLSALLOC(2c01) rgbSMONTHNAME2[] = { /* "\x0634\x0628\x0627\x0637" */
+ 0xd4, 0xc8, 0xc7, 0xd8
+};
+
+static BYTE NLSALLOC(2c01) rgbSMONTHNAME3[] = { /* "\x0622\x0630\x0627\x0631" */
+ 0xc2, 0xd0, 0xc7, 0xd1
+};
+
+static BYTE NLSALLOC(2c01) rgbSMONTHNAME4[] = { /* "\x0646\x064a\x0633\x0627\x0646" */
+ 0xe4, 0xed, 0xd3, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(2c01) rgbSMONTHNAME5[] = { /* "\x0623\x064a\x0627\x0631" */
+ 0xc3, 0xed, 0xc7, 0xd1
+};
+
+static BYTE NLSALLOC(2c01) rgbSMONTHNAME6[] = { /* "\x062d\x0632\x064a\x0631\x0627\x0646" */
+ 0xcd, 0xd2, 0xed, 0xd1, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(2c01) rgbSMONTHNAME7[] = { /* "\x062a\x0645\x0648\x0632" */
+ 0xca, 0xe3, 0xe6, 0xd2
+};
+
+static BYTE NLSALLOC(2c01) rgbSMONTHNAME8[] = { /* "\x0622\x0628" */
+ 0xc2, 0xc8
+};
+
+static BYTE NLSALLOC(2c01) rgbSMONTHNAME9[] = { /* "\x0623\x064a\x0644\x0648\x0644" */
+ 0xc3, 0xed, 0xe1, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(2c01) rgbSMONTHNAME10[] = { /* "\x062a\x0634\x0631\x064a\x0646 \x0627\x0644\x0623\x0648\x0644" */
+ 0xca, 0xd4, 0xd1, 0xed, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xc3, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(2c01) rgbSMONTHNAME11[] = { /* "\x062a\x0634\x0631\x064a\x0646 \x0627\x0644\x062b\x0627\x0646\x064a" */
+ 0xca, 0xd4, 0xd1, 0xed, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xcb, 0xc7, 0xe4, 0xed
+};
+
+static BYTE NLSALLOC(2c01) rgbSMONTHNAME12[] = { /* "\x0643\x0627\x0646\x0648\x0646 \x0627\x0644\x0623\x0648\x0644" */
+ 0xdf, 0xc7, 0xe4, 0xe6, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xc3, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVMONTHNAME1[] = { /* "\x0643\x0627\x0646\x0648\x0646 \x0627\x0644\x062b\x0627\x0646\x064a" */
+ 0xdf, 0xc7, 0xe4, 0xe6, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xcb, 0xc7, 0xe4, 0xed
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVMONTHNAME2[] = { /* "\x0634\x0628\x0627\x0637" */
+ 0xd4, 0xc8, 0xc7, 0xd8
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVMONTHNAME3[] = { /* "\x0622\x0630\x0627\x0631" */
+ 0xc2, 0xd0, 0xc7, 0xd1
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVMONTHNAME4[] = { /* "\x0646\x064a\x0633\x0627\x0646" */
+ 0xe4, 0xed, 0xd3, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVMONTHNAME5[] = { /* "\x0623\x064a\x0627\x0631" */
+ 0xc3, 0xed, 0xc7, 0xd1
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVMONTHNAME6[] = { /* "\x062d\x0632\x064a\x0631\x0627\x0646" */
+ 0xcd, 0xd2, 0xed, 0xd1, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVMONTHNAME7[] = { /* "\x062a\x0645\x0648\x0632" */
+ 0xca, 0xe3, 0xe6, 0xd2
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVMONTHNAME8[] = { /* "\x0622\x0628" */
+ 0xc2, 0xc8
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVMONTHNAME9[] = { /* "\x0623\x064a\x0644\x0648\x0644" */
+ 0xc3, 0xed, 0xe1, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVMONTHNAME10[] = { /* "\x062a\x0634\x0631\x064a\x0646 \x0627\x0644\x0623\x0648\x0644" */
+ 0xca, 0xd4, 0xd1, 0xed, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xc3, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVMONTHNAME11[] = { /* "\x062a\x0634\x0631\x064a\x0646 \x0627\x0644\x062b\x0627\x0646\x064a" */
+ 0xca, 0xd4, 0xd1, 0xed, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xcb, 0xc7, 0xe4, 0xed
+};
+
+static BYTE NLSALLOC(2c01) rgbSABBREVMONTHNAME12[] = { /* "\x0643\x0627\x0646\x0648\x0646 \x0627\x0644\x0623\x0648\x0644" */
+ 0xdf, 0xc7, 0xe4, 0xe6, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xc3, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(2c01) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(2c01) rgbIPOSSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2c01) rgbINEGSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(2c01) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2c01) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2c01) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2c01) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2c01) rgbSENGCOUNTRY[] = { /* "Jordan" */
+ 0x4a, 0x6f, 0x72, 0x64, 0x61, 0x6e
+};
+
+static BYTE NLSALLOC(2c01) rgbSENGLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(2c01) rgbIFIRSTDAYOFWEEK[] = { /* "5" */
+ 0x35
+};
+
+static BYTE NLSALLOC(2c01) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(2c01) rgbIDEFAULTANSICODEPAGE[] = { /* "1256" */
+ 0x31, 0x32, 0x35, 0x36
+};
+
+static BYTE NLSALLOC(2c01) rgbINEGNUMBER[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(2c01) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(2c01) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2c01) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(2c01) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(2c01) g_rglcinfo2c01[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 6, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 6, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 5, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 10, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 1, rgbS1159 }
+ , { 1, rgbS2359 }
+ , { 5, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 7, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 8, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 5, rgbSABBREVDAYNAME1 }
+ , { 5, rgbSABBREVDAYNAME2 }
+ , { 7, rgbSABBREVDAYNAME3 }
+ , { 8, rgbSABBREVDAYNAME4 }
+ , { 8, rgbSABBREVDAYNAME5 }
+ , { 6, rgbSABBREVDAYNAME6 }
+ , { 6, rgbSABBREVDAYNAME7 }
+ , { 12, rgbSMONTHNAME1 }
+ , { 4, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 4, rgbSMONTHNAME5 }
+ , { 6, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 2, rgbSMONTHNAME8 }
+ , { 5, rgbSMONTHNAME9 }
+ , { 11, rgbSMONTHNAME10 }
+ , { 12, rgbSMONTHNAME11 }
+ , { 11, rgbSMONTHNAME12 }
+ , { 12, rgbSABBREVMONTHNAME1 }
+ , { 4, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 5, rgbSABBREVMONTHNAME4 }
+ , { 4, rgbSABBREVMONTHNAME5 }
+ , { 6, rgbSABBREVMONTHNAME6 }
+ , { 4, rgbSABBREVMONTHNAME7 }
+ , { 2, rgbSABBREVMONTHNAME8 }
+ , { 5, rgbSABBREVMONTHNAME9 }
+ , { 11, rgbSABBREVMONTHNAME10 }
+ , { 12, rgbSABBREVMONTHNAME11 }
+ , { 11, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 6, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(2c01) g_strinfo2c01 = {
+ rgbUCase_0401
+ , rgbLCase_0401
+ , rgwCType12_0401
+ , rgwCType3_0401
+ , rgwSort_0401
+ , rgexp_0401
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/3001.c b/private/oleauto/src/dispatch/win16/3001.c
new file mode 100644
index 000000000..b60a58495
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/3001.c
@@ -0,0 +1,536 @@
+/****************************************************************************
+* 3001.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Arabic - Lebanon
+*
+* LCID = 0x3001
+*
+* CodePage = 1256
+*
+* Generated: Thu Dec 01 18:36:34 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0401[256]; // from 0401:Arabic - Saudi Arabia
+extern EXPANSION rgexp_0401[3];
+extern WORD rgwCType12_0401[256];
+extern WORD rgwCType3_0401[256];
+extern BYTE rgbUCase_0401[256];
+extern BYTE rgbLCase_0401[256];
+
+static BYTE NLSALLOC(3001) rgbILANGUAGE[] = { /* "3001" */
+ 0x33, 0x30, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(3001) rgbSLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVLANGNAME[] = { /* "ARB" */
+ 0x41, 0x52, 0x42
+};
+
+static BYTE NLSALLOC(3001) rgbSNATIVELANGNAME[] = { /* "\x0627\x0644\x0639\x0631\x0628\x064a\x0629" */
+ 0xc7, 0xe1, 0xda, 0xd1, 0xc8, 0xed, 0xc9
+};
+
+static BYTE NLSALLOC(3001) rgbICOUNTRY[] = { /* "961" */
+ 0x39, 0x36, 0x31
+};
+
+static BYTE NLSALLOC(3001) rgbSCOUNTRY[] = { /* "Lebanon" */
+ 0x4c, 0x65, 0x62, 0x61, 0x6e, 0x6f, 0x6e
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVCTRYNAME[] = { /* "LBN" */
+ 0x4c, 0x42, 0x4e
+};
+
+static BYTE NLSALLOC(3001) rgbSNATIVECTRYNAME[] = { /* "\x0644\x0628\x0646\x0627\x0646" */
+ 0xe1, 0xc8, 0xe4, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(3001) rgbIDEFAULTLANGUAGE[] = { /* "3001" */
+ 0x33, 0x30, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(3001) rgbIDEFAULTCOUNTRY[] = { /* "961" */
+ 0x39, 0x36, 0x31
+};
+
+static BYTE NLSALLOC(3001) rgbIDEFAULTCODEPAGE[] = { /* "708" */
+ 0x37, 0x30, 0x38
+};
+
+static BYTE NLSALLOC(3001) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(3001) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3001) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(3001) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(3001) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(3001) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3001) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3001) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(3001) rgbSCURRENCY[] = { /* "\x0644.\x0644.\x200f" */
+ 0xe1, 0x2e, 0xe1, 0x2e, 0xfe
+};
+
+static BYTE NLSALLOC(3001) rgbSINTLSYMBOL[] = { /* "LBP" */
+ 0x4c, 0x42, 0x50
+};
+
+static BYTE NLSALLOC(3001) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(3001) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(3001) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(3001) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3001) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3001) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3001) rgbINEGCURR[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(3001) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(3001) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(3001) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(3001) rgbSLONGDATE[] = { /* "dd/MM/yyyy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(3001) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3001) rgbILDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3001) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3001) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3001) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3001) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3001) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3001) rgbS1159[] = { /* "\x0635" */
+ 0xd5
+};
+
+static BYTE NLSALLOC(3001) rgbS2359[] = { /* "\x0645" */
+ 0xe3
+};
+
+static BYTE NLSALLOC(3001) rgbSDAYNAME1[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(3001) rgbSDAYNAME2[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(3001) rgbSDAYNAME3[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(3001) rgbSDAYNAME4[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(3001) rgbSDAYNAME5[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(3001) rgbSDAYNAME6[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(3001) rgbSDAYNAME7[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVDAYNAME1[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVDAYNAME2[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVDAYNAME3[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVDAYNAME4[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVDAYNAME5[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVDAYNAME6[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVDAYNAME7[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(3001) rgbSMONTHNAME1[] = { /* "\x0643\x0627\x0646\x0648\x0646 \x0627\x0644\x062b\x0627\x0646\x064a" */
+ 0xdf, 0xc7, 0xe4, 0xe6, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xcb, 0xc7, 0xe4, 0xed
+};
+
+static BYTE NLSALLOC(3001) rgbSMONTHNAME2[] = { /* "\x0634\x0628\x0627\x0637" */
+ 0xd4, 0xc8, 0xc7, 0xd8
+};
+
+static BYTE NLSALLOC(3001) rgbSMONTHNAME3[] = { /* "\x0622\x0630\x0627\x0631" */
+ 0xc2, 0xd0, 0xc7, 0xd1
+};
+
+static BYTE NLSALLOC(3001) rgbSMONTHNAME4[] = { /* "\x0646\x064a\x0633\x0627\x0646" */
+ 0xe4, 0xed, 0xd3, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(3001) rgbSMONTHNAME5[] = { /* "\x0623\x064a\x0627\x0631" */
+ 0xc3, 0xed, 0xc7, 0xd1
+};
+
+static BYTE NLSALLOC(3001) rgbSMONTHNAME6[] = { /* "\x062d\x0632\x064a\x0631\x0627\x0646" */
+ 0xcd, 0xd2, 0xed, 0xd1, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(3001) rgbSMONTHNAME7[] = { /* "\x062a\x0645\x0648\x0632" */
+ 0xca, 0xe3, 0xe6, 0xd2
+};
+
+static BYTE NLSALLOC(3001) rgbSMONTHNAME8[] = { /* "\x0622\x0628" */
+ 0xc2, 0xc8
+};
+
+static BYTE NLSALLOC(3001) rgbSMONTHNAME9[] = { /* "\x0623\x064a\x0644\x0648\x0644" */
+ 0xc3, 0xed, 0xe1, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(3001) rgbSMONTHNAME10[] = { /* "\x062a\x0634\x0631\x064a\x0646 \x0627\x0644\x0623\x0648\x0644" */
+ 0xca, 0xd4, 0xd1, 0xed, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xc3, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(3001) rgbSMONTHNAME11[] = { /* "\x062a\x0634\x0631\x064a\x0646 \x0627\x0644\x062b\x0627\x0646\x064a" */
+ 0xca, 0xd4, 0xd1, 0xed, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xcb, 0xc7, 0xe4, 0xed
+};
+
+static BYTE NLSALLOC(3001) rgbSMONTHNAME12[] = { /* "\x0643\x0627\x0646\x0648\x0646 \x0627\x0644\x0623\x0648\x0644" */
+ 0xdf, 0xc7, 0xe4, 0xe6, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xc3, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVMONTHNAME1[] = { /* "\x0643\x0627\x0646\x0648\x0646 \x0627\x0644\x062b\x0627\x0646\x064a" */
+ 0xdf, 0xc7, 0xe4, 0xe6, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xcb, 0xc7, 0xe4, 0xed
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVMONTHNAME2[] = { /* "\x0634\x0628\x0627\x0637" */
+ 0xd4, 0xc8, 0xc7, 0xd8
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVMONTHNAME3[] = { /* "\x0622\x0630\x0627\x0631" */
+ 0xc2, 0xd0, 0xc7, 0xd1
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVMONTHNAME4[] = { /* "\x0646\x064a\x0633\x0627\x0646" */
+ 0xe4, 0xed, 0xd3, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVMONTHNAME5[] = { /* "\x0623\x064a\x0627\x0631" */
+ 0xc3, 0xed, 0xc7, 0xd1
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVMONTHNAME6[] = { /* "\x062d\x0632\x064a\x0631\x0627\x0646" */
+ 0xcd, 0xd2, 0xed, 0xd1, 0xc7, 0xe4
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVMONTHNAME7[] = { /* "\x062a\x0645\x0648\x0632" */
+ 0xca, 0xe3, 0xe6, 0xd2
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVMONTHNAME8[] = { /* "\x0622\x0628" */
+ 0xc2, 0xc8
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVMONTHNAME9[] = { /* "\x0623\x064a\x0644\x0648\x0644" */
+ 0xc3, 0xed, 0xe1, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVMONTHNAME10[] = { /* "\x062a\x0634\x0631\x064a\x0646 \x0627\x0644\x0623\x0648\x0644" */
+ 0xca, 0xd4, 0xd1, 0xed, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xc3, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVMONTHNAME11[] = { /* "\x062a\x0634\x0631\x064a\x0646 \x0627\x0644\x062b\x0627\x0646\x064a" */
+ 0xca, 0xd4, 0xd1, 0xed, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xcb, 0xc7, 0xe4, 0xed
+};
+
+static BYTE NLSALLOC(3001) rgbSABBREVMONTHNAME12[] = { /* "\x0643\x0627\x0646\x0648\x0646 \x0627\x0644\x0623\x0648\x0644" */
+ 0xdf, 0xc7, 0xe4, 0xe6, 0xe4, 0x20, 0xc7, 0xe1
+ , 0xc3, 0xe6, 0xe1
+};
+
+static BYTE NLSALLOC(3001) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(3001) rgbIPOSSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3001) rgbINEGSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3001) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3001) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3001) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3001) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3001) rgbSENGCOUNTRY[] = { /* "Lebanon" */
+ 0x4c, 0x65, 0x62, 0x61, 0x6e, 0x6f, 0x6e
+};
+
+static BYTE NLSALLOC(3001) rgbSENGLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(3001) rgbIFIRSTDAYOFWEEK[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3001) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3001) rgbIDEFAULTANSICODEPAGE[] = { /* "1256" */
+ 0x31, 0x32, 0x35, 0x36
+};
+
+static BYTE NLSALLOC(3001) rgbINEGNUMBER[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(3001) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(3001) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3001) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3001) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(3001) g_rglcinfo3001[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 7, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 5, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 5, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 10, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 1, rgbS1159 }
+ , { 1, rgbS2359 }
+ , { 7, rgbSDAYNAME1 }
+ , { 8, rgbSDAYNAME2 }
+ , { 8, rgbSDAYNAME3 }
+ , { 6, rgbSDAYNAME4 }
+ , { 6, rgbSDAYNAME5 }
+ , { 5, rgbSDAYNAME6 }
+ , { 5, rgbSDAYNAME7 }
+ , { 7, rgbSABBREVDAYNAME1 }
+ , { 8, rgbSABBREVDAYNAME2 }
+ , { 8, rgbSABBREVDAYNAME3 }
+ , { 6, rgbSABBREVDAYNAME4 }
+ , { 6, rgbSABBREVDAYNAME5 }
+ , { 5, rgbSABBREVDAYNAME6 }
+ , { 5, rgbSABBREVDAYNAME7 }
+ , { 12, rgbSMONTHNAME1 }
+ , { 4, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 4, rgbSMONTHNAME5 }
+ , { 6, rgbSMONTHNAME6 }
+ , { 4, rgbSMONTHNAME7 }
+ , { 2, rgbSMONTHNAME8 }
+ , { 5, rgbSMONTHNAME9 }
+ , { 11, rgbSMONTHNAME10 }
+ , { 12, rgbSMONTHNAME11 }
+ , { 11, rgbSMONTHNAME12 }
+ , { 12, rgbSABBREVMONTHNAME1 }
+ , { 4, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 5, rgbSABBREVMONTHNAME4 }
+ , { 4, rgbSABBREVMONTHNAME5 }
+ , { 6, rgbSABBREVMONTHNAME6 }
+ , { 4, rgbSABBREVMONTHNAME7 }
+ , { 2, rgbSABBREVMONTHNAME8 }
+ , { 5, rgbSABBREVMONTHNAME9 }
+ , { 11, rgbSABBREVMONTHNAME10 }
+ , { 12, rgbSABBREVMONTHNAME11 }
+ , { 11, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 7, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(3001) g_strinfo3001 = {
+ rgbUCase_0401
+ , rgbLCase_0401
+ , rgwCType12_0401
+ , rgwCType3_0401
+ , rgwSort_0401
+ , rgexp_0401
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/3401.c b/private/oleauto/src/dispatch/win16/3401.c
new file mode 100644
index 000000000..8576a8467
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/3401.c
@@ -0,0 +1,528 @@
+/****************************************************************************
+* 3401.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Arabic - Kuwait
+*
+* LCID = 0x3401
+*
+* CodePage = 1256
+*
+* Generated: Thu Dec 01 18:37:28 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0401[256]; // from 0401:Arabic - Saudi Arabia
+extern EXPANSION rgexp_0401[3];
+extern WORD rgwCType12_0401[256];
+extern WORD rgwCType3_0401[256];
+extern BYTE rgbUCase_0401[256];
+extern BYTE rgbLCase_0401[256];
+
+static BYTE NLSALLOC(3401) rgbILANGUAGE[] = { /* "3401" */
+ 0x33, 0x34, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(3401) rgbSLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVLANGNAME[] = { /* "ARK" */
+ 0x41, 0x52, 0x4b
+};
+
+static BYTE NLSALLOC(3401) rgbSNATIVELANGNAME[] = { /* "\x0627\x0644\x0639\x0631\x0628\x064a\x0629" */
+ 0xc7, 0xe1, 0xda, 0xd1, 0xc8, 0xed, 0xc9
+};
+
+static BYTE NLSALLOC(3401) rgbICOUNTRY[] = { /* "965" */
+ 0x39, 0x36, 0x35
+};
+
+static BYTE NLSALLOC(3401) rgbSCOUNTRY[] = { /* "Kuwait" */
+ 0x4b, 0x75, 0x77, 0x61, 0x69, 0x74
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVCTRYNAME[] = { /* "KWT" */
+ 0x4b, 0x57, 0x54
+};
+
+static BYTE NLSALLOC(3401) rgbSNATIVECTRYNAME[] = { /* "\x0627\x0644\x0643\x0648\x064a\x062a" */
+ 0xc7, 0xe1, 0xdf, 0xe6, 0xed, 0xca
+};
+
+static BYTE NLSALLOC(3401) rgbIDEFAULTLANGUAGE[] = { /* "3401" */
+ 0x33, 0x34, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(3401) rgbIDEFAULTCOUNTRY[] = { /* "965" */
+ 0x39, 0x36, 0x35
+};
+
+static BYTE NLSALLOC(3401) rgbIDEFAULTCODEPAGE[] = { /* "708" */
+ 0x37, 0x30, 0x38
+};
+
+static BYTE NLSALLOC(3401) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(3401) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3401) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(3401) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(3401) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(3401) rgbIDIGITS[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(3401) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3401) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(3401) rgbSCURRENCY[] = { /* "\x062f.\x0643.\x200f" */
+ 0xcf, 0x2e, 0xdf, 0x2e, 0xfe
+};
+
+static BYTE NLSALLOC(3401) rgbSINTLSYMBOL[] = { /* "KWD" */
+ 0x4b, 0x57, 0x44
+};
+
+static BYTE NLSALLOC(3401) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(3401) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(3401) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(3401) rgbICURRDIGITS[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(3401) rgbIINTLCURRDIGITS[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(3401) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3401) rgbINEGCURR[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(3401) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(3401) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(3401) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(3401) rgbSLONGDATE[] = { /* "dd/MM/yyyy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(3401) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3401) rgbILDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3401) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3401) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3401) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3401) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3401) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3401) rgbS1159[] = { /* "\x0635" */
+ 0xd5
+};
+
+static BYTE NLSALLOC(3401) rgbS2359[] = { /* "\x0645" */
+ 0xe3
+};
+
+static BYTE NLSALLOC(3401) rgbSDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(3401) rgbSDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(3401) rgbSDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(3401) rgbSDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(3401) rgbSDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(3401) rgbSDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(3401) rgbSDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(3401) rgbSMONTHNAME1[] = { /* "\x064a\x0646\x0627\x064a\x0631" */
+ 0xed, 0xe4, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(3401) rgbSMONTHNAME2[] = { /* "\x0641\x0628\x0631\x0627\x064a\x0631" */
+ 0xdd, 0xc8, 0xd1, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(3401) rgbSMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(3401) rgbSMONTHNAME4[] = { /* "\x0627\x0628\x0631\x064a\x0644" */
+ 0xc7, 0xc8, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(3401) rgbSMONTHNAME5[] = { /* "\x0645\x0627\x064a\x0648" */
+ 0xe3, 0xc7, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(3401) rgbSMONTHNAME6[] = { /* "\x064a\x0648\x0646\x064a\x0648" */
+ 0xed, 0xe6, 0xe4, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(3401) rgbSMONTHNAME7[] = { /* "\x064a\x0648\x0644\x064a\x0648" */
+ 0xed, 0xe6, 0xe1, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(3401) rgbSMONTHNAME8[] = { /* "\x0623\x063a\x0633\x0637\x0633" */
+ 0xc3, 0xdb, 0xd3, 0xd8, 0xd3
+};
+
+static BYTE NLSALLOC(3401) rgbSMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3401) rgbSMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3401) rgbSMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3401) rgbSMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVMONTHNAME1[] = { /* "\x064a\x0646\x0627\x064a\x0631" */
+ 0xed, 0xe4, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVMONTHNAME2[] = { /* "\x0641\x0628\x0631\x0627\x064a\x0631" */
+ 0xdd, 0xc8, 0xd1, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVMONTHNAME4[] = { /* "\x0627\x0628\x0631\x064a\x0644" */
+ 0xc7, 0xc8, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVMONTHNAME5[] = { /* "\x0645\x0627\x064a\x0648" */
+ 0xe3, 0xc7, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVMONTHNAME6[] = { /* "\x064a\x0648\x0646\x064a\x0648" */
+ 0xed, 0xe6, 0xe4, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVMONTHNAME7[] = { /* "\x064a\x0648\x0644\x064a\x0648" */
+ 0xed, 0xe6, 0xe1, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVMONTHNAME8[] = { /* "\x0623\x063a\x0633\x0637\x0633" */
+ 0xc3, 0xdb, 0xd3, 0xd8, 0xd3
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3401) rgbSABBREVMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3401) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(3401) rgbIPOSSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3401) rgbINEGSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3401) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3401) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3401) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3401) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3401) rgbSENGCOUNTRY[] = { /* "Kuwait" */
+ 0x4b, 0x75, 0x77, 0x61, 0x69, 0x74
+};
+
+static BYTE NLSALLOC(3401) rgbSENGLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(3401) rgbIFIRSTDAYOFWEEK[] = { /* "5" */
+ 0x35
+};
+
+static BYTE NLSALLOC(3401) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3401) rgbIDEFAULTANSICODEPAGE[] = { /* "1256" */
+ 0x31, 0x32, 0x35, 0x36
+};
+
+static BYTE NLSALLOC(3401) rgbINEGNUMBER[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(3401) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(3401) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3401) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3401) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(3401) g_rglcinfo3401[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 6, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 6, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 5, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 10, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 1, rgbS1159 }
+ , { 1, rgbS2359 }
+ , { 5, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 7, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 8, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 5, rgbSABBREVDAYNAME1 }
+ , { 5, rgbSABBREVDAYNAME2 }
+ , { 7, rgbSABBREVDAYNAME3 }
+ , { 8, rgbSABBREVDAYNAME4 }
+ , { 8, rgbSABBREVDAYNAME5 }
+ , { 6, rgbSABBREVDAYNAME6 }
+ , { 6, rgbSABBREVDAYNAME7 }
+ , { 5, rgbSMONTHNAME1 }
+ , { 6, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 4, rgbSMONTHNAME5 }
+ , { 5, rgbSMONTHNAME6 }
+ , { 5, rgbSMONTHNAME7 }
+ , { 5, rgbSMONTHNAME8 }
+ , { 6, rgbSMONTHNAME9 }
+ , { 6, rgbSMONTHNAME10 }
+ , { 6, rgbSMONTHNAME11 }
+ , { 6, rgbSMONTHNAME12 }
+ , { 5, rgbSABBREVMONTHNAME1 }
+ , { 6, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 5, rgbSABBREVMONTHNAME4 }
+ , { 4, rgbSABBREVMONTHNAME5 }
+ , { 5, rgbSABBREVMONTHNAME6 }
+ , { 5, rgbSABBREVMONTHNAME7 }
+ , { 5, rgbSABBREVMONTHNAME8 }
+ , { 6, rgbSABBREVMONTHNAME9 }
+ , { 6, rgbSABBREVMONTHNAME10 }
+ , { 6, rgbSABBREVMONTHNAME11 }
+ , { 6, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 6, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(3401) g_strinfo3401 = {
+ rgbUCase_0401
+ , rgbLCase_0401
+ , rgwCType12_0401
+ , rgwCType3_0401
+ , rgwSort_0401
+ , rgexp_0401
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/3801.c b/private/oleauto/src/dispatch/win16/3801.c
new file mode 100644
index 000000000..25f0b6781
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/3801.c
@@ -0,0 +1,530 @@
+/****************************************************************************
+* 3801.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Arabic - U.A.E.
+*
+* LCID = 0x3801
+*
+* CodePage = 1256
+*
+* Generated: Thu Dec 01 18:38:26 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0401[256]; // from 0401:Arabic - Saudi Arabia
+extern EXPANSION rgexp_0401[3];
+extern WORD rgwCType12_0401[256];
+extern WORD rgwCType3_0401[256];
+extern BYTE rgbUCase_0401[256];
+extern BYTE rgbLCase_0401[256];
+
+static BYTE NLSALLOC(3801) rgbILANGUAGE[] = { /* "3801" */
+ 0x33, 0x38, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(3801) rgbSLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVLANGNAME[] = { /* "ARU" */
+ 0x41, 0x52, 0x55
+};
+
+static BYTE NLSALLOC(3801) rgbSNATIVELANGNAME[] = { /* "\x0627\x0644\x0639\x0631\x0628\x064a\x0629" */
+ 0xc7, 0xe1, 0xda, 0xd1, 0xc8, 0xed, 0xc9
+};
+
+static BYTE NLSALLOC(3801) rgbICOUNTRY[] = { /* "971" */
+ 0x39, 0x37, 0x31
+};
+
+static BYTE NLSALLOC(3801) rgbSCOUNTRY[] = { /* "U.A.E." */
+ 0x55, 0x2e, 0x41, 0x2e, 0x45, 0x2e
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVCTRYNAME[] = { /* "ARE" */
+ 0x41, 0x52, 0x45
+};
+
+static BYTE NLSALLOC(3801) rgbSNATIVECTRYNAME[] = { /* "\x0627\x0644\x0625\x0645\x0627\x0631\x0627\x062a \x0627\x0644\x0639\x0631\x0628\x064a\x0629 \x0627\x0644\x0645\x062a\x062d\x062f\x0629" */
+ 0xc7, 0xe1, 0xc5, 0xe3, 0xc7, 0xd1, 0xc7, 0xca
+ , 0x20, 0xc7, 0xe1, 0xda, 0xd1, 0xc8, 0xed, 0xc9
+ , 0x20, 0xc7, 0xe1, 0xe3, 0xca, 0xcd, 0xcf, 0xc9
+};
+
+static BYTE NLSALLOC(3801) rgbIDEFAULTLANGUAGE[] = { /* "3801" */
+ 0x33, 0x38, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(3801) rgbIDEFAULTCOUNTRY[] = { /* "971" */
+ 0x39, 0x37, 0x31
+};
+
+static BYTE NLSALLOC(3801) rgbIDEFAULTCODEPAGE[] = { /* "708" */
+ 0x37, 0x30, 0x38
+};
+
+static BYTE NLSALLOC(3801) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(3801) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3801) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(3801) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(3801) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(3801) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3801) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3801) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(3801) rgbSCURRENCY[] = { /* "\x062f.\x0625.\x200f" */
+ 0xcf, 0x2e, 0xc5, 0x2e, 0xfe
+};
+
+static BYTE NLSALLOC(3801) rgbSINTLSYMBOL[] = { /* "AED" */
+ 0x41, 0x45, 0x44
+};
+
+static BYTE NLSALLOC(3801) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(3801) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(3801) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(3801) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3801) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3801) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3801) rgbINEGCURR[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(3801) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(3801) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(3801) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(3801) rgbSLONGDATE[] = { /* "dd/MM/yyyy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(3801) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3801) rgbILDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3801) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3801) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3801) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3801) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3801) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3801) rgbS1159[] = { /* "\x0635" */
+ 0xd5
+};
+
+static BYTE NLSALLOC(3801) rgbS2359[] = { /* "\x0645" */
+ 0xe3
+};
+
+static BYTE NLSALLOC(3801) rgbSDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(3801) rgbSDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(3801) rgbSDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(3801) rgbSDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(3801) rgbSDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(3801) rgbSDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(3801) rgbSDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(3801) rgbSMONTHNAME1[] = { /* "\x064a\x0646\x0627\x064a\x0631" */
+ 0xed, 0xe4, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(3801) rgbSMONTHNAME2[] = { /* "\x0641\x0628\x0631\x0627\x064a\x0631" */
+ 0xdd, 0xc8, 0xd1, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(3801) rgbSMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(3801) rgbSMONTHNAME4[] = { /* "\x0627\x0628\x0631\x064a\x0644" */
+ 0xc7, 0xc8, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(3801) rgbSMONTHNAME5[] = { /* "\x0645\x0627\x064a\x0648" */
+ 0xe3, 0xc7, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(3801) rgbSMONTHNAME6[] = { /* "\x064a\x0648\x0646\x064a\x0648" */
+ 0xed, 0xe6, 0xe4, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(3801) rgbSMONTHNAME7[] = { /* "\x064a\x0648\x0644\x064a\x0648" */
+ 0xed, 0xe6, 0xe1, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(3801) rgbSMONTHNAME8[] = { /* "\x0623\x063a\x0633\x0637\x0633" */
+ 0xc3, 0xdb, 0xd3, 0xd8, 0xd3
+};
+
+static BYTE NLSALLOC(3801) rgbSMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3801) rgbSMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3801) rgbSMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3801) rgbSMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVMONTHNAME1[] = { /* "\x064a\x0646\x0627\x064a\x0631" */
+ 0xed, 0xe4, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVMONTHNAME2[] = { /* "\x0641\x0628\x0631\x0627\x064a\x0631" */
+ 0xdd, 0xc8, 0xd1, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVMONTHNAME4[] = { /* "\x0627\x0628\x0631\x064a\x0644" */
+ 0xc7, 0xc8, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVMONTHNAME5[] = { /* "\x0645\x0627\x064a\x0648" */
+ 0xe3, 0xc7, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVMONTHNAME6[] = { /* "\x064a\x0648\x0646\x064a\x0648" */
+ 0xed, 0xe6, 0xe4, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVMONTHNAME7[] = { /* "\x064a\x0648\x0644\x064a\x0648" */
+ 0xed, 0xe6, 0xe1, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVMONTHNAME8[] = { /* "\x0623\x063a\x0633\x0637\x0633" */
+ 0xc3, 0xdb, 0xd3, 0xd8, 0xd3
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3801) rgbSABBREVMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3801) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(3801) rgbIPOSSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3801) rgbINEGSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3801) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3801) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3801) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3801) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3801) rgbSENGCOUNTRY[] = { /* "U.A.E." */
+ 0x55, 0x2e, 0x41, 0x2e, 0x45, 0x2e
+};
+
+static BYTE NLSALLOC(3801) rgbSENGLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(3801) rgbIFIRSTDAYOFWEEK[] = { /* "5" */
+ 0x35
+};
+
+static BYTE NLSALLOC(3801) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3801) rgbIDEFAULTANSICODEPAGE[] = { /* "1256" */
+ 0x31, 0x32, 0x35, 0x36
+};
+
+static BYTE NLSALLOC(3801) rgbINEGNUMBER[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(3801) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(3801) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3801) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3801) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(3801) g_rglcinfo3801[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 6, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 24, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 5, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 10, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 1, rgbS1159 }
+ , { 1, rgbS2359 }
+ , { 5, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 7, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 8, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 5, rgbSABBREVDAYNAME1 }
+ , { 5, rgbSABBREVDAYNAME2 }
+ , { 7, rgbSABBREVDAYNAME3 }
+ , { 8, rgbSABBREVDAYNAME4 }
+ , { 8, rgbSABBREVDAYNAME5 }
+ , { 6, rgbSABBREVDAYNAME6 }
+ , { 6, rgbSABBREVDAYNAME7 }
+ , { 5, rgbSMONTHNAME1 }
+ , { 6, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 4, rgbSMONTHNAME5 }
+ , { 5, rgbSMONTHNAME6 }
+ , { 5, rgbSMONTHNAME7 }
+ , { 5, rgbSMONTHNAME8 }
+ , { 6, rgbSMONTHNAME9 }
+ , { 6, rgbSMONTHNAME10 }
+ , { 6, rgbSMONTHNAME11 }
+ , { 6, rgbSMONTHNAME12 }
+ , { 5, rgbSABBREVMONTHNAME1 }
+ , { 6, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 5, rgbSABBREVMONTHNAME4 }
+ , { 4, rgbSABBREVMONTHNAME5 }
+ , { 5, rgbSABBREVMONTHNAME6 }
+ , { 5, rgbSABBREVMONTHNAME7 }
+ , { 5, rgbSABBREVMONTHNAME8 }
+ , { 6, rgbSABBREVMONTHNAME9 }
+ , { 6, rgbSABBREVMONTHNAME10 }
+ , { 6, rgbSABBREVMONTHNAME11 }
+ , { 6, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 6, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(3801) g_strinfo3801 = {
+ rgbUCase_0401
+ , rgbLCase_0401
+ , rgwCType12_0401
+ , rgwCType3_0401
+ , rgwSort_0401
+ , rgexp_0401
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/3c01.c b/private/oleauto/src/dispatch/win16/3c01.c
new file mode 100644
index 000000000..3d7c3956c
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/3c01.c
@@ -0,0 +1,528 @@
+/****************************************************************************
+* 3c01.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Arabic - Bahrain
+*
+* LCID = 0x3c01
+*
+* CodePage = 1256
+*
+* Generated: Thu Dec 01 18:39:20 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0401[256]; // from 0401:Arabic - Saudi Arabia
+extern EXPANSION rgexp_0401[3];
+extern WORD rgwCType12_0401[256];
+extern WORD rgwCType3_0401[256];
+extern BYTE rgbUCase_0401[256];
+extern BYTE rgbLCase_0401[256];
+
+static BYTE NLSALLOC(3c01) rgbILANGUAGE[] = { /* "3c01" */
+ 0x33, 0x63, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(3c01) rgbSLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVLANGNAME[] = { /* "ARH" */
+ 0x41, 0x52, 0x48
+};
+
+static BYTE NLSALLOC(3c01) rgbSNATIVELANGNAME[] = { /* "\x0627\x0644\x0639\x0631\x0628\x064a\x0629" */
+ 0xc7, 0xe1, 0xda, 0xd1, 0xc8, 0xed, 0xc9
+};
+
+static BYTE NLSALLOC(3c01) rgbICOUNTRY[] = { /* "973" */
+ 0x39, 0x37, 0x33
+};
+
+static BYTE NLSALLOC(3c01) rgbSCOUNTRY[] = { /* "Bahrain" */
+ 0x42, 0x61, 0x68, 0x72, 0x61, 0x69, 0x6e
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVCTRYNAME[] = { /* "BHR" */
+ 0x42, 0x48, 0x52
+};
+
+static BYTE NLSALLOC(3c01) rgbSNATIVECTRYNAME[] = { /* "\x0627\x0644\x0628\x062d\x0631\x064a\x0646" */
+ 0xc7, 0xe1, 0xc8, 0xcd, 0xd1, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(3c01) rgbIDEFAULTLANGUAGE[] = { /* "3c01" */
+ 0x33, 0x63, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(3c01) rgbIDEFAULTCOUNTRY[] = { /* "973" */
+ 0x39, 0x37, 0x33
+};
+
+static BYTE NLSALLOC(3c01) rgbIDEFAULTCODEPAGE[] = { /* "708" */
+ 0x37, 0x30, 0x38
+};
+
+static BYTE NLSALLOC(3c01) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(3c01) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3c01) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(3c01) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(3c01) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(3c01) rgbIDIGITS[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(3c01) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3c01) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(3c01) rgbSCURRENCY[] = { /* "\x062f.\x0628.\x200f" */
+ 0xcf, 0x2e, 0xc8, 0x2e, 0xfe
+};
+
+static BYTE NLSALLOC(3c01) rgbSINTLSYMBOL[] = { /* "BHD" */
+ 0x42, 0x48, 0x44
+};
+
+static BYTE NLSALLOC(3c01) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(3c01) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(3c01) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(3c01) rgbICURRDIGITS[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(3c01) rgbIINTLCURRDIGITS[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(3c01) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3c01) rgbINEGCURR[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(3c01) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(3c01) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(3c01) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(3c01) rgbSLONGDATE[] = { /* "dd/MM/yyyy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(3c01) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3c01) rgbILDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3c01) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3c01) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3c01) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3c01) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3c01) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3c01) rgbS1159[] = { /* "\x0635" */
+ 0xd5
+};
+
+static BYTE NLSALLOC(3c01) rgbS2359[] = { /* "\x0645" */
+ 0xe3
+};
+
+static BYTE NLSALLOC(3c01) rgbSDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(3c01) rgbSDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(3c01) rgbSDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(3c01) rgbSDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(3c01) rgbSDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(3c01) rgbSDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(3c01) rgbSDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(3c01) rgbSMONTHNAME1[] = { /* "\x064a\x0646\x0627\x064a\x0631" */
+ 0xed, 0xe4, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(3c01) rgbSMONTHNAME2[] = { /* "\x0641\x0628\x0631\x0627\x064a\x0631" */
+ 0xdd, 0xc8, 0xd1, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(3c01) rgbSMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(3c01) rgbSMONTHNAME4[] = { /* "\x0627\x0628\x0631\x064a\x0644" */
+ 0xc7, 0xc8, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(3c01) rgbSMONTHNAME5[] = { /* "\x0645\x0627\x064a\x0648" */
+ 0xe3, 0xc7, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(3c01) rgbSMONTHNAME6[] = { /* "\x064a\x0648\x0646\x064a\x0648" */
+ 0xed, 0xe6, 0xe4, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(3c01) rgbSMONTHNAME7[] = { /* "\x064a\x0648\x0644\x064a\x0648" */
+ 0xed, 0xe6, 0xe1, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(3c01) rgbSMONTHNAME8[] = { /* "\x0623\x063a\x0633\x0637\x0633" */
+ 0xc3, 0xdb, 0xd3, 0xd8, 0xd3
+};
+
+static BYTE NLSALLOC(3c01) rgbSMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3c01) rgbSMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3c01) rgbSMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3c01) rgbSMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVMONTHNAME1[] = { /* "\x064a\x0646\x0627\x064a\x0631" */
+ 0xed, 0xe4, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVMONTHNAME2[] = { /* "\x0641\x0628\x0631\x0627\x064a\x0631" */
+ 0xdd, 0xc8, 0xd1, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVMONTHNAME4[] = { /* "\x0627\x0628\x0631\x064a\x0644" */
+ 0xc7, 0xc8, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVMONTHNAME5[] = { /* "\x0645\x0627\x064a\x0648" */
+ 0xe3, 0xc7, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVMONTHNAME6[] = { /* "\x064a\x0648\x0646\x064a\x0648" */
+ 0xed, 0xe6, 0xe4, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVMONTHNAME7[] = { /* "\x064a\x0648\x0644\x064a\x0648" */
+ 0xed, 0xe6, 0xe1, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVMONTHNAME8[] = { /* "\x0623\x063a\x0633\x0637\x0633" */
+ 0xc3, 0xdb, 0xd3, 0xd8, 0xd3
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3c01) rgbSABBREVMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(3c01) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(3c01) rgbIPOSSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3c01) rgbINEGSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(3c01) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3c01) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3c01) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3c01) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3c01) rgbSENGCOUNTRY[] = { /* "Bahrain" */
+ 0x42, 0x61, 0x68, 0x72, 0x61, 0x69, 0x6e
+};
+
+static BYTE NLSALLOC(3c01) rgbSENGLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(3c01) rgbIFIRSTDAYOFWEEK[] = { /* "5" */
+ 0x35
+};
+
+static BYTE NLSALLOC(3c01) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(3c01) rgbIDEFAULTANSICODEPAGE[] = { /* "1256" */
+ 0x31, 0x32, 0x35, 0x36
+};
+
+static BYTE NLSALLOC(3c01) rgbINEGNUMBER[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(3c01) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(3c01) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3c01) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(3c01) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(3c01) g_rglcinfo3c01[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 7, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 7, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 5, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 10, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 1, rgbS1159 }
+ , { 1, rgbS2359 }
+ , { 5, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 7, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 8, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 5, rgbSABBREVDAYNAME1 }
+ , { 5, rgbSABBREVDAYNAME2 }
+ , { 7, rgbSABBREVDAYNAME3 }
+ , { 8, rgbSABBREVDAYNAME4 }
+ , { 8, rgbSABBREVDAYNAME5 }
+ , { 6, rgbSABBREVDAYNAME6 }
+ , { 6, rgbSABBREVDAYNAME7 }
+ , { 5, rgbSMONTHNAME1 }
+ , { 6, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 4, rgbSMONTHNAME5 }
+ , { 5, rgbSMONTHNAME6 }
+ , { 5, rgbSMONTHNAME7 }
+ , { 5, rgbSMONTHNAME8 }
+ , { 6, rgbSMONTHNAME9 }
+ , { 6, rgbSMONTHNAME10 }
+ , { 6, rgbSMONTHNAME11 }
+ , { 6, rgbSMONTHNAME12 }
+ , { 5, rgbSABBREVMONTHNAME1 }
+ , { 6, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 5, rgbSABBREVMONTHNAME4 }
+ , { 4, rgbSABBREVMONTHNAME5 }
+ , { 5, rgbSABBREVMONTHNAME6 }
+ , { 5, rgbSABBREVMONTHNAME7 }
+ , { 5, rgbSABBREVMONTHNAME8 }
+ , { 6, rgbSABBREVMONTHNAME9 }
+ , { 6, rgbSABBREVMONTHNAME10 }
+ , { 6, rgbSABBREVMONTHNAME11 }
+ , { 6, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 7, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(3c01) g_strinfo3c01 = {
+ rgbUCase_0401
+ , rgbLCase_0401
+ , rgwCType12_0401
+ , rgwCType3_0401
+ , rgwSort_0401
+ , rgexp_0401
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/4001.c b/private/oleauto/src/dispatch/win16/4001.c
new file mode 100644
index 000000000..8dab5724c
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/4001.c
@@ -0,0 +1,528 @@
+/****************************************************************************
+* 4001.c
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Arabic - Qatar
+*
+* LCID = 0x4001
+*
+* CodePage = 1256
+*
+* Generated: Thu Dec 01 18:40:16 1994
+*
+* by a-KChang
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "nlsintrn.h"
+
+extern WORD rgwSort_0401[256]; // from 0401:Arabic - Saudi Arabia
+extern EXPANSION rgexp_0401[3];
+extern WORD rgwCType12_0401[256];
+extern WORD rgwCType3_0401[256];
+extern BYTE rgbUCase_0401[256];
+extern BYTE rgbLCase_0401[256];
+
+static BYTE NLSALLOC(4001) rgbILANGUAGE[] = { /* "4001" */
+ 0x34, 0x30, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(4001) rgbSLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVLANGNAME[] = { /* "ARQ" */
+ 0x41, 0x52, 0x51
+};
+
+static BYTE NLSALLOC(4001) rgbSNATIVELANGNAME[] = { /* "\x0627\x0644\x0639\x0631\x0628\x064a\x0629" */
+ 0xc7, 0xe1, 0xda, 0xd1, 0xc8, 0xed, 0xc9
+};
+
+static BYTE NLSALLOC(4001) rgbICOUNTRY[] = { /* "974" */
+ 0x39, 0x37, 0x34
+};
+
+static BYTE NLSALLOC(4001) rgbSCOUNTRY[] = { /* "Qatar" */
+ 0x51, 0x61, 0x74, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVCTRYNAME[] = { /* "QAT" */
+ 0x51, 0x41, 0x54
+};
+
+static BYTE NLSALLOC(4001) rgbSNATIVECTRYNAME[] = { /* "\x0642\x0637\x0631" */
+ 0xde, 0xd8, 0xd1
+};
+
+static BYTE NLSALLOC(4001) rgbIDEFAULTLANGUAGE[] = { /* "4001" */
+ 0x34, 0x30, 0x30, 0x31
+};
+
+static BYTE NLSALLOC(4001) rgbIDEFAULTCOUNTRY[] = { /* "974" */
+ 0x39, 0x37, 0x34
+};
+
+static BYTE NLSALLOC(4001) rgbIDEFAULTCODEPAGE[] = { /* "708" */
+ 0x37, 0x30, 0x38
+};
+
+static BYTE NLSALLOC(4001) rgbSLIST[] = { /* ";" */
+ 0x3b
+};
+
+static BYTE NLSALLOC(4001) rgbIMEASURE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(4001) rgbSDECIMAL[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(4001) rgbSTHOUSAND[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(4001) rgbSGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(4001) rgbIDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(4001) rgbILZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(4001) rgbSNATIVEDIGITS[] = { /* "0123456789" */
+ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37
+ , 0x38, 0x39
+};
+
+static BYTE NLSALLOC(4001) rgbSCURRENCY[] = { /* "\x0631.\x0642.\x200f" */
+ 0xd1, 0x2e, 0xde, 0x2e, 0xfe
+};
+
+static BYTE NLSALLOC(4001) rgbSINTLSYMBOL[] = { /* "QAR" */
+ 0x51, 0x41, 0x52
+};
+
+static BYTE NLSALLOC(4001) rgbSMONDECIMALSEP[] = { /* "." */
+ 0x2e
+};
+
+static BYTE NLSALLOC(4001) rgbSMONTHOUSANDSEP[] = { /* "," */
+ 0x2c
+};
+
+static BYTE NLSALLOC(4001) rgbSMONGROUPING[] = { /* "3;0" */
+ 0x33, 0x3b, 0x30
+};
+
+static BYTE NLSALLOC(4001) rgbICURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(4001) rgbIINTLCURRDIGITS[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(4001) rgbICURRENCY[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(4001) rgbINEGCURR[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(4001) rgbSDATE[] = { /* "/" */
+ 0x2f
+};
+
+static BYTE NLSALLOC(4001) rgbSTIME[] = { /* ":" */
+ 0x3a
+};
+
+static BYTE NLSALLOC(4001) rgbSSHORTDATE[] = { /* "dd/MM/yy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+};
+
+static BYTE NLSALLOC(4001) rgbSLONGDATE[] = { /* "dd/MM/yyyy" */
+ 0x64, 0x64, 0x2f, 0x4d, 0x4d, 0x2f, 0x79, 0x79
+ , 0x79, 0x79
+};
+
+static BYTE NLSALLOC(4001) rgbIDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(4001) rgbILDATE[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(4001) rgbITIME[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(4001) rgbICENTURY[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(4001) rgbITLZERO[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(4001) rgbIDAYLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(4001) rgbIMONLZERO[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(4001) rgbS1159[] = { /* "\x0635" */
+ 0xd5
+};
+
+static BYTE NLSALLOC(4001) rgbS2359[] = { /* "\x0645" */
+ 0xe3
+};
+
+static BYTE NLSALLOC(4001) rgbSDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(4001) rgbSDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(4001) rgbSDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(4001) rgbSDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(4001) rgbSDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(4001) rgbSDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(4001) rgbSDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVDAYNAME1[] = { /* "\x0627\x0644\x0633\x0628\x062a" */
+ 0xc7, 0xe1, 0xd3, 0xc8, 0xca
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVDAYNAME2[] = { /* "\x0627\x0644\x0623\x062d\x062f" */
+ 0xc7, 0xe1, 0xc3, 0xcd, 0xcf
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVDAYNAME3[] = { /* "\x0627\x0644\x0627\x062b\x0646\x064a\x0646" */
+ 0xc7, 0xe1, 0xc7, 0xcb, 0xe4, 0xed, 0xe4
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVDAYNAME4[] = { /* "\x0627\x0644\x062b\x0644\x0627\x062b\x0627\x0621" */
+ 0xc7, 0xe1, 0xcb, 0xe1, 0xc7, 0xcb, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVDAYNAME5[] = { /* "\x0627\x0644\x0623\x0631\x0628\x0639\x0627\x0621" */
+ 0xc7, 0xe1, 0xc3, 0xd1, 0xc8, 0xda, 0xc7, 0xc1
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVDAYNAME6[] = { /* "\x0627\x0644\x062e\x0645\x064a\x0633" */
+ 0xc7, 0xe1, 0xce, 0xe3, 0xed, 0xd3
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVDAYNAME7[] = { /* "\x0627\x0644\x062c\x0645\x0639\x0629" */
+ 0xc7, 0xe1, 0xcc, 0xe3, 0xda, 0xc9
+};
+
+static BYTE NLSALLOC(4001) rgbSMONTHNAME1[] = { /* "\x064a\x0646\x0627\x064a\x0631" */
+ 0xed, 0xe4, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(4001) rgbSMONTHNAME2[] = { /* "\x0641\x0628\x0631\x0627\x064a\x0631" */
+ 0xdd, 0xc8, 0xd1, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(4001) rgbSMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(4001) rgbSMONTHNAME4[] = { /* "\x0627\x0628\x0631\x064a\x0644" */
+ 0xc7, 0xc8, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(4001) rgbSMONTHNAME5[] = { /* "\x0645\x0627\x064a\x0648" */
+ 0xe3, 0xc7, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(4001) rgbSMONTHNAME6[] = { /* "\x064a\x0648\x0646\x064a\x0648" */
+ 0xed, 0xe6, 0xe4, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(4001) rgbSMONTHNAME7[] = { /* "\x064a\x0648\x0644\x064a\x0648" */
+ 0xed, 0xe6, 0xe1, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(4001) rgbSMONTHNAME8[] = { /* "\x0623\x063a\x0633\x0637\x0633" */
+ 0xc3, 0xdb, 0xd3, 0xd8, 0xd3
+};
+
+static BYTE NLSALLOC(4001) rgbSMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(4001) rgbSMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(4001) rgbSMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(4001) rgbSMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVMONTHNAME1[] = { /* "\x064a\x0646\x0627\x064a\x0631" */
+ 0xed, 0xe4, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVMONTHNAME2[] = { /* "\x0641\x0628\x0631\x0627\x064a\x0631" */
+ 0xdd, 0xc8, 0xd1, 0xc7, 0xed, 0xd1
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVMONTHNAME3[] = { /* "\x0645\x0627\x0631\x0633" */
+ 0xe3, 0xc7, 0xd1, 0xd3
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVMONTHNAME4[] = { /* "\x0627\x0628\x0631\x064a\x0644" */
+ 0xc7, 0xc8, 0xd1, 0xed, 0xe1
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVMONTHNAME5[] = { /* "\x0645\x0627\x064a\x0648" */
+ 0xe3, 0xc7, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVMONTHNAME6[] = { /* "\x064a\x0648\x0646\x064a\x0648" */
+ 0xed, 0xe6, 0xe4, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVMONTHNAME7[] = { /* "\x064a\x0648\x0644\x064a\x0648" */
+ 0xed, 0xe6, 0xe1, 0xed, 0xe6
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVMONTHNAME8[] = { /* "\x0623\x063a\x0633\x0637\x0633" */
+ 0xc3, 0xdb, 0xd3, 0xd8, 0xd3
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVMONTHNAME9[] = { /* "\x0633\x0628\x062a\x0645\x0628\x0631" */
+ 0xd3, 0xc8, 0xca, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVMONTHNAME10[] = { /* "\x0627\x0643\x062a\x0648\x0628\x0631" */
+ 0xc7, 0xdf, 0xca, 0xe6, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVMONTHNAME11[] = { /* "\x0646\x0648\x0641\x0645\x0628\x0631" */
+ 0xe4, 0xe6, 0xdd, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(4001) rgbSABBREVMONTHNAME12[] = { /* "\x062f\x064a\x0633\x0645\x0628\x0631" */
+ 0xcf, 0xed, 0xd3, 0xe3, 0xc8, 0xd1
+};
+
+static BYTE NLSALLOC(4001) rgbSNEGATIVESIGN[] = { /* "-" */
+ 0x2d
+};
+
+static BYTE NLSALLOC(4001) rgbIPOSSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(4001) rgbINEGSIGNPOSN[] = { /* "2" */
+ 0x32
+};
+
+static BYTE NLSALLOC(4001) rgbIPOSSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(4001) rgbIPOSSEPBYSPACE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(4001) rgbINEGSYMPRECEDES[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(4001) rgbINEGSEPBYSPACE[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(4001) rgbSENGCOUNTRY[] = { /* "Qatar" */
+ 0x51, 0x61, 0x74, 0x61, 0x72
+};
+
+static BYTE NLSALLOC(4001) rgbSENGLANGUAGE[] = { /* "Arabic" */
+ 0x41, 0x72, 0x61, 0x62, 0x69, 0x63
+};
+
+static BYTE NLSALLOC(4001) rgbIFIRSTDAYOFWEEK[] = { /* "5" */
+ 0x35
+};
+
+static BYTE NLSALLOC(4001) rgbIFIRSTWEEKOFYEAR[] = { /* "0" */
+ 0x30
+};
+
+static BYTE NLSALLOC(4001) rgbIDEFAULTANSICODEPAGE[] = { /* "1256" */
+ 0x31, 0x32, 0x35, 0x36
+};
+
+static BYTE NLSALLOC(4001) rgbINEGNUMBER[] = { /* "3" */
+ 0x33
+};
+
+static BYTE NLSALLOC(4001) rgbSTIMEFORMAT[] = { /* "H:mm:ss" */
+ 0x48, 0x3a, 0x6d, 0x6d, 0x3a, 0x73, 0x73
+};
+
+static BYTE NLSALLOC(4001) rgbITIMEMARKPOSN[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(4001) rgbICALENDARTYPE[] = { /* "1" */
+ 0x31
+};
+
+static BYTE NLSALLOC(4001) rgbIOPTIONALCALENDAR[] = { /* "0" */
+ 0x30
+};
+
+
+LCINFO NLSALLOC(4001) g_rglcinfo4001[] = {
+ { 0, NULL }
+ , { 4, rgbILANGUAGE }
+ , { 6, rgbSLANGUAGE }
+ , { 3, rgbSABBREVLANGNAME }
+ , { 7, rgbSNATIVELANGNAME }
+ , { 3, rgbICOUNTRY }
+ , { 5, rgbSCOUNTRY }
+ , { 3, rgbSABBREVCTRYNAME }
+ , { 3, rgbSNATIVECTRYNAME }
+ , { 4, rgbIDEFAULTLANGUAGE }
+ , { 3, rgbIDEFAULTCOUNTRY }
+ , { 3, rgbIDEFAULTCODEPAGE }
+ , { 1, rgbSLIST }
+ , { 1, rgbIMEASURE }
+ , { 1, rgbSDECIMAL }
+ , { 1, rgbSTHOUSAND }
+ , { 3, rgbSGROUPING }
+ , { 1, rgbIDIGITS }
+ , { 1, rgbILZERO }
+ , { 10, rgbSNATIVEDIGITS }
+ , { 5, rgbSCURRENCY }
+ , { 3, rgbSINTLSYMBOL }
+ , { 1, rgbSMONDECIMALSEP }
+ , { 1, rgbSMONTHOUSANDSEP }
+ , { 3, rgbSMONGROUPING }
+ , { 1, rgbICURRDIGITS }
+ , { 1, rgbIINTLCURRDIGITS }
+ , { 1, rgbICURRENCY }
+ , { 1, rgbINEGCURR }
+ , { 1, rgbSDATE }
+ , { 1, rgbSTIME }
+ , { 8, rgbSSHORTDATE }
+ , { 10, rgbSLONGDATE }
+ , { 1, rgbIDATE }
+ , { 1, rgbILDATE }
+ , { 1, rgbITIME }
+ , { 1, rgbICENTURY }
+ , { 1, rgbITLZERO }
+ , { 1, rgbIDAYLZERO }
+ , { 1, rgbIMONLZERO }
+ , { 1, rgbS1159 }
+ , { 1, rgbS2359 }
+ , { 5, rgbSDAYNAME1 }
+ , { 5, rgbSDAYNAME2 }
+ , { 7, rgbSDAYNAME3 }
+ , { 8, rgbSDAYNAME4 }
+ , { 8, rgbSDAYNAME5 }
+ , { 6, rgbSDAYNAME6 }
+ , { 6, rgbSDAYNAME7 }
+ , { 5, rgbSABBREVDAYNAME1 }
+ , { 5, rgbSABBREVDAYNAME2 }
+ , { 7, rgbSABBREVDAYNAME3 }
+ , { 8, rgbSABBREVDAYNAME4 }
+ , { 8, rgbSABBREVDAYNAME5 }
+ , { 6, rgbSABBREVDAYNAME6 }
+ , { 6, rgbSABBREVDAYNAME7 }
+ , { 5, rgbSMONTHNAME1 }
+ , { 6, rgbSMONTHNAME2 }
+ , { 4, rgbSMONTHNAME3 }
+ , { 5, rgbSMONTHNAME4 }
+ , { 4, rgbSMONTHNAME5 }
+ , { 5, rgbSMONTHNAME6 }
+ , { 5, rgbSMONTHNAME7 }
+ , { 5, rgbSMONTHNAME8 }
+ , { 6, rgbSMONTHNAME9 }
+ , { 6, rgbSMONTHNAME10 }
+ , { 6, rgbSMONTHNAME11 }
+ , { 6, rgbSMONTHNAME12 }
+ , { 5, rgbSABBREVMONTHNAME1 }
+ , { 6, rgbSABBREVMONTHNAME2 }
+ , { 4, rgbSABBREVMONTHNAME3 }
+ , { 5, rgbSABBREVMONTHNAME4 }
+ , { 4, rgbSABBREVMONTHNAME5 }
+ , { 5, rgbSABBREVMONTHNAME6 }
+ , { 5, rgbSABBREVMONTHNAME7 }
+ , { 5, rgbSABBREVMONTHNAME8 }
+ , { 6, rgbSABBREVMONTHNAME9 }
+ , { 6, rgbSABBREVMONTHNAME10 }
+ , { 6, rgbSABBREVMONTHNAME11 }
+ , { 6, rgbSABBREVMONTHNAME12 }
+ , { 0, NULL }
+ , { 1, rgbSNEGATIVESIGN }
+ , { 1, rgbIPOSSIGNPOSN }
+ , { 1, rgbINEGSIGNPOSN }
+ , { 1, rgbIPOSSYMPRECEDES }
+ , { 1, rgbIPOSSEPBYSPACE }
+ , { 1, rgbINEGSYMPRECEDES }
+ , { 1, rgbINEGSEPBYSPACE }
+ , { 5, rgbSENGCOUNTRY }
+ , { 6, rgbSENGLANGUAGE }
+ , { 1, rgbIFIRSTDAYOFWEEK }
+ , { 1, rgbIFIRSTWEEKOFYEAR }
+ , { 4, rgbIDEFAULTANSICODEPAGE }
+ , { 1, rgbINEGNUMBER }
+ , { 7, rgbSTIMEFORMAT }
+ , { 1, rgbITIMEMARKPOSN }
+ , { 1, rgbICALENDARTYPE }
+ , { 1, rgbIOPTIONALCALENDAR }
+ , { 0, NULL }
+ , { 0, NULL }
+};
+
+STRINFO NLSALLOC(4001) g_strinfo4001 = {
+ rgbUCase_0401
+ , rgbLCase_0401
+ , rgwCType12_0401
+ , rgwCType3_0401
+ , rgwSort_0401
+ , rgexp_0401
+ , NULL
+ , 0
+};
diff --git a/private/oleauto/src/dispatch/win16/invoke.asm b/private/oleauto/src/dispatch/win16/invoke.asm
new file mode 100644
index 000000000..e2fc79106
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/invoke.asm
@@ -0,0 +1,783 @@
+
+; TITLE invoke.asm
+;***
+;invoke.asm - automatic table driven method dispatch
+;
+; Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+; Information Contained Herein Is Proprietary and Confidential.
+;
+;Purpose:
+; This file contains the low level support for the default
+; implementaion of ITypeInfo::Invoke().
+;
+;Revision History:
+;
+; [00] 19-Oct-92 bradlo: Created from invoke.c
+;
+;Implementation Notes:
+;
+;******************************************************************************
+
+
+ .286
+ .MODEL large, C
+
+ OPTION CASEMAP:NONE
+
+
+extern g_S_OK:DWORD
+extern g_E_INVALIDARG:DWORD
+
+
+;; Note: the following must match the definitions from dispatch.h
+;;
+VT_EMPTY equ 0
+VT_NULL equ 1
+VT_I2 equ 2
+VT_I4 equ 3
+VT_R4 equ 4
+VT_R8 equ 5
+VT_CY equ 6
+VT_DATE equ 7
+VT_BSTR equ 8
+VT_DISPATCH equ 9
+VT_ERROR equ 10
+VT_BOOL equ 11
+VT_VARIANT equ 12
+VT_UNKNOWN equ 13
+
+VT_MAX equ 14
+
+IF VBA2
+;; 14 is unused
+;; 15 is unused
+;VT_I1 equ 16
+VT_UI1 equ 17
+ENDIF ;VBA2
+
+
+;; Note: the following must match the definition of VARIANT in dispatch.h
+;;
+VARIANTARG STRUCT
+ vt DW ?
+ wReserved1 DW ?
+ wReserved2 DW ?
+ wReserved3 DW ?
+ dw0 DW ?
+ dw1 DW ?
+ dw2 DW ?
+ dw3 DW ?
+VARIANTARG ENDS
+
+;; offset of the data from the beginning of the struct
+VARIANT_DATA_OFFSET equ 8
+
+
+ .CONST
+
+;; ammout of data to be pushed for the corresponding VARTYPE
+;;
+rgcbVtSize DB 0 ; VT_EMPTY
+ DB 4 ; VT_NULL
+ DB 2 ; VT_I2
+ DB 4 ; VT_I4
+ DB 4 ; VT_R4
+ DB 8 ; VT_R8
+ DB 8 ; VT_CY
+ DB 8 ; VT_DATE
+ DB 4 ; VT_BSTR
+ DB 4 ; VT_DISPATCH
+ DB 4 ; VT_ERROR
+ DB 2 ; VT_BOOL
+ DB 16 ; VT_VARIANT
+ DB 4 ; VT_UNKNOWN
+IF VBA2
+ DB 0 ; 14 is unused
+ DB 0 ; 15 is unused
+ DB 2 ; VT_I1
+ DB 2 ; VT_UI1
+ENDIF ;VBA2
+
+rgfStructReturn DB 0 ; VT_EMPTY
+ DB 0 ; VT_NULL
+ DB 0 ; VT_I2
+ DB 0 ; VT_I4
+ DB 0 ; VT_R4
+ DB 0 ; VT_R8
+ DB 1 ; VT_CY
+ DB 0 ; VT_DATE
+ DB 0 ; VT_BSTR
+ DB 0 ; VT_DISPATCH
+ DB 0 ; VT_ERROR
+ DB 0 ; VT_BOOL
+ DB 1 ; VT_VARIANT
+ DB 0 ; VT_UNKNOWN
+IF VBA2
+ DB 0 ; 14 is unused
+ DB 0 ; 15 is unused
+ DB 0 ; VT_I1
+ DB 0 ; VT_UI1
+ENDIF ;VBA2
+
+rgfFloatReturn DB 0 ; VT_EMPTY
+ DB 0 ; VT_NULL
+ DB 0 ; VT_I2
+ DB 0 ; VT_I4
+ DB 1 ; VT_R4
+ DB 1 ; VT_R8
+ DB 0 ; VT_CY
+ DB 1 ; VT_DATE
+ DB 0 ; VT_BSTR
+ DB 0 ; VT_DISPATCH
+ DB 0 ; VT_ERROR
+ DB 0 ; VT_BOOL
+ DB 0 ; VT_VARIANT
+ DB 0 ; VT_UNKNOWN
+IF VBA2
+ DB 0 ; 14 is unused
+ DB 0 ; 15 is unused
+ DB 0 ; VT_I1
+ DB 0 ; VT_UI1
+ENDIF ;VBA2
+
+ .CODE STDIMPL
+
+;***
+;InvokePascal
+;
+;extern "C" SCODE
+;InvokePascal(
+; void FAR* pvMethod,
+; SHORT oVft,
+; VARTYPE vtReturn,
+; UINT cActuals,
+; VARTYPE FAR* rgvt,
+; VARIANTARG FAR* rgpvarg,
+; VARIANTARG FAR* pvargResult)
+;
+;Purpose:
+; Invoke a virtual Pascal method using the given this pointer,
+; method index and array of parameters.
+;
+; The Pascal member function calling convention (MSC v7.0)
+; --------------------------------------------------------
+; - arguments pushed left to right
+; - callee clean (ie, the callee adjusts the sp on return)
+; - model specific this* always pushed last
+;
+; return values are handled as follows,
+;
+; vartype fundamental return location
+; ------------------------------------------------
+; VT_UI1 unsigned char al
+; VT_I2 short ax
+; VT_I4 long ax:dx
+; VT_R4 float float-return(1)
+; VT_R8 double float-return
+; VT_DATE double float-return
+; VT_CY struct struct-return(2)
+; VT_BSTR char FAR* ax:dx
+; VT_UNKNOWN void FAR* ax:dx
+; VT_DISPATCH void FAR* ax:dx
+; VT_ERROR long ax:dx
+; VT_BOOL short ax
+; VT_VARIANT VARIANTARG struct-return
+;
+; 1. floating point returns
+;
+; Floating point values are returned in a caller allocated buffer.
+; a *near* pointer to this buffer is passed as a hidden parameter,
+; and is pushed as the last (ie, rightmost) parameter. This means
+; that it is always located immediately before the 'this' pointer.
+;
+; A model specific pointer to this caller allocated buffer is
+; passed back in ax[:dx]. All this means is that the callee returns
+; the address we passed in as the hidden param, and sticks SS into
+; DX if the callee is large model (see following note).
+;
+; Note: the compiler *assumes* that this caller allocated buffer
+; is SS relative (hence the reason it only passes a near pointer),
+; so the following code is careful to ensure this.
+;
+; 2. structure returns
+;
+; Structures are returned in a caller allocated buffer, and are
+; handled exactly the same as float returns except that the pointer
+; to the buffer is always pushed as the first (leftmost) param. This
+; is opposite of the location it is passed for float returns (I
+; have no idea why there different).
+;
+;
+; Limitations & assumptions
+; -------------------------
+; Only supports far calls.
+;
+; UNDONE: no support for VT_ARRAY
+;
+;Entry:
+; pvMethod = ptr to the method to invoke
+; cArgs = count of the number of actuals
+; rgvt = array of VARTYPES describing the methods formals
+; rgpvarg = array of VARIANTARG*s, which map the actuals by position
+; vtReturn = the VARTYPE of the return value
+;
+;Exit:
+; pvargResult = VARIANTARG containing the method return value
+;
+;Uses:
+; bx, si, di
+;
+;Preserves:
+;
+;
+;***********************************************************************
+InvokePascal PROC FAR C PUBLIC USES si di,
+ _this : FAR PTR,
+ oVft : WORD,
+ vtReturn : WORD,
+ cActuals : WORD,
+ rgvt : FAR PTR,
+ rgpvarg : FAR PTR,
+ pvargResult : FAR PTR
+
+LOCAL pEnd : WORD,
+ savedSP : WORD,
+ vargHiddenParam : VARIANTARG
+
+
+ mov savedSP, sp
+
+ ;; if its a structure return, we must push the 'hidden'
+ ;; parameter first.
+ ;;
+ mov bx, ss:vtReturn
+ test bh, 040h ; VT_BYREF
+ jnz LRetInvalidArg
+ test bh, 020h ; VT_ARRAY
+ jnz LNoStructReturn
+ mov al, BYTE PTR rgfStructReturn[bx]
+ cmp al, 0
+ jz LNoStructReturn
+
+ ;; push the address of the struct return hidden param
+ ;;
+ ;; Note: the hidparam is passed as a FAR* because we
+ ;; explicitly declare all of our structs FAR.
+ ;;
+ lea ax, vargHiddenParam;
+ push ss
+ push ax
+
+LNoStructReturn:
+
+ mov cx, ss:cActuals
+ cmp cx, 0
+ jz LDoCall
+
+ ;; di = rgpvarg
+ ;;
+ mov di, WORD PTR ss:rgpvarg
+
+ ;; cx = &rgpvarg[cActuals-1] ; last arg
+ ;;
+ dec cx
+ shl cx, 2 ; log2(sizeof(FAR*))
+ add cx, di
+ mov ss:pEnd, cx
+
+
+LArgLoop:
+
+ ;; dx:cx = &rgvt[i]
+ ;;
+ mov cx, WORD PTR ss:rgvt
+ mov dx, WORD PTR ss:rgvt+2
+
+LArgsTop:
+
+ ;; bx = rgvt[i]
+ ;;
+ mov es, dx
+ mov bx, cx
+ mov bx, es:[bx]
+
+ ;; load the VARIANTARG* in preparation for pushing
+ ;;
+ mov ax, WORD PTR ss:rgpvarg+2
+ mov es, ax
+ les si, es:[di]
+
+ test bh, 060h ; VT_BYREF | VT_ARRAY
+ jnz LPush4 ; all ByRefs are sizeof(FAR*)
+
+ ;; lookup size of the param in rgcbVtSize table
+ ;;
+ and bh, 01fh ; ~(mode bits)
+ ;REVIEW: should verify index in range
+ mov al, BYTE PTR rgcbVtSize[bx]
+
+ cmp al, 0
+ jl LRetInvalidArg
+ jz LNextArg
+ sub al, 2
+ jz LPush2
+ sub al, 2
+ jz LPush4
+ sub al, 4
+ jz LPush8
+ sub al, 8
+ jz LPush16
+ jmp LRetInvalidArg
+
+ Align 2
+LPush16: ; push the entire variant
+ push es:[si+14]
+ push es:[si+12]
+ push es:[si+10]
+ push es:[si+8]
+ push es:[si+6]
+ push es:[si+4]
+ push es:[si+2]
+ push es:[si]
+ jmp LNextArg
+
+ Align 2
+LPush8: ; 8 bytes of data
+ push (VARIANTARG PTR es:[si]).dw3
+ push (VARIANTARG PTR es:[si]).dw2
+LPush4: ; 4 bytes of data
+ push (VARIANTARG PTR es:[si]).dw1
+LPush2: ; 2 bytes of data
+ push (VARIANTARG PTR es:[si]).dw0
+
+LNextArg:
+ add cx, sizeof WORD ; cx += sizeof(VARTYPE)
+ cmp di, WORD PTR ss:pEnd
+ jae LDoCall
+ add di, 4 ; di += sizeof(VARIANTARG FAR*)
+ jmp LArgsTop
+
+LDoCall:
+ ;; if its a floating point return, we must push the
+ ;; 'hidden' parameter last.
+ ;;
+ mov bx, ss:vtReturn
+ test bh, 020h ; VT_ARRAY
+ jnz LNoFloatReturn
+ mov al, rgfFloatReturn[bx]
+ cmp al, 0
+ jz LNoFloatReturn
+
+ ;; Routines that return via a hidparam, take a near ptr to the
+ ;; area in which to store the result. We dont know if the given
+ ;; pvargResult is near, so we can't push it directly. Instead we
+ ;; push something local (that we know is near because its on the
+ ;; stack), and we will copy it to pvargResult after the call.
+ ;;
+ lea ax, vargHiddenParam;
+ push ax
+
+LNoFloatReturn:
+
+ ;; push the 'this' pointer.
+ ;;
+ les bx, _this
+ push es
+ push bx
+
+ ;; load the vtable offset
+ ;;
+ mov si, ss:oVft
+
+ les bx, es:[bx] ; @ vtable*
+ call DWORD PTR es:[bx][si]
+
+ ;; CONSIDER: verify that the callee adjusted the stack the way
+ ;; we expected. something like,
+ ;;
+ ;; if(sp != savedSP){
+ ;; sp = savedSP;
+ ;; return DISP_E_BADCALLEE
+ ;; }
+ ;;
+
+ ;; Grab the return value.
+ ;; We are going to grab the value based on the VARTYPE in
+ ;; the given vtReturn. This VARTYPE is used as a description
+ ;; of the return value, not a desired target type. ie, no
+ ;; coercions are performed. See the function header for a
+ ;; description of the Pascal member function return value
+ ;; convention.
+ ;;
+
+ mov si, ax
+
+ les di, ss:pvargResult
+
+ mov bx, ss:vtReturn
+ mov (VARIANTARG PTR es:[di]).vt, bx
+
+ test bh, 060h ; VT_BYREF | VT_ARRAY
+ jnz LRetPtr
+
+ ; Assert((bh & VT_ARRAY) == 0);
+
+IF VBA2
+ cmp bx, VT_UI1
+ je ValidVartype
+ENDIF ;;VBA2
+ cmp bx, VT_MAX
+ jae LRetInvalidArg
+
+ValidVartype:
+ shl bx, 1
+ jmp WORD PTR cs:LRetValJmpTab[bx]
+
+ Align 2
+LRetValJmpTab:
+ DW LDone ; VT_EMPTY
+ DW LRetI4 ; VT_NULL
+ DW LRetI2 ; VT_I2
+ DW LRetI4 ; VT_I4
+ DW LCpy4 ; VT_R4
+ DW LCpy8 ; VT_R8
+ DW LCpy8 ; VT_CY
+ DW LCpy8 ; VT_DATE
+ DW LRetPtr ; VT_BSTR
+ DW LRetPtr ; VT_DISPATCH
+ DW LRetI4 ; VT_ERROR
+ DW LRetI2 ; VT_BOOL
+ DW LCpy16 ; VT_VARIANT
+ DW LRetPtr ; VT_UNKNOWN
+IF VBA2
+ DW LRetInvalidArg ; unused
+ DW LRetInvalidArg ; unused
+ DW LRetInvalidArg ; VT_I1
+ DW LRetUI1 ; VT_UI1
+ENDIF ;VBA2
+
+
+ Align 2
+LCpy8:
+ add di, VARIANT_DATA_OFFSET
+ mov cx, 4
+ jmp LCpy
+
+ Align 2
+LCpy4:
+ add di, VARIANT_DATA_OFFSET
+ mov cx, 2
+ jmp LCpy
+
+ Align 2
+LCpy16:
+ mov cx, 8
+ ; FALLTHROUGH
+
+LCpy:
+ rep movsw es:[di], ss:[si]
+ jmp LDone
+
+ Align 2
+LRetI4:
+LRetPtr:
+ mov (VARIANTARG PTR es:[di]).dw1, dx
+LRetI2:
+LRetUI1:
+ mov (VARIANTARG PTR es:[di]).dw0, ax
+
+LDone:
+ mov ax, WORD PTR g_S_OK
+ mov dx, WORD PTR g_S_OK+2
+ ret
+
+LRetInvalidArg:
+ mov sp, savedSP
+ mov ax, WORD PTR g_E_INVALIDARG
+ mov dx, WORD PTR g_E_INVALIDARG+2
+ ret
+InvokePascal ENDP
+
+
+;***
+;InvokeCdecl
+;
+;extern "C" SCODE CDECL
+;InvokeCdecl
+; void FAR* _this,
+; SHORT oVft,
+; VARTYPE vtReturn,
+; UINT cActuals,
+; VARTYPE FAR* rgvt,
+; VARIANTARG FAR* rgpvarg,
+; VARIANTARG FAR* pvargResult)
+;
+;Purpose:
+; see InvokePascal
+;
+;Entry:
+; see InvokePascal
+;
+;Exit:
+; see InvokePascal
+;
+;Uses:
+; bx, si, di
+;
+;Preserves:
+; UNDONE
+;
+;***********************************************************************
+InvokeCdecl PROC FAR C PUBLIC USES si di,
+ _this : FAR PTR,
+ oVft : WORD,
+ vtReturn : WORD,
+ cActuals : WORD,
+ rgvt : FAR PTR,
+ rgpvarg : FAR PTR,
+ pvargResult : FAR PTR
+
+LOCAL savedSP : WORD,
+ vargHiddenParam : VARIANTARG
+
+
+ mov savedSP, sp
+
+ ; InvokeCdecl doesn't support methods that return VT_R4 or VT_R8
+ ;
+ ; Cdecl methods return floating point values in a static
+ ; data area called __fac, and return the address of that data
+ ; area in ax. Unfortunately the data area is in the callers
+ ; default data segment, and the calling convention only returns
+ ; a near* (offset) - so we dont have any reasonable way of
+ ; locating the value.
+ ;
+ mov bx, ss:vtReturn
+ test bh, 040h ; VT_BYREF
+ jnz LRetInvalidArg
+ test bh, 020h ; VT_ARRAY
+ jnz LRetOk
+ mov al, rgfFloatReturn[bx]
+ cmp al, 0
+ jnz LRetInvalidArg
+
+LRetOk:
+
+ mov ax, ss:cActuals
+ cmp ax, 0
+ jz LDoCall
+
+ ;; di = &rgpvarg[cActuals-1]
+ ;;
+ dec ax
+ mov di, ax
+ shl di, 2 ; (cArgs-1)*sizeof(FAR*)
+ add di, WORD PTR ss:rgpvarg
+
+
+ ;; dx:cx = &rgvt[cActuals-1]
+ ;;
+ mov cx, WORD PTR ss:rgvt
+ add cx, ax
+ add cx, ax ; rgvt+((cArgs-1)*sizeof(WORD))
+ mov dx, WORD PTR ss:rgvt+2
+
+LArgsTop:
+
+ ;; bx = rgvt[i]
+ ;;
+ mov es, dx
+ mov bx, cx
+ mov bx, es:[bx]
+
+ ;; load the VARIANTARG* in preparation for pushing
+ ;;
+ mov ax, WORD PTR ss:rgpvarg+2
+ mov es, ax
+ les si, es:[di]
+
+ test bh, 060h ; VT_BYREF | VT_ARRAY
+ jnz LPush4 ; all ByRefs are sizeof(FAR*)
+
+ ;; lookup size of the param in rgcbVtSize table
+ ;;
+ and bh, 01fh ; ~(mode bits)
+ mov al, BYTE PTR rgcbVtSize[bx]
+
+ cmp al, 0
+ jl LRetInvalidArg
+ jz LNextArg
+ sub al, 2
+ jz LPush2
+ sub al, 2
+ jz LPush4
+ sub al, 4
+ jz LPush8
+ sub al, 8
+ jz LPush16
+ jmp LRetInvalidArg
+
+ Align 2
+LPush16: ; push the entire variant
+ push es:[si+14]
+ push es:[si+12]
+ push es:[si+10]
+ push es:[si+8]
+ push es:[si+6]
+ push es:[si+4]
+ push es:[si+2]
+ push es:[si]
+ jmp LNextArg
+
+ Align 2
+LPush8: ; 8 bytes of data
+ push (VARIANTARG PTR es:[si]).dw3
+ push (VARIANTARG PTR es:[si]).dw2
+LPush4: ; 4 bytes of data
+ push (VARIANTARG PTR es:[si]).dw1
+LPush2: ; 2 bytes of data
+ push (VARIANTARG PTR es:[si]).dw0
+
+LNextArg:
+ sub cx, sizeof WORD ; sizeof(VARTYPE)
+
+ cmp di, WORD PTR ss:rgpvarg
+ jbe LDoCall
+ sub di, 4 ; sizeof(VARIANTARG FAR*)
+ jmp LArgsTop
+
+LDoCall:
+ ;; if its a structure return, we must push a 'hidden' argument
+ ;;
+ mov bx, ss:vtReturn
+ test bh, 020h ; VT_ARRAY
+ jnz LPushThis
+ mov al, BYTE PTR rgfStructReturn[bx]
+ cmp al, 0
+ jz LPushThis
+
+ ;; push the address of the struct return hidden param
+ ;;
+ ;; Note: the hidparam is passed as a FAR* because we
+ ;; explicitly declare all of our structs FAR.
+ ;;
+ lea ax, vargHiddenParam;
+ push ss
+ push ax
+
+LPushThis:
+
+ ;; push the this pointer.
+ ;;
+ les bx, _this
+ push es
+ push bx
+
+ ;; load the vtable offset
+ ;;
+ mov si, ss:oVft
+
+ les bx, es:[bx] ; @ vtable*
+ call DWORD PTR es:[bx][si]
+ mov sp, savedSP
+
+ ;; CONSIDER: verify that the callee adjusted the stack the way
+ ;; we expected. something like,
+ ;;
+ ;; if(sp != savedSP){
+ ;; sp = savedSP;
+ ;; return DISP_E_SomeError
+ ;; }
+ ;;
+
+ ;; Grab the return value.
+ ;; We are going to grab the value based on the VARTYPE in
+ ;; the given vtReturn. This VARTYPE is used as a description
+ ;; of the return value, not a desired target type. ie, no
+ ;; coercions are performed. See the function header for a
+ ;; description of the Pascal member function return value
+ ;; convention.
+ ;;
+
+ mov si, ax
+
+ les di, ss:pvargResult
+
+ mov bx, ss:vtReturn
+ mov (VARIANTARG PTR es:[di]).vt, bx
+
+ test bh, 060h ; VT_BYREF | VT_ARRAY
+ jnz LRetPtr
+
+ ; Assert((bh & VT_ARRAY) == 0);
+
+IF VBA2
+ cmp bx, VT_UI1
+ je ValidVartype
+ENDIF ;;VBA2
+ cmp bx, VT_MAX
+ jae LRetInvalidArg
+
+ValidVartype:
+ shl bx, 1
+ jmp WORD PTR cs:LRetValJmpTab[bx]
+
+ Align 2
+LRetValJmpTab:
+ DW LDone ; VT_EMPTY
+ DW LRetI4 ; VT_NULL
+ DW LRetI2 ; VT_I2
+ DW LRetI4 ; VT_I4
+ DW LRetInvalidArg ; VT_R4
+ DW LRetInvalidArg ; VT_R8
+ DW LCpy8 ; VT_CY
+ DW LRetInvalidArg ; VT_DATE
+ DW LRetPtr ; VT_BSTR
+ DW LRetPtr ; VT_DISPATCH
+ DW LRetI4 ; VT_ERROR
+ DW LRetI2 ; VT_BOOL
+ DW LCpy16 ; VT_VARIANT
+ DW LRetPtr ; VT_UNKNOWN
+IF VBA2
+ DW LRetInvalidArg ; unused
+ DW LRetInvalidArg ; unused
+ DW LRetInvalidArg ; VT_I1
+ DW LRetUI1 ; VT_UI1
+ENDIF ;VBA2
+
+
+ Align 2
+LCpy8:
+ add di, VARIANT_DATA_OFFSET
+ mov cx, 4
+ jmp LCpy
+
+ Align 2
+LCpy16:
+ mov cx, 8
+ ; FALLTHROUGH
+
+LCpy:
+ rep movsw es:[di], ss:[si]
+ jmp LDone
+
+ Align 2
+LRetI4:
+LRetPtr:
+ mov (VARIANTARG PTR es:[di]).dw1, dx
+LRetI2:
+LRetUI1:
+ mov (VARIANTARG PTR es:[di]).dw0, ax
+
+LDone:
+ mov ax, WORD PTR g_S_OK
+ mov dx, WORD PTR g_S_OK+2
+ ret
+
+LRetInvalidArg:
+ mov sp, savedSP
+ mov ax, WORD PTR g_E_INVALIDARG
+ mov dx, WORD PTR g_E_INVALIDARG+2
+ ret
+InvokeCdecl ENDP
+END
diff --git a/private/oleauto/src/dispatch/win16/loc11-3.txt b/private/oleauto/src/dispatch/win16/loc11-3.txt
new file mode 100644
index 000000000..f26536ddb
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/loc11-3.txt
@@ -0,0 +1,4900 @@
+LOCALE 41
+
+BEGINLOCALE 0404 ; Chinese - Taiwan
+
+ ILANGUAGE 0404
+ SENGLANGUAGE Chinese
+ SABBREVLANGNAME CHT
+ SNATIVELANGNAME \x4e2d\x6587
+
+ ICOUNTRY 886
+ SENGCOUNTRY Taiwan
+ SABBREVCTRYNAME TWN
+ SNATIVECTRYNAME \x4e2d\x83ef\x6c11\x570b
+
+ IDEFAULTLANGUAGE 0404
+ IDEFAULTCOUNTRY 886
+ IDEFAULTANSICODEPAGE 950
+ IDEFAULTOEMCODEPAGE 950
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY NT$
+ SINTLSYMBOL TWD
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 2
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 tt h:mm:ss
+ tt hh:mm:ss
+ H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 0
+ ITLZERO 0
+ S1159 \x4e0a\x5348
+ S2359 \x4e0b\x5348
+
+ SSHORTDATE 4 yy/M/d
+ yy/MM/dd
+ yyyy/M/d
+ yyyy/MM/dd
+ SDATE /
+ IDATE 2
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 0
+
+ SLONGDATE 3 dddd yyyy MMMM dd
+ dddd' 'yyyy' 'MM' 'dd
+ yyyy' 'MM' 'dd
+ ILDATE 2
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 4\xffffEra: Year of the Republic of China
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 6
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x661f\x671f\x4e00
+ SDAYNAME2 \x661f\x671f\x4e8c
+ SDAYNAME3 \x661f\x671f\x4e09
+ SDAYNAME4 \x661f\x671f\x56db
+ SDAYNAME5 \x661f\x671f\x4e94
+ SDAYNAME6 \x661f\x671f\x516d
+ SDAYNAME7 \x661f\x671f\x65e5
+
+ SABBREVDAYNAME1 \x661f\x671f\x4e00
+ SABBREVDAYNAME2 \x661f\x671f\x4e8c
+ SABBREVDAYNAME3 \x661f\x671f\x4e09
+ SABBREVDAYNAME4 \x661f\x671f\x56db
+ SABBREVDAYNAME5 \x661f\x671f\x4e94
+ SABBREVDAYNAME6 \x661f\x671f\x516d
+ SABBREVDAYNAME7 \x661f\x671f\x65e5
+
+ SMONTHNAME1 \x4e00\x6708
+ SMONTHNAME2 \x4e8c\x6708
+ SMONTHNAME3 \x4e09\x6708
+ SMONTHNAME4 \x56db\x6708
+ SMONTHNAME5 \x4e94\x6708
+ SMONTHNAME6 \x516d\x6708
+ SMONTHNAME7 \x4e03\x6708
+ SMONTHNAME8 \x516b\x6708
+ SMONTHNAME9 \x4e5d\x6708
+ SMONTHNAME10 \x5341\x6708
+ SMONTHNAME11 \x5341\x4e00\x6708
+ SMONTHNAME12 \x5341\x4e8c\x6708
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 \x4e00\x6708
+ SABBREVMONTHNAME2 \x4e8c\x6708
+ SABBREVMONTHNAME3 \x4e09\x6708
+ SABBREVMONTHNAME4 \x56db\x6708
+ SABBREVMONTHNAME5 \x4e94\x6708
+ SABBREVMONTHNAME6 \x516d\x6708
+ SABBREVMONTHNAME7 \x4e03\x6708
+ SABBREVMONTHNAME8 \x516b\x6708
+ SABBREVMONTHNAME9 \x4e5d\x6708
+ SABBREVMONTHNAME10 \x5341\x6708
+ SABBREVMONTHNAME11 \x5341\x4e00\x6708
+ SABBREVMONTHNAME12 \x5341\x4e8c\x6708
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0804 ; Chinese - PRC
+
+ ILANGUAGE 0804
+ SENGLANGUAGE Chinese
+ SABBREVLANGNAME CHS
+ SNATIVELANGNAME \x4e2d\x6587
+
+ ICOUNTRY 86
+ SENGCOUNTRY Peoples' Republic of China
+ SABBREVCTRYNAME CHN
+ SNATIVECTRYNAME \x4e2d\x534e\x4eba\x6c11\x5171\x548c\x56fd
+
+ IDEFAULTLANGUAGE 0804
+ IDEFAULTCOUNTRY 86
+ IDEFAULTANSICODEPAGE 936
+ IDEFAULTOEMCODEPAGE 936
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY \x00a5
+ SINTLSYMBOL CNY
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 2
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 tt h:mm:ss
+ tt hh:mm:ss
+ H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 0
+ ITLZERO 0
+ S1159 \x4e0a\x5348
+ S2359 \x4e0b\x5348
+
+ SSHORTDATE 4 yy/M/d
+ yy/MM/dd
+ yyyy/M/d
+ yyyy/MM/dd
+ SDATE /
+ IDATE 2
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 0
+
+ SLONGDATE 3 dddd, MMMM d, yyyy
+ yyyy' 'MM' 'dd
+ dddd' 'yyyy' 'MM' 'dd
+ ILDATE 2
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 6
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x661f\x671f\x4e00
+ SDAYNAME2 \x661f\x671f\x4e8c
+ SDAYNAME3 \x661f\x671f\x4e09
+ SDAYNAME4 \x661f\x671f\x56db
+ SDAYNAME5 \x661f\x671f\x4e94
+ SDAYNAME6 \x661f\x671f\x516d
+ SDAYNAME7 \x661f\x671f\x65e5
+
+ SABBREVDAYNAME1 \x661f\x671f\x4e00
+ SABBREVDAYNAME2 \x661f\x671f\x4e8c
+ SABBREVDAYNAME3 \x661f\x671f\x4e09
+ SABBREVDAYNAME4 \x661f\x671f\x56db
+ SABBREVDAYNAME5 \x661f\x671f\x4e94
+ SABBREVDAYNAME6 \x661f\x671f\x516d
+ SABBREVDAYNAME7 \x661f\x671f\x65e5
+
+ SMONTHNAME1 \x4e00\x6708
+ SMONTHNAME2 \x4e8c\x6708
+ SMONTHNAME3 \x4e09\x6708
+ SMONTHNAME4 \x56db\x6708
+ SMONTHNAME5 \x4e94\x6708
+ SMONTHNAME6 \x516d\x6708
+ SMONTHNAME7 \x4e03\x6708
+ SMONTHNAME8 \x516b\x6708
+ SMONTHNAME9 \x4e5d\x6708
+ SMONTHNAME10 \x5341\x6708
+ SMONTHNAME11 \x5341\x4e00\x6708
+ SMONTHNAME12 \x5341\x4e8c\x6708
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 \x4e00\x6708
+ SABBREVMONTHNAME2 \x4e8c\x6708
+ SABBREVMONTHNAME3 \x4e09\x6708
+ SABBREVMONTHNAME4 \x56db\x6708
+ SABBREVMONTHNAME5 \x4e94\x6708
+ SABBREVMONTHNAME6 \x516d\x6708
+ SABBREVMONTHNAME7 \x4e03\x6708
+ SABBREVMONTHNAME8 \x516b\x6708
+ SABBREVMONTHNAME9 \x4e5d\x6708
+ SABBREVMONTHNAME10 \x5341\x6708
+ SABBREVMONTHNAME11 \x5341\x4e00\x6708
+ SABBREVMONTHNAME12 \x5341\x4e8c\x6708
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0C04 ; Chinese - Hong Kong
+
+ ILANGUAGE 0C04
+ SENGLANGUAGE Chinese
+ SABBREVLANGNAME CHH
+ SNATIVELANGNAME \x4e2d\x6587
+
+ ICOUNTRY 852
+ SENGCOUNTRY Hong Kong
+ SABBREVCTRYNAME HKG
+ SNATIVECTRYNAME \x9999\x6e2f
+
+ IDEFAULTLANGUAGE 0C04
+ IDEFAULTCOUNTRY 852
+ IDEFAULTANSICODEPAGE 950
+ IDEFAULTOEMCODEPAGE 950
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY HK$
+ SINTLSYMBOL HKD
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 0
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 tt h:mm:ss
+ tt hh:mm:ss
+ H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 0
+ ITLZERO 0
+ S1159 AM
+ S2359 PM
+
+ SSHORTDATE 6 d/M/yy
+ dd/MM/yy
+ yy/M/d
+ yy/MM/dd
+ yyyy/M/d
+ yyyy/MM/dd
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 0
+
+ SLONGDATE 3 dddd, d MMMM, yyyy
+ dddd' 'yyyy' 'MM' 'dd
+ yyyy' 'MM' 'dd
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 6
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x661f\x671f\x4e00
+ SDAYNAME2 \x661f\x671f\x4e8c
+ SDAYNAME3 \x661f\x671f\x4e09
+ SDAYNAME4 \x661f\x671f\x56db
+ SDAYNAME5 \x661f\x671f\x4e94
+ SDAYNAME6 \x661f\x671f\x516d
+ SDAYNAME7 \x661f\x671f\x65e5
+
+ SABBREVDAYNAME1 \x661f\x671f\x4e00
+ SABBREVDAYNAME2 \x661f\x671f\x4e8c
+ SABBREVDAYNAME3 \x661f\x671f\x4e09
+ SABBREVDAYNAME4 \x661f\x671f\x56db
+ SABBREVDAYNAME5 \x661f\x671f\x4e94
+ SABBREVDAYNAME6 \x661f\x671f\x516d
+ SABBREVDAYNAME7 \x661f\x671f\x65e5
+
+ SMONTHNAME1 \x4e00\x6708
+ SMONTHNAME2 \x4e8c\x6708
+ SMONTHNAME3 \x4e09\x6708
+ SMONTHNAME4 \x56db\x6708
+ SMONTHNAME5 \x4e94\x6708
+ SMONTHNAME6 \x516d\x6708
+ SMONTHNAME7 \x4e03\x6708
+ SMONTHNAME8 \x516b\x6708
+ SMONTHNAME9 \x4e5d\x6708
+ SMONTHNAME10 \x5341\x6708
+ SMONTHNAME11 \x5341\x4e00\x6708
+ SMONTHNAME12 \x5341\x4e8c\x6708
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 \x4e00\x6708
+ SABBREVMONTHNAME2 \x4e8c\x6708
+ SABBREVMONTHNAME3 \x4e09\x6708
+ SABBREVMONTHNAME4 \x56db\x6708
+ SABBREVMONTHNAME5 \x4e94\x6708
+ SABBREVMONTHNAME6 \x516d\x6708
+ SABBREVMONTHNAME7 \x4e03\x6708
+ SABBREVMONTHNAME8 \x516b\x6708
+ SABBREVMONTHNAME9 \x4e5d\x6708
+ SABBREVMONTHNAME10 \x5341\x6708
+ SABBREVMONTHNAME11 \x5341\x4e00\x6708
+ SABBREVMONTHNAME12 \x5341\x4e8c\x6708
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 1004 ; Chinese - Singapore
+
+ ILANGUAGE 1004
+ SENGLANGUAGE Chinese
+ SABBREVLANGNAME CHI
+ SNATIVELANGNAME \x4e2d\x6587
+
+ ICOUNTRY 65
+ SENGCOUNTRY Singapore
+ SABBREVCTRYNAME SGP
+ SNATIVECTRYNAME \x65b0\x52a0\x5761
+
+ IDEFAULTLANGUAGE 1004
+ IDEFAULTCOUNTRY 65
+ IDEFAULTANSICODEPAGE 936
+ IDEFAULTOEMCODEPAGE 936
+
+ SLIST ,
+ IMEASURE 1
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY $
+ SINTLSYMBOL SGD
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 0
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 tt h:mm:ss
+ tt hh:mm:ss
+ H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 0
+ ITLZERO 0
+ S1159 AM
+ S2359 PM
+
+ SSHORTDATE 6 d/M/yy
+ dd/MM/yy
+ yy/M/d
+ yy/MM/dd
+ yyyy/M/d
+ yyyy/MM/dd
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 0
+
+ SLONGDATE 3 dddd, d MMMM, yyyy
+ dddd' 'yyyy' 'MM' 'dd
+ yyyy' 'MM' 'dd
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 6
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x661f\x671f\x4e00
+ SDAYNAME2 \x661f\x671f\x4e8c
+ SDAYNAME3 \x661f\x671f\x4e09
+ SDAYNAME4 \x661f\x671f\x56db
+ SDAYNAME5 \x661f\x671f\x4e94
+ SDAYNAME6 \x661f\x671f\x516d
+ SDAYNAME7 \x661f\x671f\x65e5
+
+ SABBREVDAYNAME1 \x661f\x671f\x4e00
+ SABBREVDAYNAME2 \x661f\x671f\x4e8c
+ SABBREVDAYNAME3 \x661f\x671f\x4e09
+ SABBREVDAYNAME4 \x661f\x671f\x56db
+ SABBREVDAYNAME5 \x661f\x671f\x4e94
+ SABBREVDAYNAME6 \x661f\x671f\x516d
+ SABBREVDAYNAME7 \x661f\x671f\x65e5
+
+ SMONTHNAME1 \x4e00\x6708
+ SMONTHNAME2 \x4e8c\x6708
+ SMONTHNAME3 \x4e09\x6708
+ SMONTHNAME4 \x56db\x6708
+ SMONTHNAME5 \x4e94\x6708
+ SMONTHNAME6 \x516d\x6708
+ SMONTHNAME7 \x4e03\x6708
+ SMONTHNAME8 \x516b\x6708
+ SMONTHNAME9 \x4e5d\x6708
+ SMONTHNAME10 \x5341\x6708
+ SMONTHNAME11 \x5341\x4e00\x6708
+ SMONTHNAME12 \x5341\x4e8c\x6708
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 \x4e00\x6708
+ SABBREVMONTHNAME2 \x4e8c\x6708
+ SABBREVMONTHNAME3 \x4e09\x6708
+ SABBREVMONTHNAME4 \x56db\x6708
+ SABBREVMONTHNAME5 \x4e94\x6708
+ SABBREVMONTHNAME6 \x516d\x6708
+ SABBREVMONTHNAME7 \x4e03\x6708
+ SABBREVMONTHNAME8 \x516b\x6708
+ SABBREVMONTHNAME9 \x4e5d\x6708
+ SABBREVMONTHNAME10 \x5341\x6708
+ SABBREVMONTHNAME11 \x5341\x4e00\x6708
+ SABBREVMONTHNAME12 \x5341\x4e8c\x6708
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0405 ; Czech - Czech Republic
+
+ ILANGUAGE 0405
+ SENGLANGUAGE Czech
+ SABBREVLANGNAME CSY
+ SNATIVELANGNAME \x010cesk\x00fd
+
+ ICOUNTRY 42
+ SENGCOUNTRY Czech Republic
+ SABBREVCTRYNAME CZK
+ SNATIVECTRYNAME \x010cesk\x00e1\x00a0republika
+
+ IDEFAULTLANGUAGE 0405
+ IDEFAULTCOUNTRY 42
+ IDEFAULTANSICODEPAGE 1250
+ IDEFAULTOEMCODEPAGE 852
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY K\x010d
+ SINTLSYMBOL CZK
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 HH.mm.ss
+ H.mm.ss
+ HH:mm:ss
+ H:mm:ss
+ STIME .
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd.MM.yyyy
+ dd-MM-yy
+ yyyy-MM-dd
+ yy-MM-dd
+ SDATE .
+ IDATE 1
+ ICENTURY 1
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 d. MMMM yyyy
+ dd. MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 pon\x00d4\x011bl\x00ed
+ SDAYNAME2 \x00fater\x00fd
+ SDAYNAME3 st\x0159eda
+ SDAYNAME4 \x010dtvrtek
+ SDAYNAME5 pátek
+ SDAYNAME6 sobota
+ SDAYNAME7 ned\x0159le
+
+ SABBREVDAYNAME1 po
+ SABBREVDAYNAME2 út
+ SABBREVDAYNAME3 st
+ SABBREVDAYNAME4 \x010dt
+ SABBREVDAYNAME5 pá
+ SABBREVDAYNAME6 so
+ SABBREVDAYNAME7 ne
+
+ SMONTHNAME1 leden
+ SMONTHNAME2 únor
+ SMONTHNAME3 b\x0159ezen
+ SMONTHNAME4 duben
+ SMONTHNAME5 kv\x011bten
+ SMONTHNAME6 \x010derven
+ SMONTHNAME7 \x010dervenec
+ SMONTHNAME8 srpen
+ SMONTHNAME9 z\x00e1\x0159\x00ed
+ SMONTHNAME10 \x0159\x00edjen
+ SMONTHNAME11 listopad
+ SMONTHNAME12 prosinec
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 led
+ SABBREVMONTHNAME2 únor
+ SABBREVMONTHNAME3 b\x0159ez
+ SABBREVMONTHNAME4 dub
+ SABBREVMONTHNAME5 kv\x011bt
+ SABBREVMONTHNAME6 \x010derv
+ SABBREVMONTHNAME7 \x010derc
+ SABBREVMONTHNAME8 srp
+ SABBREVMONTHNAME9 z\x00e1\x0159
+ SABBREVMONTHNAME10 \x0159\x00edj
+ SABBREVMONTHNAME11 list
+ SABBREVMONTHNAME12 pros
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0406 ; Danish - Denmark
+
+ ILANGUAGE 0406
+ SENGLANGUAGE Danish
+ SABBREVLANGNAME DAN
+ SNATIVELANGNAME Dansk
+
+ ICOUNTRY 45
+ SENGCOUNTRY Denmark
+ SABBREVCTRYNAME DNK
+ SNATIVECTRYNAME Danmark
+
+ IDEFAULTLANGUAGE 0406
+ IDEFAULTCOUNTRY 45
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY kr
+ SINTLSYMBOL DKK
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 2
+ INEGCURR 12
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 3 HH.mm.ss
+ H.mm.ss
+ HH:mm
+ STIME .
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd-MM-yy
+ yyyy-MM-dd
+ yyyy MM dd
+ dd/M-yy
+ SDATE -
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 d. MMMM yyyy
+ dd. MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 mandag
+ SDAYNAME2 tirsdag
+ SDAYNAME3 onsdag
+ SDAYNAME4 torsdag
+ SDAYNAME5 fredag
+ SDAYNAME6 lørdag
+ SDAYNAME7 søndag
+
+ SABBREVDAYNAME1 ma
+ SABBREVDAYNAME2 ti
+ SABBREVDAYNAME3 on
+ SABBREVDAYNAME4 to
+ SABBREVDAYNAME5 fr
+ SABBREVDAYNAME6 lø
+ SABBREVDAYNAME7 sø
+
+ SMONTHNAME1 januar
+ SMONTHNAME2 februar
+ SMONTHNAME3 marts
+ SMONTHNAME4 april
+ SMONTHNAME5 maj
+ SMONTHNAME6 juni
+ SMONTHNAME7 juli
+ SMONTHNAME8 august
+ SMONTHNAME9 september
+ SMONTHNAME10 oktober
+ SMONTHNAME11 november
+ SMONTHNAME12 december
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 apr
+ SABBREVMONTHNAME5 maj
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 aug
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 okt
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0407 ; German - Germany
+
+ ILANGUAGE 0407
+ SENGLANGUAGE German
+ SABBREVLANGNAME DEU
+ SNATIVELANGNAME Deutsch
+
+ ICOUNTRY 49
+ SENGCOUNTRY Germany
+ SABBREVCTRYNAME DEU
+ SNATIVECTRYNAME Deutschland
+
+ IDEFAULTLANGUAGE 0407
+ IDEFAULTCOUNTRY 49
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY DM
+ SINTLSYMBOL DEM
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 HH:mm:ss
+ H:mm:ss
+ H.mm
+ H.mm' Uhr '
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd.MM.yy
+ d.MM.yy
+ d.M.yy
+ d.M.yyyy
+ SDATE .
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 3 dddd, d. MMMM yyyy
+ d. MMMM yyyy
+ d. MMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorianischer Kalender
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Montag
+ SDAYNAME2 Dienstag
+ SDAYNAME3 Mittwoch
+ SDAYNAME4 Donnerstag
+ SDAYNAME5 Freitag
+ SDAYNAME6 Samstag
+ SDAYNAME7 Sonntag
+
+ SABBREVDAYNAME1 Mo
+ SABBREVDAYNAME2 Di
+ SABBREVDAYNAME3 Mi
+ SABBREVDAYNAME4 Do
+ SABBREVDAYNAME5 Fr
+ SABBREVDAYNAME6 Sa
+ SABBREVDAYNAME7 So
+
+ SMONTHNAME1 Januar
+ SMONTHNAME2 Februar
+ SMONTHNAME3 März
+ SMONTHNAME4 April
+ SMONTHNAME5 Mai
+ SMONTHNAME6 Juni
+ SMONTHNAME7 Juli
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 Oktober
+ SMONTHNAME11 November
+ SMONTHNAME12 Dezember
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mär
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 Mai
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Okt
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dez
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0807 ; German - Switzerland
+
+ ILANGUAGE 0807
+ SENGLANGUAGE German
+ SABBREVLANGNAME DES
+ SNATIVELANGNAME Deutsch
+
+ ICOUNTRY 41
+ SENGCOUNTRY Switzerland
+ SABBREVCTRYNAME CHE
+ SNATIVECTRYNAME Schweiz
+
+ IDEFAULTLANGUAGE 0807
+ IDEFAULTCOUNTRY 41
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND '
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY SFr.
+ SINTLSYMBOL CHF
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP '
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 2
+ INEGCURR 2
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 5 HH:mm:ss
+ H:mm:ss
+ H.mm' h'
+ HH.mm' h'
+ H.mm' Uhr'
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 5 dd.MM.yyyy
+ dd.MM.yy
+ d.MM.yy
+ dd. M. yy
+ d.M.yy
+ SDATE .
+ IDATE 1
+ ICENTURY 1
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 3 dddd, d. MMMM yyyy
+ d. MMMM yyyy
+ d. MMM yy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorianischer Kalender
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Montag
+ SDAYNAME2 Dienstag
+ SDAYNAME3 Mittwoch
+ SDAYNAME4 Donnerstag
+ SDAYNAME5 Freitag
+ SDAYNAME6 Samstag
+ SDAYNAME7 Sonntag
+
+ SABBREVDAYNAME1 Mo
+ SABBREVDAYNAME2 Di
+ SABBREVDAYNAME3 Mi
+ SABBREVDAYNAME4 Do
+ SABBREVDAYNAME5 Fr
+ SABBREVDAYNAME6 Sa
+ SABBREVDAYNAME7 So
+
+ SMONTHNAME1 Januar
+ SMONTHNAME2 Februar
+ SMONTHNAME3 März
+ SMONTHNAME4 April
+ SMONTHNAME5 Mai
+ SMONTHNAME6 Juni
+ SMONTHNAME7 Juli
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 Oktober
+ SMONTHNAME11 November
+ SMONTHNAME12 Dezember
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mär
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 Mai
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Okt
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dez
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0C07 ; German - Austria
+
+ ILANGUAGE 0C07
+ SENGLANGUAGE German
+ SABBREVLANGNAME DEA
+ SNATIVELANGNAME Deutsch
+
+ ICOUNTRY 43
+ SENGCOUNTRY Austria
+ SABBREVCTRYNAME AUT
+ SNATIVECTRYNAME Österreich
+
+ IDEFAULTLANGUAGE 0C07
+ IDEFAULTCOUNTRY 43
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY S
+ SINTLSYMBOL ATS
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 2
+ INEGCURR 9
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 HH:mm:ss
+ H:mm:ss
+ HH:mm
+ HH:mm' Uhr'
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 dd.MM.yy
+ dd.M.yyyy
+ yyMMdd
+ SDATE .
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 4 dddd, dd. MMMM yyyy
+ d.MMMM yyyy
+ d.MMMyyyy
+ d MMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorianischer Kalender
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Montag
+ SDAYNAME2 Dienstag
+ SDAYNAME3 Mittwoch
+ SDAYNAME4 Donnerstag
+ SDAYNAME5 Freitag
+ SDAYNAME6 Samstag
+ SDAYNAME7 Sonntag
+
+ SABBREVDAYNAME1 Mo
+ SABBREVDAYNAME2 Di
+ SABBREVDAYNAME3 Mi
+ SABBREVDAYNAME4 Do
+ SABBREVDAYNAME5 Fr
+ SABBREVDAYNAME6 Sa
+ SABBREVDAYNAME7 So
+
+ SMONTHNAME1 Januar
+ SMONTHNAME2 Februar
+ SMONTHNAME3 März
+ SMONTHNAME4 April
+ SMONTHNAME5 Mai
+ SMONTHNAME6 Juni
+ SMONTHNAME7 Juli
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 Oktober
+ SMONTHNAME11 November
+ SMONTHNAME12 Dezember
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mär
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 Mai
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Okt
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dez
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0408 ; Greek - Greece
+
+ ILANGUAGE 0408
+ SENGLANGUAGE Greek
+ SABBREVLANGNAME ELL
+ SNATIVELANGNAME \x0395\x03bb\x03bb\x03b7\x03bd\x03b9\x03ba\x03ac
+
+ ICOUNTRY 30
+ SENGCOUNTRY Greece
+ SABBREVCTRYNAME GRC
+ SNATIVECTRYNAME \x0395\x03bb\x03bb\x03ac\x03b4\x03b1
+
+ IDEFAULTLANGUAGE 0408
+ IDEFAULTCOUNTRY 30
+ IDEFAULTANSICODEPAGE 1253
+ IDEFAULTOEMCODEPAGE 869
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 0
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY \x03b4\x03c1\x03c7
+ SINTLSYMBOL GRD
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 3
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 h:mm:ss tt
+ hh:mm:ss tt
+ H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 0
+ ITLZERO 0
+ S1159 \x03c0\x03bc
+ S2359 \x03bc\x03bc
+
+ SSHORTDATE 4 d/M/yyyy
+ dd/MM/yyyy
+ d/M/yy
+ dd/MM/yy
+ SDATE /
+ IDATE 1
+ ICENTURY 1
+ IDAYLZERO 0
+ IMONLZERO 0
+
+ SLONGDATE 2 dddd, d MMMM yyyy
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x0394\x03b5\x03c5\x03c4\x03ad\x03c1\x03b1
+ SDAYNAME2 \x03a4\x03c1\x03af\x03c4\x03b7
+ SDAYNAME3 \x03a4\x03b5\x03c4\x03ac\x03c1\x03c4\x03b7
+ SDAYNAME4 \x03a0\x03ad\x03bc\x03c0\x03c4\x03b7
+ SDAYNAME5 \x03a0\x03b1\x03c1\x03b1\x03c3\x03ba\x03b5\x03c5\x03ae
+ SDAYNAME6 \x03a3\x03ac\x03b2\x03b2\x03b1\x03c4\x03bf
+ SDAYNAME7 \x039a\x03c5\x03c1\x03b9\x03b1\x03ba\x03ae
+
+ SABBREVDAYNAME1 \x0394\x03b5\x03c5
+ SABBREVDAYNAME2 \x03a4\x03c1\x03b9
+ SABBREVDAYNAME3 \x03a4\x03b5\x03c4
+ SABBREVDAYNAME4 \x03a0\x03b5\x03bc
+ SABBREVDAYNAME5 \x03a0\x03b1\x03c1
+ SABBREVDAYNAME6 \x03a3\x03b1\x03b2
+ SABBREVDAYNAME7 \x039a\x03c5\x03c1
+
+ SMONTHNAME1 \x0399\x03b1\x03bd\x03bf\x03c5\x03b1\x03c1\x03af\x03bf\x03c5
+ SMONTHNAME2 \x03a6\x03b5\x03b2\x03c1\x03bf\x03c5\x03b1\x03c1\x03af\x03bf\x03c5
+ SMONTHNAME3 \x039c\x03b1\x03c1\x03c4\x03af\x03bf\x03c5
+ SMONTHNAME4 \x0391\x03c0\x03c1\x03b9\x03bb\x03af\x03bf\x03c5
+ SMONTHNAME5 \x039c\x03b1\x0390\x03bf\x03c5
+ SMONTHNAME6 \x0399\x03bf\x03c5\x03bd\x03af\x03bf\x03c5
+ SMONTHNAME7 \x0399\x03bf\x03c5\x03bb\x03af\x03bf\x03c5
+ SMONTHNAME8 \x0391\x03c5\x03b3\x03bf\x03cd\x03c3\x03c4\x03bf\x03c5
+ SMONTHNAME9 \x03a3\x03b5\x03c0\x03c4\x03b5\x03bc\x03b2\x03c1\x03af\x03bf\x03c5
+ SMONTHNAME10 \x039f\x03ba\x03c4\x03c9\x03b2\x03c1\x03af\x03bf\x03c5
+ SMONTHNAME11 \x039d\x03bf\x03b5\x03bc\x03b2\x03c1\x03af\x03bf\x03c5
+ SMONTHNAME12 \x0394\x03b5\x03ba\x03b5\x03bc\x03b2\x03c1\x03af\x03bf\x03c5
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 \x0399\x03b1\x03bd
+ SABBREVMONTHNAME2 \x03a6\x03b5\x03b2
+ SABBREVMONTHNAME3 \x039c\x03b1\x03c1
+ SABBREVMONTHNAME4 \x0391\x03c0\x03c1
+ SABBREVMONTHNAME5 \x039c\x03b1\x03ca
+ SABBREVMONTHNAME6 \x0399\x03bf\x03c5\x03bd
+ SABBREVMONTHNAME7 \x0399\x03bf\x03c5\x03bb
+ SABBREVMONTHNAME8 \x0391\x03c5\x03b3
+ SABBREVMONTHNAME9 \x03a3\x03b5\x03c0
+ SABBREVMONTHNAME10 \x039f\x03ba\x03c4
+ SABBREVMONTHNAME11 \x039d\x03bf\x03b5
+ SABBREVMONTHNAME12 \x0394\x03b5\x03ba
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0409 ; English - United States
+
+ ILANGUAGE 0409
+ SENGLANGUAGE English
+ SABBREVLANGNAME ENU
+ SNATIVELANGNAME English
+
+ ICOUNTRY 1
+ SENGCOUNTRY United States
+ SABBREVCTRYNAME USA
+ SNATIVECTRYNAME United States
+
+ IDEFAULTLANGUAGE 0409
+ IDEFAULTCOUNTRY 1
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 437
+
+ SLIST ,
+ IMEASURE 1
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY $
+ SINTLSYMBOL USD
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 h:mm:ss tt
+ hh:mm:ss tt
+ H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 0
+ ITLZERO 0
+ S1159 AM
+ S2359 PM
+
+ SSHORTDATE 6 M/d/yy
+ M/d/yyyy
+ MM/dd/yy
+ MM/dd/yyyy
+ yy/MM/dd
+ dd-MMM-yy
+ SDATE /
+ IDATE 0
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 0
+
+ SLONGDATE 4 dddd, MMMM dd, yyyy
+ MMMM dd, yyyy
+ dddd, dd MMMM, yyyy
+ dd MMMM, yyyy
+ ILDATE 0
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Monday
+ SDAYNAME2 Tuesday
+ SDAYNAME3 Wednesday
+ SDAYNAME4 Thursday
+ SDAYNAME5 Friday
+ SDAYNAME6 Saturday
+ SDAYNAME7 Sunday
+
+ SABBREVDAYNAME1 Mon
+ SABBREVDAYNAME2 Tue
+ SABBREVDAYNAME3 Wed
+ SABBREVDAYNAME4 Thu
+ SABBREVDAYNAME5 Fri
+ SABBREVDAYNAME6 Sat
+ SABBREVDAYNAME7 Sun
+
+ SMONTHNAME1 January
+ SMONTHNAME2 February
+ SMONTHNAME3 March
+ SMONTHNAME4 April
+ SMONTHNAME5 May
+ SMONTHNAME6 June
+ SMONTHNAME7 July
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 October
+ SMONTHNAME11 November
+ SMONTHNAME12 December
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mar
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 May
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Oct
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0809 ; English - United Kingdom
+
+ ILANGUAGE 0809
+ SENGLANGUAGE English
+ SABBREVLANGNAME ENG
+ SNATIVELANGNAME English
+
+ ICOUNTRY 44
+ SENGCOUNTRY United Kingdom
+ SABBREVCTRYNAME GBR
+ SNATIVECTRYNAME England
+
+ IDEFAULTLANGUAGE 0809
+ IDEFAULTCOUNTRY 44
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY £
+ SINTLSYMBOL GBP
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 HH:mm:ss
+ H:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd/MM/yy
+ d/M/yy
+ d.M.yy
+ ddMMyy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 dd MMMM yyyy
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Monday
+ SDAYNAME2 Tuesday
+ SDAYNAME3 Wednesday
+ SDAYNAME4 Thursday
+ SDAYNAME5 Friday
+ SDAYNAME6 Saturday
+ SDAYNAME7 Sunday
+
+ SABBREVDAYNAME1 Mon
+ SABBREVDAYNAME2 Tue
+ SABBREVDAYNAME3 Wed
+ SABBREVDAYNAME4 Thu
+ SABBREVDAYNAME5 Fri
+ SABBREVDAYNAME6 Sat
+ SABBREVDAYNAME7 Sun
+
+ SMONTHNAME1 January
+ SMONTHNAME2 February
+ SMONTHNAME3 March
+ SMONTHNAME4 April
+ SMONTHNAME5 May
+ SMONTHNAME6 June
+ SMONTHNAME7 July
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 October
+ SMONTHNAME11 November
+ SMONTHNAME12 December
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mar
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 May
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Oct
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0C09 ; English - Australia
+
+ ILANGUAGE 0C09
+ SENGLANGUAGE English
+ SABBREVLANGNAME ENA
+ SNATIVELANGNAME English
+
+ ICOUNTRY 61
+ SENGCOUNTRY Australia
+ SABBREVCTRYNAME AUS
+ SNATIVECTRYNAME Australia
+
+ IDEFAULTLANGUAGE 0C09
+ IDEFAULTCOUNTRY 61
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY $
+ SINTLSYMBOL AUD
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 d/MM/yy
+ d/M/yy
+ dd/MM/yy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 1
+
+ SLONGDATE 2 dddd, d MMMM yyyy
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Monday
+ SDAYNAME2 Tuesday
+ SDAYNAME3 Wednesday
+ SDAYNAME4 Thursday
+ SDAYNAME5 Friday
+ SDAYNAME6 Saturday
+ SDAYNAME7 Sunday
+
+ SABBREVDAYNAME1 Mon
+ SABBREVDAYNAME2 Tue
+ SABBREVDAYNAME3 Wed
+ SABBREVDAYNAME4 Thu
+ SABBREVDAYNAME5 Fri
+ SABBREVDAYNAME6 Sat
+ SABBREVDAYNAME7 Sun
+
+ SMONTHNAME1 January
+ SMONTHNAME2 February
+ SMONTHNAME3 March
+ SMONTHNAME4 April
+ SMONTHNAME5 May
+ SMONTHNAME6 June
+ SMONTHNAME7 July
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 October
+ SMONTHNAME11 November
+ SMONTHNAME12 December
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mar
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 May
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Oct
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 1009 ; English - Canada
+
+ ILANGUAGE 1009
+ SENGLANGUAGE English
+ SABBREVLANGNAME ENC
+ SNATIVELANGNAME English
+
+ ICOUNTRY 2
+ SENGCOUNTRY Canada
+ SABBREVCTRYNAME CAN
+ SNATIVECTRYNAME Canada
+
+ IDEFAULTLANGUAGE 1009
+ IDEFAULTCOUNTRY 2
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY $
+ SINTLSYMBOL CAD
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 HH:mm:ss
+ H:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd/MM/yy
+ d/M/yy
+ yy-MM-dd
+ m/dd/yy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 MMMM d, yyyy
+ d-MMM-yy
+ ILDATE 0
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Monday
+ SDAYNAME2 Tuesday
+ SDAYNAME3 Wednesday
+ SDAYNAME4 Thursday
+ SDAYNAME5 Friday
+ SDAYNAME6 Saturday
+ SDAYNAME7 Sunday
+
+ SABBREVDAYNAME1 Mon
+ SABBREVDAYNAME2 Tue
+ SABBREVDAYNAME3 Wed
+ SABBREVDAYNAME4 Thu
+ SABBREVDAYNAME5 Fri
+ SABBREVDAYNAME6 Sat
+ SABBREVDAYNAME7 Sun
+
+ SMONTHNAME1 January
+ SMONTHNAME2 February
+ SMONTHNAME3 March
+ SMONTHNAME4 April
+ SMONTHNAME5 May
+ SMONTHNAME6 June
+ SMONTHNAME7 July
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 October
+ SMONTHNAME11 November
+ SMONTHNAME12 December
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mar
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 May
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Oct
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 1409 ; English - New Zealand
+
+ ILANGUAGE 1409
+ SENGLANGUAGE English
+ SABBREVLANGNAME ENZ
+ SNATIVELANGNAME English
+
+ ICOUNTRY 64
+ SENGCOUNTRY New Zealand
+ SABBREVCTRYNAME NZL
+ SNATIVECTRYNAME New Zealand
+
+ IDEFAULTLANGUAGE 1409
+ IDEFAULTCOUNTRY 64
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY $
+ SINTLSYMBOL NZD
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 HH:mm:ss
+ H:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 d/MM/yy
+ dd/MM/yy
+ d.MM.yy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 1
+
+ SLONGDATE 2 dddd, d MMMM yyyy
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Monday
+ SDAYNAME2 Tuesday
+ SDAYNAME3 Wednesday
+ SDAYNAME4 Thursday
+ SDAYNAME5 Friday
+ SDAYNAME6 Saturday
+ SDAYNAME7 Sunday
+
+ SABBREVDAYNAME1 Mon
+ SABBREVDAYNAME2 Tue
+ SABBREVDAYNAME3 Wed
+ SABBREVDAYNAME4 Thu
+ SABBREVDAYNAME5 Fri
+ SABBREVDAYNAME6 Sat
+ SABBREVDAYNAME7 Sun
+
+ SMONTHNAME1 January
+ SMONTHNAME2 February
+ SMONTHNAME3 March
+ SMONTHNAME4 April
+ SMONTHNAME5 May
+ SMONTHNAME6 June
+ SMONTHNAME7 July
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 October
+ SMONTHNAME11 November
+ SMONTHNAME12 December
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mar
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 May
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Oct
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 1809 ; English - Ireland
+
+ ILANGUAGE 1809
+ SENGLANGUAGE English
+ SABBREVLANGNAME ENI
+ SNATIVELANGNAME English
+
+ ICOUNTRY 353
+ SENGCOUNTRY Ireland
+ SABBREVCTRYNAME IRL
+ SNATIVECTRYNAME Eire
+
+ IDEFAULTLANGUAGE 1809
+ IDEFAULTCOUNTRY 353
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY IR£
+ SINTLSYMBOL IRP
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 HH:mm:ss
+ H:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd/MM/yy
+ d/M/yy
+ d.M.yy
+ ddMMyy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 dd MMMM yyyy
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Monday
+ SDAYNAME2 Tuesday
+ SDAYNAME3 Wednesday
+ SDAYNAME4 Thursday
+ SDAYNAME5 Friday
+ SDAYNAME6 Saturday
+ SDAYNAME7 Sunday
+
+ SABBREVDAYNAME1 Mon
+ SABBREVDAYNAME2 Tue
+ SABBREVDAYNAME3 Wed
+ SABBREVDAYNAME4 Thu
+ SABBREVDAYNAME5 Fri
+ SABBREVDAYNAME6 Sat
+ SABBREVDAYNAME7 Sun
+
+ SMONTHNAME1 January
+ SMONTHNAME2 February
+ SMONTHNAME3 March
+ SMONTHNAME4 April
+ SMONTHNAME5 May
+ SMONTHNAME6 June
+ SMONTHNAME7 July
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 October
+ SMONTHNAME11 November
+ SMONTHNAME12 December
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mar
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 May
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Oct
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 040A ; Spanish - Spain (Traditional Sort)
+
+ ILANGUAGE 040A
+ SENGLANGUAGE Spanish - Traditional Sort
+ SABBREVLANGNAME ESP
+ SNATIVELANGNAME Español
+
+ ICOUNTRY 34
+ SENGCOUNTRY Spain
+ SABBREVCTRYNAME ESP
+ SNATIVECTRYNAME España
+
+ IDEFAULTLANGUAGE 040A
+ IDEFAULTCOUNTRY 34
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY Pts
+ SINTLSYMBOL ESP
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 0
+ IINTLCURRDIGITS 0
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 H:mm:ss
+ HH:mm:ss
+ HH:mm
+ HH'H'mm'''
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 d/MM/yy
+ d/M/yy
+ dd-MM-yy
+ dd.MM.yy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 1
+
+ SLONGDATE 2 dddd d' de 'MMMM' de 'yyyy
+ d' de 'MMMM' de 'yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 lunes
+ SDAYNAME2 martes
+ SDAYNAME3 miércoles
+ SDAYNAME4 jueves
+ SDAYNAME5 viernes
+ SDAYNAME6 sábado
+ SDAYNAME7 domingo
+
+ SABBREVDAYNAME1 lun
+ SABBREVDAYNAME2 mar
+ SABBREVDAYNAME3 mié
+ SABBREVDAYNAME4 jue
+ SABBREVDAYNAME5 vie
+ SABBREVDAYNAME6 sáb
+ SABBREVDAYNAME7 dom
+
+ SMONTHNAME1 enero
+ SMONTHNAME2 febrero
+ SMONTHNAME3 marzo
+ SMONTHNAME4 abril
+ SMONTHNAME5 mayo
+ SMONTHNAME6 junio
+ SMONTHNAME7 julio
+ SMONTHNAME8 agosto
+ SMONTHNAME9 septiembre
+ SMONTHNAME10 octubre
+ SMONTHNAME11 noviembre
+ SMONTHNAME12 diciembre
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 ene
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 abr
+ SABBREVMONTHNAME5 may
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 ago
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 oct
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dic
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 080A ; Spanish - Mexico
+
+ ILANGUAGE 080A
+ SENGLANGUAGE Spanish
+ SABBREVLANGNAME ESM
+ SNATIVELANGNAME Español
+
+ ICOUNTRY 52
+ SENGCOUNTRY Mexico
+ SABBREVCTRYNAME MEX
+ SNATIVECTRYNAME México
+
+ IDEFAULTLANGUAGE 080A
+ IDEFAULTCOUNTRY 52
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY N$
+ SINTLSYMBOL MXP
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 0
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 h:mm:ss tt
+ hh:mm:ss tt
+ H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 0
+ ITLZERO 0
+ S1159 AM
+ S2359 PM
+
+ SSHORTDATE 4 d/MM/yy
+ d/M/yy
+ dd/MM/yy
+ dd-MM-yy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 1
+
+ SLONGDATE 2 dddd d' de 'MMMM' de 'yyyy
+ d' de 'MMMM' de 'yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 lunes
+ SDAYNAME2 martes
+ SDAYNAME3 miércoles
+ SDAYNAME4 jueves
+ SDAYNAME5 viernes
+ SDAYNAME6 sábado
+ SDAYNAME7 domingo
+
+ SABBREVDAYNAME1 lun
+ SABBREVDAYNAME2 mar
+ SABBREVDAYNAME3 mié
+ SABBREVDAYNAME4 jue
+ SABBREVDAYNAME5 vie
+ SABBREVDAYNAME6 sáb
+ SABBREVDAYNAME7 dom
+
+ SMONTHNAME1 enero
+ SMONTHNAME2 febrero
+ SMONTHNAME3 marzo
+ SMONTHNAME4 abril
+ SMONTHNAME5 mayo
+ SMONTHNAME6 junio
+ SMONTHNAME7 julio
+ SMONTHNAME8 agosto
+ SMONTHNAME9 septiembre
+ SMONTHNAME10 octubre
+ SMONTHNAME11 noviembre
+ SMONTHNAME12 diciembre
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 ene
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 abr
+ SABBREVMONTHNAME5 may
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 ago
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 oct
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dic
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0C0A ; Spanish - Spain (Modern Sort)
+
+ ILANGUAGE 0C0A
+ SENGLANGUAGE Spanish - Modern Sort
+ SABBREVLANGNAME ESN
+ SNATIVELANGNAME Español
+
+ ICOUNTRY 34
+ SENGCOUNTRY Spain
+ SABBREVCTRYNAME ESP
+ SNATIVECTRYNAME España
+
+ IDEFAULTLANGUAGE 0C0A
+ IDEFAULTCOUNTRY 34
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY Pts
+ SINTLSYMBOL ESP
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 0
+ IINTLCURRDIGITS 0
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 H:mm:ss
+ HH:mm:ss
+ HH:mm
+ HH'H'mm'''
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 d/MM/yy
+ dd/MM/yy
+ dd-MM-yy
+ dd.MM.yy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 1
+
+ SLONGDATE 2 dddd d' de 'MMMM' de 'yyyy
+ d' de 'MMMM' de 'yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 lunes
+ SDAYNAME2 martes
+ SDAYNAME3 miércoles
+ SDAYNAME4 jueves
+ SDAYNAME5 viernes
+ SDAYNAME6 sábado
+ SDAYNAME7 domingo
+
+ SABBREVDAYNAME1 lun
+ SABBREVDAYNAME2 mar
+ SABBREVDAYNAME3 mié
+ SABBREVDAYNAME4 jue
+ SABBREVDAYNAME5 vie
+ SABBREVDAYNAME6 sáb
+ SABBREVDAYNAME7 dom
+
+ SMONTHNAME1 enero
+ SMONTHNAME2 febrero
+ SMONTHNAME3 marzo
+ SMONTHNAME4 abril
+ SMONTHNAME5 mayo
+ SMONTHNAME6 junio
+ SMONTHNAME7 julio
+ SMONTHNAME8 agosto
+ SMONTHNAME9 septiembre
+ SMONTHNAME10 octubre
+ SMONTHNAME11 noviembre
+ SMONTHNAME12 diciembre
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 ene
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 abr
+ SABBREVMONTHNAME5 may
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 ago
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 oct
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dic
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 040B ; Finnish - Finland
+
+ ILANGUAGE 040B
+ SENGLANGUAGE Finnish
+ SABBREVLANGNAME FIN
+ SNATIVELANGNAME suomi
+
+ ICOUNTRY 358
+ SENGCOUNTRY Finland
+ SABBREVCTRYNAME FIN
+ SNATIVECTRYNAME Suomi
+
+ IDEFAULTLANGUAGE 040B
+ IDEFAULTCOUNTRY 358
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY mk
+ SINTLSYMBOL FIM
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 3 H.mm.ss
+ HH.mm.ss
+ H.mm
+ STIME .
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 d.M.yyyy
+ dd.MM.yyyy
+ d.M.yy
+ yyyy-MM-dd
+ SDATE .
+ IDATE 1
+ ICENTURY 1
+ IDAYLZERO 0
+ IMONLZERO 0
+
+ SLONGDATE 2 d. MMMM'ta 'yyyy
+ dd. MMMM'ta 'yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 maanantai
+ SDAYNAME2 tiistai
+ SDAYNAME3 keskiviikko
+ SDAYNAME4 torstai
+ SDAYNAME5 perjantai
+ SDAYNAME6 lauantai
+ SDAYNAME7 sunnuntai
+
+ SABBREVDAYNAME1 ma
+ SABBREVDAYNAME2 ti
+ SABBREVDAYNAME3 ke
+ SABBREVDAYNAME4 to
+ SABBREVDAYNAME5 pe
+ SABBREVDAYNAME6 la
+ SABBREVDAYNAME7 su
+
+ SMONTHNAME1 tammikuu
+ SMONTHNAME2 helmikuu
+ SMONTHNAME3 maaliskuu
+ SMONTHNAME4 huhtikuu
+ SMONTHNAME5 toukokuu
+ SMONTHNAME6 kesäkuu
+ SMONTHNAME7 heinäkuu
+ SMONTHNAME8 elokuu
+ SMONTHNAME9 syyskuu
+ SMONTHNAME10 lokakuu
+ SMONTHNAME11 marraskuu
+ SMONTHNAME12 joulukuu
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 tammi
+ SABBREVMONTHNAME2 helmi
+ SABBREVMONTHNAME3 maalis
+ SABBREVMONTHNAME4 huhti
+ SABBREVMONTHNAME5 touko
+ SABBREVMONTHNAME6 kesä
+ SABBREVMONTHNAME7 heinä
+ SABBREVMONTHNAME8 elo
+ SABBREVMONTHNAME9 syys
+ SABBREVMONTHNAME10 loka
+ SABBREVMONTHNAME11 marras
+ SABBREVMONTHNAME12 joulu
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 040C ; French - France
+
+ ILANGUAGE 040C
+ SENGLANGUAGE French
+ SABBREVLANGNAME FRA
+ SNATIVELANGNAME français
+
+ ICOUNTRY 33
+ SENGCOUNTRY France
+ SABBREVCTRYNAME FRA
+ SNATIVECTRYNAME France
+
+ IDEFAULTLANGUAGE 040C
+ IDEFAULTCOUNTRY 33
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY F
+ SINTLSYMBOL FRF
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 HH:mm:ss
+ H:mm:ss
+ HH.mm
+ HH' h 'mm
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd/MM/yy
+ dd.MM.yy
+ dd-MM-yy
+ dd/MM/yyyy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 3 dddd d MMMM yyyy
+ d MMM yy
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 lundi
+ SDAYNAME2 mardi
+ SDAYNAME3 mercredi
+ SDAYNAME4 jeudi
+ SDAYNAME5 vendredi
+ SDAYNAME6 samedi
+ SDAYNAME7 dimanche
+
+ SABBREVDAYNAME1 lun.
+ SABBREVDAYNAME2 mar.
+ SABBREVDAYNAME3 mer.
+ SABBREVDAYNAME4 jeu.
+ SABBREVDAYNAME5 ven.
+ SABBREVDAYNAME6 sam.
+ SABBREVDAYNAME7 dim.
+
+ SMONTHNAME1 janvier
+ SMONTHNAME2 février
+ SMONTHNAME3 mars
+ SMONTHNAME4 avril
+ SMONTHNAME5 mai
+ SMONTHNAME6 juin
+ SMONTHNAME7 juillet
+ SMONTHNAME8 août
+ SMONTHNAME9 septembre
+ SMONTHNAME10 octobre
+ SMONTHNAME11 novembre
+ SMONTHNAME12 décembre
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 janv.
+ SABBREVMONTHNAME2 févr.
+ SABBREVMONTHNAME3 mars
+ SABBREVMONTHNAME4 avr.
+ SABBREVMONTHNAME5 mai
+ SABBREVMONTHNAME6 juin
+ SABBREVMONTHNAME7 juil.
+ SABBREVMONTHNAME8 août
+ SABBREVMONTHNAME9 sept.
+ SABBREVMONTHNAME10 oct.
+ SABBREVMONTHNAME11 nov.
+ SABBREVMONTHNAME12 déc.
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 080C ; French - Belgium
+
+ ILANGUAGE 080C
+ SENGLANGUAGE French
+ SABBREVLANGNAME FRB
+ SNATIVELANGNAME français
+
+ ICOUNTRY 32
+ SENGCOUNTRY Belgium
+ SABBREVCTRYNAME BEL
+ SNATIVECTRYNAME Belgique
+
+ IDEFAULTLANGUAGE 080C
+ IDEFAULTCOUNTRY 32
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY FB
+ SINTLSYMBOL BEF
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 5 H:mm:ss
+ HH:mm:ss
+ H.mm
+ H' h 'mm
+ H' h 'm' min 's' s '
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 d/MM/yy
+ dd.MM.yy
+ yy/mm/dd
+ dd-MM-yy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 1
+
+ SLONGDATE 4 dddd d MMMM yyyy
+ d MMMM yyyy
+ dd-MMM-yy
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 lundi
+ SDAYNAME2 mardi
+ SDAYNAME3 mercredi
+ SDAYNAME4 jeudi
+ SDAYNAME5 vendredi
+ SDAYNAME6 samedi
+ SDAYNAME7 dimanche
+
+ SABBREVDAYNAME1 lun.
+ SABBREVDAYNAME2 mar.
+ SABBREVDAYNAME3 mer.
+ SABBREVDAYNAME4 jeu.
+ SABBREVDAYNAME5 ven.
+ SABBREVDAYNAME6 sam.
+ SABBREVDAYNAME7 dim.
+
+ SMONTHNAME1 janvier
+ SMONTHNAME2 février
+ SMONTHNAME3 mars
+ SMONTHNAME4 avril
+ SMONTHNAME5 mai
+ SMONTHNAME6 juin
+ SMONTHNAME7 juillet
+ SMONTHNAME8 août
+ SMONTHNAME9 septembre
+ SMONTHNAME10 octobre
+ SMONTHNAME11 novembre
+ SMONTHNAME12 décembre
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 janv.
+ SABBREVMONTHNAME2 févr.
+ SABBREVMONTHNAME3 mars
+ SABBREVMONTHNAME4 avr.
+ SABBREVMONTHNAME5 mai
+ SABBREVMONTHNAME6 juin
+ SABBREVMONTHNAME7 juil.
+ SABBREVMONTHNAME8 août
+ SABBREVMONTHNAME9 sept.
+ SABBREVMONTHNAME10 oct.
+ SABBREVMONTHNAME11 nov.
+ SABBREVMONTHNAME12 déc.
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0C0C ; French - Canada
+
+ ILANGUAGE 0C0C
+ SENGLANGUAGE French
+ SABBREVLANGNAME FRC
+ SNATIVELANGNAME français
+
+ ICOUNTRY 2
+ SENGCOUNTRY Canada
+ SABBREVCTRYNAME CAN
+ SNATIVECTRYNAME Canada
+
+ IDEFAULTLANGUAGE 0C0C
+ IDEFAULTCOUNTRY 2
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY $
+ SINTLSYMBOL CAD
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 4
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 HH:mm:ss
+ H:mm:ss
+ H' h 'mm
+ H:mm
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 yy-MM-dd
+ dd-MM-yy
+ yy MM dd
+ dd/MM/yy
+ SDATE -
+ IDATE 2
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 d MMMM, yyyy
+ d MMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 lundi
+ SDAYNAME2 mardi
+ SDAYNAME3 mercredi
+ SDAYNAME4 jeudi
+ SDAYNAME5 vendredi
+ SDAYNAME6 samedi
+ SDAYNAME7 dimanche
+
+ SABBREVDAYNAME1 lun.
+ SABBREVDAYNAME2 mar.
+ SABBREVDAYNAME3 mer.
+ SABBREVDAYNAME4 jeu.
+ SABBREVDAYNAME5 ven.
+ SABBREVDAYNAME6 sam.
+ SABBREVDAYNAME7 dim.
+
+ SMONTHNAME1 janvier
+ SMONTHNAME2 février
+ SMONTHNAME3 mars
+ SMONTHNAME4 avril
+ SMONTHNAME5 mai
+ SMONTHNAME6 juin
+ SMONTHNAME7 juillet
+ SMONTHNAME8 août
+ SMONTHNAME9 septembre
+ SMONTHNAME10 octobre
+ SMONTHNAME11 novembre
+ SMONTHNAME12 décembre
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 janv.
+ SABBREVMONTHNAME2 févr.
+ SABBREVMONTHNAME3 mars
+ SABBREVMONTHNAME4 avr.
+ SABBREVMONTHNAME5 mai
+ SABBREVMONTHNAME6 juin
+ SABBREVMONTHNAME7 juil.
+ SABBREVMONTHNAME8 août
+ SABBREVMONTHNAME9 sept.
+ SABBREVMONTHNAME10 oct.
+ SABBREVMONTHNAME11 nov.
+ SABBREVMONTHNAME12 déc.
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 100C ; French - Switzerland
+
+ ILANGUAGE 100C
+ SENGLANGUAGE French
+ SABBREVLANGNAME FRS
+ SNATIVELANGNAME français
+
+ ICOUNTRY 41
+ SENGCOUNTRY Switzerland
+ SABBREVCTRYNAME CHE
+ SNATIVECTRYNAME Suisse
+
+ IDEFAULTLANGUAGE 100C
+ IDEFAULTCOUNTRY 41
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND '
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY SFr.
+ SINTLSYMBOL CHF
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP '
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 2
+ INEGCURR 2
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 3 HH:mm:ss
+ H:mm:ss
+ HH.mm' h'
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 dd.MM.yyyy
+ dd. M. yy
+ d.M.yy
+ SDATE .
+ IDATE 1
+ ICENTURY 1
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 3 dddd, d. MMMM yyyy
+ d. MMMM yyyy
+ d MMM yy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 lundi
+ SDAYNAME2 mardi
+ SDAYNAME3 mercredi
+ SDAYNAME4 jeudi
+ SDAYNAME5 vendredi
+ SDAYNAME6 samedi
+ SDAYNAME7 dimanche
+
+ SABBREVDAYNAME1 lun.
+ SABBREVDAYNAME2 mar.
+ SABBREVDAYNAME3 mer.
+ SABBREVDAYNAME4 jeu.
+ SABBREVDAYNAME5 ven.
+ SABBREVDAYNAME6 sam.
+ SABBREVDAYNAME7 dim.
+
+ SMONTHNAME1 janvier
+ SMONTHNAME2 fevrier
+ SMONTHNAME3 mars
+ SMONTHNAME4 avril
+ SMONTHNAME5 mai
+ SMONTHNAME6 juin
+ SMONTHNAME7 juillet
+ SMONTHNAME8 août
+ SMONTHNAME9 septembre
+ SMONTHNAME10 octobre
+ SMONTHNAME11 novembre
+ SMONTHNAME12 décembre
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 janv.
+ SABBREVMONTHNAME2 févr.
+ SABBREVMONTHNAME3 mars
+ SABBREVMONTHNAME4 avr.
+ SABBREVMONTHNAME5 mai
+ SABBREVMONTHNAME6 juin
+ SABBREVMONTHNAME7 juil.
+ SABBREVMONTHNAME8 août
+ SABBREVMONTHNAME9 sept.
+ SABBREVMONTHNAME10 oct.
+ SABBREVMONTHNAME11 nov.
+ SABBREVMONTHNAME12 déc.
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 040e ; Hungarian - Hungary
+
+ ILANGUAGE 040e
+ SENGLANGUAGE Hungarian
+ SABBREVLANGNAME HUN
+ SNATIVELANGNAME magyar
+
+ ICOUNTRY 36
+ SENGCOUNTRY Hungary
+ SABBREVCTRYNAME HUN
+ SNATIVECTRYNAME Magyarország
+
+ IDEFAULTLANGUAGE 040e
+ IDEFAULTCOUNTRY 36
+ IDEFAULTANSICODEPAGE 1250
+ IDEFAULTOEMCODEPAGE 852
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY Ft
+ SINTLSYMBOL HUF
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 3 H.mm.ss
+ HH.mm.ss
+ H:mm:ss
+ STIME .
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 yyyy.MM.dd.
+ yyyy-MM-dd
+ yy-MM-dd
+ SDATE .
+ IDATE 2
+ ICENTURY 1
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 yyyy. MMMM d.
+ yyyy. MMMM dd.
+ ILDATE 2
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 h\x00e9tf\x0151
+ SDAYNAME2 kedd
+ SDAYNAME3 szerda
+ SDAYNAME4 csütörtök
+ SDAYNAME5 péntek
+ SDAYNAME6 szombat
+ SDAYNAME7 vasárnap
+
+ SABBREVDAYNAME1 H
+ SABBREVDAYNAME2 K
+ SABBREVDAYNAME3 Sze
+ SABBREVDAYNAME4 Cs
+ SABBREVDAYNAME5 P
+ SABBREVDAYNAME6 Szo
+ SABBREVDAYNAME7 V
+
+ SMONTHNAME1 január
+ SMONTHNAME2 február
+ SMONTHNAME3 márclus
+ SMONTHNAME4 április
+ SMONTHNAME5 május
+ SMONTHNAME6 június
+ SMONTHNAME7 július
+ SMONTHNAME8 augusztus
+ SMONTHNAME9 szeptember
+ SMONTHNAME10 október
+ SMONTHNAME11 november
+ SMONTHNAME12 december
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 már
+ SABBREVMONTHNAME4 ápr
+ SABBREVMONTHNAME5 máj
+ SABBREVMONTHNAME6 jún
+ SABBREVMONTHNAME7 júl
+ SABBREVMONTHNAME8 aug
+ SABBREVMONTHNAME9 sze
+ SABBREVMONTHNAME10 okt
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 040F ; Icelandic - Iceland
+
+ ILANGUAGE 040F
+ SENGLANGUAGE Icelandic
+ SABBREVLANGNAME ISL
+ SNATIVELANGNAME Íslenska
+
+ ICOUNTRY 354
+ SENGCOUNTRY Iceland
+ SABBREVCTRYNAME ISL
+ SNATIVECTRYNAME Ísland
+
+ IDEFAULTLANGUAGE 040F
+ IDEFAULTCOUNTRY 354
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY kr
+ SINTLSYMBOL ISK
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 3 HH:mm:ss
+ H:mm:ss
+ HH:mm
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 5 yyyy-MM-dd
+ dd.MM.yy
+ d. M. yyyy.
+ d. M. 'yy.
+ yy MM dd
+ SDATE -
+ IDATE 2
+ ICENTURY 1
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 d. MMMM yyyy
+ dd. MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 mánudagur
+ SDAYNAME2 þriðjudagur
+ SDAYNAME3 miðvikudagur
+ SDAYNAME4 fimmtudagur
+ SDAYNAME5 föstudagur
+ SDAYNAME6 laugardagur
+ SDAYNAME7 sunnudagur
+
+ SABBREVDAYNAME1 mán.
+ SABBREVDAYNAME2 þri.
+ SABBREVDAYNAME3 mið.
+ SABBREVDAYNAME4 fim.
+ SABBREVDAYNAME5 fös.
+ SABBREVDAYNAME6 lau.
+ SABBREVDAYNAME7 sun.
+
+ SMONTHNAME1 janúar
+ SMONTHNAME2 febrúar
+ SMONTHNAME3 mars
+ SMONTHNAME4 apríl
+ SMONTHNAME5 maí
+ SMONTHNAME6 júní
+ SMONTHNAME7 júlí
+ SMONTHNAME8 ágúst
+ SMONTHNAME9 september
+ SMONTHNAME10 október
+ SMONTHNAME11 nóvember
+ SMONTHNAME12 desember
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan.
+ SABBREVMONTHNAME2 febr.
+ SABBREVMONTHNAME3 mars
+ SABBREVMONTHNAME4 apr.
+ SABBREVMONTHNAME5 maí
+ SABBREVMONTHNAME6 júní
+ SABBREVMONTHNAME7 júlí
+ SABBREVMONTHNAME8 ág.
+ SABBREVMONTHNAME9 sept.
+ SABBREVMONTHNAME10 okt.
+ SABBREVMONTHNAME11 nóv.
+ SABBREVMONTHNAME12 des.
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0410 ; Italian - Italy
+
+ ILANGUAGE 0410
+ SENGLANGUAGE Italian
+ SABBREVLANGNAME ITA
+ SNATIVELANGNAME Italiano
+
+ ICOUNTRY 39
+ SENGCOUNTRY Italy
+ SABBREVCTRYNAME ITA
+ SNATIVECTRYNAME Italia
+
+ IDEFAULTLANGUAGE 0410
+ IDEFAULTCOUNTRY 39
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY L.
+ SINTLSYMBOL ITL
+ SMONDECIMALSEP \x0000
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 0
+ IINTLCURRDIGITS 0
+ ICURRENCY 2
+ INEGCURR 9
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 H.mm.ss
+ HH.mm.ss
+ H.mm
+ H:mm
+ STIME .
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd/MM/yy
+ dd/MM/yyyy
+ dd.M.yy
+ d/M/yy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 3 dddd d MMMM yyyy
+ d-MMM-yy
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 lunedì
+ SDAYNAME2 martedì
+ SDAYNAME3 mercoledì
+ SDAYNAME4 giovedì
+ SDAYNAME5 venerdì
+ SDAYNAME6 sabato
+ SDAYNAME7 domenica
+
+ SABBREVDAYNAME1 lun
+ SABBREVDAYNAME2 mar
+ SABBREVDAYNAME3 mer
+ SABBREVDAYNAME4 gio
+ SABBREVDAYNAME5 ven
+ SABBREVDAYNAME6 sab
+ SABBREVDAYNAME7 dom
+
+ SMONTHNAME1 gennaio
+ SMONTHNAME2 febbraio
+ SMONTHNAME3 marzo
+ SMONTHNAME4 aprile
+ SMONTHNAME5 maggio
+ SMONTHNAME6 giugno
+ SMONTHNAME7 luglio
+ SMONTHNAME8 agosto
+ SMONTHNAME9 settembre
+ SMONTHNAME10 ottobre
+ SMONTHNAME11 novembre
+ SMONTHNAME12 dicembre
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 gen
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 apr
+ SABBREVMONTHNAME5 mag
+ SABBREVMONTHNAME6 giu
+ SABBREVMONTHNAME7 lug
+ SABBREVMONTHNAME8 ago
+ SABBREVMONTHNAME9 set
+ SABBREVMONTHNAME10 ott
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dic
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0810 ; Italian - Switzerland
+
+ ILANGUAGE 0810
+ SENGLANGUAGE Italian
+ SABBREVLANGNAME ITS
+ SNATIVELANGNAME Italiano
+
+ ICOUNTRY 41
+ SENGCOUNTRY Switzerland
+ SABBREVCTRYNAME CHE
+ SNATIVECTRYNAME Svizzera
+
+ IDEFAULTLANGUAGE 0810
+ IDEFAULTCOUNTRY 41
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND '
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY SFr.
+ SINTLSYMBOL CHF
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP '
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 2
+ INEGCURR 2
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 3 HH:mm:ss
+ H:mm:ss
+ H.mm' h'
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd.MM.yyyy
+ dd. MM. yy
+ d/M/yy
+ dd.M.yy
+ SDATE .
+ IDATE 1
+ ICENTURY 1
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 3 dddd, d. MMMM yyyy
+ d-MMM-yy
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 lunedì
+ SDAYNAME2 martedì
+ SDAYNAME3 mercoledì
+ SDAYNAME4 giovedì
+ SDAYNAME5 venerdì
+ SDAYNAME6 sabato
+ SDAYNAME7 domenica
+
+ SABBREVDAYNAME1 lun
+ SABBREVDAYNAME2 mar
+ SABBREVDAYNAME3 mer
+ SABBREVDAYNAME4 gio
+ SABBREVDAYNAME5 ven
+ SABBREVDAYNAME6 sab
+ SABBREVDAYNAME7 dom
+
+ SMONTHNAME1 gennaio
+ SMONTHNAME2 febbraio
+ SMONTHNAME3 marzo
+ SMONTHNAME4 aprile
+ SMONTHNAME5 maggio
+ SMONTHNAME6 giugno
+ SMONTHNAME7 luglio
+ SMONTHNAME8 agosto
+ SMONTHNAME9 settembre
+ SMONTHNAME10 ottobre
+ SMONTHNAME11 novembre
+ SMONTHNAME12 dicembre
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 gen
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 apr
+ SABBREVMONTHNAME5 mag
+ SABBREVMONTHNAME6 gio
+ SABBREVMONTHNAME7 lug
+ SABBREVMONTHNAME8 ago
+ SABBREVMONTHNAME9 set
+ SABBREVMONTHNAME10 ott
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dic
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0411 ; Japanese - Japan
+
+ ILANGUAGE 0411
+ SENGLANGUAGE Japanese
+ SABBREVLANGNAME JPN
+ SNATIVELANGNAME \x65e5\x672c\x8a9e
+
+ ICOUNTRY 81
+ SENGCOUNTRY Japan
+ SABBREVCTRYNAME JPN
+ SNATIVECTRYNAME \x65e5\x672c
+
+ IDEFAULTLANGUAGE 0411
+ IDEFAULTCOUNTRY 81
+ IDEFAULTANSICODEPAGE 932
+ IDEFAULTOEMCODEPAGE 932
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY \xffe5
+ SINTLSYMBOL YEN
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 0
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 tt h:mm:ss
+ tt hh:mm:ss
+ H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 0
+ ITLZERO 0
+ S1159 \x5348\x524d
+ S2359 \x5348\x5f8c
+
+ SSHORTDATE 4 yy/MM/dd
+ yy/M/d
+ yyyy/MM/dd
+ yyyy/M/d
+ SDATE /
+ IDATE 2
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 yyyy'\x5e74'M'\x6708'd'\x65e5'
+ yyyy'\x5e74'MM'\x6708'dd'\x65e5'
+ ILDATE 2
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 3 3\xffffEra: Year of the Emperor
+ 2\xffffGregorian (U.S. English)
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 6
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x6708\x66dc\x65e5
+ SDAYNAME2 \x706b\x66dc\x65e5
+ SDAYNAME3 \x6c34\x66dc\x65e5
+ SDAYNAME4 \x6728\x66dc\x65e5
+ SDAYNAME5 \x91d1\x66dc\x65e5
+ SDAYNAME6 \x571f\x66dc\x65e5
+ SDAYNAME7 \x65e5\x66dc\x65e5
+
+ SABBREVDAYNAME1 \x6708
+ SABBREVDAYNAME2 \x706b
+ SABBREVDAYNAME3 \x6c34
+ SABBREVDAYNAME4 \x6728
+ SABBREVDAYNAME5 \x91d1
+ SABBREVDAYNAME6 \x571f
+ SABBREVDAYNAME7 \x65e5
+
+ SMONTHNAME1 \xff11\x6708
+ SMONTHNAME2 \xff12\x6708
+ SMONTHNAME3 \xff13\x6708
+ SMONTHNAME4 \xff14\x6708
+ SMONTHNAME5 \xff15\x6708
+ SMONTHNAME6 \xff16\x6708
+ SMONTHNAME7 \xff17\x6708
+ SMONTHNAME8 \xff18\x6708
+ SMONTHNAME9 \xff19\x6708
+ SMONTHNAME10 \xff11\xff10\x6708
+ SMONTHNAME11 \xff11\xff11\x6708
+ SMONTHNAME12 \xff11\xff12\x6708
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 1
+ SABBREVMONTHNAME2 2
+ SABBREVMONTHNAME3 3
+ SABBREVMONTHNAME4 4
+ SABBREVMONTHNAME5 5
+ SABBREVMONTHNAME6 6
+ SABBREVMONTHNAME7 7
+ SABBREVMONTHNAME8 8
+ SABBREVMONTHNAME9 9
+ SABBREVMONTHNAME10 10
+ SABBREVMONTHNAME11 11
+ SABBREVMONTHNAME12 12
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0412 ; Korean - Korea
+
+ ILANGUAGE 0412
+ SENGLANGUAGE Korean
+ SABBREVLANGNAME KOR
+ SNATIVELANGNAME \x3ca2\x3476\x3971
+ ICOUNTRY 82
+ SENGCOUNTRY Korea
+ SABBREVCTRYNAME KOR
+ SNATIVECTRYNAME \x35c2\x3ca2\x377b\x3476
+
+ IDEFAULTLANGUAGE 0412
+ IDEFAULTCOUNTRY 82
+ IDEFAULTANSICODEPAGE 949
+ IDEFAULTOEMCODEPAGE 949
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 0
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY \x20a9
+ SINTLSYMBOL KRW
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 HH:mm:ss
+ H:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x39a1\x3a3b
+ S2359 \x39a1\x3cf3
+
+ SSHORTDATE 4 yy-MM-dd
+ yy-M-d
+ yyyy-M-d
+ yyyy-MM-dd
+ SDATE -
+ IDATE 2
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 yyyy'\x355b' M'\x39da' d'\x3a0e'
+ yyyy'\x355b' MM'\x39da' dd'\x3a0e'
+ ILDATE 2
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 5\xffffTangun Era
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 6
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x39da\x39c5\x3a0e
+ SDAYNAME2 \x3cdc\x39c5\x3a0e
+ SDAYNAME3 \x38bd\x39c5\x3a0e
+ SDAYNAME4 \x3740\x39c5\x3a0e
+ SDAYNAME5 \x349a\x39c5\x3a0e
+ SDAYNAME6 \x3bf9\x39c5\x3a0e
+ SDAYNAME7 \x39da\x39c5\x3a0e
+
+ SABBREVDAYNAME1 \x39da
+ SABBREVDAYNAME2 \x3cdc
+ SABBREVDAYNAME3 \x38bd
+ SABBREVDAYNAME4 \x3740
+ SABBREVDAYNAME5 \x349a
+ SABBREVDAYNAME6 \x3bf9
+ SABBREVDAYNAME7 \x39da
+
+ SMONTHNAME1 \x0031\x39da
+ SMONTHNAME2 \x0032\x39da
+ SMONTHNAME3 \x0033\x39da
+ SMONTHNAME4 \x0034\x39da
+ SMONTHNAME5 \x0035\x39da
+ SMONTHNAME6 \x0036\x39da
+ SMONTHNAME7 \x0037\x39da
+ SMONTHNAME8 \x0038\x39da
+ SMONTHNAME9 \x0039\x39da
+ SMONTHNAME10 \x0031\x0030\x39da
+ SMONTHNAME11 \x0031\x0031\x39da
+ SMONTHNAME12 \x0031\x0032\x39da
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 \x0031\x39da
+ SABBREVMONTHNAME2 \x0032\x39da
+ SABBREVMONTHNAME3 \x0033\x39da
+ SABBREVMONTHNAME4 \x0034\x39da
+ SABBREVMONTHNAME5 \x0035\x39da
+ SABBREVMONTHNAME6 \x0036\x39da
+ SABBREVMONTHNAME7 \x0037\x39da
+ SABBREVMONTHNAME8 \x0038\x39da
+ SABBREVMONTHNAME9 \x0039\x39da
+ SABBREVMONTHNAME10 \x0031\x0030\x39da
+ SABBREVMONTHNAME11 \x0031\x0031\x39da
+ SABBREVMONTHNAME12 \x0031\x0032\x39da
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0413 ; Dutch - Netherlands
+
+ ILANGUAGE 0413
+ SENGLANGUAGE Dutch
+ SABBREVLANGNAME NLD
+ SNATIVELANGNAME Nederlands
+
+ ICOUNTRY 31
+ SENGCOUNTRY Netherlands
+ SABBREVCTRYNAME NLD
+ SNATIVECTRYNAME Nederland
+
+ IDEFAULTLANGUAGE 0413
+ IDEFAULTCOUNTRY 31
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY F
+ SINTLSYMBOL NLG
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 2
+ INEGCURR 11
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 6 H:mm:ss
+ HH:mm:ss
+ H:mm
+ H.mm
+ HH.mm.ss' uur'
+ HH:mm:ss' uur'
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 d-MM-yy
+ dd-MM-yy
+ dd/MM/yy
+ dd.MM.yy
+ SDATE -
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 1
+
+ SLONGDATE 4 dddd d MMMM yyyy
+ d-MMM-yy
+ d MMMM yyyy
+ d MMM yy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 maandag
+ SDAYNAME2 dinsdag
+ SDAYNAME3 woensdag
+ SDAYNAME4 donderdag
+ SDAYNAME5 vrijdag
+ SDAYNAME6 zaterdag
+ SDAYNAME7 zondag
+
+ SABBREVDAYNAME1 ma
+ SABBREVDAYNAME2 di
+ SABBREVDAYNAME3 wo
+ SABBREVDAYNAME4 do
+ SABBREVDAYNAME5 vr
+ SABBREVDAYNAME6 za
+ SABBREVDAYNAME7 zo
+
+ SMONTHNAME1 januari
+ SMONTHNAME2 februari
+ SMONTHNAME3 maart
+ SMONTHNAME4 april
+ SMONTHNAME5 mei
+ SMONTHNAME6 juni
+ SMONTHNAME7 juli
+ SMONTHNAME8 augustus
+ SMONTHNAME9 september
+ SMONTHNAME10 oktober
+ SMONTHNAME11 november
+ SMONTHNAME12 december
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mrt
+ SABBREVMONTHNAME4 apr
+ SABBREVMONTHNAME5 mei
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 aug
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 okt
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0813 ; Dutch - Belgium
+
+ ILANGUAGE 0813
+ SENGLANGUAGE Dutch
+ SABBREVLANGNAME NLB
+ SNATIVELANGNAME Nederlands
+
+ ICOUNTRY 32
+ SENGCOUNTRY Belgium
+ SABBREVCTRYNAME BEL
+ SNATIVECTRYNAME België
+
+ IDEFAULTLANGUAGE 0813
+ IDEFAULTCOUNTRY 32
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY BF
+ SINTLSYMBOL BEF
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 H:mm:ss
+ HH:mm:ss
+ H.mm' u.'
+ H:mm
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 d/MM/yy
+ dd-mm-yy
+ dd.MM.yy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 1
+
+ SLONGDATE 4 dddd d MMMM yyyy
+ dd-MMM-yy
+ d MMMM yyyy
+ dd MMM yy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 maandag
+ SDAYNAME2 dinsdag
+ SDAYNAME3 woensdag
+ SDAYNAME4 donderdag
+ SDAYNAME5 vrijdag
+ SDAYNAME6 zaterdag
+ SDAYNAME7 zondag
+
+ SABBREVDAYNAME1 ma
+ SABBREVDAYNAME2 di
+ SABBREVDAYNAME3 wo
+ SABBREVDAYNAME4 do
+ SABBREVDAYNAME5 vr
+ SABBREVDAYNAME6 za
+ SABBREVDAYNAME7 zo
+
+ SMONTHNAME1 januari
+ SMONTHNAME2 februari
+ SMONTHNAME3 maart
+ SMONTHNAME4 april
+ SMONTHNAME5 mei
+ SMONTHNAME6 juni
+ SMONTHNAME7 juli
+ SMONTHNAME8 augustus
+ SMONTHNAME9 september
+ SMONTHNAME10 oktober
+ SMONTHNAME11 november
+ SMONTHNAME12 december
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mrt
+ SABBREVMONTHNAME4 apr
+ SABBREVMONTHNAME5 mei
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 aug
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 okt
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0414 ; Norwegian - Norway (Bokmal)
+
+ ILANGUAGE 0414
+ SENGLANGUAGE Norwegian (Bokmal)
+ SABBREVLANGNAME NOR
+ SNATIVELANGNAME Norsk
+
+ ICOUNTRY 47
+ SENGCOUNTRY Norway
+ SABBREVCTRYNAME NOR
+ SNATIVECTRYNAME Norge
+
+ IDEFAULTLANGUAGE 0414
+ IDEFAULTCOUNTRY 47
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY kr
+ SINTLSYMBOL NOK
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 2
+ INEGCURR 2
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 HH:mm:ss
+ H:mm:ss
+ 'kl 'HH.mm
+ HH.mm.ss
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 5 dd.MM.yy
+ yyyy-MM-dd
+ d.M.yy
+ ddMMyy
+ dd.MM.yy
+ SDATE .
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 d. MMMM yyyy
+ dd. MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 mandag
+ SDAYNAME2 tirsdag
+ SDAYNAME3 onsdag
+ SDAYNAME4 torsdag
+ SDAYNAME5 fredag
+ SDAYNAME6 lørdag
+ SDAYNAME7 søndag
+
+ SABBREVDAYNAME1 ma
+ SABBREVDAYNAME2 ti
+ SABBREVDAYNAME3 on
+ SABBREVDAYNAME4 to
+ SABBREVDAYNAME5 fr
+ SABBREVDAYNAME6 lø
+ SABBREVDAYNAME7 sø
+
+ SMONTHNAME1 januar
+ SMONTHNAME2 februar
+ SMONTHNAME3 mars
+ SMONTHNAME4 april
+ SMONTHNAME5 mai
+ SMONTHNAME6 juni
+ SMONTHNAME7 juli
+ SMONTHNAME8 august
+ SMONTHNAME9 september
+ SMONTHNAME10 oktober
+ SMONTHNAME11 november
+ SMONTHNAME12 desember
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 apr
+ SABBREVMONTHNAME5 mai
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 aug
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 okt
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 des
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0814 ; Norwegian - Norway (Nynorsk)
+
+ ILANGUAGE 0814
+ SENGLANGUAGE Norwegian (Nynorsk)
+ SABBREVLANGNAME NON
+ SNATIVELANGNAME Norsk
+
+ ICOUNTRY 47
+ SENGCOUNTRY Norway
+ SABBREVCTRYNAME NOR
+ SNATIVECTRYNAME Norge
+
+ IDEFAULTLANGUAGE 0814
+ IDEFAULTCOUNTRY 47
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY kr
+ SINTLSYMBOL NOK
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 2
+ INEGCURR 2
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 HH:mm:ss
+ H:mm:ss
+ 'kl 'HH.mm
+ HH.mm.ss
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 5 dd.MM.yy
+ yyyy-MM-dd
+ d.M.yy
+ ddMMyy
+ dd.MM.yy
+ SDATE .
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 d. MMMM yyyy
+ dd. MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 mandag
+ SDAYNAME2 tirsdag
+ SDAYNAME3 onsdag
+ SDAYNAME4 torsdag
+ SDAYNAME5 fredag
+ SDAYNAME6 lørdag
+ SDAYNAME7 søndag
+
+ SABBREVDAYNAME1 ma
+ SABBREVDAYNAME2 ti
+ SABBREVDAYNAME3 on
+ SABBREVDAYNAME4 to
+ SABBREVDAYNAME5 fr
+ SABBREVDAYNAME6 lø
+ SABBREVDAYNAME7 sø
+
+ SMONTHNAME1 januar
+ SMONTHNAME2 februar
+ SMONTHNAME3 mars
+ SMONTHNAME4 april
+ SMONTHNAME5 mai
+ SMONTHNAME6 juni
+ SMONTHNAME7 juli
+ SMONTHNAME8 august
+ SMONTHNAME9 september
+ SMONTHNAME10 oktober
+ SMONTHNAME11 november
+ SMONTHNAME12 desember
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 apr
+ SABBREVMONTHNAME5 mai
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 aug
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 okt
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 des
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0415 ; Polish - Poland
+
+ ILANGUAGE 0415
+ SENGLANGUAGE Polish
+ SABBREVLANGNAME PLK
+ SNATIVELANGNAME Polski
+
+ ICOUNTRY 48
+ SENGCOUNTRY Poland
+ SABBREVCTRYNAME POL
+ SNATIVECTRYNAME Polska
+
+ IDEFAULTLANGUAGE 0415
+ IDEFAULTCOUNTRY 48
+ IDEFAULTANSICODEPAGE 1250
+ IDEFAULTOEMCODEPAGE 852
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY z\x0142
+ SINTLSYMBOL PLZ
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 HH:mm:ss
+ H:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 yy.MM.dd
+ yyyy-MM-dd
+ yy-MM-dd
+ SDATE .
+ IDATE 2
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 d MMMM yyyy
+ dd MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Poniedzia\x0142ek
+ SDAYNAME2 Wtorek
+ SDAYNAME3 \x015aroda
+ SDAYNAME4 Czwartek
+ SDAYNAME5 Pi\x0105tek
+ SDAYNAME6 Sobota
+ SDAYNAME7 Niedziela
+
+ SABBREVDAYNAME1 pn.
+ SABBREVDAYNAME2 wt.
+ SABBREVDAYNAME3 \x015br.
+ SABBREVDAYNAME4 czw.
+ SABBREVDAYNAME5 pt.
+ SABBREVDAYNAME6 sob.
+ SABBREVDAYNAME7 ndz.
+
+ SMONTHNAME1 Styze\x0144
+ SMONTHNAME2 Luty
+ SMONTHNAME3 Marzec
+ SMONTHNAME4 Kwiecie\x0144
+ SMONTHNAME5 Maj
+ SMONTHNAME6 Czerwiec
+ SMONTHNAME7 Lipiec
+ SMONTHNAME8 Sierpie\x0144
+ SMONTHNAME9 Wrzesie\x0144
+ SMONTHNAME10 Pa\x017adziernik
+ SMONTHNAME11 Listopad
+ SMONTHNAME12 Grudzie\x0144
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Sty
+ SABBREVMONTHNAME2 Lut
+ SABBREVMONTHNAME3 Mar
+ SABBREVMONTHNAME4 Kwi
+ SABBREVMONTHNAME5 Maj
+ SABBREVMONTHNAME6 Cze
+ SABBREVMONTHNAME7 Lip
+ SABBREVMONTHNAME8 Sie
+ SABBREVMONTHNAME9 Wrz
+ SABBREVMONTHNAME10 Pa\x017a
+ SABBREVMONTHNAME11 Lis
+ SABBREVMONTHNAME12 Gru
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0416 ; Portuguese - Brazil
+
+ ILANGUAGE 0416
+ SENGLANGUAGE Portuguese
+ SABBREVLANGNAME PTB
+ SNATIVELANGNAME Português
+
+ ICOUNTRY 55
+ SENGCOUNTRY Brazil
+ SABBREVCTRYNAME BRA
+ SNATIVECTRYNAME Brasil
+
+ IDEFAULTLANGUAGE 0416
+ IDEFAULTCOUNTRY 55
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY Cr$
+ SINTLSYMBOL BRC
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 2
+ INEGCURR 0
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 dd/MM/yy
+ dd/MM/yyyy
+ yyyy.MM.dd
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 dddd, d' de 'MMMM' de 'yyyy
+ d' de 'MMMM' de 'yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 segunda-feira
+ SDAYNAME2 terça-feira
+ SDAYNAME3 quarta-feira
+ SDAYNAME4 quinta-feira
+ SDAYNAME5 sexta-feira
+ SDAYNAME6 sábado
+ SDAYNAME7 domingo
+
+ SABBREVDAYNAME1 seg
+ SABBREVDAYNAME2 ter
+ SABBREVDAYNAME3 qua
+ SABBREVDAYNAME4 qui
+ SABBREVDAYNAME5 sex
+ SABBREVDAYNAME6 sáb
+ SABBREVDAYNAME7 dom
+
+ SMONTHNAME1 janeiro
+ SMONTHNAME2 fevereiro
+ SMONTHNAME3 março
+ SMONTHNAME4 abril
+ SMONTHNAME5 maio
+ SMONTHNAME6 junho
+ SMONTHNAME7 julho
+ SMONTHNAME8 agosto
+ SMONTHNAME9 setembro
+ SMONTHNAME10 outubro
+ SMONTHNAME11 novembro
+ SMONTHNAME12 dezembro
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan
+ SABBREVMONTHNAME2 fev
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 abr
+ SABBREVMONTHNAME5 mai
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 ago
+ SABBREVMONTHNAME9 set
+ SABBREVMONTHNAME10 out
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dez
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0816 ; Portuguese - Portugal
+
+ ILANGUAGE 0816
+ SENGLANGUAGE Portuguese
+ SABBREVLANGNAME PTG
+ SNATIVELANGNAME Português
+
+ ICOUNTRY 351
+ SENGCOUNTRY Portugal
+ SABBREVCTRYNAME PRT
+ SNATIVECTRYNAME Portugal
+
+ IDEFAULTLANGUAGE 0816
+ IDEFAULTCOUNTRY 351
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY Esc.
+ SINTLSYMBOL PTE
+ SMONDECIMALSEP $
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 3 H:mm:ss
+ HH:mm:ss
+ HH'H'mm'm'
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 5 dd-MM-yyyy
+ yy.MM.dd
+ d.M.yy
+ dd/MM/yy
+ yyyy-MM-dd
+ SDATE -
+ IDATE 1
+ ICENTURY 1
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 4 dddd, d' de 'MMMM' de 'yyyy
+ d' de 'MMMM' de 'yyyy
+ d/MMM/yy
+ d.MMM.yy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 segunda-feira
+ SDAYNAME2 terça-feira
+ SDAYNAME3 quarta-feira
+ SDAYNAME4 quinta-feira
+ SDAYNAME5 sexta-feira
+ SDAYNAME6 sábado
+ SDAYNAME7 domingo
+
+ SABBREVDAYNAME1 seg
+ SABBREVDAYNAME2 ter
+ SABBREVDAYNAME3 qua
+ SABBREVDAYNAME4 qui
+ SABBREVDAYNAME5 sex
+ SABBREVDAYNAME6 sáb
+ SABBREVDAYNAME7 dom
+
+ SMONTHNAME1 janeiro
+ SMONTHNAME2 fevereiro
+ SMONTHNAME3 março
+ SMONTHNAME4 abril
+ SMONTHNAME5 maio
+ SMONTHNAME6 junho
+ SMONTHNAME7 julho
+ SMONTHNAME8 agosto
+ SMONTHNAME9 setembro
+ SMONTHNAME10 outubro
+ SMONTHNAME11 novembro
+ SMONTHNAME12 dezembro
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan
+ SABBREVMONTHNAME2 fev
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 abr
+ SABBREVMONTHNAME5 mai
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 ago
+ SABBREVMONTHNAME9 set
+ SABBREVMONTHNAME10 out
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dez
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0419 ; Russian - Russia
+
+ ILANGUAGE 0419
+ SENGLANGUAGE Russian
+ SABBREVLANGNAME RUS
+ SNATIVELANGNAME \x0420\x0443\x0441\x0441\x043a\x0438\x0439
+
+ ICOUNTRY 7
+ SENGCOUNTRY Russia
+ SABBREVCTRYNAME RUS
+ SNATIVECTRYNAME \x0420\x043e\x0441\x0441\x0438\x044f
+
+ IDEFAULTLANGUAGE 0419
+ IDEFAULTCOUNTRY 7
+ IDEFAULTANSICODEPAGE 1251
+ IDEFAULTOEMCODEPAGE 866
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY \x0440.
+ SINTLSYMBOL SUR
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 5
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 dd.MM.yy
+ d.M.yy
+ dd/MM/yy
+ SDATE .
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 d MMMM yyyy
+ dd MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x041f\x043e\x043d\x0435\x0434\x0435\x043b\x044c\x043d\x0438\x043a
+ SDAYNAME2 \x0412\x0442\x043e\x0440\x043d\x0438\x043a
+ SDAYNAME3 \x0421\x0440\x0435\x0434\x0430
+ SDAYNAME4 \x0427\x0435\x0442\x0432\x0435\x0440\x0433
+ SDAYNAME5 \x041f\x044f\x0442\x043d\x0438\x0446\x0430
+ SDAYNAME6 \x0421\x0443\x0431\x0431\x043e\x0442\x0430
+ SDAYNAME7 \x0412\x043e\x0441\x043a\x0440\x0435\x0441\x0435\x043d\x044c\x0435
+
+ SABBREVDAYNAME1 \x041f\x043e\x043d
+ SABBREVDAYNAME2 \x0412\x0442\x043e
+ SABBREVDAYNAME3 \x0421\x0440\x0435
+ SABBREVDAYNAME4 \x0427\x0435\x0442
+ SABBREVDAYNAME5 \x041f\x044f\x0442
+ SABBREVDAYNAME6 \x0421\x0443\x0431
+ SABBREVDAYNAME7 \x0412\x043e\x0441
+
+ SMONTHNAME1 \x042f\x043d\x0432\x0430\x0440\x044c\xffff\x044f\x043d\x0432\x0430\x0440\x044f
+ SMONTHNAME2 \x0424\x0435\x0432\x0440\x0430\x043b\x044c\xffff\x0444\x0435\x0432\x0440\x0430\x043b\x044f
+ SMONTHNAME3 \x041c\x0430\x0440\x0442\xffff\x043c\x0430\x0440\x0442\x0430
+ SMONTHNAME4 \x0410\x043f\x0440\x0435\x043b\x044c\xffff\x0430\x043f\x0440\x0435\x043b\x044f
+ SMONTHNAME5 \x041c\x0430\x0439\xffff\x043c\x0430\x044f
+ SMONTHNAME6 \x0418\x044e\x043d\x044c\xffff\x0438\x044e\x043d\x044f
+ SMONTHNAME7 \x0418\x044e\x043b\x044c\xffff\x0438\x044e\x043b\x044f
+ SMONTHNAME8 \x0410\x0432\x0433\x0443\x0441\x0442\xffff\x0430\x0432\x0433\x0443\x0441\x0442\x0430
+ SMONTHNAME9 \x0421\x0435\x043d\x0442\x044f\x0431\x0440\x044c\xffff\x0441\x0435\x043d\x0442\x044f\x0431\x0440\x044f
+ SMONTHNAME10 \x041e\x043a\x0442\x044f\x0431\x0440\x044c\xffff\x043e\x043a\x0442\x044f\x0431\x0440\x044f
+ SMONTHNAME11 \x041d\x043e\x044f\x0431\x0440\x044c\xffff\x043d\x043e\x044f\x0431\x0440\x044f
+ SMONTHNAME12 \x0414\x0435\x043a\x0430\x0431\x0440\x044c\xffff\x0434\x0435\x043a\x0430\x0431\x0440\x044f
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 \x042f\x043d\x0432
+ SABBREVMONTHNAME2 \x0424\x0435\x0432
+ SABBREVMONTHNAME3 \x041c\x0430\x0440
+ SABBREVMONTHNAME4 \x0410\x043f\x0440
+ SABBREVMONTHNAME5 \x041c\x0430\x0439\xffff\x043c\x0430\x044f
+ SABBREVMONTHNAME6 \x0418\x044e\x043d
+ SABBREVMONTHNAME7 \x0418\x044e\x043b
+ SABBREVMONTHNAME8 \x0410\x0432\x0433
+ SABBREVMONTHNAME9 \x0421\x0435\x043d
+ SABBREVMONTHNAME10 \x041e\x043a\x0442
+ SABBREVMONTHNAME11 \x041d\x043e\x044f
+ SABBREVMONTHNAME12 \x0414\x0435\x043a
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 041B ; Slovak - Slovak Republic
+
+ ILANGUAGE 041B
+ SENGLANGUAGE Slovak
+ SABBREVLANGNAME SKY
+ SNATIVELANGNAME Slovenský
+
+ ICOUNTRY 42
+ SENGCOUNTRY Slovak Republic
+ SABBREVCTRYNAME SVK
+ SNATIVECTRYNAME Slovenská republika
+
+ IDEFAULTLANGUAGE 041B
+ IDEFAULTCOUNTRY 42
+ IDEFAULTANSICODEPAGE 1250
+ IDEFAULTOEMCODEPAGE 852
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY Sk
+ SINTLSYMBOL SKK
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 HH.mm.ss
+ H.mm.ss
+ STIME .
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd.MM.yyyy
+ dd-MM-yy
+ yyyy-MM-dd
+ yy-MM-dd
+ SDATE .
+ IDATE 1
+ ICENTURY 1
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 d. MMMM yyyy
+ dd. MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 pondelok
+ SDAYNAME2 utorok
+ SDAYNAME3 streda
+ SDAYNAME4 \x0161tvrtok
+ SDAYNAME5 piatok
+ SDAYNAME6 sobota
+ SDAYNAME7 nede\x013ea
+
+ SABBREVDAYNAME1 po
+ SABBREVDAYNAME2 ut
+ SABBREVDAYNAME3 st
+ SABBREVDAYNAME4 \x0161t
+ SABBREVDAYNAME5 pi
+ SABBREVDAYNAME6 so
+ SABBREVDAYNAME7 ne
+
+ SMONTHNAME1 január
+ SMONTHNAME2 február
+ SMONTHNAME3 marec
+ SMONTHNAME4 apríl
+ SMONTHNAME5 máj
+ SMONTHNAME6 jún
+ SMONTHNAME7 júl
+ SMONTHNAME8 august
+ SMONTHNAME9 september
+ SMONTHNAME10 október
+ SMONTHNAME11 november
+ SMONTHNAME12 december
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 apr
+ SABBREVMONTHNAME5 máj
+ SABBREVMONTHNAME6 jún
+ SABBREVMONTHNAME7 júl
+ SABBREVMONTHNAME8 aug
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 okt
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 041D ; Swedish - Sweden
+
+ ILANGUAGE 041D
+ SENGLANGUAGE Swedish
+ SABBREVLANGNAME SVE
+ SNATIVELANGNAME Svenska
+
+ ICOUNTRY 46
+ SENGCOUNTRY Sweden
+ SABBREVCTRYNAME SWE
+ SNATIVECTRYNAME Sverige
+
+ IDEFAULTLANGUAGE 041D
+ IDEFAULTCOUNTRY 46
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY kr
+ SINTLSYMBOL SEK
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 3 HH.mm.ss
+ H.mm.ss
+ 'kl 'H.mm
+ STIME .
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 yyyy-MM-dd
+ yy-MM-dd
+ yyMMdd
+ d/M-yy
+ SDATE -
+ IDATE 2
+ ICENTURY 1
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 ' den 'd MMMM yyyy
+ ' den 'dd MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 måndag
+ SDAYNAME2 tisdag
+ SDAYNAME3 onsdag
+ SDAYNAME4 torsdag
+ SDAYNAME5 fredag
+ SDAYNAME6 lördag
+ SDAYNAME7 söndag
+
+ SABBREVDAYNAME1 må
+ SABBREVDAYNAME2 ti
+ SABBREVDAYNAME3 on
+ SABBREVDAYNAME4 to
+ SABBREVDAYNAME5 fr
+ SABBREVDAYNAME6 lö
+ SABBREVDAYNAME7 sö
+
+ SMONTHNAME1 januari
+ SMONTHNAME2 februari
+ SMONTHNAME3 mars
+ SMONTHNAME4 april
+ SMONTHNAME5 maj
+ SMONTHNAME6 juni
+ SMONTHNAME7 juli
+ SMONTHNAME8 augusti
+ SMONTHNAME9 september
+ SMONTHNAME10 oktober
+ SMONTHNAME11 november
+ SMONTHNAME12 december
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 apr
+ SABBREVMONTHNAME5 maj
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 aug
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 okt
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 041F ; Turkish - Turkey
+
+ ILANGUAGE 041F
+ SENGLANGUAGE Turkish
+ SABBREVLANGNAME TRK
+ SNATIVELANGNAME Türkçe
+
+ ICOUNTRY 90
+ SENGCOUNTRY Turkey
+ SABBREVCTRYNAME TUR
+ SNATIVECTRYNAME Türkiye
+
+ IDEFAULTLANGUAGE 041F
+ IDEFAULTCOUNTRY 90
+ IDEFAULTANSICODEPAGE 1254
+ IDEFAULTOEMCODEPAGE 857
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY TL
+ SINTLSYMBOL TRL
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 d/M/yyyy
+ dd/MM/yy
+ yy/MM/dd
+ SDATE /
+ IDATE 1
+ ICENTURY 1
+ IDAYLZERO 0
+ IMONLZERO 0
+
+ SLONGDATE 3 d MMMM yyyy, dddd
+ dd MMMM yyyy, dddd
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Pazartesi
+ SDAYNAME2 Sae\x0131
+ SDAYNAME3 \x00c7ar\x015famba
+ SDAYNAME4 per\x015fembe
+ SDAYNAME5 Cuma
+ SDAYNAME6 Cumartesi
+ SDAYNAME7 Pazar
+
+ SABBREVDAYNAME1 Pazartesi
+ SABBREVDAYNAME2 Sae\x0131
+ SABBREVDAYNAME3 \x00c7ar\x015famba
+ SABBREVDAYNAME4 per\x015fembe
+ SABBREVDAYNAME5 Cuma
+ SABBREVDAYNAME6 Cumartesi
+ SABBREVDAYNAME7 Pazar
+
+ SMONTHNAME1 Ocak
+ SMONTHNAME2 \x015eubat
+ SMONTHNAME3 Mart
+ SMONTHNAME4 Nisan
+ SMONTHNAME5 May\x0131s
+ SMONTHNAME6 Haziran
+ SMONTHNAME7 Temmuz
+ SMONTHNAME8 A\x011fustos
+ SMONTHNAME9 Eylül
+ SMONTHNAME10 Ekim
+ SMONTHNAME11 Kas\x0131m
+ SMONTHNAME12 Aral\x0131k
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Ocak
+ SABBREVMONTHNAME2 \x015eubat
+ SABBREVMONTHNAME3 Mart
+ SABBREVMONTHNAME4 Nisan
+ SABBREVMONTHNAME5 May\x0131s
+ SABBREVMONTHNAME6 Haziran
+ SABBREVMONTHNAME7 Temmuz
+ SABBREVMONTHNAME8 A\x011fustos
+ SABBREVMONTHNAME9 Eylül
+ SABBREVMONTHNAME10 Ekim
+ SABBREVMONTHNAME11 Kas\x0131m
+ SABBREVMONTHNAME12 Aral\x0131k
+ SABBREVMONTHNAME13 \x0000
+
+
+ENDLOCALE
+
+
+
+CALENDAR 7
+
+
+ BEGINCALENDAR 1 ; Gregorian (localized)
+
+ SCALENDAR 1
+
+ SERARANGES 0
+
+ SSHORTDATE 1 \x0000
+ SLONGDATE 1 \x0000
+
+ IF_NAMES 0
+
+
+ BEGINCALENDAR 2 ; Gregorian (U.S. English only)
+
+ SCALENDAR 2
+
+ SERARANGES 0
+
+ SSHORTDATE 4 M/d/yy
+ M/d/yyyy
+ MM/dd/yy
+ MM/dd/yyyy
+ SLONGDATE 2 dddd, MMMM dd, yyyy
+ MMMM dd, yyyy
+
+ IF_NAMES 1
+
+ SDAYNAME1 Monday
+ SDAYNAME2 Tuesday
+ SDAYNAME3 Wednesday
+ SDAYNAME4 Thursday
+ SDAYNAME5 Friday
+ SDAYNAME6 Saturday
+ SDAYNAME7 Sunday
+
+ SABBREVDAYNAME1 Mon
+ SABBREVDAYNAME2 Tue
+ SABBREVDAYNAME3 Wed
+ SABBREVDAYNAME4 Thu
+ SABBREVDAYNAME5 Fri
+ SABBREVDAYNAME6 Sat
+ SABBREVDAYNAME7 Sun
+
+ SMONTHNAME1 January
+ SMONTHNAME2 February
+ SMONTHNAME3 March
+ SMONTHNAME4 April
+ SMONTHNAME5 May
+ SMONTHNAME6 June
+ SMONTHNAME7 July
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 October
+ SMONTHNAME11 November
+ SMONTHNAME12 December
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mar
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 May
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Oct
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dec
+ SABBREVMONTHNAME13 \x0000
+
+
+ BEGINCALENDAR 3 ; Japanese Era - Year of the Emperor
+
+ SCALENDAR 3
+
+ SERARANGES 4 1989\xffff\x337b
+ 1926\xffff\x337c
+ 1912\xffff\x337d
+ 1868\xffff\x337e
+
+ SSHORTDATE 1 ggyyyy/MM/dd
+ SLONGDATE 1 ggyyyy'\x5e74'M'\x6708'd'\x65e5'
+
+ IF_NAMES 0
+
+
+ BEGINCALENDAR 4 ; Taiwan Era - Year of the Republic of China
+
+ SCALENDAR 4
+
+ SERARANGES 1 1912\xffff\x4e2d\x83ef\x6c11\x570b
+
+ SSHORTDATE 1 ggyyyy/MM/dd
+ SLONGDATE 1 ggyyyy MMMM dd
+
+ IF_NAMES 0
+
+
+ BEGINCALENDAR 5 ; Korean - Tangun Era
+
+ SCALENDAR 5
+
+ SERARANGES 1 2333\xffff
+
+ SSHORTDATE 1 yy-MM-dd
+ SLONGDATE 1 yyyy'\x355b' M'\x39da' d'\x3a0e'
+
+ IF_NAMES 0
+
+
+ BEGINCALENDAR 6 ; Hijri - not yet implemented (JDB)
+
+ SCALENDAR 6
+
+ SERARANGES 0
+
+ SSHORTDATE 1 \x0000
+ SLONGDATE 1 \x0000
+
+ IF_NAMES 0
+
+
+ BEGINCALENDAR 7 ; Thai - not yet implemented (JDB)
+
+ SCALENDAR 7
+
+ SERARANGES 1 543\xffff
+
+ SSHORTDATE 1 yyyy/MM/dd
+ SLONGDATE 1 yyyy MMMM dd
+
+ IF_NAMES 0
+
+
+ENDCALENDAR
+ \ No newline at end of file
diff --git a/private/oleauto/src/dispatch/win16/locale.jap b/private/oleauto/src/dispatch/win16/locale.jap
new file mode 100644
index 000000000..105ecc139
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/locale.jap
@@ -0,0 +1,111 @@
+BEGINLOCALE 0411
+
+ ILANGUAGE 0411
+ SENGLANGUAGE Japanese
+ SABBREVLANGNAME JPN
+ SNATIVELANGNAME \x65e5\x672c\x8a9e ;“ú–{Œê/93fa/967b/8cea
+
+ ICOUNTRY 81
+ SENGCOUNTRY Japan
+ SABBREVCTRYNAME JPN
+ SNATIVECTRYNAME \x65e5\x672c ;“ú–{/93fa/967b
+
+ IDEFAULTLANGUAGE 0411
+ IDEFAULTCOUNTRY 81
+ IDEFAULTANSICODEPAGE 932
+ IDEFAULTOEMCODEPAGE 932
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY \xffe5 ;/818f
+ SINTLSYMBOL YEN
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 0
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT tt h:mm:ss
+ STIME :
+ ITIME 0
+ ITLZERO 0
+ ITIMEMARKPOSN 0
+ S1159 \x5348\x524d ;Œß‘O/8cdf/914f
+ S2359 \x5348\x5f8c ;Χ΋/8cdf/8ce3
+
+ SSHORTDATE yy/MM/dd
+ SDATE /
+ IDATE 2
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE ' 'yyyy'\x5e74'M'\x6708'd'\x65e5'WW ;”NŒŽ“ú/944e/8c8e/93fa
+ ILDATE 2
+ ICENTURYLONGDATE 1
+ IDAYLZEROLONGDATE 0
+ IMONLZEROLONGDATE 0
+
+ ICALENDARTYPE 0
+ IADDDATEFORMAT 1
+ IOPTIONALCALENDAR 1
+
+ IFIRSTDAYOFWEEK 6
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x6708\x66dc\x65e5 ;ŒŽ—j“ú/8c8e/976a/93fa
+ SDAYNAME2 \x706b\x66dc\x65e5 ;‰Î—j“ú/89ce/976a/93fa
+ SDAYNAME3 \x6c34\x66dc\x65e5 ;…—j“ú/9085/976a/93fa
+ SDAYNAME4 \x6728\x66dc\x65e5 ;–Ø—j“ú/96d8/976a/93fa
+ SDAYNAME5 \x91d1\x66dc\x65e5 ;‹à—j“ú/8be0/976a/93fa
+ SDAYNAME6 \x571f\x66dc\x65e5 ;“y—j“ú/9379/976a/93fa
+ SDAYNAME7 \x65e5\x66dc\x65e5 ;“ú—j“ú/93fa/976a/93fa
+
+ SABBREVDAYNAME1 \x6708 ;ŒŽ/8c8e
+ SABBREVDAYNAME2 \x706b ;‰Î/89ce
+ SABBREVDAYNAME3 \x6c34 ;…/9085
+ SABBREVDAYNAME4 \x6728 ;–Ø/96d8
+ SABBREVDAYNAME5 \x91d1 ;‹à/8be0
+ SABBREVDAYNAME6 \x571f ;“y/9379
+ SABBREVDAYNAME7 \x65e5 ;“ú/93fa
+
+ SMONTHNAME1 \xff11\x6708 ;‚PŒŽ/8250/8c8e
+ SMONTHNAME2 \xff12\x6708 ;‚QŒŽ/8251/8c8e
+ SMONTHNAME3 \xff13\x6708 ;‚RŒŽ/8252/8c8e
+ SMONTHNAME4 \xff14\x6708 ;‚SŒŽ/8253/8c8e
+ SMONTHNAME5 \xff15\x6708 ;‚TŒŽ/8254/8c8e
+ SMONTHNAME6 \xff16\x6708 ;‚UŒŽ/8255/8c8e
+ SMONTHNAME7 \xff17\x6708 ;‚VŒŽ/8256/8c8e
+ SMONTHNAME8 \xff18\x6708 ;‚WŒŽ/8257/8c8e
+ SMONTHNAME9 \xff19\x6708 ;‚XŒŽ/8258/8c8e
+ SMONTHNAME10 \xff11\xff10\x6708 ;‚P‚OŒŽ/8250/824f/8c8e
+ SMONTHNAME11 \xff11\xff11\x6708 ;‚P‚PŒŽ/8250/8250/8c8e
+ SMONTHNAME12 \xff11\xff12\x6708 ;‚P‚QŒŽ/8250/8251/8c8e
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 1
+ SABBREVMONTHNAME2 2
+ SABBREVMONTHNAME3 3
+ SABBREVMONTHNAME4 4
+ SABBREVMONTHNAME5 5
+ SABBREVMONTHNAME6 6
+ SABBREVMONTHNAME7 7
+ SABBREVMONTHNAME8 8
+ SABBREVMONTHNAME9 9
+ SABBREVMONTHNAME10 10
+ SABBREVMONTHNAME11 11
+ SABBREVMONTHNAME12 12
+ SABBREVMONTHNAME13 \x0000
diff --git a/private/oleauto/src/dispatch/win16/locale.kor b/private/oleauto/src/dispatch/win16/locale.kor
new file mode 100644
index 000000000..8001134e4
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/locale.kor
@@ -0,0 +1,110 @@
+BEGINLOCALE 0412
+
+ ILANGUAGE 0412
+ SENGLANGUAGE Korean
+ SABBREVLANGNAME KOR
+ SNATIVELANGNAME \x3ca2\x3476\x3971 ;Çѱ¹¾î/C7D1/B1B9/BEEE
+ ICOUNTRY 82
+ SENGCOUNTRY Korea
+ SABBREVCTRYNAME KOR
+ SNATIVECTRYNAME \x35c2\x3ca2\x377b\x3476 ;´ëÇѹα¹/B4EB/C7D1/B9CE/B1B9
+
+ IDEFAULTLANGUAGE 0412
+ IDEFAULTCOUNTRY 82
+ IDEFAULTANSICODEPAGE 949
+ IDEFAULTOEMCODEPAGE 949
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 0
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY \x20A9 ;\/5C
+ SINTLSYMBOL KRW
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT HH:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ ITIMEMARKPOSN 0
+ S1159 \x39a1\x3a3b ;¿ÀÀü/BFC0/C0FC
+ S2359 \x39a1\x3cf3 ;¿ÀÈÄ/BFC0/C8C4
+
+ SSHORTDATE yy-MM-dd
+ SDATE -
+ IDATE 2
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE yyyy\x355b M\x39da d\x3a0e ;³â¿ùÀÏ/B3E2/BFF9/C0CF
+ ILDATE 2
+ ICENTURYLONGDATE 1
+ IDAYLZEROLONGDATE 0
+ IMONLZEROLONGDATE 0
+
+ ICALENDARTYPE 0
+ IADDDATEFORMAT 0
+ IOPTIONALCALENDAR 1
+
+ IFIRSTDAYOFWEEK 6
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x39da\x39c5\x3a0e ;¿ù¿äÀÏ/BFF9/BFE4/C0CF
+ SDAYNAME2 \x3cdc\x39c5\x3a0e ;È­¿äÀÏ/C8AD/BFE4/C0CF
+ SDAYNAME3 \x38bd\x39c5\x3a0e ;¼ö¿äÀÏ/BCF6/BFE4/C0CF
+ SDAYNAME4 \x3740\x39c5\x3a0e ;¸ñ¿äÀÏ/B8F1/BFE4/C0CF
+ SDAYNAME5 \x349a\x39c5\x3a0e ;±Ý¿äÀÏ/B1DD/BFE4/C0CF
+ SDAYNAME6 \x3bf9\x39c5\x3a0e ;Åä¿äÀÏ/C5E4/BFE4/C0CF
+ SDAYNAME7 \x39da\x39c5\x3a0e ;¿ù¿äÀÏ/BFF9/BFE4/C0CF
+
+ SABBREVDAYNAME1 \x39da ;¿ù/BFF9
+ SABBREVDAYNAME2 \x3cdc ;È­/C8AD
+ SABBREVDAYNAME3 \x38bd ;¼ö/BCF6
+ SABBREVDAYNAME4 \x3740 ;¸ñ/B8F1
+ SABBREVDAYNAME5 \x349a ;±Ý/B1DD
+ SABBREVDAYNAME6 \x3bf9 ;Åä/C5E4
+ SABBREVDAYNAME7 \x39da ;¿ù/BFF9
+
+ SMONTHNAME1 \x0031\x39da ;1¿ù/31/BFF9
+ SMONTHNAME2 \x0032\x39da ;2¿ù/32/BFF9
+ SMONTHNAME3 \x0033\x39da ;3¿ù/33/BFF9
+ SMONTHNAME4 \x0034\x39da ;4¿ù/34/BFF9
+ SMONTHNAME5 \x0035\x39da ;5¿ù/35/BFF9
+ SMONTHNAME6 \x0036\x39da ;6¿ù/36/BFF9
+ SMONTHNAME7 \x0037\x39da ;7¿ù/37/BFF9
+ SMONTHNAME8 \x0038\x39da ;8¿ù/38/BFF9
+ SMONTHNAME9 \x0039\x39da ;9¿ù/39/BFF9
+ SMONTHNAME10 \x0031\x0030\x39da ;10¿ù/31/30/BFF9
+ SMONTHNAME11 \x0031\x0031\x39da ;11¿ù/31/31/BFF9
+ SMONTHNAME12 \x0031\x0032\x39da ;12¿ù/31/32/BFF9
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 \x0031\x39da ;1¿ù/31/BFF9
+ SABBREVMONTHNAME2 \x0032\x39da ;2¿ù/32/BFF9
+ SABBREVMONTHNAME3 \x0033\x39da ;3¿ù/33/BFF9
+ SABBREVMONTHNAME4 \x0034\x39da ;4¿ù/34/BFF9
+ SABBREVMONTHNAME5 \x0035\x39da ;5¿ù/35/BFF9
+ SABBREVMONTHNAME6 \x0036\x39da ;6¿ù/36/BFF9
+ SABBREVMONTHNAME7 \x0037\x39da ;7¿ù/37/BFF9
+ SABBREVMONTHNAME8 \x0038\x39da ;8¿ù/38/BFF9
+ SABBREVMONTHNAME9 \x0039\x39da ;9¿ù/39/BFF9
+ SABBREVMONTHNAME10 \x0031\x0030\x39da ;10¿ù/31/30/BFF9
+ SABBREVMONTHNAME11 \x0031\x0031\x39da ;11¿ù/31/31/BFF9
+ SABBREVMONTHNAME12 \x0031\x0032\x39da ;12¿ù/31/32/BFF9
+ SABBREVMONTHNAME13 \x0000
diff --git a/private/oleauto/src/dispatch/win16/locale.prc b/private/oleauto/src/dispatch/win16/locale.prc
new file mode 100644
index 000000000..5ddf95f67
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/locale.prc
@@ -0,0 +1,113 @@
+BEGINLOCALE 0804
+
+ ILANGUAGE 0804
+ SENGLANGUAGE Chinese
+ SABBREVLANGNAME CHS
+ SNATIVELANGNAME \x4e2d\x6587 ;ÖÐÎÄ/d6d0/cec4
+
+ ICOUNTRY 086
+ SENGCOUNTRY Peoples' Republic of China
+ SABBREVCTRYNAME CHN
+ SNATIVECTRYNAME \x4e2d\x534e\x4eba\x6c11\x5171\x548c\x56fd
+
+ ;ÖлªÈËÃñ¹²ºÍ¹ú/d6d0/bbaa/c8cb/c3f1/b9b2/bacd/b9fa
+
+ IDEFAULTLANGUAGE 0804
+ IDEFAULTCOUNTRY 086
+ IDEFAULTANSICODEPAGE 936
+ IDEFAULTOEMCODEPAGE 936
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY \x00a5 ;£¤/a3a4
+ SINTLSYMBOL CNY
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 2
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT h:m:s
+ STIME :
+ ITIME 0
+ ITLZERO 0
+ ITIMEMARKPOSN 1
+ S1159 \x4e0a\x5348 ;ÉÏÎç/c9cf/cee7
+ S2359 \x4e0b\x5348 ;ÏÂÎç/cfc2/cee7
+
+ SSHORTDATE yy/M/d
+ SDATE /
+ IDATE 2
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 0
+
+ SLONGDATE dddd, MMMM dd, yyyy
+ ILDATE 2
+ ICENTURYLONGDATE 1
+ IDAYLZEROLONGDATE 0
+ IMONLZEROLONGDATE 0
+
+ ICALENDARTYPE 0
+ IADDDATEFORMAT 0
+ IOPTIONALCALENDAR 1
+
+ IFIRSTDAYOFWEEK 6
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x661f\x671f\x4e00 ;ÐÇÆÚÒ»/d0c7/c6da/d2bb
+ SDAYNAME2 \x661f\x671f\x4e8c ;ÐÇÆÚ¶þ/d0c7/c6da/b6fe
+ SDAYNAME3 \x661f\x671f\x4e09 ;ÐÇÆÚÈý/d0c7/c6da/c8fd
+ SDAYNAME4 \x661f\x671f\x56db ;ÐÇÆÚËÄ/d0c7/c6da/cbc4
+ SDAYNAME5 \x661f\x671f\x4e94 ;ÐÇÆÚÎå/d0c7/c6da/cee5
+ SDAYNAME6 \x661f\x671f\x516d ;ÐÇÆÚÁù/d0c7/c6da/c1f9
+ SDAYNAME7 \x661f\x671f\x65e5 ;ÐÇÆÚÈÕ/d0c7/c6da/c8d5
+
+ SABBREVDAYNAME1 \x0000
+ SABBREVDAYNAME2 \x0000
+ SABBREVDAYNAME3 \x0000
+ SABBREVDAYNAME4 \x0000
+ SABBREVDAYNAME5 \x0000
+ SABBREVDAYNAME6 \x0000
+ SABBREVDAYNAME7 \x0000
+
+ SMONTHNAME1 \x4e00\x6708 ;Ò»ÔÂ /d2bb/d4c2
+ SMONTHNAME2 \x4e8c\x6708 ;¶þÔÂ /b6fe/d4c2
+ SMONTHNAME3 \x4e09\x6708 ;ÈýÔÂ /c8fd/d4c2
+ SMONTHNAME4 \x56db\x6708 ;ËÄÔÂ /cbc4/d4c2
+ SMONTHNAME5 \x4e94\x6708 ;ÎåÔÂ /cee5/d4c2
+ SMONTHNAME6 \x516d\x6708 ;ÁùÔÂ /c1f9/d4c2
+ SMONTHNAME7 \x4e03\x6708 ;ÆßÔÂ /c6df/d4c2
+ SMONTHNAME8 \x516b\x6708 ;°ËÔÂ /b0cb/d4c2
+ SMONTHNAME9 \x4e5d\x6708 ;¾ÅÔ /bec5/d4c2
+ SMONTHNAME10 \x5341\x6708 ;ʮԠ/caae/d4c2
+ SMONTHNAME11 \x5341\x4e00\x6708 ;ʮһÔÂ/caae/d2bb/d4c2
+ SMONTHNAME12 \x5341\x4e8c\x6708 ;Ê®¶þÔÂ/caae/b6fe/d4c2
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 \x0000
+ SABBREVMONTHNAME2 \x0000
+ SABBREVMONTHNAME3 \x0000
+ SABBREVMONTHNAME4 \x0000
+ SABBREVMONTHNAME5 \x0000
+ SABBREVMONTHNAME6 \x0000
+ SABBREVMONTHNAME7 \x0000
+ SABBREVMONTHNAME8 \x0000
+ SABBREVMONTHNAME9 \x0000
+ SABBREVMONTHNAME10 \x0000
+ SABBREVMONTHNAME11 \x0000
+ SABBREVMONTHNAME12 \x0000
+ SABBREVMONTHNAME13 \x0000
diff --git a/private/oleauto/src/dispatch/win16/locale.twn b/private/oleauto/src/dispatch/win16/locale.twn
new file mode 100644
index 000000000..cba82c1e3
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/locale.twn
@@ -0,0 +1,111 @@
+BEGINLOCALE 0404
+
+ ILANGUAGE 0404
+ SENGLANGUAGE Chinese
+ SABBREVLANGNAME CHT
+ SNATIVELANGNAME \x4e2d\x6587 ;¤¤¤å/a4a4/a4e5
+
+ ICOUNTRY 886
+ SENGCOUNTRY Taiwan
+ SABBREVCTRYNAME TWN
+ SNATIVECTRYNAME \x4e2d\x83ef\x6c11\x570b ;¤¤µØ¥Á°ê/a4a4/b5d8/a5c1/b0ea
+
+ IDEFAULTLANGUAGE 0404
+ IDEFAULTCOUNTRY 886
+ IDEFAULTANSICODEPAGE 950
+ IDEFAULTOEMCODEPAGE 950
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY NT$
+ SINTLSYMBOL TWD
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 2
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT h:m:s
+ STIME :
+ ITIME 0
+ ITLZERO 0
+ ITIMEMARKPOSN 1
+ S1159 \x4e0a\x5348 ;¤W¤È/a457/a4c8
+ S2359 \x4e0b\x5348 ;¤U¤È/a455/a4c8
+
+ SSHORTDATE yy/M/d
+ SDATE /
+ IDATE 2
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 0
+
+ SLONGDATE dddd' 'yyyy' 'MM' 'dd
+ ILDATE 2
+ ICENTURYLONGDATE 1
+ IDAYLZEROLONGDATE 0
+ IMONLZEROLONGDATE 0
+
+ ICALENDARTYPE 2
+ IADDDATEFORMAT 0
+ IOPTIONALCALENDAR 1
+
+ IFIRSTDAYOFWEEK 6
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x661f\x671f\x4e00 ;¬P´Á¤@/ac50/b4c1/a440
+ SDAYNAME2 \x661f\x671f\x4e8c ;¬P´Á¤G/ac50/b4c1/a447
+ SDAYNAME3 \x661f\x671f\x4e09 ;¬P´Á¤T/ac50/b4c1/a454
+ SDAYNAME4 \x661f\x671f\x56db ;¬P´Á¥|/ac50/b4c1/a57c
+ SDAYNAME5 \x661f\x671f\x4e94 ;¬P´Á¤­/ac50/b4c1/a4ad
+ SDAYNAME6 \x661f\x671f\x516d ;¬P´Á¤»/ac50/b4c1/a4bb
+ SDAYNAME7 \x661f\x671f\x65e5 ;¬P´Á¤é/ac50/b4c1/a4e9
+
+ SABBREVDAYNAME1 \x0000
+ SABBREVDAYNAME2 \x0000
+ SABBREVDAYNAME3 \x0000
+ SABBREVDAYNAME4 \x0000
+ SABBREVDAYNAME5 \x0000
+ SABBREVDAYNAME6 \x0000
+ SABBREVDAYNAME7 \x0000
+
+ SMONTHNAME1 \x4e00\x6708 ;¤@¤ë /a440/a4eb
+ SMONTHNAME2 \x4e8c\x6708 ;¤G¤ë /a447/a4eb
+ SMONTHNAME3 \x4e09\x6708 ;¤T¤ë /a454/a4eb
+ SMONTHNAME4 \x56db\x6708 ;¥|¤ë /a57c/a4eb
+ SMONTHNAME5 \x4e94\x6708 ;¤­¤ë /a4ad/a4eb
+ SMONTHNAME6 \x516d\x6708 ;¤»¤ë /a4bb/a4eb
+ SMONTHNAME7 \x4e03\x6708 ;¤C¤ë /a443/a4eb
+ SMONTHNAME8 \x516b\x6708 ;¤K¤ë /a44b/a4eb
+ SMONTHNAME9 \x4e5d\x6708 ;¤E¤ë /a445/a4eb
+ SMONTHNAME10 \x5341\x6708 ;¤Q¤ë /a451/a4eb
+ SMONTHNAME11 \x5341\x4e00\x6708 ;¤Q¤@¤ë/a451/a440/a4eb
+ SMONTHNAME12 \x5341\x4e8c\x6708 ;¤Q¤G¤ë/a451/a447/a4eb
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 \x0000
+ SABBREVMONTHNAME2 \x0000
+ SABBREVMONTHNAME3 \x0000
+ SABBREVMONTHNAME4 \x0000
+ SABBREVMONTHNAME5 \x0000
+ SABBREVMONTHNAME6 \x0000
+ SABBREVMONTHNAME7 \x0000
+ SABBREVMONTHNAME8 \x0000
+ SABBREVMONTHNAME9 \x0000
+ SABBREVMONTHNAME10 \x0000
+ SABBREVMONTHNAME11 \x0000
+ SABBREVMONTHNAME12 \x0000
+ SABBREVMONTHNAME13 \x0000
diff --git a/private/oleauto/src/dispatch/win16/locale.txt b/private/oleauto/src/dispatch/win16/locale.txt
new file mode 100644
index 000000000..a54dc1ab5
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/locale.txt
@@ -0,0 +1,4877 @@
+LOCALE 41
+
+BEGINLOCALE 0404 ; Chinese - Taiwan
+
+ ILANGUAGE 0404
+ SENGLANGUAGE Chinese
+ SABBREVLANGNAME CHT
+ SNATIVELANGNAME \x4e2d\x6587
+
+ ICOUNTRY 886
+ SENGCOUNTRY Taiwan
+ SABBREVCTRYNAME TWN
+ SNATIVECTRYNAME \x4e2d\x83ef\x6c11\x570b
+
+ IDEFAULTLANGUAGE 0404
+ IDEFAULTCOUNTRY 886
+ IDEFAULTANSICODEPAGE 950
+ IDEFAULTOEMCODEPAGE 950
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY NT$
+ SINTLSYMBOL TWD
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 2
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 tt h:mm:ss
+ tt hh:mm:ss
+ H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 0
+ ITLZERO 0
+ S1159 \x4e0a\x5348
+ S2359 \x4e0b\x5348
+
+ SSHORTDATE 4 yy/M/d
+ yy/MM/dd
+ yyyy/M/d
+ yyyy/MM/dd
+ SDATE /
+ IDATE 2
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 0
+
+ SLONGDATE 3 dddd yyyy MMMM dd
+ dddd yyyy MM dd
+ yyyy MM dd
+ ILDATE 2
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 4\xffffEra: Year of the Republic of China
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 6
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x661f\x671f\x4e00
+ SDAYNAME2 \x661f\x671f\x4e8c
+ SDAYNAME3 \x661f\x671f\x4e09
+ SDAYNAME4 \x661f\x671f\x56db
+ SDAYNAME5 \x661f\x671f\x4e94
+ SDAYNAME6 \x661f\x671f\x516d
+ SDAYNAME7 \x661f\x671f\x65e5
+
+ SABBREVDAYNAME1 \x661f\x671f\x4e00
+ SABBREVDAYNAME2 \x661f\x671f\x4e8c
+ SABBREVDAYNAME3 \x661f\x671f\x4e09
+ SABBREVDAYNAME4 \x661f\x671f\x56db
+ SABBREVDAYNAME5 \x661f\x671f\x4e94
+ SABBREVDAYNAME6 \x661f\x671f\x516d
+ SABBREVDAYNAME7 \x661f\x671f\x65e5
+
+ SMONTHNAME1 \x4e00\x6708
+ SMONTHNAME2 \x4e8c\x6708
+ SMONTHNAME3 \x4e09\x6708
+ SMONTHNAME4 \x56db\x6708
+ SMONTHNAME5 \x4e94\x6708
+ SMONTHNAME6 \x516d\x6708
+ SMONTHNAME7 \x4e03\x6708
+ SMONTHNAME8 \x516b\x6708
+ SMONTHNAME9 \x4e5d\x6708
+ SMONTHNAME10 \x5341\x6708
+ SMONTHNAME11 \x5341\x4e00\x6708
+ SMONTHNAME12 \x5341\x4e8c\x6708
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 \x4e00\x6708
+ SABBREVMONTHNAME2 \x4e8c\x6708
+ SABBREVMONTHNAME3 \x4e09\x6708
+ SABBREVMONTHNAME4 \x56db\x6708
+ SABBREVMONTHNAME5 \x4e94\x6708
+ SABBREVMONTHNAME6 \x516d\x6708
+ SABBREVMONTHNAME7 \x4e03\x6708
+ SABBREVMONTHNAME8 \x516b\x6708
+ SABBREVMONTHNAME9 \x4e5d\x6708
+ SABBREVMONTHNAME10 \x5341\x6708
+ SABBREVMONTHNAME11 \x5341\x4e00\x6708
+ SABBREVMONTHNAME12 \x5341\x4e8c\x6708
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0804 ; Chinese - PRC
+
+ ILANGUAGE 0804
+ SENGLANGUAGE Chinese
+ SABBREVLANGNAME CHS
+ SNATIVELANGNAME \x4e2d\x6587
+
+ ICOUNTRY 86
+ SENGCOUNTRY Peoples' Republic of China
+ SABBREVCTRYNAME CHN
+ SNATIVECTRYNAME \x4e2d\x534e\x4eba\x6c11\x5171\x548c\x56fd
+
+ IDEFAULTLANGUAGE 0804
+ IDEFAULTCOUNTRY 86
+ IDEFAULTANSICODEPAGE 936
+ IDEFAULTOEMCODEPAGE 936
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY \x00a5
+ SINTLSYMBOL CNY
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 2
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 tt h:mm:ss
+ tt hh:mm:ss
+ H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 0
+ ITLZERO 0
+ S1159 \x4e0a\x5348
+ S2359 \x4e0b\x5348
+
+ SSHORTDATE 4 yy/M/d
+ yy/MM/dd
+ yyyy/M/d
+ yyyy/MM/dd
+ SDATE /
+ IDATE 2
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 0
+
+ SLONGDATE 4 dddd, MMMM d, yyyy
+ MMMM d, yyyy
+ yyyy MM dd
+ dddd yyyy MM dd
+ ILDATE 0
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 6
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x661f\x671f\x4e00
+ SDAYNAME2 \x661f\x671f\x4e8c
+ SDAYNAME3 \x661f\x671f\x4e09
+ SDAYNAME4 \x661f\x671f\x56db
+ SDAYNAME5 \x661f\x671f\x4e94
+ SDAYNAME6 \x661f\x671f\x516d
+ SDAYNAME7 \x661f\x671f\x65e5
+
+ SABBREVDAYNAME1 \x661f\x671f\x4e00
+ SABBREVDAYNAME2 \x661f\x671f\x4e8c
+ SABBREVDAYNAME3 \x661f\x671f\x4e09
+ SABBREVDAYNAME4 \x661f\x671f\x56db
+ SABBREVDAYNAME5 \x661f\x671f\x4e94
+ SABBREVDAYNAME6 \x661f\x671f\x516d
+ SABBREVDAYNAME7 \x661f\x671f\x65e5
+
+ SMONTHNAME1 \x4e00\x6708
+ SMONTHNAME2 \x4e8c\x6708
+ SMONTHNAME3 \x4e09\x6708
+ SMONTHNAME4 \x56db\x6708
+ SMONTHNAME5 \x4e94\x6708
+ SMONTHNAME6 \x516d\x6708
+ SMONTHNAME7 \x4e03\x6708
+ SMONTHNAME8 \x516b\x6708
+ SMONTHNAME9 \x4e5d\x6708
+ SMONTHNAME10 \x5341\x6708
+ SMONTHNAME11 \x5341\x4e00\x6708
+ SMONTHNAME12 \x5341\x4e8c\x6708
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 \x4e00\x6708
+ SABBREVMONTHNAME2 \x4e8c\x6708
+ SABBREVMONTHNAME3 \x4e09\x6708
+ SABBREVMONTHNAME4 \x56db\x6708
+ SABBREVMONTHNAME5 \x4e94\x6708
+ SABBREVMONTHNAME6 \x516d\x6708
+ SABBREVMONTHNAME7 \x4e03\x6708
+ SABBREVMONTHNAME8 \x516b\x6708
+ SABBREVMONTHNAME9 \x4e5d\x6708
+ SABBREVMONTHNAME10 \x5341\x6708
+ SABBREVMONTHNAME11 \x5341\x4e00\x6708
+ SABBREVMONTHNAME12 \x5341\x4e8c\x6708
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0c04 ; Chinese - Hong Kong
+
+ ILANGUAGE 0c04
+ SENGLANGUAGE Chinese
+ SABBREVLANGNAME CHH
+ SNATIVELANGNAME \x4e2d\x6587
+
+ ICOUNTRY 852
+ SENGCOUNTRY Hong Kong
+ SABBREVCTRYNAME HKG
+ SNATIVECTRYNAME \x9999\x6e2f
+
+ IDEFAULTLANGUAGE 0c04
+ IDEFAULTCOUNTRY 852
+ IDEFAULTANSICODEPAGE 950
+ IDEFAULTOEMCODEPAGE 950
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY HK$
+ SINTLSYMBOL HKD
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 0
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 6 d/M/yy
+ dd/MM/yy
+ yy/M/d
+ yy/MM/dd
+ yyyy/M/d
+ yyyy/MM/dd
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 0
+
+ SLONGDATE 4 dddd, d MMMM, yyyy
+ d MMMM, yyyy
+ dddd yyyy MM dd
+ yyyy MM dd
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 6
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x661f\x671f\x4e00
+ SDAYNAME2 \x661f\x671f\x4e8c
+ SDAYNAME3 \x661f\x671f\x4e09
+ SDAYNAME4 \x661f\x671f\x56db
+ SDAYNAME5 \x661f\x671f\x4e94
+ SDAYNAME6 \x661f\x671f\x516d
+ SDAYNAME7 \x661f\x671f\x65e5
+
+ SABBREVDAYNAME1 \x661f\x671f\x4e00
+ SABBREVDAYNAME2 \x661f\x671f\x4e8c
+ SABBREVDAYNAME3 \x661f\x671f\x4e09
+ SABBREVDAYNAME4 \x661f\x671f\x56db
+ SABBREVDAYNAME5 \x661f\x671f\x4e94
+ SABBREVDAYNAME6 \x661f\x671f\x516d
+ SABBREVDAYNAME7 \x661f\x671f\x65e5
+
+ SMONTHNAME1 \x4e00\x6708
+ SMONTHNAME2 \x4e8c\x6708
+ SMONTHNAME3 \x4e09\x6708
+ SMONTHNAME4 \x56db\x6708
+ SMONTHNAME5 \x4e94\x6708
+ SMONTHNAME6 \x516d\x6708
+ SMONTHNAME7 \x4e03\x6708
+ SMONTHNAME8 \x516b\x6708
+ SMONTHNAME9 \x4e5d\x6708
+ SMONTHNAME10 \x5341\x6708
+ SMONTHNAME11 \x5341\x4e00\x6708
+ SMONTHNAME12 \x5341\x4e8c\x6708
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 \x4e00\x6708
+ SABBREVMONTHNAME2 \x4e8c\x6708
+ SABBREVMONTHNAME3 \x4e09\x6708
+ SABBREVMONTHNAME4 \x56db\x6708
+ SABBREVMONTHNAME5 \x4e94\x6708
+ SABBREVMONTHNAME6 \x516d\x6708
+ SABBREVMONTHNAME7 \x4e03\x6708
+ SABBREVMONTHNAME8 \x516b\x6708
+ SABBREVMONTHNAME9 \x4e5d\x6708
+ SABBREVMONTHNAME10 \x5341\x6708
+ SABBREVMONTHNAME11 \x5341\x4e00\x6708
+ SABBREVMONTHNAME12 \x5341\x4e8c\x6708
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 1004 ; Chinese - Singapore
+
+ ILANGUAGE 1004
+ SENGLANGUAGE Chinese
+ SABBREVLANGNAME CHI
+ SNATIVELANGNAME \x4e2d\x6587
+
+ ICOUNTRY 65
+ SENGCOUNTRY Singapore
+ SABBREVCTRYNAME SGP
+ SNATIVECTRYNAME \x65b0\x52a0\x5761
+
+ IDEFAULTLANGUAGE 1004
+ IDEFAULTCOUNTRY 65
+ IDEFAULTANSICODEPAGE 936
+ IDEFAULTOEMCODEPAGE 936
+
+ SLIST ,
+ IMEASURE 1
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY $
+ SINTLSYMBOL SGD
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 0
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 tt h:mm:ss
+ tt hh:mm:ss
+ H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 0
+ ITLZERO 0
+ S1159 AM
+ S2359 PM
+
+ SSHORTDATE 6 d/M/yy
+ dd/MM/yy
+ yy/M/d
+ yy/MM/dd
+ yyyy/M/d
+ yyyy/MM/dd
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 0
+
+ SLONGDATE 4 dddd, d MMMM, yyyy
+ d MMMM, yyyy
+ dddd yyyy MM dd
+ yyyy MM dd
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 6
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x661f\x671f\x4e00
+ SDAYNAME2 \x661f\x671f\x4e8c
+ SDAYNAME3 \x661f\x671f\x4e09
+ SDAYNAME4 \x661f\x671f\x56db
+ SDAYNAME5 \x661f\x671f\x4e94
+ SDAYNAME6 \x661f\x671f\x516d
+ SDAYNAME7 \x661f\x671f\x65e5
+
+ SABBREVDAYNAME1 \x661f\x671f\x4e00
+ SABBREVDAYNAME2 \x661f\x671f\x4e8c
+ SABBREVDAYNAME3 \x661f\x671f\x4e09
+ SABBREVDAYNAME4 \x661f\x671f\x56db
+ SABBREVDAYNAME5 \x661f\x671f\x4e94
+ SABBREVDAYNAME6 \x661f\x671f\x516d
+ SABBREVDAYNAME7 \x661f\x671f\x65e5
+
+ SMONTHNAME1 \x4e00\x6708
+ SMONTHNAME2 \x4e8c\x6708
+ SMONTHNAME3 \x4e09\x6708
+ SMONTHNAME4 \x56db\x6708
+ SMONTHNAME5 \x4e94\x6708
+ SMONTHNAME6 \x516d\x6708
+ SMONTHNAME7 \x4e03\x6708
+ SMONTHNAME8 \x516b\x6708
+ SMONTHNAME9 \x4e5d\x6708
+ SMONTHNAME10 \x5341\x6708
+ SMONTHNAME11 \x5341\x4e00\x6708
+ SMONTHNAME12 \x5341\x4e8c\x6708
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 \x4e00\x6708
+ SABBREVMONTHNAME2 \x4e8c\x6708
+ SABBREVMONTHNAME3 \x4e09\x6708
+ SABBREVMONTHNAME4 \x56db\x6708
+ SABBREVMONTHNAME5 \x4e94\x6708
+ SABBREVMONTHNAME6 \x516d\x6708
+ SABBREVMONTHNAME7 \x4e03\x6708
+ SABBREVMONTHNAME8 \x516b\x6708
+ SABBREVMONTHNAME9 \x4e5d\x6708
+ SABBREVMONTHNAME10 \x5341\x6708
+ SABBREVMONTHNAME11 \x5341\x4e00\x6708
+ SABBREVMONTHNAME12 \x5341\x4e8c\x6708
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0405 ; Czech - Czech Republic
+
+ ILANGUAGE 0405
+ SENGLANGUAGE Czech
+ SABBREVLANGNAME CSY
+ SNATIVELANGNAME \x010cesk\x00fd
+
+ ICOUNTRY 42
+ SENGCOUNTRY Czech Republic
+ SABBREVCTRYNAME CZK
+ SNATIVECTRYNAME \x010cesk\x00e1\x00a0republika
+
+ IDEFAULTLANGUAGE 0405
+ IDEFAULTCOUNTRY 42
+ IDEFAULTANSICODEPAGE 1250
+ IDEFAULTOEMCODEPAGE 852
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY K\x010d
+ SINTLSYMBOL CZK
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 HH.mm.ss
+ H.mm.ss
+ HH:mm:ss
+ H:mm:ss
+ STIME .
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd.MM.yyyy
+ dd-MM-yy
+ yyyy-MM-dd
+ yy-MM-dd
+ SDATE .
+ IDATE 1
+ ICENTURY 1
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 d. MMMM yyyy
+ dd. MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 pon\x00d4\x011bl\x00ed
+ SDAYNAME2 \x00fater\x00fd
+ SDAYNAME3 st\x0159eda
+ SDAYNAME4 \x010dtvrtek
+ SDAYNAME5 pátek
+ SDAYNAME6 sobota
+ SDAYNAME7 ned\x0159le
+
+ SABBREVDAYNAME1 po
+ SABBREVDAYNAME2 út
+ SABBREVDAYNAME3 st
+ SABBREVDAYNAME4 \x010dt
+ SABBREVDAYNAME5 pá
+ SABBREVDAYNAME6 so
+ SABBREVDAYNAME7 ne
+
+ SMONTHNAME1 leden
+ SMONTHNAME2 únor
+ SMONTHNAME3 b\x0159ezen
+ SMONTHNAME4 duben
+ SMONTHNAME5 kv\x011bten
+ SMONTHNAME6 \x010derven
+ SMONTHNAME7 \x010dervenec
+ SMONTHNAME8 srpen
+ SMONTHNAME9 z\x00e1\x0159\x00ed
+ SMONTHNAME10 \x0159\x00edjen
+ SMONTHNAME11 listopad
+ SMONTHNAME12 prosinec
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 led
+ SABBREVMONTHNAME2 únor
+ SABBREVMONTHNAME3 b\x0159ez
+ SABBREVMONTHNAME4 dub
+ SABBREVMONTHNAME5 kv\x011bt
+ SABBREVMONTHNAME6 \x010derv
+ SABBREVMONTHNAME7 \x010derc
+ SABBREVMONTHNAME8 srp
+ SABBREVMONTHNAME9 z\x00e1\x0159
+ SABBREVMONTHNAME10 \x0159\x00edj
+ SABBREVMONTHNAME11 list
+ SABBREVMONTHNAME12 pros
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0406 ; Danish - Denmark
+
+ ILANGUAGE 0406
+ SENGLANGUAGE Danish
+ SABBREVLANGNAME DAN
+ SNATIVELANGNAME Dansk
+
+ ICOUNTRY 45
+ SENGCOUNTRY Denmark
+ SABBREVCTRYNAME DNK
+ SNATIVECTRYNAME Danmark
+
+ IDEFAULTLANGUAGE 0406
+ IDEFAULTCOUNTRY 45
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY kr
+ SINTLSYMBOL DKK
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 2
+ INEGCURR 12
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 3 HH.mm.ss
+ H.mm.ss
+ HH:mm
+ STIME .
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd-MM-yy
+ yyyy-MM-dd
+ yyyy MM dd
+ dd/M-yy
+ SDATE -
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 d. MMMM yyyy
+ dd. MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 mandag
+ SDAYNAME2 tirsdag
+ SDAYNAME3 onsdag
+ SDAYNAME4 torsdag
+ SDAYNAME5 fredag
+ SDAYNAME6 lørdag
+ SDAYNAME7 søndag
+
+ SABBREVDAYNAME1 ma
+ SABBREVDAYNAME2 ti
+ SABBREVDAYNAME3 on
+ SABBREVDAYNAME4 to
+ SABBREVDAYNAME5 fr
+ SABBREVDAYNAME6 lø
+ SABBREVDAYNAME7 sø
+
+ SMONTHNAME1 januar
+ SMONTHNAME2 februar
+ SMONTHNAME3 marts
+ SMONTHNAME4 april
+ SMONTHNAME5 maj
+ SMONTHNAME6 juni
+ SMONTHNAME7 juli
+ SMONTHNAME8 august
+ SMONTHNAME9 september
+ SMONTHNAME10 oktober
+ SMONTHNAME11 november
+ SMONTHNAME12 december
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 apr
+ SABBREVMONTHNAME5 maj
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 aug
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 okt
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0407 ; German - Germany
+
+ ILANGUAGE 0407
+ SENGLANGUAGE German
+ SABBREVLANGNAME DEU
+ SNATIVELANGNAME Deutsch
+
+ ICOUNTRY 49
+ SENGCOUNTRY Germany
+ SABBREVCTRYNAME DEU
+ SNATIVECTRYNAME Deutschland
+
+ IDEFAULTLANGUAGE 0407
+ IDEFAULTCOUNTRY 49
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY DM
+ SINTLSYMBOL DEM
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 HH:mm:ss
+ H:mm:ss
+ H.mm
+ H.mm' Uhr '
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd.MM.yy
+ d.MM.yy
+ d.M.yy
+ d.M.yyyy
+ SDATE .
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 3 dddd, d. MMMM yyyy
+ d. MMMM yyyy
+ d. MMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorianischer Kalender
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Montag
+ SDAYNAME2 Dienstag
+ SDAYNAME3 Mittwoch
+ SDAYNAME4 Donnerstag
+ SDAYNAME5 Freitag
+ SDAYNAME6 Samstag
+ SDAYNAME7 Sonntag
+
+ SABBREVDAYNAME1 Mo
+ SABBREVDAYNAME2 Di
+ SABBREVDAYNAME3 Mi
+ SABBREVDAYNAME4 Do
+ SABBREVDAYNAME5 Fr
+ SABBREVDAYNAME6 Sa
+ SABBREVDAYNAME7 So
+
+ SMONTHNAME1 Januar
+ SMONTHNAME2 Februar
+ SMONTHNAME3 März
+ SMONTHNAME4 April
+ SMONTHNAME5 Mai
+ SMONTHNAME6 Juni
+ SMONTHNAME7 Juli
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 Oktober
+ SMONTHNAME11 November
+ SMONTHNAME12 Dezember
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mär
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 Mai
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Okt
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dez
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0807 ; German - Switzerland
+
+ ILANGUAGE 0807
+ SENGLANGUAGE German
+ SABBREVLANGNAME DES
+ SNATIVELANGNAME Deutsch
+
+ ICOUNTRY 41
+ SENGCOUNTRY Switzerland
+ SABBREVCTRYNAME CHE
+ SNATIVECTRYNAME Schweiz
+
+ IDEFAULTLANGUAGE 0807
+ IDEFAULTCOUNTRY 41
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND '
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY SFr.
+ SINTLSYMBOL CHF
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP '
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 2
+ INEGCURR 2
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 5 HH:mm:ss
+ H:mm:ss
+ H.mm' h'
+ HH.mm' h'
+ H.mm' Uhr'
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 5 dd.MM.yyyy
+ dd.MM.yy
+ d.MM.yy
+ dd. M. yy
+ d.M.yy
+ SDATE .
+ IDATE 1
+ ICENTURY 1
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 3 dddd, d. MMMM yyyy
+ d. MMMM yyyy
+ d. MMM yy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorianischer Kalender
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Montag
+ SDAYNAME2 Dienstag
+ SDAYNAME3 Mittwoch
+ SDAYNAME4 Donnerstag
+ SDAYNAME5 Freitag
+ SDAYNAME6 Samstag
+ SDAYNAME7 Sonntag
+
+ SABBREVDAYNAME1 Mo
+ SABBREVDAYNAME2 Di
+ SABBREVDAYNAME3 Mi
+ SABBREVDAYNAME4 Do
+ SABBREVDAYNAME5 Fr
+ SABBREVDAYNAME6 Sa
+ SABBREVDAYNAME7 So
+
+ SMONTHNAME1 Januar
+ SMONTHNAME2 Februar
+ SMONTHNAME3 März
+ SMONTHNAME4 April
+ SMONTHNAME5 Mai
+ SMONTHNAME6 Juni
+ SMONTHNAME7 Juli
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 Oktober
+ SMONTHNAME11 November
+ SMONTHNAME12 Dezember
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mär
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 Mai
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Okt
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dez
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0c07 ; German - Austria
+
+ ILANGUAGE 0c07
+ SENGLANGUAGE German
+ SABBREVLANGNAME DEA
+ SNATIVELANGNAME Deutsch
+
+ ICOUNTRY 43
+ SENGCOUNTRY Austria
+ SABBREVCTRYNAME AUT
+ SNATIVECTRYNAME Österreich
+
+ IDEFAULTLANGUAGE 0c07
+ IDEFAULTCOUNTRY 43
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY S
+ SINTLSYMBOL ATS
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 2
+ INEGCURR 9
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 HH:mm:ss
+ H:mm:ss
+ HH:mm
+ HH:mm' Uhr'
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 dd.MM.yy
+ dd.M.yyyy
+ yyMMdd
+ SDATE .
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 4 dddd, dd. MMMM yyyy
+ d.MMMM yyyy
+ d.MMMyyyy
+ d MMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorianischer Kalender
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Montag
+ SDAYNAME2 Dienstag
+ SDAYNAME3 Mittwoch
+ SDAYNAME4 Donnerstag
+ SDAYNAME5 Freitag
+ SDAYNAME6 Samstag
+ SDAYNAME7 Sonntag
+
+ SABBREVDAYNAME1 Mo
+ SABBREVDAYNAME2 Di
+ SABBREVDAYNAME3 Mi
+ SABBREVDAYNAME4 Do
+ SABBREVDAYNAME5 Fr
+ SABBREVDAYNAME6 Sa
+ SABBREVDAYNAME7 So
+
+ SMONTHNAME1 Januar
+ SMONTHNAME2 Februar
+ SMONTHNAME3 März
+ SMONTHNAME4 April
+ SMONTHNAME5 Mai
+ SMONTHNAME6 Juni
+ SMONTHNAME7 Juli
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 Oktober
+ SMONTHNAME11 November
+ SMONTHNAME12 Dezember
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mär
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 Mai
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Okt
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dez
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0408 ; Greek - Greece
+
+ ILANGUAGE 0408
+ SENGLANGUAGE Greek
+ SABBREVLANGNAME ELL
+ SNATIVELANGNAME \x0395\x03bb\x03bb\x03b7\x03bd\x03b9\x03ba\x03ac
+
+ ICOUNTRY 30
+ SENGCOUNTRY Greece
+ SABBREVCTRYNAME GRC
+ SNATIVECTRYNAME \x0395\x03bb\x03bb\x03ac\x03b4\x03b1
+
+ IDEFAULTLANGUAGE 0408
+ IDEFAULTCOUNTRY 30
+ IDEFAULTANSICODEPAGE 1253
+ IDEFAULTOEMCODEPAGE 737
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 0
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY \x03b4\x03c1\x03c7
+ SINTLSYMBOL GRD
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 3
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 h:mm:ss tt
+ hh:mm:ss tt
+ H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 0
+ ITLZERO 0
+ S1159 \x03c0\x03bc
+ S2359 \x03bc\x03bc
+
+ SSHORTDATE 4 d/M/yyyy
+ dd/MM/yyyy
+ d/M/yy
+ dd/MM/yy
+ SDATE /
+ IDATE 1
+ ICENTURY 1
+ IDAYLZERO 0
+ IMONLZERO 0
+
+ SLONGDATE 2 dddd, d MMMM yyyy
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x0394\x03b5\x03c5\x03c4\x03ad\x03c1\x03b1
+ SDAYNAME2 \x03a4\x03c1\x03af\x03c4\x03b7
+ SDAYNAME3 \x03a4\x03b5\x03c4\x03ac\x03c1\x03c4\x03b7
+ SDAYNAME4 \x03a0\x03ad\x03bc\x03c0\x03c4\x03b7
+ SDAYNAME5 \x03a0\x03b1\x03c1\x03b1\x03c3\x03ba\x03b5\x03c5\x03ae
+ SDAYNAME6 \x03a3\x03ac\x03b2\x03b2\x03b1\x03c4\x03bf
+ SDAYNAME7 \x039a\x03c5\x03c1\x03b9\x03b1\x03ba\x03ae
+
+ SABBREVDAYNAME1 \x0394\x03b5\x03c5
+ SABBREVDAYNAME2 \x03a4\x03c1\x03b9
+ SABBREVDAYNAME3 \x03a4\x03b5\x03c4
+ SABBREVDAYNAME4 \x03a0\x03b5\x03bc
+ SABBREVDAYNAME5 \x03a0\x03b1\x03c1
+ SABBREVDAYNAME6 \x03a3\x03b1\x03b2
+ SABBREVDAYNAME7 \x039a\x03c5\x03c1
+
+ SMONTHNAME1 \x0399\x03b1\x03bd\x03bf\x03c5\x03b1\x03c1\x03af\x03bf\x03c5
+ SMONTHNAME2 \x03a6\x03b5\x03b2\x03c1\x03bf\x03c5\x03b1\x03c1\x03af\x03bf\x03c5
+ SMONTHNAME3 \x039c\x03b1\x03c1\x03c4\x03af\x03bf\x03c5
+ SMONTHNAME4 \x0391\x03c0\x03c1\x03b9\x03bb\x03af\x03bf\x03c5
+ SMONTHNAME5 \x039c\x03b1\x0390\x03bf\x03c5
+ SMONTHNAME6 \x0399\x03bf\x03c5\x03bd\x03af\x03bf\x03c5
+ SMONTHNAME7 \x0399\x03bf\x03c5\x03bb\x03af\x03bf\x03c5
+ SMONTHNAME8 \x0391\x03c5\x03b3\x03bf\x03cd\x03c3\x03c4\x03bf\x03c5
+ SMONTHNAME9 \x03a3\x03b5\x03c0\x03c4\x03b5\x03bc\x03b2\x03c1\x03af\x03bf\x03c5
+ SMONTHNAME10 \x039f\x03ba\x03c4\x03c9\x03b2\x03c1\x03af\x03bf\x03c5
+ SMONTHNAME11 \x039d\x03bf\x03b5\x03bc\x03b2\x03c1\x03af\x03bf\x03c5
+ SMONTHNAME12 \x0394\x03b5\x03ba\x03b5\x03bc\x03b2\x03c1\x03af\x03bf\x03c5
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 \x0399\x03b1\x03bd
+ SABBREVMONTHNAME2 \x03a6\x03b5\x03b2
+ SABBREVMONTHNAME3 \x039c\x03b1\x03c1
+ SABBREVMONTHNAME4 \x0391\x03c0\x03c1
+ SABBREVMONTHNAME5 \x039c\x03b1\x03ca
+ SABBREVMONTHNAME6 \x0399\x03bf\x03c5\x03bd
+ SABBREVMONTHNAME7 \x0399\x03bf\x03c5\x03bb
+ SABBREVMONTHNAME8 \x0391\x03c5\x03b3
+ SABBREVMONTHNAME9 \x03a3\x03b5\x03c0
+ SABBREVMONTHNAME10 \x039f\x03ba\x03c4
+ SABBREVMONTHNAME11 \x039d\x03bf\x03b5
+ SABBREVMONTHNAME12 \x0394\x03b5\x03ba
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0409 ; English - United States
+
+ ILANGUAGE 0409
+ SENGLANGUAGE English
+ SABBREVLANGNAME ENU
+ SNATIVELANGNAME English
+
+ ICOUNTRY 1
+ SENGCOUNTRY United States
+ SABBREVCTRYNAME USA
+ SNATIVECTRYNAME United States
+
+ IDEFAULTLANGUAGE 0409
+ IDEFAULTCOUNTRY 1
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 437
+
+ SLIST ,
+ IMEASURE 1
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY $
+ SINTLSYMBOL USD
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 h:mm:ss tt
+ hh:mm:ss tt
+ H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 0
+ ITLZERO 0
+ S1159 AM
+ S2359 PM
+
+ SSHORTDATE 6 M/d/yy
+ M/d/yyyy
+ MM/dd/yy
+ MM/dd/yyyy
+ yy/MM/dd
+ dd-MMM-yy
+ SDATE /
+ IDATE 0
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 0
+
+ SLONGDATE 4 dddd, MMMM dd, yyyy
+ MMMM dd, yyyy
+ dddd, dd MMMM, yyyy
+ dd MMMM, yyyy
+ ILDATE 0
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Monday
+ SDAYNAME2 Tuesday
+ SDAYNAME3 Wednesday
+ SDAYNAME4 Thursday
+ SDAYNAME5 Friday
+ SDAYNAME6 Saturday
+ SDAYNAME7 Sunday
+
+ SABBREVDAYNAME1 Mon
+ SABBREVDAYNAME2 Tue
+ SABBREVDAYNAME3 Wed
+ SABBREVDAYNAME4 Thu
+ SABBREVDAYNAME5 Fri
+ SABBREVDAYNAME6 Sat
+ SABBREVDAYNAME7 Sun
+
+ SMONTHNAME1 January
+ SMONTHNAME2 February
+ SMONTHNAME3 March
+ SMONTHNAME4 April
+ SMONTHNAME5 May
+ SMONTHNAME6 June
+ SMONTHNAME7 July
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 October
+ SMONTHNAME11 November
+ SMONTHNAME12 December
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mar
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 May
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Oct
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0809 ; English - United Kingdom
+
+ ILANGUAGE 0809
+ SENGLANGUAGE English
+ SABBREVLANGNAME ENG
+ SNATIVELANGNAME English
+
+ ICOUNTRY 44
+ SENGCOUNTRY United Kingdom
+ SABBREVCTRYNAME GBR
+ SNATIVECTRYNAME England
+
+ IDEFAULTLANGUAGE 0809
+ IDEFAULTCOUNTRY 44
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY £
+ SINTLSYMBOL GBP
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 HH:mm:ss
+ H:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd/MM/yy
+ d/M/yy
+ d.M.yy
+ ddMMyy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 dd MMMM yyyy
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Monday
+ SDAYNAME2 Tuesday
+ SDAYNAME3 Wednesday
+ SDAYNAME4 Thursday
+ SDAYNAME5 Friday
+ SDAYNAME6 Saturday
+ SDAYNAME7 Sunday
+
+ SABBREVDAYNAME1 Mon
+ SABBREVDAYNAME2 Tue
+ SABBREVDAYNAME3 Wed
+ SABBREVDAYNAME4 Thu
+ SABBREVDAYNAME5 Fri
+ SABBREVDAYNAME6 Sat
+ SABBREVDAYNAME7 Sun
+
+ SMONTHNAME1 January
+ SMONTHNAME2 February
+ SMONTHNAME3 March
+ SMONTHNAME4 April
+ SMONTHNAME5 May
+ SMONTHNAME6 June
+ SMONTHNAME7 July
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 October
+ SMONTHNAME11 November
+ SMONTHNAME12 December
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mar
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 May
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Oct
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0c09 ; English - Australia
+
+ ILANGUAGE 0c09
+ SENGLANGUAGE English
+ SABBREVLANGNAME ENA
+ SNATIVELANGNAME English
+
+ ICOUNTRY 61
+ SENGCOUNTRY Australia
+ SABBREVCTRYNAME AUS
+ SNATIVECTRYNAME Australia
+
+ IDEFAULTLANGUAGE 0c09
+ IDEFAULTCOUNTRY 61
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY $
+ SINTLSYMBOL AUD
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 d/MM/yy
+ d/M/yy
+ dd/MM/yy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 1
+
+ SLONGDATE 2 dddd, d MMMM yyyy
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Monday
+ SDAYNAME2 Tuesday
+ SDAYNAME3 Wednesday
+ SDAYNAME4 Thursday
+ SDAYNAME5 Friday
+ SDAYNAME6 Saturday
+ SDAYNAME7 Sunday
+
+ SABBREVDAYNAME1 Mon
+ SABBREVDAYNAME2 Tue
+ SABBREVDAYNAME3 Wed
+ SABBREVDAYNAME4 Thu
+ SABBREVDAYNAME5 Fri
+ SABBREVDAYNAME6 Sat
+ SABBREVDAYNAME7 Sun
+
+ SMONTHNAME1 January
+ SMONTHNAME2 February
+ SMONTHNAME3 March
+ SMONTHNAME4 April
+ SMONTHNAME5 May
+ SMONTHNAME6 June
+ SMONTHNAME7 July
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 October
+ SMONTHNAME11 November
+ SMONTHNAME12 December
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mar
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 May
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Oct
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 1009 ; English - Canada
+
+ ILANGUAGE 1009
+ SENGLANGUAGE English
+ SABBREVLANGNAME ENC
+ SNATIVELANGNAME English
+
+ ICOUNTRY 2
+ SENGCOUNTRY Canada
+ SABBREVCTRYNAME CAN
+ SNATIVECTRYNAME Canada
+
+ IDEFAULTLANGUAGE 1009
+ IDEFAULTCOUNTRY 2
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY $
+ SINTLSYMBOL CAD
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 HH:mm:ss
+ H:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd/MM/yy
+ d/M/yy
+ yy-MM-dd
+ m/dd/yy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 MMMM d, yyyy
+ d-MMM-yy
+ ILDATE 0
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Monday
+ SDAYNAME2 Tuesday
+ SDAYNAME3 Wednesday
+ SDAYNAME4 Thursday
+ SDAYNAME5 Friday
+ SDAYNAME6 Saturday
+ SDAYNAME7 Sunday
+
+ SABBREVDAYNAME1 Mon
+ SABBREVDAYNAME2 Tue
+ SABBREVDAYNAME3 Wed
+ SABBREVDAYNAME4 Thu
+ SABBREVDAYNAME5 Fri
+ SABBREVDAYNAME6 Sat
+ SABBREVDAYNAME7 Sun
+
+ SMONTHNAME1 January
+ SMONTHNAME2 February
+ SMONTHNAME3 March
+ SMONTHNAME4 April
+ SMONTHNAME5 May
+ SMONTHNAME6 June
+ SMONTHNAME7 July
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 October
+ SMONTHNAME11 November
+ SMONTHNAME12 December
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mar
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 May
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Oct
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 1409 ; English - New Zealand
+
+ ILANGUAGE 1409
+ SENGLANGUAGE English
+ SABBREVLANGNAME ENZ
+ SNATIVELANGNAME English
+
+ ICOUNTRY 64
+ SENGCOUNTRY New Zealand
+ SABBREVCTRYNAME NZL
+ SNATIVECTRYNAME New Zealand
+
+ IDEFAULTLANGUAGE 1409
+ IDEFAULTCOUNTRY 64
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY $
+ SINTLSYMBOL NZD
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 HH:mm:ss
+ H:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 d/MM/yy
+ dd/MM/yy
+ d.MM.yy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 1
+
+ SLONGDATE 2 dddd, d MMMM yyyy
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Monday
+ SDAYNAME2 Tuesday
+ SDAYNAME3 Wednesday
+ SDAYNAME4 Thursday
+ SDAYNAME5 Friday
+ SDAYNAME6 Saturday
+ SDAYNAME7 Sunday
+
+ SABBREVDAYNAME1 Mon
+ SABBREVDAYNAME2 Tue
+ SABBREVDAYNAME3 Wed
+ SABBREVDAYNAME4 Thu
+ SABBREVDAYNAME5 Fri
+ SABBREVDAYNAME6 Sat
+ SABBREVDAYNAME7 Sun
+
+ SMONTHNAME1 January
+ SMONTHNAME2 February
+ SMONTHNAME3 March
+ SMONTHNAME4 April
+ SMONTHNAME5 May
+ SMONTHNAME6 June
+ SMONTHNAME7 July
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 October
+ SMONTHNAME11 November
+ SMONTHNAME12 December
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mar
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 May
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Oct
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 1809 ; English - Ireland
+
+ ILANGUAGE 1809
+ SENGLANGUAGE English
+ SABBREVLANGNAME ENI
+ SNATIVELANGNAME English
+
+ ICOUNTRY 353
+ SENGCOUNTRY Ireland
+ SABBREVCTRYNAME IRL
+ SNATIVECTRYNAME Eire
+
+ IDEFAULTLANGUAGE 1809
+ IDEFAULTCOUNTRY 353
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY IR£
+ SINTLSYMBOL IRP
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 HH:mm:ss
+ H:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd/MM/yy
+ d/M/yy
+ d.M.yy
+ ddMMyy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 dd MMMM yyyy
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Monday
+ SDAYNAME2 Tuesday
+ SDAYNAME3 Wednesday
+ SDAYNAME4 Thursday
+ SDAYNAME5 Friday
+ SDAYNAME6 Saturday
+ SDAYNAME7 Sunday
+
+ SABBREVDAYNAME1 Mon
+ SABBREVDAYNAME2 Tue
+ SABBREVDAYNAME3 Wed
+ SABBREVDAYNAME4 Thu
+ SABBREVDAYNAME5 Fri
+ SABBREVDAYNAME6 Sat
+ SABBREVDAYNAME7 Sun
+
+ SMONTHNAME1 January
+ SMONTHNAME2 February
+ SMONTHNAME3 March
+ SMONTHNAME4 April
+ SMONTHNAME5 May
+ SMONTHNAME6 June
+ SMONTHNAME7 July
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 October
+ SMONTHNAME11 November
+ SMONTHNAME12 December
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mar
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 May
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Oct
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 040a ; Spanish - Spain (Traditional Sort)
+
+ ILANGUAGE 040a
+ SENGLANGUAGE Spanish - Traditional Sort
+ SABBREVLANGNAME ESP
+ SNATIVELANGNAME Español
+
+ ICOUNTRY 34
+ SENGCOUNTRY Spain
+ SABBREVCTRYNAME ESP
+ SNATIVECTRYNAME España
+
+ IDEFAULTLANGUAGE 040a
+ IDEFAULTCOUNTRY 34
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY Pts
+ SINTLSYMBOL ESP
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 0
+ IINTLCURRDIGITS 0
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 H:mm:ss
+ HH:mm:ss
+ HH:mm
+ HH'H'mm'''
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 d/MM/yy
+ d/M/yy
+ dd-MM-yy
+ dd.MM.yy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 1
+
+ SLONGDATE 2 dddd d' de 'MMMM' de 'yyyy
+ d' de 'MMMM' de 'yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 lunes
+ SDAYNAME2 martes
+ SDAYNAME3 miércoles
+ SDAYNAME4 jueves
+ SDAYNAME5 viernes
+ SDAYNAME6 sábado
+ SDAYNAME7 domingo
+
+ SABBREVDAYNAME1 lun
+ SABBREVDAYNAME2 mar
+ SABBREVDAYNAME3 mié
+ SABBREVDAYNAME4 jue
+ SABBREVDAYNAME5 vie
+ SABBREVDAYNAME6 sáb
+ SABBREVDAYNAME7 dom
+
+ SMONTHNAME1 enero
+ SMONTHNAME2 febrero
+ SMONTHNAME3 marzo
+ SMONTHNAME4 abril
+ SMONTHNAME5 mayo
+ SMONTHNAME6 junio
+ SMONTHNAME7 julio
+ SMONTHNAME8 agosto
+ SMONTHNAME9 septiembre
+ SMONTHNAME10 octubre
+ SMONTHNAME11 noviembre
+ SMONTHNAME12 diciembre
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 ene
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 abr
+ SABBREVMONTHNAME5 may
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 ago
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 oct
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dic
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 080a ; Spanish - Mexico
+
+ ILANGUAGE 080a
+ SENGLANGUAGE Spanish
+ SABBREVLANGNAME ESM
+ SNATIVELANGNAME Español
+
+ ICOUNTRY 52
+ SENGCOUNTRY Mexico
+ SABBREVCTRYNAME MEX
+ SNATIVECTRYNAME México
+
+ IDEFAULTLANGUAGE 080a
+ IDEFAULTCOUNTRY 52
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY N$
+ SINTLSYMBOL MXP
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 0
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 h:mm:ss tt
+ hh:mm:ss tt
+ H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 0
+ ITLZERO 0
+ S1159 AM
+ S2359 PM
+
+ SSHORTDATE 4 d/MM/yy
+ d/M/yy
+ dd/MM/yy
+ dd-MM-yy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 1
+
+ SLONGDATE 2 dddd d' de 'MMMM' de 'yyyy
+ d' de 'MMMM' de 'yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 lunes
+ SDAYNAME2 martes
+ SDAYNAME3 miércoles
+ SDAYNAME4 jueves
+ SDAYNAME5 viernes
+ SDAYNAME6 sábado
+ SDAYNAME7 domingo
+
+ SABBREVDAYNAME1 lun
+ SABBREVDAYNAME2 mar
+ SABBREVDAYNAME3 mié
+ SABBREVDAYNAME4 jue
+ SABBREVDAYNAME5 vie
+ SABBREVDAYNAME6 sáb
+ SABBREVDAYNAME7 dom
+
+ SMONTHNAME1 enero
+ SMONTHNAME2 febrero
+ SMONTHNAME3 marzo
+ SMONTHNAME4 abril
+ SMONTHNAME5 mayo
+ SMONTHNAME6 junio
+ SMONTHNAME7 julio
+ SMONTHNAME8 agosto
+ SMONTHNAME9 septiembre
+ SMONTHNAME10 octubre
+ SMONTHNAME11 noviembre
+ SMONTHNAME12 diciembre
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 ene
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 abr
+ SABBREVMONTHNAME5 may
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 ago
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 oct
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dic
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0c0a ; Spanish - Spain (Modern Sort)
+
+ ILANGUAGE 0c0a
+ SENGLANGUAGE Spanish - Modern Sort
+ SABBREVLANGNAME ESN
+ SNATIVELANGNAME Español
+
+ ICOUNTRY 34
+ SENGCOUNTRY Spain
+ SABBREVCTRYNAME ESP
+ SNATIVECTRYNAME España
+
+ IDEFAULTLANGUAGE 0c0a
+ IDEFAULTCOUNTRY 34
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY Pts
+ SINTLSYMBOL ESP
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 0
+ IINTLCURRDIGITS 0
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 H:mm:ss
+ HH:mm:ss
+ HH:mm
+ HH'H'mm'''
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 d/MM/yy
+ dd/MM/yy
+ dd-MM-yy
+ dd.MM.yy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 1
+
+ SLONGDATE 2 dddd d' de 'MMMM' de 'yyyy
+ d' de 'MMMM' de 'yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 lunes
+ SDAYNAME2 martes
+ SDAYNAME3 miércoles
+ SDAYNAME4 jueves
+ SDAYNAME5 viernes
+ SDAYNAME6 sábado
+ SDAYNAME7 domingo
+
+ SABBREVDAYNAME1 lun
+ SABBREVDAYNAME2 mar
+ SABBREVDAYNAME3 mié
+ SABBREVDAYNAME4 jue
+ SABBREVDAYNAME5 vie
+ SABBREVDAYNAME6 sáb
+ SABBREVDAYNAME7 dom
+
+ SMONTHNAME1 enero
+ SMONTHNAME2 febrero
+ SMONTHNAME3 marzo
+ SMONTHNAME4 abril
+ SMONTHNAME5 mayo
+ SMONTHNAME6 junio
+ SMONTHNAME7 julio
+ SMONTHNAME8 agosto
+ SMONTHNAME9 septiembre
+ SMONTHNAME10 octubre
+ SMONTHNAME11 noviembre
+ SMONTHNAME12 diciembre
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 ene
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 abr
+ SABBREVMONTHNAME5 may
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 ago
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 oct
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dic
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 040b ; Finnish - Finland
+
+ ILANGUAGE 040b
+ SENGLANGUAGE Finnish
+ SABBREVLANGNAME FIN
+ SNATIVELANGNAME suomi
+
+ ICOUNTRY 358
+ SENGCOUNTRY Finland
+ SABBREVCTRYNAME FIN
+ SNATIVECTRYNAME Suomi
+
+ IDEFAULTLANGUAGE 040b
+ IDEFAULTCOUNTRY 358
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY mk
+ SINTLSYMBOL FIM
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 3 H.mm.ss
+ HH.mm.ss
+ H.mm
+ STIME .
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 d.M.yyyy
+ dd.MM.yyyy
+ d.M.yy
+ yyyy-MM-dd
+ SDATE .
+ IDATE 1
+ ICENTURY 1
+ IDAYLZERO 0
+ IMONLZERO 0
+
+ SLONGDATE 2 d. MMMM'ta 'yyyy
+ dd. MMMM'ta 'yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 maanantai
+ SDAYNAME2 tiistai
+ SDAYNAME3 keskiviikko
+ SDAYNAME4 torstai
+ SDAYNAME5 perjantai
+ SDAYNAME6 lauantai
+ SDAYNAME7 sunnuntai
+
+ SABBREVDAYNAME1 ma
+ SABBREVDAYNAME2 ti
+ SABBREVDAYNAME3 ke
+ SABBREVDAYNAME4 to
+ SABBREVDAYNAME5 pe
+ SABBREVDAYNAME6 la
+ SABBREVDAYNAME7 su
+
+ SMONTHNAME1 tammikuu
+ SMONTHNAME2 helmikuu
+ SMONTHNAME3 maaliskuu
+ SMONTHNAME4 huhtikuu
+ SMONTHNAME5 toukokuu
+ SMONTHNAME6 kesäkuu
+ SMONTHNAME7 heinäkuu
+ SMONTHNAME8 elokuu
+ SMONTHNAME9 syyskuu
+ SMONTHNAME10 lokakuu
+ SMONTHNAME11 marraskuu
+ SMONTHNAME12 joulukuu
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 tammi
+ SABBREVMONTHNAME2 helmi
+ SABBREVMONTHNAME3 maalis
+ SABBREVMONTHNAME4 huhti
+ SABBREVMONTHNAME5 touko
+ SABBREVMONTHNAME6 kesä
+ SABBREVMONTHNAME7 heinä
+ SABBREVMONTHNAME8 elo
+ SABBREVMONTHNAME9 syys
+ SABBREVMONTHNAME10 loka
+ SABBREVMONTHNAME11 marras
+ SABBREVMONTHNAME12 joulu
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 040c ; French - France
+
+ ILANGUAGE 040c
+ SENGLANGUAGE French
+ SABBREVLANGNAME FRA
+ SNATIVELANGNAME français
+
+ ICOUNTRY 33
+ SENGCOUNTRY France
+ SABBREVCTRYNAME FRA
+ SNATIVECTRYNAME France
+
+ IDEFAULTLANGUAGE 040c
+ IDEFAULTCOUNTRY 33
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY F
+ SINTLSYMBOL FRF
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 HH:mm:ss
+ H:mm:ss
+ HH.mm
+ HH' h 'mm
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd/MM/yy
+ dd.MM.yy
+ dd-MM-yy
+ dd/MM/yyyy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 3 dddd d MMMM yyyy
+ d MMM yy
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 lundi
+ SDAYNAME2 mardi
+ SDAYNAME3 mercredi
+ SDAYNAME4 jeudi
+ SDAYNAME5 vendredi
+ SDAYNAME6 samedi
+ SDAYNAME7 dimanche
+
+ SABBREVDAYNAME1 lun.
+ SABBREVDAYNAME2 mar.
+ SABBREVDAYNAME3 mer.
+ SABBREVDAYNAME4 jeu.
+ SABBREVDAYNAME5 ven.
+ SABBREVDAYNAME6 sam.
+ SABBREVDAYNAME7 dim.
+
+ SMONTHNAME1 janvier
+ SMONTHNAME2 février
+ SMONTHNAME3 mars
+ SMONTHNAME4 avril
+ SMONTHNAME5 mai
+ SMONTHNAME6 juin
+ SMONTHNAME7 juillet
+ SMONTHNAME8 août
+ SMONTHNAME9 septembre
+ SMONTHNAME10 octobre
+ SMONTHNAME11 novembre
+ SMONTHNAME12 décembre
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 janv.
+ SABBREVMONTHNAME2 févr.
+ SABBREVMONTHNAME3 mars
+ SABBREVMONTHNAME4 avr.
+ SABBREVMONTHNAME5 mai
+ SABBREVMONTHNAME6 juin
+ SABBREVMONTHNAME7 juil.
+ SABBREVMONTHNAME8 août
+ SABBREVMONTHNAME9 sept.
+ SABBREVMONTHNAME10 oct.
+ SABBREVMONTHNAME11 nov.
+ SABBREVMONTHNAME12 déc.
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 080c ; French - Belgium
+
+ ILANGUAGE 080c
+ SENGLANGUAGE French
+ SABBREVLANGNAME FRB
+ SNATIVELANGNAME français
+
+ ICOUNTRY 32
+ SENGCOUNTRY Belgium
+ SABBREVCTRYNAME BEL
+ SNATIVECTRYNAME Belgique
+
+ IDEFAULTLANGUAGE 080c
+ IDEFAULTCOUNTRY 32
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY FB
+ SINTLSYMBOL BEF
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 5 H:mm:ss
+ HH:mm:ss
+ H.mm
+ H' h 'mm
+ H' h 'm' min 's' s '
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 d/MM/yy
+ dd.MM.yy
+ yy/mm/dd
+ dd-MM-yy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 1
+
+ SLONGDATE 4 dddd d MMMM yyyy
+ d MMMM yyyy
+ dd-MMM-yy
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 lundi
+ SDAYNAME2 mardi
+ SDAYNAME3 mercredi
+ SDAYNAME4 jeudi
+ SDAYNAME5 vendredi
+ SDAYNAME6 samedi
+ SDAYNAME7 dimanche
+
+ SABBREVDAYNAME1 lun.
+ SABBREVDAYNAME2 mar.
+ SABBREVDAYNAME3 mer.
+ SABBREVDAYNAME4 jeu.
+ SABBREVDAYNAME5 ven.
+ SABBREVDAYNAME6 sam.
+ SABBREVDAYNAME7 dim.
+
+ SMONTHNAME1 janvier
+ SMONTHNAME2 février
+ SMONTHNAME3 mars
+ SMONTHNAME4 avril
+ SMONTHNAME5 mai
+ SMONTHNAME6 juin
+ SMONTHNAME7 juillet
+ SMONTHNAME8 août
+ SMONTHNAME9 septembre
+ SMONTHNAME10 octobre
+ SMONTHNAME11 novembre
+ SMONTHNAME12 décembre
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 janv.
+ SABBREVMONTHNAME2 févr.
+ SABBREVMONTHNAME3 mars
+ SABBREVMONTHNAME4 avr.
+ SABBREVMONTHNAME5 mai
+ SABBREVMONTHNAME6 juin
+ SABBREVMONTHNAME7 juil.
+ SABBREVMONTHNAME8 août
+ SABBREVMONTHNAME9 sept.
+ SABBREVMONTHNAME10 oct.
+ SABBREVMONTHNAME11 nov.
+ SABBREVMONTHNAME12 déc.
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0c0c ; French - Canada
+
+ ILANGUAGE 0c0c
+ SENGLANGUAGE French
+ SABBREVLANGNAME FRC
+ SNATIVELANGNAME français
+
+ ICOUNTRY 2
+ SENGCOUNTRY Canada
+ SABBREVCTRYNAME CAN
+ SNATIVECTRYNAME Canada
+
+ IDEFAULTLANGUAGE 0c0c
+ IDEFAULTCOUNTRY 2
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY $
+ SINTLSYMBOL CAD
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 4
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 HH:mm:ss
+ H:mm:ss
+ H' h 'mm
+ H:mm
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 yy-MM-dd
+ dd-MM-yy
+ yy MM dd
+ dd/MM/yy
+ SDATE -
+ IDATE 2
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 d MMMM, yyyy
+ d MMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 lundi
+ SDAYNAME2 mardi
+ SDAYNAME3 mercredi
+ SDAYNAME4 jeudi
+ SDAYNAME5 vendredi
+ SDAYNAME6 samedi
+ SDAYNAME7 dimanche
+
+ SABBREVDAYNAME1 lun.
+ SABBREVDAYNAME2 mar.
+ SABBREVDAYNAME3 mer.
+ SABBREVDAYNAME4 jeu.
+ SABBREVDAYNAME5 ven.
+ SABBREVDAYNAME6 sam.
+ SABBREVDAYNAME7 dim.
+
+ SMONTHNAME1 janvier
+ SMONTHNAME2 février
+ SMONTHNAME3 mars
+ SMONTHNAME4 avril
+ SMONTHNAME5 mai
+ SMONTHNAME6 juin
+ SMONTHNAME7 juillet
+ SMONTHNAME8 août
+ SMONTHNAME9 septembre
+ SMONTHNAME10 octobre
+ SMONTHNAME11 novembre
+ SMONTHNAME12 décembre
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 janv.
+ SABBREVMONTHNAME2 févr.
+ SABBREVMONTHNAME3 mars
+ SABBREVMONTHNAME4 avr.
+ SABBREVMONTHNAME5 mai
+ SABBREVMONTHNAME6 juin
+ SABBREVMONTHNAME7 juil.
+ SABBREVMONTHNAME8 août
+ SABBREVMONTHNAME9 sept.
+ SABBREVMONTHNAME10 oct.
+ SABBREVMONTHNAME11 nov.
+ SABBREVMONTHNAME12 déc.
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 100c ; French - Switzerland
+
+ ILANGUAGE 100c
+ SENGLANGUAGE French
+ SABBREVLANGNAME FRS
+ SNATIVELANGNAME français
+
+ ICOUNTRY 41
+ SENGCOUNTRY Switzerland
+ SABBREVCTRYNAME CHE
+ SNATIVECTRYNAME Suisse
+
+ IDEFAULTLANGUAGE 100c
+ IDEFAULTCOUNTRY 41
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND '
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY SFr.
+ SINTLSYMBOL CHF
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP '
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 2
+ INEGCURR 2
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 3 HH:mm:ss
+ H:mm:ss
+ HH.mm' h'
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 dd.MM.yyyy
+ dd. M. yy
+ d.M.yy
+ SDATE .
+ IDATE 1
+ ICENTURY 1
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 3 dddd, d. MMMM yyyy
+ d. MMMM yyyy
+ d MMM yy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 lundi
+ SDAYNAME2 mardi
+ SDAYNAME3 mercredi
+ SDAYNAME4 jeudi
+ SDAYNAME5 vendredi
+ SDAYNAME6 samedi
+ SDAYNAME7 dimanche
+
+ SABBREVDAYNAME1 lun.
+ SABBREVDAYNAME2 mar.
+ SABBREVDAYNAME3 mer.
+ SABBREVDAYNAME4 jeu.
+ SABBREVDAYNAME5 ven.
+ SABBREVDAYNAME6 sam.
+ SABBREVDAYNAME7 dim.
+
+ SMONTHNAME1 janvier
+ SMONTHNAME2 fevrier
+ SMONTHNAME3 mars
+ SMONTHNAME4 avril
+ SMONTHNAME5 mai
+ SMONTHNAME6 juin
+ SMONTHNAME7 juillet
+ SMONTHNAME8 août
+ SMONTHNAME9 septembre
+ SMONTHNAME10 octobre
+ SMONTHNAME11 novembre
+ SMONTHNAME12 décembre
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 janv.
+ SABBREVMONTHNAME2 févr.
+ SABBREVMONTHNAME3 mars
+ SABBREVMONTHNAME4 avr.
+ SABBREVMONTHNAME5 mai
+ SABBREVMONTHNAME6 juin
+ SABBREVMONTHNAME7 juil.
+ SABBREVMONTHNAME8 août
+ SABBREVMONTHNAME9 sept.
+ SABBREVMONTHNAME10 oct.
+ SABBREVMONTHNAME11 nov.
+ SABBREVMONTHNAME12 déc.
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 040e ; Hungarian - Hungary
+
+ ILANGUAGE 040e
+ SENGLANGUAGE Hungarian
+ SABBREVLANGNAME HUN
+ SNATIVELANGNAME magyar
+
+ ICOUNTRY 36
+ SENGCOUNTRY Hungary
+ SABBREVCTRYNAME HUN
+ SNATIVECTRYNAME Magyarország
+
+ IDEFAULTLANGUAGE 040e
+ IDEFAULTCOUNTRY 36
+ IDEFAULTANSICODEPAGE 1250
+ IDEFAULTOEMCODEPAGE 852
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY Ft
+ SINTLSYMBOL HUF
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 3 H.mm.ss
+ HH.mm.ss
+ H:mm:ss
+ STIME .
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 yyyy.MM.dd.
+ yyyy-MM-dd
+ yy-MM-dd
+ SDATE .
+ IDATE 2
+ ICENTURY 1
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 yyyy. MMMM d.
+ yyyy. MMMM dd.
+ ILDATE 2
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 h\x00e9tf\x00f5
+ SDAYNAME2 kedd
+ SDAYNAME3 szerda
+ SDAYNAME4 csütörtök
+ SDAYNAME5 péntek
+ SDAYNAME6 szombat
+ SDAYNAME7 vasárnap
+
+ SABBREVDAYNAME1 H
+ SABBREVDAYNAME2 K
+ SABBREVDAYNAME3 Sze
+ SABBREVDAYNAME4 Cs
+ SABBREVDAYNAME5 P
+ SABBREVDAYNAME6 Szo
+ SABBREVDAYNAME7 V
+
+ SMONTHNAME1 január
+ SMONTHNAME2 február
+ SMONTHNAME3 március
+ SMONTHNAME4 április
+ SMONTHNAME5 május
+ SMONTHNAME6 június
+ SMONTHNAME7 július
+ SMONTHNAME8 augusztus
+ SMONTHNAME9 szeptember
+ SMONTHNAME10 október
+ SMONTHNAME11 november
+ SMONTHNAME12 december
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan.
+ SABBREVMONTHNAME2 febr.
+ SABBREVMONTHNAME3 márc.
+ SABBREVMONTHNAME4 ápr.
+ SABBREVMONTHNAME5 máj.
+ SABBREVMONTHNAME6 jún.
+ SABBREVMONTHNAME7 júl.
+ SABBREVMONTHNAME8 aug.
+ SABBREVMONTHNAME9 szept.
+ SABBREVMONTHNAME10 okt.
+ SABBREVMONTHNAME11 nov.
+ SABBREVMONTHNAME12 dec.
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 040f ; Icelandic - Iceland
+
+ ILANGUAGE 040f
+ SENGLANGUAGE Icelandic
+ SABBREVLANGNAME ISL
+ SNATIVELANGNAME Íslenska
+
+ ICOUNTRY 354
+ SENGCOUNTRY Iceland
+ SABBREVCTRYNAME ISL
+ SNATIVECTRYNAME Ísland
+
+ IDEFAULTLANGUAGE 040f
+ IDEFAULTCOUNTRY 354
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY kr
+ SINTLSYMBOL ISK
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 3 HH:mm:ss
+ H:mm:ss
+ HH:mm
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 5 yyyy-MM-dd
+ dd.MM.yy
+ d. M. yyyy.
+ d. M. 'yy.
+ yy MM dd
+ SDATE -
+ IDATE 2
+ ICENTURY 1
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 d. MMMM yyyy
+ dd. MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 mánudagur
+ SDAYNAME2 þriðjudagur
+ SDAYNAME3 miðvikudagur
+ SDAYNAME4 fimmtudagur
+ SDAYNAME5 föstudagur
+ SDAYNAME6 laugardagur
+ SDAYNAME7 sunnudagur
+
+ SABBREVDAYNAME1 mán.
+ SABBREVDAYNAME2 þri.
+ SABBREVDAYNAME3 mið.
+ SABBREVDAYNAME4 fim.
+ SABBREVDAYNAME5 fös.
+ SABBREVDAYNAME6 lau.
+ SABBREVDAYNAME7 sun.
+
+ SMONTHNAME1 janúar
+ SMONTHNAME2 febrúar
+ SMONTHNAME3 mars
+ SMONTHNAME4 apríl
+ SMONTHNAME5 maí
+ SMONTHNAME6 júní
+ SMONTHNAME7 júlí
+ SMONTHNAME8 ágúst
+ SMONTHNAME9 september
+ SMONTHNAME10 október
+ SMONTHNAME11 nóvember
+ SMONTHNAME12 desember
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan.
+ SABBREVMONTHNAME2 febr.
+ SABBREVMONTHNAME3 mars
+ SABBREVMONTHNAME4 apr.
+ SABBREVMONTHNAME5 maí
+ SABBREVMONTHNAME6 júní
+ SABBREVMONTHNAME7 júlí
+ SABBREVMONTHNAME8 ág.
+ SABBREVMONTHNAME9 sept.
+ SABBREVMONTHNAME10 okt.
+ SABBREVMONTHNAME11 nóv.
+ SABBREVMONTHNAME12 des.
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0410 ; Italian - Italy
+
+ ILANGUAGE 0410
+ SENGLANGUAGE Italian
+ SABBREVLANGNAME ITA
+ SNATIVELANGNAME Italiano
+
+ ICOUNTRY 39
+ SENGCOUNTRY Italy
+ SABBREVCTRYNAME ITA
+ SNATIVECTRYNAME Italia
+
+ IDEFAULTLANGUAGE 0410
+ IDEFAULTCOUNTRY 39
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY L.
+ SINTLSYMBOL ITL
+ SMONDECIMALSEP \x0000
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 0
+ IINTLCURRDIGITS 0
+ ICURRENCY 2
+ INEGCURR 9
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 H.mm.ss
+ HH.mm.ss
+ H.mm
+ H:mm
+ STIME .
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd/MM/yy
+ dd/MM/yyyy
+ dd.M.yy
+ d/M/yy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 3 dddd d MMMM yyyy
+ d-MMM-yy
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 lunedì
+ SDAYNAME2 martedì
+ SDAYNAME3 mercoledì
+ SDAYNAME4 giovedì
+ SDAYNAME5 venerdì
+ SDAYNAME6 sabato
+ SDAYNAME7 domenica
+
+ SABBREVDAYNAME1 lun
+ SABBREVDAYNAME2 mar
+ SABBREVDAYNAME3 mer
+ SABBREVDAYNAME4 gio
+ SABBREVDAYNAME5 ven
+ SABBREVDAYNAME6 sab
+ SABBREVDAYNAME7 dom
+
+ SMONTHNAME1 gennaio
+ SMONTHNAME2 febbraio
+ SMONTHNAME3 marzo
+ SMONTHNAME4 aprile
+ SMONTHNAME5 maggio
+ SMONTHNAME6 giugno
+ SMONTHNAME7 luglio
+ SMONTHNAME8 agosto
+ SMONTHNAME9 settembre
+ SMONTHNAME10 ottobre
+ SMONTHNAME11 novembre
+ SMONTHNAME12 dicembre
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 gen
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 apr
+ SABBREVMONTHNAME5 mag
+ SABBREVMONTHNAME6 giu
+ SABBREVMONTHNAME7 lug
+ SABBREVMONTHNAME8 ago
+ SABBREVMONTHNAME9 set
+ SABBREVMONTHNAME10 ott
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dic
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0810 ; Italian - Switzerland
+
+ ILANGUAGE 0810
+ SENGLANGUAGE Italian
+ SABBREVLANGNAME ITS
+ SNATIVELANGNAME Italiano
+
+ ICOUNTRY 41
+ SENGCOUNTRY Switzerland
+ SABBREVCTRYNAME CHE
+ SNATIVECTRYNAME Svizzera
+
+ IDEFAULTLANGUAGE 0810
+ IDEFAULTCOUNTRY 41
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND '
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY SFr.
+ SINTLSYMBOL CHF
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP '
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 2
+ INEGCURR 2
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 3 HH:mm:ss
+ H:mm:ss
+ H.mm' h'
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd.MM.yyyy
+ dd. MM. yy
+ d/M/yy
+ dd.M.yy
+ SDATE .
+ IDATE 1
+ ICENTURY 1
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 3 dddd, d. MMMM yyyy
+ d-MMM-yy
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 lunedì
+ SDAYNAME2 martedì
+ SDAYNAME3 mercoledì
+ SDAYNAME4 giovedì
+ SDAYNAME5 venerdì
+ SDAYNAME6 sabato
+ SDAYNAME7 domenica
+
+ SABBREVDAYNAME1 lun
+ SABBREVDAYNAME2 mar
+ SABBREVDAYNAME3 mer
+ SABBREVDAYNAME4 gio
+ SABBREVDAYNAME5 ven
+ SABBREVDAYNAME6 sab
+ SABBREVDAYNAME7 dom
+
+ SMONTHNAME1 gennaio
+ SMONTHNAME2 febbraio
+ SMONTHNAME3 marzo
+ SMONTHNAME4 aprile
+ SMONTHNAME5 maggio
+ SMONTHNAME6 giugno
+ SMONTHNAME7 luglio
+ SMONTHNAME8 agosto
+ SMONTHNAME9 settembre
+ SMONTHNAME10 ottobre
+ SMONTHNAME11 novembre
+ SMONTHNAME12 dicembre
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 gen
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 apr
+ SABBREVMONTHNAME5 mag
+ SABBREVMONTHNAME6 gio
+ SABBREVMONTHNAME7 lug
+ SABBREVMONTHNAME8 ago
+ SABBREVMONTHNAME9 set
+ SABBREVMONTHNAME10 ott
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dic
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0411 ; Japanese - Japan
+
+ ILANGUAGE 0411
+ SENGLANGUAGE Japanese
+ SABBREVLANGNAME JPN
+ SNATIVELANGNAME \x65e5\x672c\x8a9e
+
+ ICOUNTRY 81
+ SENGCOUNTRY Japan
+ SABBREVCTRYNAME JPN
+ SNATIVECTRYNAME \x65e5\x672c
+
+ IDEFAULTLANGUAGE 0411
+ IDEFAULTCOUNTRY 81
+ IDEFAULTANSICODEPAGE 932
+ IDEFAULTOEMCODEPAGE 932
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY \xffe5
+ SINTLSYMBOL YEN
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 0
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 tt h:mm:ss
+ tt hh:mm:ss
+ H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 0
+ ITLZERO 0
+ S1159 \x5348\x524d
+ S2359 \x5348\x5f8c
+
+ SSHORTDATE 4 yy/MM/dd
+ yy/M/d
+ yyyy/MM/dd
+ yyyy/M/d
+ SDATE /
+ IDATE 2
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 yyyy'\x5e74'M'\x6708'd'\x65e5'
+ yyyy'\x5e74'MM'\x6708'dd'\x65e5'
+ ILDATE 2
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 3 3\xffffEra: Year of the Emperor
+ 2\xffffGregorian (U.S. English)
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 6
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x6708\x66dc\x65e5
+ SDAYNAME2 \x706b\x66dc\x65e5
+ SDAYNAME3 \x6c34\x66dc\x65e5
+ SDAYNAME4 \x6728\x66dc\x65e5
+ SDAYNAME5 \x91d1\x66dc\x65e5
+ SDAYNAME6 \x571f\x66dc\x65e5
+ SDAYNAME7 \x65e5\x66dc\x65e5
+
+ SABBREVDAYNAME1 \x6708
+ SABBREVDAYNAME2 \x706b
+ SABBREVDAYNAME3 \x6c34
+ SABBREVDAYNAME4 \x6728
+ SABBREVDAYNAME5 \x91d1
+ SABBREVDAYNAME6 \x571f
+ SABBREVDAYNAME7 \x65e5
+
+ SMONTHNAME1 \xff11\x6708
+ SMONTHNAME2 \xff12\x6708
+ SMONTHNAME3 \xff13\x6708
+ SMONTHNAME4 \xff14\x6708
+ SMONTHNAME5 \xff15\x6708
+ SMONTHNAME6 \xff16\x6708
+ SMONTHNAME7 \xff17\x6708
+ SMONTHNAME8 \xff18\x6708
+ SMONTHNAME9 \xff19\x6708
+ SMONTHNAME10 \xff11\xff10\x6708
+ SMONTHNAME11 \xff11\xff11\x6708
+ SMONTHNAME12 \xff11\xff12\x6708
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 1
+ SABBREVMONTHNAME2 2
+ SABBREVMONTHNAME3 3
+ SABBREVMONTHNAME4 4
+ SABBREVMONTHNAME5 5
+ SABBREVMONTHNAME6 6
+ SABBREVMONTHNAME7 7
+ SABBREVMONTHNAME8 8
+ SABBREVMONTHNAME9 9
+ SABBREVMONTHNAME10 10
+ SABBREVMONTHNAME11 11
+ SABBREVMONTHNAME12 12
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0412 ; Korean - Korea
+
+ ILANGUAGE 0412
+ SENGLANGUAGE Korean
+ SABBREVLANGNAME KOR
+ SNATIVELANGNAME \x3ca2\x3476\x3971
+ ICOUNTRY 82
+ SENGCOUNTRY Korea
+ SABBREVCTRYNAME KOR
+ SNATIVECTRYNAME \x35c2\x3ca2\x377b\x3476
+
+ IDEFAULTLANGUAGE 0412
+ IDEFAULTCOUNTRY 82
+ IDEFAULTANSICODEPAGE 949
+ IDEFAULTOEMCODEPAGE 949
+
+ SLIST ,
+ IMEASURE 0
+
+ SDECIMAL .
+ STHOUSAND ,
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 0
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY \x20a9
+ SINTLSYMBOL KRW
+ SMONDECIMALSEP .
+ SMONTHOUSANDSEP ,
+ SMONGROUPING 3;0
+ ICURRDIGITS 0
+ IINTLCURRDIGITS 2
+ ICURRENCY 0
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 HH:mm:ss
+ H:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x39a1\x3a3b
+ S2359 \x39a1\x3cf3
+
+ SSHORTDATE 4 yy-MM-dd
+ yy-M-d
+ yyyy-M-d
+ yyyy-MM-dd
+ SDATE -
+ IDATE 2
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 yyyy'\x355b' M'\x39da' d'\x3a0e'
+ yyyy'\x355b' MM'\x39da' dd'\x3a0e'
+ ILDATE 2
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 5\xffffTangun Era
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 6
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x39da\x39c5\x3a0e
+ SDAYNAME2 \x3cdc\x39c5\x3a0e
+ SDAYNAME3 \x38bd\x39c5\x3a0e
+ SDAYNAME4 \x3740\x39c5\x3a0e
+ SDAYNAME5 \x349a\x39c5\x3a0e
+ SDAYNAME6 \x3bf9\x39c5\x3a0e
+ SDAYNAME7 \x3a0e\x39c5\x3a0e
+
+ SABBREVDAYNAME1 \x39da
+ SABBREVDAYNAME2 \x3cdc
+ SABBREVDAYNAME3 \x38bd
+ SABBREVDAYNAME4 \x3740
+ SABBREVDAYNAME5 \x349a
+ SABBREVDAYNAME6 \x3bf9
+ SABBREVDAYNAME7 \x3a0e
+
+ SMONTHNAME1 \x0031\x39da
+ SMONTHNAME2 \x0032\x39da
+ SMONTHNAME3 \x0033\x39da
+ SMONTHNAME4 \x0034\x39da
+ SMONTHNAME5 \x0035\x39da
+ SMONTHNAME6 \x0036\x39da
+ SMONTHNAME7 \x0037\x39da
+ SMONTHNAME8 \x0038\x39da
+ SMONTHNAME9 \x0039\x39da
+ SMONTHNAME10 \x0031\x0030\x39da
+ SMONTHNAME11 \x0031\x0031\x39da
+ SMONTHNAME12 \x0031\x0032\x39da
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 \x0031\x39da
+ SABBREVMONTHNAME2 \x0032\x39da
+ SABBREVMONTHNAME3 \x0033\x39da
+ SABBREVMONTHNAME4 \x0034\x39da
+ SABBREVMONTHNAME5 \x0035\x39da
+ SABBREVMONTHNAME6 \x0036\x39da
+ SABBREVMONTHNAME7 \x0037\x39da
+ SABBREVMONTHNAME8 \x0038\x39da
+ SABBREVMONTHNAME9 \x0039\x39da
+ SABBREVMONTHNAME10 \x0031\x0030\x39da
+ SABBREVMONTHNAME11 \x0031\x0031\x39da
+ SABBREVMONTHNAME12 \x0031\x0032\x39da
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0413 ; Dutch - Netherlands
+
+ ILANGUAGE 0413
+ SENGLANGUAGE Dutch
+ SABBREVLANGNAME NLD
+ SNATIVELANGNAME Nederlands
+
+ ICOUNTRY 31
+ SENGCOUNTRY Netherlands
+ SABBREVCTRYNAME NLD
+ SNATIVECTRYNAME Nederland
+
+ IDEFAULTLANGUAGE 0413
+ IDEFAULTCOUNTRY 31
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY F
+ SINTLSYMBOL NLG
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 2
+ INEGCURR 11
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 6 H:mm:ss
+ HH:mm:ss
+ H:mm
+ H.mm
+ HH.mm.ss' uur'
+ HH:mm:ss' uur'
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 d-MM-yy
+ dd-MM-yy
+ dd/MM/yy
+ dd.MM.yy
+ SDATE -
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 1
+
+ SLONGDATE 4 dddd d MMMM yyyy
+ d-MMM-yy
+ d MMMM yyyy
+ d MMM yy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 maandag
+ SDAYNAME2 dinsdag
+ SDAYNAME3 woensdag
+ SDAYNAME4 donderdag
+ SDAYNAME5 vrijdag
+ SDAYNAME6 zaterdag
+ SDAYNAME7 zondag
+
+ SABBREVDAYNAME1 ma
+ SABBREVDAYNAME2 di
+ SABBREVDAYNAME3 wo
+ SABBREVDAYNAME4 do
+ SABBREVDAYNAME5 vr
+ SABBREVDAYNAME6 za
+ SABBREVDAYNAME7 zo
+
+ SMONTHNAME1 januari
+ SMONTHNAME2 februari
+ SMONTHNAME3 maart
+ SMONTHNAME4 april
+ SMONTHNAME5 mei
+ SMONTHNAME6 juni
+ SMONTHNAME7 juli
+ SMONTHNAME8 augustus
+ SMONTHNAME9 september
+ SMONTHNAME10 oktober
+ SMONTHNAME11 november
+ SMONTHNAME12 december
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mrt
+ SABBREVMONTHNAME4 apr
+ SABBREVMONTHNAME5 mei
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 aug
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 okt
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0813 ; Dutch - Belgium
+
+ ILANGUAGE 0813
+ SENGLANGUAGE Dutch
+ SABBREVLANGNAME NLB
+ SNATIVELANGNAME Nederlands
+
+ ICOUNTRY 32
+ SENGCOUNTRY Belgium
+ SABBREVCTRYNAME BEL
+ SNATIVECTRYNAME België
+
+ IDEFAULTLANGUAGE 0813
+ IDEFAULTCOUNTRY 32
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY BF
+ SINTLSYMBOL BEF
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 H:mm:ss
+ HH:mm:ss
+ H.mm' u.'
+ H:mm
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 d/MM/yy
+ dd-mm-yy
+ dd.MM.yy
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 0
+ IMONLZERO 1
+
+ SLONGDATE 4 dddd d MMMM yyyy
+ dd-MMM-yy
+ d MMMM yyyy
+ dd MMM yy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 maandag
+ SDAYNAME2 dinsdag
+ SDAYNAME3 woensdag
+ SDAYNAME4 donderdag
+ SDAYNAME5 vrijdag
+ SDAYNAME6 zaterdag
+ SDAYNAME7 zondag
+
+ SABBREVDAYNAME1 ma
+ SABBREVDAYNAME2 di
+ SABBREVDAYNAME3 wo
+ SABBREVDAYNAME4 do
+ SABBREVDAYNAME5 vr
+ SABBREVDAYNAME6 za
+ SABBREVDAYNAME7 zo
+
+ SMONTHNAME1 januari
+ SMONTHNAME2 februari
+ SMONTHNAME3 maart
+ SMONTHNAME4 april
+ SMONTHNAME5 mei
+ SMONTHNAME6 juni
+ SMONTHNAME7 juli
+ SMONTHNAME8 augustus
+ SMONTHNAME9 september
+ SMONTHNAME10 oktober
+ SMONTHNAME11 november
+ SMONTHNAME12 december
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mrt
+ SABBREVMONTHNAME4 apr
+ SABBREVMONTHNAME5 mei
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 aug
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 okt
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0414 ; Norwegian - Norway (Bokmal)
+
+ ILANGUAGE 0414
+ SENGLANGUAGE Norwegian (Bokmal)
+ SABBREVLANGNAME NOR
+ SNATIVELANGNAME Norsk
+
+ ICOUNTRY 47
+ SENGCOUNTRY Norway
+ SABBREVCTRYNAME NOR
+ SNATIVECTRYNAME Norge
+
+ IDEFAULTLANGUAGE 0414
+ IDEFAULTCOUNTRY 47
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY kr
+ SINTLSYMBOL NOK
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 2
+ INEGCURR 2
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 HH:mm:ss
+ H:mm:ss
+ 'kl 'HH.mm
+ HH.mm.ss
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 5 dd.MM.yy
+ yyyy-MM-dd
+ d.M.yy
+ ddMMyy
+ dd.MM.yy
+ SDATE .
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 d. MMMM yyyy
+ dd. MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 mandag
+ SDAYNAME2 tirsdag
+ SDAYNAME3 onsdag
+ SDAYNAME4 torsdag
+ SDAYNAME5 fredag
+ SDAYNAME6 lørdag
+ SDAYNAME7 søndag
+
+ SABBREVDAYNAME1 ma
+ SABBREVDAYNAME2 ti
+ SABBREVDAYNAME3 on
+ SABBREVDAYNAME4 to
+ SABBREVDAYNAME5 fr
+ SABBREVDAYNAME6 lø
+ SABBREVDAYNAME7 sø
+
+ SMONTHNAME1 januar
+ SMONTHNAME2 februar
+ SMONTHNAME3 mars
+ SMONTHNAME4 april
+ SMONTHNAME5 mai
+ SMONTHNAME6 juni
+ SMONTHNAME7 juli
+ SMONTHNAME8 august
+ SMONTHNAME9 september
+ SMONTHNAME10 oktober
+ SMONTHNAME11 november
+ SMONTHNAME12 desember
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 apr
+ SABBREVMONTHNAME5 mai
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 aug
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 okt
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 des
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0814 ; Norwegian - Norway (Nynorsk)
+
+ ILANGUAGE 0814
+ SENGLANGUAGE Norwegian (Nynorsk)
+ SABBREVLANGNAME NON
+ SNATIVELANGNAME Norsk
+
+ ICOUNTRY 47
+ SENGCOUNTRY Norway
+ SABBREVCTRYNAME NOR
+ SNATIVECTRYNAME Norge
+
+ IDEFAULTLANGUAGE 0814
+ IDEFAULTCOUNTRY 47
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY kr
+ SINTLSYMBOL NOK
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 2
+ INEGCURR 2
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 4 HH:mm:ss
+ H:mm:ss
+ 'kl 'HH.mm
+ HH.mm.ss
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 5 dd.MM.yy
+ yyyy-MM-dd
+ d.M.yy
+ ddMMyy
+ dd.MM.yy
+ SDATE .
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 d. MMMM yyyy
+ dd. MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 mandag
+ SDAYNAME2 tirsdag
+ SDAYNAME3 onsdag
+ SDAYNAME4 torsdag
+ SDAYNAME5 fredag
+ SDAYNAME6 lørdag
+ SDAYNAME7 søndag
+
+ SABBREVDAYNAME1 ma
+ SABBREVDAYNAME2 ti
+ SABBREVDAYNAME3 on
+ SABBREVDAYNAME4 to
+ SABBREVDAYNAME5 fr
+ SABBREVDAYNAME6 lø
+ SABBREVDAYNAME7 sø
+
+ SMONTHNAME1 januar
+ SMONTHNAME2 februar
+ SMONTHNAME3 mars
+ SMONTHNAME4 april
+ SMONTHNAME5 mai
+ SMONTHNAME6 juni
+ SMONTHNAME7 juli
+ SMONTHNAME8 august
+ SMONTHNAME9 september
+ SMONTHNAME10 oktober
+ SMONTHNAME11 november
+ SMONTHNAME12 desember
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 apr
+ SABBREVMONTHNAME5 mai
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 aug
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 okt
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 des
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0415 ; Polish - Poland
+
+ ILANGUAGE 0415
+ SENGLANGUAGE Polish
+ SABBREVLANGNAME PLK
+ SNATIVELANGNAME Polski
+
+ ICOUNTRY 48
+ SENGCOUNTRY Poland
+ SABBREVCTRYNAME POL
+ SNATIVECTRYNAME Polska
+
+ IDEFAULTLANGUAGE 0415
+ IDEFAULTCOUNTRY 48
+ IDEFAULTANSICODEPAGE 1250
+ IDEFAULTOEMCODEPAGE 852
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY z\x0142
+ SINTLSYMBOL PLZ
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 HH:mm:ss
+ H:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 yy.MM.dd
+ yyyy-MM-dd
+ yy-MM-dd
+ SDATE .
+ IDATE 2
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 d MMMM yyyy
+ dd MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Poniedzia\x0142ek
+ SDAYNAME2 Wtorek
+ SDAYNAME3 \x015aroda
+ SDAYNAME4 Czwartek
+ SDAYNAME5 Pi\x0105tek
+ SDAYNAME6 Sobota
+ SDAYNAME7 Niedziela
+
+ SABBREVDAYNAME1 pn.
+ SABBREVDAYNAME2 wt.
+ SABBREVDAYNAME3 \x015br.
+ SABBREVDAYNAME4 czw.
+ SABBREVDAYNAME5 pt.
+ SABBREVDAYNAME6 sob.
+ SABBREVDAYNAME7 ndz.
+
+ SMONTHNAME1 Styze\x0144
+ SMONTHNAME2 Luty
+ SMONTHNAME3 Marzec
+ SMONTHNAME4 Kwiecie\x0144
+ SMONTHNAME5 Maj
+ SMONTHNAME6 Czerwiec
+ SMONTHNAME7 Lipiec
+ SMONTHNAME8 Sierpie\x0144
+ SMONTHNAME9 Wrzesie\x0144
+ SMONTHNAME10 Pa\x017adziernik
+ SMONTHNAME11 Listopad
+ SMONTHNAME12 Grudzie\x0144
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Sty
+ SABBREVMONTHNAME2 Lut
+ SABBREVMONTHNAME3 Mar
+ SABBREVMONTHNAME4 Kwi
+ SABBREVMONTHNAME5 Maj
+ SABBREVMONTHNAME6 Cze
+ SABBREVMONTHNAME7 Lip
+ SABBREVMONTHNAME8 Sie
+ SABBREVMONTHNAME9 Wrz
+ SABBREVMONTHNAME10 Pa\x017a
+ SABBREVMONTHNAME11 Lis
+ SABBREVMONTHNAME12 Gru
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0416 ; Portuguese - Brazil
+
+ ILANGUAGE 0416
+ SENGLANGUAGE Portuguese
+ SABBREVLANGNAME PTB
+ SNATIVELANGNAME Português
+
+ ICOUNTRY 55
+ SENGCOUNTRY Brazil
+ SABBREVCTRYNAME BRA
+ SNATIVECTRYNAME Brasil
+
+ IDEFAULTLANGUAGE 0416
+ IDEFAULTCOUNTRY 55
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY Cr$
+ SINTLSYMBOL BRC
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 2
+ INEGCURR 0
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 dd/MM/yy
+ dd/MM/yyyy
+ yyyy.MM.dd
+ SDATE /
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 dddd, d' de 'MMMM' de 'yyyy
+ d' de 'MMMM' de 'yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 segunda-feira
+ SDAYNAME2 terça-feira
+ SDAYNAME3 quarta-feira
+ SDAYNAME4 quinta-feira
+ SDAYNAME5 sexta-feira
+ SDAYNAME6 sábado
+ SDAYNAME7 domingo
+
+ SABBREVDAYNAME1 seg
+ SABBREVDAYNAME2 ter
+ SABBREVDAYNAME3 qua
+ SABBREVDAYNAME4 qui
+ SABBREVDAYNAME5 sex
+ SABBREVDAYNAME6 sáb
+ SABBREVDAYNAME7 dom
+
+ SMONTHNAME1 janeiro
+ SMONTHNAME2 fevereiro
+ SMONTHNAME3 março
+ SMONTHNAME4 abril
+ SMONTHNAME5 maio
+ SMONTHNAME6 junho
+ SMONTHNAME7 julho
+ SMONTHNAME8 agosto
+ SMONTHNAME9 setembro
+ SMONTHNAME10 outubro
+ SMONTHNAME11 novembro
+ SMONTHNAME12 dezembro
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan
+ SABBREVMONTHNAME2 fev
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 abr
+ SABBREVMONTHNAME5 mai
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 ago
+ SABBREVMONTHNAME9 set
+ SABBREVMONTHNAME10 out
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dez
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0816 ; Portuguese - Portugal
+
+ ILANGUAGE 0816
+ SENGLANGUAGE Portuguese
+ SABBREVLANGNAME PTG
+ SNATIVELANGNAME Português
+
+ ICOUNTRY 351
+ SENGCOUNTRY Portugal
+ SABBREVCTRYNAME PRT
+ SNATIVECTRYNAME Portugal
+
+ IDEFAULTLANGUAGE 0816
+ IDEFAULTCOUNTRY 351
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY Esc.
+ SINTLSYMBOL PTE
+ SMONDECIMALSEP $
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 3 H:mm:ss
+ HH:mm:ss
+ HH'H'mm'm'
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 5 dd-MM-yyyy
+ yy.MM.dd
+ d.M.yy
+ dd/MM/yy
+ yyyy-MM-dd
+ SDATE -
+ IDATE 1
+ ICENTURY 1
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 4 dddd, d' de 'MMMM' de 'yyyy
+ d' de 'MMMM' de 'yyyy
+ d/MMM/yy
+ d.MMM.yy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 segunda-feira
+ SDAYNAME2 terça-feira
+ SDAYNAME3 quarta-feira
+ SDAYNAME4 quinta-feira
+ SDAYNAME5 sexta-feira
+ SDAYNAME6 sábado
+ SDAYNAME7 domingo
+
+ SABBREVDAYNAME1 seg
+ SABBREVDAYNAME2 ter
+ SABBREVDAYNAME3 qua
+ SABBREVDAYNAME4 qui
+ SABBREVDAYNAME5 sex
+ SABBREVDAYNAME6 sáb
+ SABBREVDAYNAME7 dom
+
+ SMONTHNAME1 janeiro
+ SMONTHNAME2 fevereiro
+ SMONTHNAME3 março
+ SMONTHNAME4 abril
+ SMONTHNAME5 maio
+ SMONTHNAME6 junho
+ SMONTHNAME7 julho
+ SMONTHNAME8 agosto
+ SMONTHNAME9 setembro
+ SMONTHNAME10 outubro
+ SMONTHNAME11 novembro
+ SMONTHNAME12 dezembro
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan
+ SABBREVMONTHNAME2 fev
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 abr
+ SABBREVMONTHNAME5 mai
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 ago
+ SABBREVMONTHNAME9 set
+ SABBREVMONTHNAME10 out
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dez
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 0419 ; Russian - Russia
+
+ ILANGUAGE 0419
+ SENGLANGUAGE Russian
+ SABBREVLANGNAME RUS
+ SNATIVELANGNAME \x0420\x0443\x0441\x0441\x043a\x0438\x0439
+
+ ICOUNTRY 7
+ SENGCOUNTRY Russia
+ SABBREVCTRYNAME RUS
+ SNATIVECTRYNAME \x0420\x043e\x0441\x0441\x0438\x044f
+
+ IDEFAULTLANGUAGE 0419
+ IDEFAULTCOUNTRY 7
+ IDEFAULTANSICODEPAGE 1251
+ IDEFAULTOEMCODEPAGE 866
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY \x0440.
+ SINTLSYMBOL SUR
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 5
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 dd.MM.yy
+ d.M.yy
+ dd/MM/yy
+ SDATE .
+ IDATE 1
+ ICENTURY 0
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 d MMMM yyyy
+ dd MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 \x041f\x043e\x043d\x0435\x0434\x0435\x043b\x044c\x043d\x0438\x043a
+ SDAYNAME2 \x0412\x0442\x043e\x0440\x043d\x0438\x043a
+ SDAYNAME3 \x0421\x0440\x0435\x0434\x0430
+ SDAYNAME4 \x0427\x0435\x0442\x0432\x0435\x0440\x0433
+ SDAYNAME5 \x041f\x044f\x0442\x043d\x0438\x0446\x0430
+ SDAYNAME6 \x0421\x0443\x0431\x0431\x043e\x0442\x0430
+ SDAYNAME7 \x0412\x043e\x0441\x043a\x0440\x0435\x0441\x0435\x043d\x044c\x0435
+
+ SABBREVDAYNAME1 \x041f\x043e\x043d
+ SABBREVDAYNAME2 \x0412\x0442\x043e
+ SABBREVDAYNAME3 \x0421\x0440\x0435
+ SABBREVDAYNAME4 \x0427\x0435\x0442
+ SABBREVDAYNAME5 \x041f\x044f\x0442
+ SABBREVDAYNAME6 \x0421\x0443\x0431
+ SABBREVDAYNAME7 \x0412\x043e\x0441
+
+ SMONTHNAME1 \x042f\x043d\x0432\x0430\x0440\x044c\xffff\x044f\x043d\x0432\x0430\x0440\x044f
+ SMONTHNAME2 \x0424\x0435\x0432\x0440\x0430\x043b\x044c\xffff\x0444\x0435\x0432\x0440\x0430\x043b\x044f
+ SMONTHNAME3 \x041c\x0430\x0440\x0442\xffff\x043c\x0430\x0440\x0442\x0430
+ SMONTHNAME4 \x0410\x043f\x0440\x0435\x043b\x044c\xffff\x0430\x043f\x0440\x0435\x043b\x044f
+ SMONTHNAME5 \x041c\x0430\x0439\xffff\x043c\x0430\x044f
+ SMONTHNAME6 \x0418\x044e\x043d\x044c\xffff\x0438\x044e\x043d\x044f
+ SMONTHNAME7 \x0418\x044e\x043b\x044c\xffff\x0438\x044e\x043b\x044f
+ SMONTHNAME8 \x0410\x0432\x0433\x0443\x0441\x0442\xffff\x0430\x0432\x0433\x0443\x0441\x0442\x0430
+ SMONTHNAME9 \x0421\x0435\x043d\x0442\x044f\x0431\x0440\x044c\xffff\x0441\x0435\x043d\x0442\x044f\x0431\x0440\x044f
+ SMONTHNAME10 \x041e\x043a\x0442\x044f\x0431\x0440\x044c\xffff\x043e\x043a\x0442\x044f\x0431\x0440\x044f
+ SMONTHNAME11 \x041d\x043e\x044f\x0431\x0440\x044c\xffff\x043d\x043e\x044f\x0431\x0440\x044f
+ SMONTHNAME12 \x0414\x0435\x043a\x0430\x0431\x0440\x044c\xffff\x0434\x0435\x043a\x0430\x0431\x0440\x044f
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 \x042f\x043d\x0432
+ SABBREVMONTHNAME2 \x0424\x0435\x0432
+ SABBREVMONTHNAME3 \x041c\x0430\x0440
+ SABBREVMONTHNAME4 \x0410\x043f\x0440
+ SABBREVMONTHNAME5 \x041c\x0430\x0439\xffff\x043c\x0430\x044f
+ SABBREVMONTHNAME6 \x0418\x044e\x043d
+ SABBREVMONTHNAME7 \x0418\x044e\x043b
+ SABBREVMONTHNAME8 \x0410\x0432\x0433
+ SABBREVMONTHNAME9 \x0421\x0435\x043d
+ SABBREVMONTHNAME10 \x041e\x043a\x0442
+ SABBREVMONTHNAME11 \x041d\x043e\x044f
+ SABBREVMONTHNAME12 \x0414\x0435\x043a
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 041b ; Slovak - Slovak Republic
+
+ ILANGUAGE 041b
+ SENGLANGUAGE Slovak
+ SABBREVLANGNAME SKY
+ SNATIVELANGNAME Slovenský
+
+ ICOUNTRY 42
+ SENGCOUNTRY Slovak Republic
+ SABBREVCTRYNAME SVK
+ SNATIVECTRYNAME Slovenská republika
+
+ IDEFAULTLANGUAGE 041b
+ IDEFAULTCOUNTRY 42
+ IDEFAULTANSICODEPAGE 1250
+ IDEFAULTOEMCODEPAGE 852
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY Sk
+ SINTLSYMBOL SKK
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 HH.mm.ss
+ H.mm.ss
+ STIME .
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 dd.MM.yyyy
+ dd-MM-yy
+ yyyy-MM-dd
+ yy-MM-dd
+ SDATE .
+ IDATE 1
+ ICENTURY 1
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 d. MMMM yyyy
+ dd. MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 pondelok
+ SDAYNAME2 utorok
+ SDAYNAME3 streda
+ SDAYNAME4 \x0161tvrtok
+ SDAYNAME5 piatok
+ SDAYNAME6 sobota
+ SDAYNAME7 nede\x013ea
+
+ SABBREVDAYNAME1 po
+ SABBREVDAYNAME2 ut
+ SABBREVDAYNAME3 st
+ SABBREVDAYNAME4 \x0161t
+ SABBREVDAYNAME5 pi
+ SABBREVDAYNAME6 so
+ SABBREVDAYNAME7 ne
+
+ SMONTHNAME1 január
+ SMONTHNAME2 február
+ SMONTHNAME3 marec
+ SMONTHNAME4 apríl
+ SMONTHNAME5 máj
+ SMONTHNAME6 jún
+ SMONTHNAME7 júl
+ SMONTHNAME8 august
+ SMONTHNAME9 september
+ SMONTHNAME10 október
+ SMONTHNAME11 november
+ SMONTHNAME12 december
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 apr
+ SABBREVMONTHNAME5 máj
+ SABBREVMONTHNAME6 jún
+ SABBREVMONTHNAME7 júl
+ SABBREVMONTHNAME8 aug
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 okt
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 041d ; Swedish - Sweden
+
+ ILANGUAGE 041d
+ SENGLANGUAGE Swedish
+ SABBREVLANGNAME SVE
+ SNATIVELANGNAME Svenska
+
+ ICOUNTRY 46
+ SENGCOUNTRY Sweden
+ SABBREVCTRYNAME SWE
+ SNATIVECTRYNAME Sverige
+
+ IDEFAULTLANGUAGE 041d
+ IDEFAULTCOUNTRY 46
+ IDEFAULTANSICODEPAGE 1252
+ IDEFAULTOEMCODEPAGE 850
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND \x00a0
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY kr
+ SINTLSYMBOL SEK
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP \x00a0
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 8
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 3 HH.mm.ss
+ H.mm.ss
+ 'kl 'H.mm
+ STIME .
+ ITIME 1
+ ITLZERO 1
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 4 yyyy-MM-dd
+ yy-MM-dd
+ yyMMdd
+ d/M-yy
+ SDATE -
+ IDATE 2
+ ICENTURY 1
+ IDAYLZERO 1
+ IMONLZERO 1
+
+ SLONGDATE 2 ' den 'd MMMM yyyy
+ ' den 'dd MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 måndag
+ SDAYNAME2 tisdag
+ SDAYNAME3 onsdag
+ SDAYNAME4 torsdag
+ SDAYNAME5 fredag
+ SDAYNAME6 lördag
+ SDAYNAME7 söndag
+
+ SABBREVDAYNAME1 må
+ SABBREVDAYNAME2 ti
+ SABBREVDAYNAME3 on
+ SABBREVDAYNAME4 to
+ SABBREVDAYNAME5 fr
+ SABBREVDAYNAME6 lö
+ SABBREVDAYNAME7 sö
+
+ SMONTHNAME1 januari
+ SMONTHNAME2 februari
+ SMONTHNAME3 mars
+ SMONTHNAME4 april
+ SMONTHNAME5 maj
+ SMONTHNAME6 juni
+ SMONTHNAME7 juli
+ SMONTHNAME8 augusti
+ SMONTHNAME9 september
+ SMONTHNAME10 oktober
+ SMONTHNAME11 november
+ SMONTHNAME12 december
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 jan
+ SABBREVMONTHNAME2 feb
+ SABBREVMONTHNAME3 mar
+ SABBREVMONTHNAME4 apr
+ SABBREVMONTHNAME5 maj
+ SABBREVMONTHNAME6 jun
+ SABBREVMONTHNAME7 jul
+ SABBREVMONTHNAME8 aug
+ SABBREVMONTHNAME9 sep
+ SABBREVMONTHNAME10 okt
+ SABBREVMONTHNAME11 nov
+ SABBREVMONTHNAME12 dec
+ SABBREVMONTHNAME13 \x0000
+
+
+BEGINLOCALE 041f ; Turkish - Turkey
+
+ ILANGUAGE 041f
+ SENGLANGUAGE Turkish
+ SABBREVLANGNAME TRK
+ SNATIVELANGNAME Türkçe
+
+ ICOUNTRY 90
+ SENGCOUNTRY Turkey
+ SABBREVCTRYNAME TUR
+ SNATIVECTRYNAME Türkiye
+
+ IDEFAULTLANGUAGE 041f
+ IDEFAULTCOUNTRY 90
+ IDEFAULTANSICODEPAGE 1254
+ IDEFAULTOEMCODEPAGE 857
+
+ SLIST ;
+ IMEASURE 0
+
+ SDECIMAL ,
+ STHOUSAND .
+ SGROUPING 3;0
+ IDIGITS 2
+ ILZERO 1
+ INEGNUMBER 1
+ SNATIVEDIGITS 0123456789
+
+ SCURRENCY TL
+ SINTLSYMBOL TRL
+ SMONDECIMALSEP ,
+ SMONTHOUSANDSEP .
+ SMONGROUPING 3;0
+ ICURRDIGITS 2
+ IINTLCURRDIGITS 2
+ ICURRENCY 3
+ INEGCURR 1
+ SPOSITIVESIGN \x0000
+ SNEGATIVESIGN -
+
+ STIMEFORMAT 2 H:mm:ss
+ HH:mm:ss
+ STIME :
+ ITIME 1
+ ITLZERO 0
+ S1159 \x0000
+ S2359 \x0000
+
+ SSHORTDATE 3 d/M/yyyy
+ dd/MM/yy
+ yy/MM/dd
+ SDATE /
+ IDATE 1
+ ICENTURY 1
+ IDAYLZERO 0
+ IMONLZERO 0
+
+ SLONGDATE 3 d MMMM yyyy, dddd
+ dd MMMM yyyy, dddd
+ d MMMM yyyy
+ ILDATE 1
+
+ ICALENDARTYPE 1
+ IOPTIONALCALENDAR 2 0\xffff
+ 1\xffffGregorian
+
+ IFIRSTDAYOFWEEK 0
+ IFIRSTWEEKOFYEAR 0
+
+ SDAYNAME1 Pazartesi
+ SDAYNAME2 Sae\x0131
+ SDAYNAME3 \x00c7ar\x015famba
+ SDAYNAME4 per\x015fembe
+ SDAYNAME5 Cuma
+ SDAYNAME6 Cumartesi
+ SDAYNAME7 Pazar
+
+ SABBREVDAYNAME1 Pazartesi
+ SABBREVDAYNAME2 Sae\x0131
+ SABBREVDAYNAME3 \x00c7ar\x015famba
+ SABBREVDAYNAME4 per\x015fembe
+ SABBREVDAYNAME5 Cuma
+ SABBREVDAYNAME6 Cumartesi
+ SABBREVDAYNAME7 Pazar
+
+ SMONTHNAME1 Ocak
+ SMONTHNAME2 \x015eubat
+ SMONTHNAME3 Mart
+ SMONTHNAME4 Nisan
+ SMONTHNAME5 May\x0131s
+ SMONTHNAME6 Haziran
+ SMONTHNAME7 Temmuz
+ SMONTHNAME8 A\x011fustos
+ SMONTHNAME9 Eylül
+ SMONTHNAME10 Ekim
+ SMONTHNAME11 Kas\x0131m
+ SMONTHNAME12 Aral\x0131k
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Ocak
+ SABBREVMONTHNAME2 \x015eubat
+ SABBREVMONTHNAME3 Mart
+ SABBREVMONTHNAME4 Nisan
+ SABBREVMONTHNAME5 May\x0131s
+ SABBREVMONTHNAME6 Haziran
+ SABBREVMONTHNAME7 Temmuz
+ SABBREVMONTHNAME8 A\x011fustos
+ SABBREVMONTHNAME9 Eylül
+ SABBREVMONTHNAME10 Ekim
+ SABBREVMONTHNAME11 Kas\x0131m
+ SABBREVMONTHNAME12 Aral\x0131k
+ SABBREVMONTHNAME13 \x0000
+
+
+ENDLOCALE
+
+
+
+CALENDAR 5
+
+
+ BEGINCALENDAR 1 ; Gregorian (localized)
+
+ SCALENDAR 1
+
+ SERARANGES 0
+
+ SSHORTDATE 1 \x0000
+ SLONGDATE 1 \x0000
+
+ IF_NAMES 0
+
+
+ BEGINCALENDAR 2 ; Gregorian (U.S. English only)
+
+ SCALENDAR 2
+
+ SERARANGES 0
+
+ SSHORTDATE 4 M/d/yy
+ M/d/yyyy
+ MM/dd/yy
+ MM/dd/yyyy
+ SLONGDATE 2 dddd, MMMM dd, yyyy
+ MMMM dd, yyyy
+
+ IF_NAMES 1
+
+ SDAYNAME1 Monday
+ SDAYNAME2 Tuesday
+ SDAYNAME3 Wednesday
+ SDAYNAME4 Thursday
+ SDAYNAME5 Friday
+ SDAYNAME6 Saturday
+ SDAYNAME7 Sunday
+
+ SABBREVDAYNAME1 Mon
+ SABBREVDAYNAME2 Tue
+ SABBREVDAYNAME3 Wed
+ SABBREVDAYNAME4 Thu
+ SABBREVDAYNAME5 Fri
+ SABBREVDAYNAME6 Sat
+ SABBREVDAYNAME7 Sun
+
+ SMONTHNAME1 January
+ SMONTHNAME2 February
+ SMONTHNAME3 March
+ SMONTHNAME4 April
+ SMONTHNAME5 May
+ SMONTHNAME6 June
+ SMONTHNAME7 July
+ SMONTHNAME8 August
+ SMONTHNAME9 September
+ SMONTHNAME10 October
+ SMONTHNAME11 November
+ SMONTHNAME12 December
+ SMONTHNAME13 \x0000
+
+ SABBREVMONTHNAME1 Jan
+ SABBREVMONTHNAME2 Feb
+ SABBREVMONTHNAME3 Mar
+ SABBREVMONTHNAME4 Apr
+ SABBREVMONTHNAME5 May
+ SABBREVMONTHNAME6 Jun
+ SABBREVMONTHNAME7 Jul
+ SABBREVMONTHNAME8 Aug
+ SABBREVMONTHNAME9 Sep
+ SABBREVMONTHNAME10 Oct
+ SABBREVMONTHNAME11 Nov
+ SABBREVMONTHNAME12 Dec
+ SABBREVMONTHNAME13 \x0000
+
+
+ BEGINCALENDAR 3 ; Japanese Era - Year of the Emperor
+
+ SCALENDAR 3
+
+ SERARANGES 4 1989\xffff\x337b
+ 1926\xffff\x337c
+ 1912\xffff\x337d
+ 1868\xffff\x337e
+
+ SSHORTDATE 1 ggyyyy/MM/dd
+ SLONGDATE 1 ggyyyy'\x5e74'M'\x6708'd'\x65e5'
+
+ IF_NAMES 0
+
+
+ BEGINCALENDAR 4 ; Taiwan Era - Year of the Republic of China
+
+ SCALENDAR 4
+
+ SERARANGES 1 1912\xffff\x4e2d\x83ef\x6c11\x570b
+
+ SSHORTDATE 1 ggyyyy/MM/dd
+ SLONGDATE 1 ggyyyy MMMM dd
+
+ IF_NAMES 0
+
+
+ BEGINCALENDAR 5 ; Korean - Tangun Era
+
+ SCALENDAR 5
+
+ SERARANGES 1 2333\xffff
+
+ SSHORTDATE 1 yy-MM-dd
+ SLONGDATE 1 yyyy'\x355b' M'\x39da' d'\x3a0e'
+
+ IF_NAMES 0
+
+
+ENDCALENDAR
+ \ No newline at end of file
diff --git a/private/oleauto/src/dispatch/win16/ole2disp.def b/private/oleauto/src/dispatch/win16/ole2disp.def
new file mode 100644
index 000000000..c1e908230
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/ole2disp.def
@@ -0,0 +1,207 @@
+LIBRARY OLE2DISP
+DESCRIPTION 'OLE Automation Library'
+EXETYPE WINDOWS 3.0
+HEAPSIZE 0
+
+DATA PRELOAD MOVEABLE SINGLE
+CODE LOADONCALL MOVEABLE DISCARDABLE
+SEGMENTS
+ _TEXT PRELOAD MOVEABLE DISCARDABLE
+ _COMDATS PRELOAD MOVEABLE DISCARDABLE
+ RT LOADONCALL MOVEABLE DISCARDABLE
+ RPC LOADONCALL MOVEABLE DISCARDABLE
+ RPC2 LOADONCALL MOVEABLE DISCARDABLE
+ BSTR LOADONCALL MOVEABLE DISCARDABLE
+ RUNTIME LOADONCALL MOVEABLE DISCARDABLE
+ STDIMPL LOADONCALL MOVEABLE DISCARDABLE
+ UPS LOADONCALL MOVEABLE DISCARDABLE
+
+
+EXPORTS
+ WEP @0 RESIDENTNAME
+
+ DLLGETCLASSOBJECT @1
+
+ ; BSTR API
+ ;
+ SYSALLOCSTRING @2
+ SYSREALLOCSTRING @3
+ SYSALLOCSTRINGLEN @4
+ SYSREALLOCSTRINGLEN @5
+ SYSFREESTRING @6
+ SYSSTRINGLEN @7
+
+ ; VARIANT API
+ ;
+ VARIANTINIT @8
+ VARIANTCLEAR @9
+ VARIANTCOPY @10
+ VARIANTCOPYIND @11
+ VARIANTCHANGETYPE @12
+
+ ; VARIANT TIME API
+ ;
+ VARIANTTIMETODOSDATETIME @13
+ DOSDATETIMETOVARIANTTIME @14
+
+ ; SAFEARRAY API
+ ;
+ SAFEARRAYCREATE @15
+ SAFEARRAYDESTROY @16
+ SAFEARRAYGETDIM @17
+ SAFEARRAYGETELEMSIZE @18
+ SAFEARRAYGETUBOUND @19
+ SAFEARRAYGETLBOUND @20
+ SAFEARRAYLOCK @21
+ SAFEARRAYUNLOCK @22
+ SAFEARRAYACCESSDATA @23
+ SAFEARRAYUNACCESSDATA @24
+ SAFEARRAYGETELEMENT @25
+ SAFEARRAYPUTELEMENT @26
+ SAFEARRAYCOPY @27
+
+ ; IDispatch helpers/implementation
+ ;
+ DISPGETPARAM @28
+ DISPGETIDSOFNAMES @29
+ DISPINVOKE @30
+ CREATEDISPTYPEINFO @31
+ CREATESTDDISPATCH @32
+
+ ; IIDs
+ ;
+ _IID_IDispatch @33
+ _IID_IEnumVARIANT @34
+
+ ; Active Object API
+ ;
+ REGISTERACTIVEOBJECT @35
+ REVOKEACTIVEOBJECT @36
+ GETACTIVEOBJECT @37
+
+ ; additional SafeArray APIs
+ ;
+ SAFEARRAYALLOCDESCRIPTOR @38
+ SAFEARRAYALLOCDATA @39
+ SAFEARRAYDESTROYDESCRIPTOR @40
+ SAFEARRAYDESTROYDATA @41
+ SAFEARRAYREDIM @42
+
+ ; low-level VARTYPE coersion API
+ ;
+ VARI2FROMI4 @43
+ VARI2FROMR4 @44
+ VARI2FROMR8 @45
+ VARI2FROMCY @46
+ VARI2FROMDATE @47
+ VARI2FROMSTR @48
+ VARI2FROMDISP @49
+ VARI2FROMBOOL @50
+
+ VARI4FROMI2 @51
+ VARI4FROMR4 @52
+ VARI4FROMR8 @53
+ VARI4FROMCY @54
+ VARI4FROMDATE @55
+ VARI4FROMSTR @56
+ VARI4FROMDISP @57
+ VARI4FROMBOOL @58
+
+ VARR4FROMI2 @59
+ VARR4FROMI4 @60
+ VARR4FROMR8 @61
+ VARR4FROMCY @62
+ VARR4FROMDATE @63
+ VARR4FROMSTR @64
+ VARR4FROMDISP @65
+ VARR4FROMBOOL @66
+
+ VARR8FROMI2 @67
+ VARR8FROMI4 @68
+ VARR8FROMR4 @69
+ VARR8FROMCY @70
+ VARR8FROMDATE @71
+ VARR8FROMSTR @72
+ VARR8FROMDISP @73
+ VARR8FROMBOOL @74
+
+ VARDATEFROMI2 @75
+ VARDATEFROMI4 @76
+ VARDATEFROMR4 @77
+ VARDATEFROMR8 @78
+ VARDATEFROMCY @79
+ VARDATEFROMSTR @80
+ VARDATEFROMDISP @81
+ VARDATEFROMBOOL @82
+
+ VARCYFROMI2 @83
+ VARCYFROMI4 @84
+ VARCYFROMR4 @85
+ VARCYFROMR8 @86
+ VARCYFROMDATE @87
+ VARCYFROMSTR @88
+ VARCYFROMDISP @89
+ VARCYFROMBOOL @90
+
+ VARBSTRFROMI2 @91
+ VARBSTRFROMI4 @92
+ VARBSTRFROMR4 @93
+ VARBSTRFROMR8 @94
+ VARBSTRFROMCY @95
+ VARBSTRFROMDATE @96
+ VARBSTRFROMDISP @97
+ VARBSTRFROMBOOL @98
+
+ VARBOOLFROMI2 @99
+ VARBOOLFROMI4 @100
+ VARBOOLFROMR4 @101
+ VARBOOLFROMR8 @102
+ VARBOOLFROMDATE @103
+ VARBOOLFROMCY @104
+ VARBOOLFROMSTR @105
+ VARBOOLFROMDISP @106
+
+
+ ; Private API for use by TYPELIB.DLL
+ ;
+ DOINVOKEMETHOD @107
+
+
+ ; Varaint Coersion API Extension
+ VARIANTCHANGETYPEEX @108
+
+
+ ; SAFEARRAY API
+ ;
+ SAFEARRAYPTROFINDEX @109
+
+
+ ; Rich Error APIs
+ SETERRORINFO @110
+ GETERRORINFO @111
+ CREATEERRORINFO @112
+ _IID_IErrorInfo @113
+ _IID_ICreateErrorInfo @114
+ _IID_ISupportErrorInfo @115
+
+
+ ; More variant conversion routines
+ ;
+ VARUI1FROMI2 @116
+ VARUI1FROMI4 @117
+ VARUI1FROMR4 @118
+ VARUI1FROMR8 @119
+ VARUI1FROMCY @120
+ VARUI1FROMDATE @121
+ VARUI1FROMSTR @122
+ VARUI1FROMDISP @123
+ VARUI1FROMBOOL @124
+
+ VARI2FROMUI1 @125
+ VARI4FROMUI1 @126
+ VARR4FROMUI1 @127
+ VARR8FROMUI1 @128
+ VARDATEFROMUI1 @129
+ VARCYFROMUI1 @130
+ VARBSTRFROMUI1 @131
+ VARBOOLFROMUI1 @132
diff --git a/private/oleauto/src/dispatch/win16/ole2disp.rc b/private/oleauto/src/dispatch/win16/ole2disp.rc
new file mode 100644
index 000000000..4382cb340
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/ole2disp.rc
@@ -0,0 +1,92 @@
+/***
+*ole2disp.rc - Resource file for OLE2DISP.DLL
+*
+* Copyright (C) 1992 - 1993, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file is the resource file for OLE2DISP.DLL.
+*
+*
+*Revision History:
+* [00] 12-Jan-93 bradlo: added version resource.
+*
+*****************************************************************************/
+
+#include <windows.h>
+#include <ver.h>
+
+#include "verstamp.h"
+
+#ifdef _DEBUG
+# include "assert.dlg"
+#endif
+
+
+#ifndef OLEMINORVERS
+#define OLEMINORVERS 02 // assume OLE 2.02
+#endif //!OLEMINORVERS
+
+
+#if 0
+/* Define the version string with more preprocessor magic */
+#define STRING(x) #x
+#define VERSTRINGX(maj,min,rev) STRING(maj ## . ## min ## . ## rev ## \0)
+#define VERSTRING VERSTRINGX(rmj,rmm,rup)
+#endif
+
+VS_VERSION_INFO VERSIONINFO
+FILEVERSION 2,OLEMINORVERS,rup,01
+PRODUCTVERSION 2,OLEMINORVERS,rup,01
+FILEFLAGSMASK VS_FFI_FILEFLAGSMASK
+#ifdef _DEBUG
+FILEFLAGS VS_FF_DEBUG
+#else
+FILEFLAGS 0L
+#endif
+#if (OLEMINORVERS == 02)
+// re-distributable 16-bit DLL
+FILEOS VOS_DOS_WINDOWS16
+#else
+FILEOS VOS_DOS_WINDOWS32
+// non-re-distributable 16-bit DLL (shipped with the OS)
+#endif
+FILETYPE VFT_DLL
+FILESUBTYPE 0
+
+BEGIN
+ BLOCK "StringFileInfo"
+ BEGIN
+ BLOCK "040904E4"
+ BEGIN
+#if (OLEMINORVERS == 02)
+// re-distributable 16-bit DLL
+ VALUE "CompanyName", "Microsoft Corporation\0"
+ VALUE "FileDescription", "OLE Automation Library\0"
+ VALUE "FileVersion", "2.02\0"
+ VALUE "InternalName", "OLE2DISP.DLL\0"
+ VALUE "LegalCopyright", "Copyright \251 Microsoft Corp. 1992-1995\0"
+ VALUE "LegalTrademarks", "Microsoft\256 is a registered trademark of Microsoft Corporation. Windows(TM) is a trademark of Microsoft Corporation.\0"
+ VALUE "ProductName", "Microsoft OLE 2.02 for Windows\0"
+ VALUE "ProductVersion", "2.02\0"
+ VALUE "Comments", "Windows OLE DLLs\0"
+#else
+// non-re-distributable 16-bit DLL (shipped with the OS)
+ VALUE "CompanyName", "Microsoft Corporation\0"
+ VALUE "FileDescription", "OLE 2.1 16/32 Interoperability Library\0"
+ VALUE "FileVersion", "2.1\0"
+ VALUE "InternalName", "OLE2DISP.DLL\0"
+ VALUE "LegalCopyright", "Copyright \251 Microsoft Corp. 1992-1995\0"
+ VALUE "LegalTrademarks", "Microsoft\256 is a registered trademark of Microsoft Corporation. Windows(TM) is a trademark of Microsoft Corporation.\0"
+ VALUE "ProductName", "Microsoft OLE 2.1 16/32 Interoperability for Windows NT\0"
+ VALUE "ProductVersion", "2.1\0"
+ VALUE "Comments", "Windows NT OLE 16/32 Interoperability DLLs\0"
+#endif
+ END
+ END
+
+ BLOCK "VarFileInfo"
+ BEGIN
+ VALUE "Translation", 0x409, 1252
+ END
+END
diff --git a/private/oleauto/src/dispatch/win16/ole2nls.def b/private/oleauto/src/dispatch/win16/ole2nls.def
new file mode 100644
index 000000000..15891ee79
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/ole2nls.def
@@ -0,0 +1,80 @@
+LIBRARY OLE2NLS
+DESCRIPTION 'National Language Support Library'
+EXETYPE WINDOWS 3.1
+HEAPSIZE 2048
+
+CODE MOVEABLE DISCARDABLE
+DATA MOVEABLE SINGLE
+SEGMENTS
+ _TEXT PRELOAD MOVEABLE DISCARDABLE
+ NLS0405_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0406_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0407_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0409_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS040a_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS040b_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS040c_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS040e_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0410_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0413_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0414_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0415_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0416_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0419_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS041b_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS041d_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0807_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0809_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS080a_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS080c_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0810_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0813_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0816_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0c07_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0c09_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0c0a_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0c0c_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS1009_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS100c_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS1409_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0404_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0411_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0412_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0804_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS1809_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0814_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS041f_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS040f_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0408_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0403_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0429_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS040d_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0401_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0801_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS0c01_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS1001_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS1401_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS1801_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS1c01_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS2001_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS2401_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS2801_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS2c01_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS3001_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS3401_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS3801_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS3c01_TEXT LOADONCALL MOVEABLE DISCARDABLE
+ NLS4001_TEXT LOADONCALL MOVEABLE DISCARDABLE
+
+EXPORTS
+ WEP @0 RESIDENTNAME
+
+ GETUSERDEFAULTLCID @1
+ GETSYSTEMDEFAULTLCID @2
+ GETUSERDEFAULTLANGID @3
+ GETSYSTEMDEFAULTLANGID @4
+ GETLOCALEINFOA @5
+ LCMAPSTRINGA @6
+ GETSTRINGTYPEA @7
+ COMPARESTRINGA @8
+ REGISTERNLSINFOCHANGED @9
diff --git a/private/oleauto/src/dispatch/win16/ole2nls.rc b/private/oleauto/src/dispatch/win16/ole2nls.rc
new file mode 100644
index 000000000..e65da66e9
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/ole2nls.rc
@@ -0,0 +1,93 @@
+/***
+*ole2nls.rc - Resource file for OLE2NLS.DLL
+*
+* Copyright (C) 1992 - 1993, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file is the resource file for OLE2NLS.DLL
+*
+*
+*Revision History:
+* [00] 13-Nov-92 petergo: Created.
+*
+*****************************************************************************/
+
+#include <windows.h>
+#include <ver.h>
+
+#include "verstamp.h"
+
+#ifdef _DEBUG
+# include "assert.dlg"
+#endif
+
+#include "nlsintrn.h"
+
+
+#ifndef OLEMINORVERS
+#define OLEMINORVERS 02 // assume OLE 2.02
+#endif //!OLEMINORVERS
+
+#if 0
+/* Define the version string with more preprocessor magic */
+#define STRING(x) #x
+#define VERSTRINGX(maj,min,rev) STRING(maj ## . ## min ## . ## rev ## \0)
+#define VERSTRING VERSTRINGX(rmj,rmm,rup)
+#endif
+
+VS_VERSION_INFO VERSIONINFO
+FILEVERSION 2,OLEMINORVERS,rup,01
+PRODUCTVERSION 2,OLEMINORVERS,rup,01
+FILEFLAGSMASK VS_FFI_FILEFLAGSMASK
+#ifdef _DEBUG
+FILEFLAGS VS_FF_DEBUG
+#else
+FILEFLAGS 0L
+#endif
+#if (OLEMINORVERS == 02)
+// re-distributable 16-bit DLL
+FILEOS VOS_DOS_WINDOWS16
+#else
+FILEOS VOS_DOS_WINDOWS32
+// non-re-distributable 16-bit DLL (shipped with the OS)
+#endif
+FILETYPE VFT_DLL
+FILESUBTYPE 0
+
+BEGIN
+ BLOCK "StringFileInfo"
+ BEGIN
+ BLOCK "040904E4"
+ BEGIN
+#if (OLEMINORVERS == 02)
+// re-distributable 16-bit DLL
+ VALUE "CompanyName", "Microsoft Corporation\0"
+ VALUE "FileDescription", "OLE NLS Library\0"
+ VALUE "FileVersion", "2.02\0"
+ VALUE "InternalName", "OLE2NLS.DLL\0"
+ VALUE "LegalCopyright", "Copyright \251 Microsoft Corp. 1992-1995\0"
+ VALUE "LegalTrademarks", "Microsoft\256 is a registered trademark of Microsoft Corporation. Windows(TM) is a trademark of Microsoft Corporation.\0"
+ VALUE "ProductName", "Microsoft OLE 2.02 for Windows\0"
+ VALUE "ProductVersion", "2.02\0"
+ VALUE "Comments", "Windows OLE DLLs\0"
+#else
+// non-re-distributable 16-bit DLL (shipped with the OS)
+ VALUE "CompanyName", "Microsoft Corporation\0"
+ VALUE "FileDescription", "OLE 2.1 16/32 Interoperability Library\0"
+ VALUE "FileVersion", "2.1\0"
+ VALUE "InternalName", "OLE2NLS.DLL\0"
+ VALUE "LegalCopyright", "Copyright \251 Microsoft Corp. 1992-1995\0"
+ VALUE "LegalTrademarks", "Microsoft\256 is a registered trademark of Microsoft Corporation. Windows(TM) is a trademark of Microsoft Corporation.\0"
+ VALUE "ProductName", "Microsoft OLE 2.1 16/32 Interoperability for Windows NT\0"
+ VALUE "ProductVersion", "2.1\0"
+ VALUE "Comments", "Windows NT OLE 16/32 Interoperability DLLs\0"
+#endif
+ END
+ END
+
+ BLOCK "VarFileInfo"
+ BEGIN
+ VALUE "Translation", 0x409, 1252
+ END
+END
diff --git a/private/oleauto/src/dispatch/win16/oleconva.asm b/private/oleauto/src/dispatch/win16/oleconva.asm
new file mode 100644
index 000000000..5a3884cbf
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/oleconva.asm
@@ -0,0 +1,653 @@
+;***
+;oleconva.a - Machine-specific conversion helpers
+;
+; Copyright (C) 1993, Microsoft Corporation. All Rights Reserved.
+; Information Contained Herein Is Proprietary and Confidential.
+;
+;Purpose:
+; Type conversion helper functions.
+;
+;Revision History:
+;[nnn] dd-mmm-yy alias___ Comment
+;
+; [] 18-Mar-93 timp Module created.
+;[001] 31-May-93 bradlo Added overflow checking.
+;[002] 12-Jul-93 timp Save/restore x87 control word.
+;
+;******************************************************************************
+
+
+ .286
+ .MODEL large
+
+EXTERNDEF PASCAL ReportOverflow:FAR
+
+ .DATA
+BigCyVal dw 0000,0000,0000,0ddfH
+
+ .CODE RT
+
+; floating point <-> currency scaling factor
+CYFACTOR equ 10000
+g_wCyFactor dw CYFACTOR
+g_fltCyFactor REAL4 10000.0
+
+TenTo18 dt 1.0E18
+
+g_CwStd dw 137fH ;Mask all errors, 64-bit, round near
+CwTrunc dw 1F7fH ;Mask all errors, 64-bit, chop
+
+FPERR equ 0DH ;Overflow, zero divide, invalid errs
+
+
+SETUP87 MACRO CwSave, cw:=<g_CwStd>
+ fstcw CwSave ;;Save existing environment
+ fldcw cw ;;Use our own CW
+ ENDM
+
+
+RESTORE87 MACRO CwSave
+ fclex ;;Prevent 486 bug on FLDCW
+ fldcw CwSave ;;Restore original CW
+ ENDM
+
+
+CHKERR87 MACRO CwSave, ErrLoc
+ fstsw ax ;;Get error flags
+ fclex ;;Don't let caller see errors
+ test al,FPERR ;;See if any errors
+ fldcw CwSave ;;Restore original CW
+ jnz ErrLoc ;;Go handle error if bit set
+ ENDM
+
+;******************************************************************************
+;
+;PUBLIC HRESULT ErrCyFromI2(short sIn, CY *pcyOut)
+;
+;Purpose:
+; Convert Integer to Currency
+;
+;Entry:
+; sIn = Integer to convert
+;
+;Exit:
+; return value = HRESULT
+;
+;*****
+
+ErrCyFromI2 PROC FAR PASCAL PUBLIC, sIn:SWORD, pcyOut:FAR PTR
+
+ mov ax,sIn
+ imul g_wCyFactor ;Scale the I2
+ les bx,pcyOut
+ mov es:[bx],ax ;Store result
+ mov es:[bx+2],dx
+ xchg ax,dx ;Move high word to ax
+ cwd ;Get sign extension
+ mov es:[bx+4],dx
+ mov es:[bx+6],dx
+
+ xor ax,ax ;NOERROR
+ xor dx,dx
+ ret
+
+ErrCyFromI2 ENDP
+
+
+;******************************************************************************
+;
+;PUBLIC HRESULT ErrCyFromI4(long lIn, CY *pcyOut)
+;
+;Purpose:
+; Convert Long to Currency
+;
+;Entry:
+; lIn = Long to convert
+;
+;Exit:
+; return value = HRESULT
+;
+;*****
+
+ErrCyFromI4 PROC FAR PASCAL PUBLIC, lIn: SDWORD, pcyOut:FAR PTR
+
+;Mulitply I4 by CYFACTOR (=10000), result is currency
+;
+;This routine uses Booth's algorithm for a twos-complement signed
+;multiply. This algorithm says to compute the product with unsigned
+;arithmetic. Then correct the result by looking at the signs of the
+;original operands: for each operand that is negative, subtract the
+;other operand from the high half of the product. (The mathematical
+;proof is a fun 15-minute exercise. Go for it.) In our case, one of
+;the operands is a positive constant, so the correction is especially
+;easy.
+
+ mov ax,word ptr lIn ;Get low half of Long
+ mul g_wCyFactor ;Scale low half
+ les bx,pcyOut
+ mov es:[bx],ax ;Save low word of result
+ mov cx,dx
+ mov ax,word ptr lIn+2 ;Get high half of Long
+ mul g_wCyFactor ;Scale high half
+ add ax,cx
+ adc dx,0
+ mov es:[bx+2],ax ;Save mid-low word of result
+ xor ax,ax ;ax:dx has high half of CY result
+ cmp byte ptr lIn+3,0 ;Is input negative?
+ jns PosCy
+ sub dx,CYFACTOR
+ dec ax ;Previous sub will alway borrow
+PosCy:
+ mov es:[bx+4],dx ;Save mid-high word of result
+ mov es:[bx+6],ax ;Save high word of result
+
+ xor ax,ax ;NOERROR
+ xor dx,dx
+ ret
+
+ErrCyFromI4 ENDP
+
+
+;******************************************************************************
+;
+;PUBLIC HRESULT ErrCyFromR4(float FAR* pfltIn, CY *pcyOut)
+;
+;Purpose:
+; Convert Single to Currency
+;
+;Entry:
+; pfltIn = Single to convert
+; pcyOut = pointer to Currency to hold result
+;
+;Exit:
+; return value = HRESULT
+;
+;*****
+
+ErrCyFromR4 PROC FAR PASCAL PUBLIC, pfltIn:FAR PTR, pcyOut:FAR PTR
+
+LOCAL cw:WORD
+
+ SETUP87 cw
+ les bx,pfltIn
+ fld dword ptr es:[bx] ;Load R4
+ fmul g_fltCyFactor ;Scale it
+
+ les bx,pcyOut
+ fistp qword ptr es:[bx] ;Store CY result
+
+ CHKERR87 cw, LOvfl
+ xor ax,ax ;NOERROR
+ xor dx,dx
+ ret
+
+LOvfl:
+ call ReportOverflow ;DISP_E_OVERFLOW
+ ret
+
+ErrCyFromR4 ENDP
+
+
+;******************************************************************************
+;
+;PUBLIC HRESULT ErrCyFromR8(double FAR* pdlbIn, CY FAR* pcyOut)
+;
+;Purpose:
+; Convert Double to Currency
+;
+;Entry:
+; pdblIn = Double to convert
+; pcyOut = pointer to Currency to hold result
+;
+;Exit:
+; return value = HRESULT
+;
+;*****
+
+ErrCyFromR8 PROC FAR PASCAL PUBLIC, pdblIn:FAR PTR, pcyOut:FAR PTR
+
+LOCAL cw:WORD
+
+ SETUP87 cw
+ les bx,pdblIn
+ fld qword ptr es:[bx]
+ fmul g_fltCyFactor ;Scale it
+
+ les bx,pcyOut
+ fistp qword ptr es:[bx]
+
+ CHKERR87 cw, LOvfl
+ xor ax,ax ;NOERROR
+ xor dx,dx
+ ret
+
+LOvfl:
+ call ReportOverflow ;DISP_E_OVERFLOW
+ ret
+
+ErrCyFromR8 ENDP
+
+
+;******************************************************************************
+;
+;PUBLIC HRESULT ErrI2FromCy(CY cyIn, short *psOut)
+;
+;Purpose:
+; Convert Currency to Integer
+;
+;Entry:
+; cyIn = Currency to convert
+; psOut = pointer to Integer to hold result
+;
+;Exit:
+; return value = HRESULT
+;
+;*****
+
+ErrI2FromCy PROC FAR PASCAL PUBLIC, cyIn:QWORD, psOut:FAR PTR
+
+LOCAL cw:WORD
+
+ SETUP87 cw
+ fild cyIn
+ fdiv g_fltCyFactor ;Remove scaling
+
+ les bx,psOut
+ fistp word ptr es:[bx]
+
+ CHKERR87 cw, LOvfl
+ xor ax,ax ;NOERROR
+ xor dx,dx
+ ret
+
+LOvfl:
+ call ReportOverflow ;DISP_E_OVERFLOW
+ ret
+
+ErrI2FromCy ENDP
+
+
+;******************************************************************************
+;
+;PUBLIC HRESULT ErrI4FromCy(CY cyIn, long *plOut)
+;
+;Purpose:
+; Convert Currency to Long
+;
+;Entry:
+; cyIn = Currency to convert
+; plOut = pointer to Long to hold result
+;
+;Exit:
+; return value = HRESULT
+;
+;*****
+
+ErrI4FromCy PROC FAR PASCAL PUBLIC, cyIn:QWORD, plOut:FAR PTR
+
+LOCAL cw:WORD
+
+ SETUP87 cw
+ fild cyIn ;Load CY
+ fdiv g_fltCyFactor ;Remove scaling
+
+ les bx,plOut
+ fistp dword ptr es:[bx]
+
+ CHKERR87 cw, LOvfl
+ xor ax,ax ;NOERROR
+ xor dx,dx
+ ret
+
+LOvfl:
+ call ReportOverflow ;DISP_E_OVERFLOW
+ ret
+
+ErrI4FromCy ENDP
+
+
+;******************************************************************************
+;
+;PUBLIC HRESULT ErrR4FromCy(CY cyIn, float *pfltOut)
+;
+;Purpose:
+; Convert Currency to Single
+;
+;Entry:
+; cyIn = Currency to convert
+;
+;Exit:
+; return value = HRESULT
+;
+;*****
+
+ErrR4FromCy PROC FAR PASCAL PUBLIC, cyIn:QWORD, pfltOut:FAR PTR
+
+LOCAL cw:WORD
+
+ SETUP87 cw
+ fild cyIn ;Load CY
+ fdiv g_fltCyFactor ;Remove scaling
+ les bx,pfltOut
+ fstp dword ptr es:[bx]
+
+ RESTORE87 cw
+ xor ax,ax ;NOERROR
+ xor dx,dx
+ ret
+
+ErrR4FromCy ENDP
+
+
+;******************************************************************************
+;
+;PUBLIC HRESULT PASCAL ErrR8FromCy(CY cyIn, double FAR* pdblOut)
+;
+;Purpose:
+; Convert Currency to Double
+;
+;Entry:
+; cyIn = Currency to convert
+;
+;Exit:
+; return value = HRESULT
+;
+;*****
+
+ErrR8FromCy PROC FAR PASCAL PUBLIC, cyIn:QWORD, pdblOut:FAR PTR
+
+LOCAL cw:WORD
+
+ SETUP87 cw
+ fild cyIn ;Load CY
+ fdiv g_fltCyFactor ;Remove scaling
+ les bx,pdblOut
+ fstp qword ptr es:[bx]
+
+ RESTORE87 cw
+ xor ax,ax ;NOERROR
+ xor dx,dx
+ ret
+
+ErrR8FromCy ENDP
+
+
+;******************************************************************************
+;
+;PUBLIC HRESULT ErrMultCyI4(CY cyIn, long lIn, CY *pcyOut);
+;
+;Purpose:
+; Multiply Currency by Long with Currency result
+;
+;Entry:
+; cyIn = Currency multiplicand
+; lIn = Long multiplier
+; pcyOut = Pointer to result Currency location
+;
+;Outputs:
+; return value = HRESULT
+;
+;*****
+
+ErrMultCyI4 PROC FAR PASCAL PUBLIC, cyIn:QWORD, lIn:DWORD, pcyOut:FAR PTR
+
+LOCAL cw:WORD
+
+ SETUP87 cw
+ fild cyIn
+ fild lIn
+ fmul ;Product
+
+ les bx,pcyOut ;Get pointer to result location
+ fistp qword ptr es:[bx] ;Save result
+
+ CHKERR87 cw, LOvfl
+ xor ax,ax ;NOERROR
+ xor dx,dx
+ ret
+
+LOvfl:
+ call ReportOverflow ;DISP_E_OVERFLOW
+ ret
+
+ErrMultCyI4 ENDP
+
+
+
+;******************************************************************************
+;
+;void FAR PASCAL DetectFbstpImplemented(void);
+;
+;Purpose:
+; Decide if FBSTP instruction is implemented or not - see oledisp.cpp for
+; details.
+;
+;Entry:
+; None.
+;
+;Outputs:
+; AX = 0 if FBSTP is broken, nonzero if FBSTP is OK.
+;
+;*****
+
+
+;This constant is the upper bits of the 64-bit integer representation
+;of 10^18. CY values at or above this will overflow FBSTP.
+
+;MAX18CY equ 0DE0B6B3H
+MAX18CY equ 0DE0H
+
+
+ .CODE _TEXT ; place in the same segment as the caller (LibMain)
+
+DetectFbstpImplemented proc far pascal public
+
+ mov bx, OFFSET BigCyVal ; ds:bx = ptr to BigCyVal
+
+ fild qword ptr [bx] ; load the CY value
+ fbstp tbyte ptr [bx] ; try to convert to BCD
+ fwait ; wait for it to finish
+
+ mov ax, WORD PTR [bx] ; get the low-word of the result
+ cmp ax, 9456h ; does it match expected val?
+ jz @F ; brif so - return the non-zero ax reg
+
+ fstp st ; fbstp failed - clean up the 0 in ST
+ xor ax, ax ; return 0
+
+@@:
+ ret
+
+DetectFbstpImplemented endp
+
+ .CODE RT
+
+
+
+
+
+;******************************************************************************
+;
+;void NEAR PASCAL DoFbstp(CY NEAR *pcyIn, DIGARY NEAR *pdigOut);
+;
+;Purpose:
+; Do x87 FBSTP instruction on currency type. Check to see if CY is too
+; big first and compute 19th digit separately.
+;
+;Entry:
+; pcyIn = Type currency to convert
+; pdigOut = pointer to result packed BCD digits
+;
+;Outputs:
+; None.
+;
+;*****
+
+DoFbstp proc near pascal public, pcyIn:near ptr qword, pdigOut:near ptr tbyte
+
+LOCAL cw:WORD, iTemp:WORD
+
+ mov bx,pcyIn
+ fild qword ptr ss:[bx]
+ mov ax,ss:[bx+6]
+ mov bx,pdigOut
+ cmp ax,MAX18CY
+ jge Get19
+ cmp ax,-MAX18CY
+ jle Get19
+ fbstp tbyte ptr ss:[bx]
+ fwait
+ ret
+
+Get19:
+ SETUP87 cw,CwTrunc
+ fld TenTo18
+ fld st(1) ;Copy input
+ fdiv st,st(1) ;Compute last digit
+ frndint ;Chop to integer
+ fist iTemp ;Get value of MSD
+ fmul
+ fsub ;Remove MSD
+ fbstp tbyte ptr ss:[bx]
+ mov ax,[iTemp]
+;Take absolute value
+ cwd ;Extend sign through dx
+ xor ax,dx ;NOT if negative
+ sub ax,dx ;INC if negative
+ RESTORE87 cw
+ and dl,80h ;set sign bit in AL
+ or al, dl
+ mov ss:[bx+9],al ;Set 19th digit & sign bit
+ ret
+
+DoFbstp endp
+
+
+;******************************************************************************
+;
+;int ConvFloatToAscii(double dblIn, DIGARY NEAR *pdigOut)
+;
+;Purpose:
+; Convert double to packed BCD digit string plus base-10 exponent.
+;
+;Entry:
+; dblIn = Type double to convert
+; pdigOut = pointer to result packed BCD digits
+;
+;Outputs:
+; return value = power of 10 of the 18-digit integer.
+;
+;*****
+
+ConvFloatToAscii PROC FAR PASCAL PUBLIC, dblIn:REAL8, pdigOut:NEAR PTR TBYTE
+
+LOCAL cw:WORD, temp:TBYTE
+
+ SETUP87 cw
+ fld dblIn ;Put double on x87
+
+;What we want now is equivalent to FXTRACT, but it's faster just
+;to store the tbyte and look at it directly. The reasone we don't
+;use the double's exponent is in case it's denormal.
+;
+ fld st ;Make a copy
+ fstp temp
+ mov ax,word ptr [temp+8] ;Get word with exponent
+ and ah,not 80H ;Zero out sign
+
+;2^59 = 5.7E17 (18 digits). A 59-bit integer could be 2^59 - 1.
+;Our goal now is to find a power of ten to multiply by that will give us
+;a 55- to 59-bit integer. We'll target 58 bits so the multiply can carry
+;to 59, and truncate while figuring the power so we never exceed it.
+
+ sub ax,16382 + 58 ;Remove bias and 58 bits
+
+;Find power of 10 by multiplying base 2 exponent by log10(2)
+
+ mov dx,19728 ;log10(2) * 2^16 = .30103 * 65536
+ imul dx
+ add ax,0FFFFH ;Round up
+ adc dx,0
+ mov ax,dx
+ call MulPower10 ;ax preserved
+ mov bx,pdigOut
+ fbstp tbyte ptr ss:[bx]
+ RESTORE87 cw
+ ret
+
+ConvFloatToAscii endp
+
+
+MulPower10:
+;dx = negative of power of 10 required
+;ax preserved
+ or dx,dx
+ jz NoPower
+ push si
+ mov si,offset cs:tNegPower
+ jns GetPower
+ mov si,offset cs:tPosPower
+ neg dx
+GetPower:
+ mov bx,dx
+ and bx,0FH ;Use low 4 exponent bits
+ jz NoMul
+ dec bx
+ imul bx,size tbyte ;Index into table of powers
+ fld tbyte ptr cs:[bx+si]
+ fmul
+NoMul:
+ add si,15 * size tbyte ;Advance to next table
+ shr dx,4 ;Get next exponent bits
+ jnz GetPower
+ pop si
+NoPower:
+ ret
+
+
+;******************************************************************************
+;
+;Power of 10 tables
+;
+;Two tables: one positive powers, the other negative. Each table is broken
+;into three groups: 10^1 to 10^15 by 1, 10^16 to 10^240 by 16, and
+;(theoretically) 10^256 to ... by 256. However, because the maximum value
+;is about 10^309, only one entry in the last group is needed (10^256), so
+;it is slipped on to the end of the previous group.
+
+
+SetPower10 macro Power
+ dt 1.0E&Power
+ ENDM
+
+
+tPosPower label Tbyte
+
+Power = 1
+ REPT 15
+ SetPower10 %Power
+Power = Power + 1
+ ENDM
+
+ REPT 16
+ SetPower10 %Power
+Power = Power + 16
+ ENDM
+
+
+tNegPower label Tbyte
+
+Power = 1
+ REPT 15
+ SetPower10 -%Power
+Power = Power + 1
+ ENDM
+
+ REPT 16
+ SetPower10 -%Power
+Power = Power + 16
+ ENDM
+
+
+
+ END
diff --git a/private/oleauto/src/dispatch/win16/oledisp.cpp b/private/oleauto/src/dispatch/win16/oledisp.cpp
new file mode 100644
index 000000000..15da4d3af
--- /dev/null
+++ b/private/oleauto/src/dispatch/win16/oledisp.cpp
@@ -0,0 +1,89 @@
+/***
+*oledisp.cpp
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file contains the oledisp.dll initialization and termination code.
+*
+*Revision History:
+*
+* [00] 15-Oct-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+ASSERTDATA
+
+extern "C" {
+HINSTANCE g_hinstDLL = NULL;
+
+// non-zero if fbstp instruction works. Zero on WFW 3.11, Daytona WOW on
+// Intel, Mips, and Alpha. When zero, the instruction is a no-op and doesn't
+// pop a value from the FP stack or write to the destination address. :-(
+BOOL g_fbstpImplemented;
+extern BOOL FAR PASCAL DetectFbstpImplemented(void);
+}
+
+//---------------------------------------------------------------------------
+// Initialize library.
+// This routine is called from the DLL entry point in LIBINIT.ASM
+// which is called when the first client loads the DLL.
+//
+// NOTE: other one time initialization occurs in ctors for global objects
+//---------------------------------------------------------------------------
+extern "C" BOOL FAR PASCAL
+LibMain(HINSTANCE hinst, HANDLE segDS, UINT cbHeapSize, LPSTR lpCmdLine)
+{
+ (segDS, cbHeapSize, lpCmdLine); // UNUSED
+
+ g_hinstDLL = hinst;
+
+ // detect if fpstb instruction is implemented or not (VBA2 #3514)
+ // The rules are:
+ // Win16 w/ 80x87 - use fbstp
+ // Win16 no 80x87 - don't use fbstp - it GPFs
+ // WOW - don't use - unreliable
+ //
+ if (GetWinFlags() & WF_80x87) {
+ // we're running either on Win16 with a math coprocessor or on Mips/Alpha
+ // WOW - if on WOW, don't use fbstp
+ g_fbstpImplemented = DetectFbstpImplemented();
+ }
+
+ // register a callback function with ole2nls.dll which gets called
+ // whenever WIN.INI changes (and once at startup).
+ RegisterNLSInfoChanged((FARPROC)NLSInfoChangedHandler);
+
+ return TRUE;
+}
+
+
+//---------------------------------------------------------------------------
+// Handle exit notification from Windows.
+// This routine is called by Windows when the library is freed
+// by its last client.
+//---------------------------------------------------------------------------
+extern "C" void _fpmath(void);
+
+extern "C" int FAR PASCAL __export _WEP(BOOL fSystemExit)
+{
+ UNUSED(fSystemExit);
+
+ // unregister the callback with ole2nls.dll
+ RegisterNLSInfoChanged((FARPROC)NULL);
+
+ // NOTE: The C8 runtime does not correctly terminate the
+ // floating point emulator, so we call the termination routine
+ // ourselves below
+ //
+ _asm{
+ mov bx,2
+ call _fpmath
+ }
+
+ return 1;
+}
diff --git a/private/oleauto/src/dispatch/win32/alpha/invoke.s b/private/oleauto/src/dispatch/win32/alpha/invoke.s
new file mode 100644
index 000000000..02cc51580
--- /dev/null
+++ b/private/oleauto/src/dispatch/win32/alpha/invoke.s
@@ -0,0 +1,728 @@
+// TITLE("invoke.s for OLE Automation")
+//++
+//
+// Copyright (c) 1993 Microsoft Corporation
+//
+// Module Name:
+//
+// invoke.s
+//
+// Abstract:
+//
+// This module implements the low-level v-table based dispatching
+// support for the default implementation of IDispatch::Invoke()
+// on DEC Alpha hardware.
+//
+// Author:
+//
+// tomteng 11-2-93: Created
+//
+// Environment:
+//
+// User mode.
+//
+// Revision History:
+//
+//--
+
+#include "ksalpha.h"
+
+ .extern g_S_OK 8
+ .extern g_E_INVALIDARG 8
+
+
+// Note: the following must match the definition of VARIANT in variant.h
+
+#define VT_EMPTY 0
+#define VT_NULL 1
+#define VT_I2 2
+#define VT_I4 3
+#define VT_R4 4
+#define VT_R8 5
+#define VT_CY 6
+#define VT_DATE 7
+#define VT_BSTR 8
+#define VT_DISPATCH 9
+#define VT_ERROR 10
+#define VT_BOOL 11
+#define VT_VARIANT 12
+#define VT_UNKNOWN 13
+#define VT_MAX 14
+// 14 is unused
+// 15 is unused
+//#define VT_I1 16
+#define VT_UI1 17
+
+#define VT_BYREF 0x4000
+#define VT_ARRAY 0x2000
+#define VT_NOMODE 0x00ff
+
+
+ .struct 0
+vt: .space 2
+wReserved1: .space 2
+wReserved2: .space 2
+wReserved3: .space 2
+dw0: .space 2
+dw1: .space 2
+dw2: .space 2
+dw3: .space 2
+VariantArg:
+
+#define VARIANT_DATA_OFFSET 8 // offset to union of data
+
+
+
+ SBTTL("InvokeStdCall")
+//++
+//
+// ULONG // HRESULT
+// InvokeStdCall (
+// IN PVOID _this, // void FAR*
+// IN DWORD oVft, // unsigned int
+// IN DWORD vtReturn, // unsigned int
+// IN DWORD cActuals, // unsigned int
+// IN PVOID rgvt, // VARTYPE FAR*
+// IN PVOID rgpvarg, // VARIANTARG FAR* FAR*
+// OUT PVOID pvargResult // VARIANT FAR*
+// )
+//
+// Routine Description:
+//
+// Invoke a virtual StdCall method using the given _this pointer,
+// method index and array of parameters.
+//
+// Arguments:
+//
+// _this (a0) - Supplies a pointer to the method to invoke.
+//
+// oVft (a1) - vTable offset into _this ptr
+//
+// vtReturn (a2) - the VARTYPE of the return value.
+//
+// cActuals (a3) - count of the number of actuals.
+//
+// rgvt 4*4(sp) (a4) - array of VARTYPES describing the methods formals.
+//
+// rgpvarg 5*4(sp) (a5) - array of VARIANTARG*s, which map the actuals by
+// position.
+//
+// pvargResult 6*4(sp) - VARIANTARG containing the method return value.
+//
+// Return Value:
+//
+// v0 - g_S_OK (extern value)
+// g_E_INVALIDARG (extern value)
+//
+// Implementation Note:
+//
+// ALPHA StdCall method arguments are push on the stack left to right.
+// The stack grows downward (pushing decrements stack address). Data
+// alignment on the stack starts from arg1 upward. Callee cleans.
+//
+// Per ALPHA calling conventions, the following rules are followed:
+//
+// 1. Stack frame must be OCTAWORD (128-bits) aligned.
+//
+// 2. All arguments are push on the stack as a QWORD (64-bits).
+//
+// 3. Structures are pushed on the stack by value. They are returned in
+// the v0 register which contains the address of a hidden argument
+// (vargHiddenParm) allocated by the caller and pushed as the second
+// argument [a1] on the stack (1st argument [a0] for non-vtable
+// calls).
+//
+// 4. On vtable-based calls, _this is passed as the first argument [a0].
+//
+// 5. Six integer/floating registers [a0 - a5] & [f16 - f21] must be set
+// before calling, if used. Type and order of arguments determine the
+// registers used. (e.g., (int, float) means that a0 <- int;
+// f17 <- float)
+//
+// 6. Return values are handled as follows:
+//
+// vartype fundamental return register
+// ---------------------------------------------------
+// VT_UI1 unsigned char v0
+// VT_I2 short v0
+// VT_I4 long v0
+// VT_R4 float f0
+// VT_R8 double f0
+// VT_DATE double f0
+// VT_CY struct v0 (address of struct return)
+// VT_BSTR char FAR* v0
+// VT_UNKNOWN void FAR* v0
+// VT_DISPATCH void FAR* v0
+// VT_ERROR long v0
+// VT_BOOL short v0
+// VT_VARIANT VARIANTARG v0 (address of struct return)
+//
+//
+// NOTES: NO support for VT_ARRAY
+//
+//--
+
+
+// Stack Frame
+ .struct 0
+
+SavedS0: .space 8
+SavedS1: .space 8
+SavedSP: .space 8
+SavedRA: .space 8
+
+ .align 8
+vargHiddenParm: .space 8*4 // temporary for struct return
+
+_this: .space 8 // a0 0*8(sp)
+oVft: .space 8 // a1 1*8(sp) arg only takes 2 bytes
+vtReturn: .space 8 // a2 2*8(sp) arg only takes 2 bytes
+cActuals: .space 8 // a3 3*8(sp)
+rgvt: .space 8 // 4*8(sp)
+rgpvarg: .space 8 // 5*8(sp)
+
+StackFrameSize:
+pvargResult: .space 8 // 6*8(sp)
+
+
+ .text
+ .align 4
+ .globl InvokeStdCall
+ .ent InvokeStdCall, 0
+
+InvokeStdCall:
+ .frame sp, StackFrameSize, ra
+
+ lda sp, -StackFrameSize(sp) // Setup our stack frame
+
+ stq s0, SavedS0(sp) // Save our current s0
+ stq s1, SavedS1(sp) // Save our current s1
+ stq ra, SavedRA(sp) // Save $ra
+ stq sp, SavedSP(sp) // Save our current sp
+
+ stq a0, _this(sp) // Save
+ stq a1, oVft(sp) // all
+ stq a2, vtReturn(sp) // arg
+ stq a3, cActuals(sp) // regs
+ stq a4, rgvt(sp)
+ stq a5, rgpvarg(sp)
+
+
+ // cannot return byRef
+ //
+ mov a2, t0
+ and t0, VT_BYREF // Isolate VT_Mode bits
+ bne t0, LRetInvalidArg // Check VT_Type
+
+ // Setup arguments if any
+ //
+ mov sp, s1 // s1 = new stack pointer
+ beq a3, LSetupParms
+
+
+LCalcStackSize:
+
+ // calculate space need for pushing arguments on stack
+
+ ldq t3, rgvt(sp) // t3 = &rgvt[0]
+ mov 1, t9 // t9 = running arg count
+
+ ldq t1, vtReturn(sp) // check if struct return
+#if 0
+ and t1, VT_NOMODE
+#else
+ and t1, VT_BYREF | VT_ARRAY, t0 // Byref's aren't struct's
+ bne t0, LCalcStackLoop
+#endif
+
+ lda t0, rgfStructReturn
+ addq t0, t1, t0
+ ldl t0, 0(t0)
+ and t0, 0xff
+ beq t0, LCalcStackLoop
+
+ addq t9, 1, t9
+
+
+LCalcStackLoop:
+
+ ldl t6, (t3) // t6 = rgvt[i]
+ mov 8, t4 // t4 = default size
+
+ mov t6, t1
+ and t1, VT_NOMODE // Turn off mode bits
+ cmpeq t1, VT_UI1, t0
+ bne t0, LValidVartype1
+ cmplt t1, VT_MAX, t0
+ beq t0, LRetInvalidArg // Error if Max or above
+
+LValidVartype1:
+ addq t9, 1, t9 // bump arg count
+ cmpeq t6, VT_VARIANT, t0
+ addq t9, t0, t9 // BYVAL VARIANT bump twice
+
+ cmplt t9, 7, t0
+ bne t0, LCalcNext // Skip arguments in registers
+
+ cmpeq t6, VT_VARIANT, t0 // BYVAL VARIANT?
+ beq t0, LCalcAdd
+
+ mov 16, t4 // BYVAL VARIANT takes 16 bytes
+
+LCalcAdd:
+
+ subq s1, t4, s1 // decrement stack
+
+
+LCalcNext:
+
+ addq t3, 2, t3 // &rgvt[i++]
+ addq a3, -1, a3 // cActual--
+ bne a3, LCalcStackLoop // If more args, go again
+
+ mov s1, t0 // make sure new 0(sp)
+ and t0, 0xf // at QWORD (128-bit) boundary
+ beq t0, LSetupParms
+
+ addq s1, -8, s1 // aligned stack
+
+
+
+LSetupParms:
+
+ mov s1, s0 // s0 = temporary stack loc
+
+ ldq t2, rgpvarg(sp) // t2 = &rgpvarg[0]
+ ldq t3, rgvt(sp) // t3 = &rgvt[0]
+ ldq t4, cActuals(sp) // t4 = cActuals
+
+ addq t4, -1, t0
+ sll t0, 2
+ addq t2, t0, t8 // t8 = &rgpvarg[cArgs - 1]
+ mov zero, t9 // t9 = running argument count
+
+
+LPushThis: // this already in a0
+
+ ldq a0, _this(sp)
+ addq t9, 1, t9 // Bump up argument count
+
+
+LPushHiddenArg:
+
+ // Check if we need to return a structure, if so
+ // move the address of the vargHiddenParm as
+ // the second (hidden) argument
+ //
+
+ ldq t1, vtReturn(sp)
+#if 0
+ and t1, VT_NOMODE // Turn off mode bits
+#else
+ and t1, VT_BYREF | VT_ARRAY, t0 // Byref's aren't struct's
+ bne t0, LCheckArgs
+#endif
+
+ lda t0, rgfStructReturn // t0 = &rgfStructReturn
+ addq t0, t1, t0 // t0 = &rgfStructReturn[i]
+ ldl t0, 0(t0) // t0 = rgfStructReturn[i]
+ and t0, 0xff
+
+ beq t0, LCheckArgs // Jmp if no struc to be ret
+
+ lda a1, vargHiddenParm(sp) // Have to push an extra parm
+
+ addq t9, 1, t9 // Bump up argument count
+
+
+LCheckArgs:
+
+ beq t4, LDoCall
+
+
+LPushArgs:
+
+ ldl t5, (t2) // t5 = rgpvarg[i]
+ ldl t6, (t3) // t6 = rgvt[i]
+
+ and t6, VT_BYREF | VT_ARRAY // Isolate mode bits
+ bne t6, LPush4 // all ByRefs are sizeof(FAR*)
+
+ ldl t6, (t3) // t6 = rgvt[i]
+ and t6, VT_NOMODE // Turn off mode bits
+ cmpeq t6, VT_UI1, t0
+ bne t0, LValidVartype2
+ cmplt t6, VT_MAX, t0
+ beq t0, LRetInvalidArg // Error if Max or above
+
+LValidVartype2:
+ mov t6, t1
+ sll t1, 3 // ADDRESS offset
+ lda t0, LPushValJmpTab // Get Address of ret table
+ addq t0, t1, t0 // Get Address of ret routine
+ ldq t0, 0(t0)
+ jmp (t0) // Go execute the push code
+
+
+LPush2: // 4 bytes of data
+
+ ldl t7, dw0(t5) // Push HWORD (as 32-bit)
+ sll t7, 48, t7
+ sra t7, 48, t7
+
+ cmplt t9, 6, t0
+ bne t0, LIntReg // Pass argument in register
+
+ stq t7, 0(s0) // Save on stack
+ addq s0, 8, s0 // adjust arg loc
+ br LNextArg
+
+
+LPush4: // 4 bytes of data
+
+ ldl t7, dw0(t5) // Push 1st WORD
+
+ cmplt t9, 6, t0
+ bne t0, LIntReg // Pass argument in register
+
+ stq t7, 0(s0)
+ addq s0, 8, s0 // adjust arg loc
+ br LNextArg
+
+
+LPushR4:
+
+ lds f10, dw0(t5)
+
+ cmplt t9, 6, t0
+ bne t0, LFloatReg // Pass argument in register
+
+ sts f10, 0(s0)
+ addq s0, 8, s0 // adjust arg loc
+ br LNextArg
+
+
+LPushR8: // 8 bytes of R8 data
+
+ ldt f10, dw0(t5)
+
+ cmplt t9, 6, t0
+ bne t0, LFloatReg // Pass argument in register
+
+ stt f10, 0(s0)
+ addq s0, 8, s0 // adjust arg loc
+ br LNextArg
+
+
+LPush8: // 8 bytes of data
+
+ ldq t7, dw0(t5)
+
+ cmplt t9, 6, t0
+ bne t0, LIntReg // Pass argument in register
+
+ stq t7, 0(s0)
+ addq s0, 8, s0 // adjust arg loc
+ br LNextArg
+
+
+LPushVar: // 16 bytes of data
+
+ ldq t7, 0(t5)
+ ldq t10, 8(t5)
+
+ cmplt t9, 6, t0
+ bne t0, LPushVarReg // Pass argument in register
+
+ stq t7, 0(s0)
+ stq t10, 8(s0)
+
+ addq s0, 16, s0 // adjust arg loc
+ br LNextArg
+
+
+LPushVarReg:
+
+ mov t9, t0
+ addq t0, -1
+ mulq t0, 12
+
+ lda t1, LVPushReg
+ addq t1, t0, t0
+
+ addq t9, 2, t9 // Bump up argument count
+ jmp (t0)
+
+
+LVPushReg:
+
+ mov t7, a1
+ mov t10, a2
+ br LNextArg
+ mov t7, a2
+ mov t10, a3
+ br LNextArg
+ mov t7, a3
+ mov t10, a4
+ br LNextArg
+ mov t7, a4
+ mov t10, a5
+ br LNextArg
+ mov t7, a5
+ stq t10, 0(s0)
+ addq s0, 8, s0 // adjust arg loc
+ br LNextArg
+
+
+LIntReg: // load integer registers
+
+ mov t9, t0
+ sll t0, 3
+
+ lda t1, LIPushReg
+ addq t1, t0, t0
+
+ addq t9, 1, t9 // Bump up argument count
+ jmp (t0)
+
+
+LIPushReg:
+
+ mov t7, a0
+ br LNextArg
+ mov t7, a1
+ br LNextArg
+ mov t7, a2
+ br LNextArg
+ mov t7, a3
+ br LNextArg
+ mov t7, a4
+ br LNextArg
+ mov t7, a5
+ br LNextArg
+
+
+LFloatReg: // load floating registers
+
+ mov t9, t0
+ sll t0, 3
+
+ lda t1, LFPushReg
+ addq t1, t0, t0
+
+ addq t9, 1, t9 // Bump up argument count
+ jmp (t0)
+
+
+LFPushReg:
+
+ fmov f10, f16
+ br LNextArg
+ fmov f10, f17
+ br LNextArg
+ fmov f10, f18
+ br LNextArg
+ fmov f10, f19
+ br LNextArg
+ fmov f10, f20
+ br LNextArg
+ fmov f10, f21
+ br LNextArg
+
+
+LNextArg:
+
+ addq t2, 4, t2 // &rgpvarg[i++]
+ addq t3, 2, t3 // &rgvt[i++]
+
+ cmple t2, t8, t0
+ bne t0, LPushArgs // If more args, go again
+
+
+LDoCall:
+
+ // load the vtable offset
+ //
+ ldl t0, 0(a0) // address of vtable
+
+ ldq t1, oVft(sp) // Get the vtable offset
+ addl t0, t1, t0 // Get addr of ptr to func
+ ldl t0, (t0) // Get ptr to func in vtable
+
+
+ // call virtual member function
+ //
+ mov sp, s0 // Save SP
+ mov s1, sp
+ jsr ra, (t0) // Invoke the Idispatch func
+ mov s0, sp // Restore SP
+
+
+ // Get return argument
+ //
+
+ ldq t1, vtReturn(sp) // t1 = vtType to return
+ ldq t3, pvargResult(sp) // Get RetData Area
+ stl t1, vt(t3) // varResult->vt
+
+ mov t1, t2
+ and t2, VT_BYREF | VT_ARRAY // Check ret mode
+ bne t2, LRetPtr // If !0 -> go ret a ptr
+
+ and t1, VT_NOMODE // Turn off mode bits
+ cmpeq t1, VT_UI1, t0
+ bne t0, LValidVartype3
+ cmplt t1, VT_MAX, t0
+ beq t0, LRetInvalidArg // Error if Max or above
+
+LValidVartype3:
+ sll t1, 3 // ADDRESS offset
+ lda t2, LRetValJmpTab // Get Address of ret table
+ addq t2, t1, t2 // Get Address of ret routine
+ ldq t2, 0(t2)
+ jmp (t2) // Go execute the ret code
+
+
+LRetI4:
+LRetPtr:
+
+ stl v0, VARIANT_DATA_OFFSET(t3)
+ br LDone // Done
+
+
+
+LRetI2:
+LRetUI1:
+
+ stl v0, VARIANT_DATA_OFFSET(t3)
+ br LDone // Done
+
+
+LRetR4:
+
+ sts f0, VARIANT_DATA_OFFSET(t3) //*
+ br LDone // Done
+
+
+
+LRetR8:
+
+ stt f0, VARIANT_DATA_OFFSET(t3) //*
+ br LDone // Done
+
+
+
+LRetCy:
+
+ ldl t1, 0(v0) // cy.Lo
+ stl t1, dw0(t3)
+
+ ldl t1, 4(v0) // cy.Hi
+ stl t1, dw2(t3) //*
+
+ br LDone // Done
+
+
+LRetVar:
+ ldq t1, 0(v0) // Get 1st QWORD
+ stq t1, 0(t3) // Save it in pvArgResult
+
+ ldq t1, 8(v0) // Get 2nd QWORD
+ stq t1, 8(t3) // Store 2nd QWORD
+
+
+LDone:
+
+ lda t0, g_S_OK //*v0 = g_S_OK
+ ldl v0, (t0)
+ br ExitInvoke
+
+
+LRetInvalidArg:
+
+ lda t0, g_E_INVALIDARG // v0 = g_E_INVALIDARG
+ ldl v0, (t0)
+
+
+ExitInvoke:
+
+ ldq s0, SavedS0(sp) // Restore s0
+ ldq s1, SavedS1(sp) // Restore s1
+ ldq ra, SavedRA(sp) // Restore ra
+ ldq sp, SavedSP(sp) // Restore sp
+
+ lda sp, StackFrameSize(sp)
+ ret ra
+
+
+ .align 2
+rgfStructReturn:
+ .byte 0 // VT_EMPTY
+ .byte 0 // VT_NULL
+ .byte 0 // VT_I2
+ .byte 0 // VT_I4
+ .byte 0 // VT_R4
+ .byte 0 // VT_R8
+ .byte 1 // VT_CY
+ .byte 0 // VT_DATE
+ .byte 0 // VT_BSTR
+ .byte 0 // VT_DISPATCH
+ .byte 0 // VT_ERROR
+ .byte 0 // VT_BOOL
+ .byte 1 // VT_VARIANT
+ .byte 0 // VT_UNKNOWN
+ .byte 0 // unused
+ .byte 0 // unused
+ .byte 0 // VT_I1
+ .byte 0 // VT_UI1
+
+
+
+
+ .align 8
+LPushValJmpTab:
+ .quad LNextArg // VT_EMPTY [0]
+ .quad LPush4 // VT_NULL [4]
+ .quad LPush2 // VT_I2 [2]
+ .quad LPush4 // VT_I4 [4]
+ .quad LPushR4 // VT_R4 [4]
+ .quad LPushR8 // VT_R8 [8]
+ .quad LPush8 // VT_CY [8]
+ .quad LPushR8 // VT_DATE [8]
+ .quad LPush4 // VT_BSTR [4]
+ .quad LPush4 // VT_DISPATCH [4]
+ .quad LPush4 // VT_ERROR [4]
+ .quad LPush2 // VT_BOOL [2]
+ .quad LPushVar // VT_VARIANT [16]
+ .quad LPush4 // VT_UNKNOWN [4]
+ .quad 0 // unused
+ .quad 0 // unused
+ .quad 0 // unused (VT_I1)
+ .quad LPush2 // VT_UI1
+
+
+ .align 8
+LRetValJmpTab:
+ .quad LDone // VT_EMPTY
+ .quad LRetI4 // VT_NULL
+ .quad LRetI2 // VT_I2
+ .quad LRetI4 // VT_I4
+ .quad LRetR4 // VT_R4
+ .quad LRetR8 // VT_R8
+ .quad LRetCy // VT_CY
+ .quad LRetR8 // VT_DATE
+ .quad LRetPtr // VT_BSTR
+ .quad LRetPtr // VT_DISPATCH
+ .quad LRetI4 // VT_ERROR
+ .quad LRetI2 // VT_BOOL
+ .quad LRetVar // VT_VARIANT
+ .quad LRetPtr // VT_UNKNOWN
+ .quad 0 // unused
+ .quad 0 // unused
+ .quad 0 // unused (VT_I1)
+ .quad LRetI2 // VT_UI1
+
+
+ .end InvokeStdCall
+
+
diff --git a/private/oleauto/src/dispatch/win32/i386/invoke.asm b/private/oleauto/src/dispatch/win32/i386/invoke.asm
new file mode 100644
index 000000000..3e5dfe703
--- /dev/null
+++ b/private/oleauto/src/dispatch/win32/i386/invoke.asm
@@ -0,0 +1,832 @@
+; TITLE invoke.asm
+;***
+;invoke.asm - automatic table driven method dispatch
+;
+; Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+; Information Contained Herein Is Proprietary and Confidential.
+;
+;Purpose:
+; This file contains the low level support for the default
+; implementaion of ITypeInfo::Invoke().
+;
+;Revision History:
+;
+; [00] 1-Apr-93 tomteng: Created from win16 invoke.asm
+; [01] 2-Aug-94 barrybo: Added native Universal Method
+;
+;Implementation Notes:
+;
+;******************************************************************************
+
+ .386
+ .MODEL flat, C
+
+ OPTION CASEMAP:NONE
+
+
+extern g_S_OK:DWORD
+extern g_E_INVALIDARG:DWORD
+ProxyMethod PROTO STDCALL pProx:DWORD, n:DWORD, args:DWORD, pbStackCleanup:DWORD
+
+
+;; Note: the following must match the definitions from dispatch.h
+;;
+VT_EMPTY equ 0
+VT_NULL equ 1
+VT_I2 equ 2
+VT_I4 equ 3
+VT_R4 equ 4
+VT_R8 equ 5
+VT_CY equ 6
+VT_DATE equ 7
+VT_BSTR equ 8
+VT_DISPATCH equ 9
+VT_ERROR equ 10
+VT_BOOL equ 11
+VT_VARIANT equ 12
+VT_UNKNOWN equ 13
+
+VT_MAX equ 14
+;; 14 is unused
+;; 15 is unused
+;VT_I1 equ 16
+VT_UI1 equ 17
+
+
+;; Note: the following must match the definition of VARIANT in dispatch.h
+;;
+VARIANTARG STRUCT
+ vt DW ?
+ wReserved1 DW ?
+ wReserved2 DW ?
+ wReserved3 DW ?
+ dw0 DW ?
+ dw1 DW ?
+ dw2 DW ?
+ dw3 DW ?
+VARIANTARG ENDS
+
+;; offset of the data from the beginning of the struct
+VARIANT_DATA_OFFSET equ 8
+
+
+ .CONST
+
+;; ammout of data to be pushed for the corresponding VARTYPE
+;;
+
+rgcbVtSize BYTE 0 ; VT_EMPTY
+ BYTE 4 ; VT_NULL
+ BYTE 2 ; VT_I2
+ BYTE 4 ; VT_I4
+ BYTE 4 ; VT_R4
+ BYTE 8 ; VT_R8
+ BYTE 8 ; VT_CY
+ BYTE 8 ; VT_DATE
+ BYTE 4 ; VT_BSTR
+ BYTE 4 ; VT_DISPATCH
+ BYTE 4 ; VT_ERROR
+ BYTE 2 ; VT_BOOL
+ BYTE 16 ; VT_VARIANT
+ BYTE 4 ; VT_UNKNOWN
+ BYTE 0 ; 14 is unused
+ BYTE 0 ; 15 is unused
+ BYTE 2 ; VT_I1
+ BYTE 2 ; VT_UI1
+
+
+rgfStructReturn BYTE 0 ; VT_EMPTY
+ BYTE 0 ; VT_NULL
+ BYTE 0 ; VT_I2
+ BYTE 0 ; VT_I4
+ BYTE 0 ; VT_R4
+ BYTE 0 ; VT_R8
+ BYTE 1 ; VT_CY ; For C++ only!
+ BYTE 0 ; VT_DATE
+ BYTE 0 ; VT_BSTR
+ BYTE 0 ; VT_DISPATCH
+ BYTE 0 ; VT_ERROR
+ BYTE 0 ; VT_BOOL
+ BYTE 1 ; VT_VARIANT
+ BYTE 0 ; VT_UNKNOWN
+ BYTE 0 ; 14 is unused
+ BYTE 0 ; 15 is unused
+ BYTE 0 ; VT_I1
+ BYTE 0 ; VT_UI1
+
+ .CODE
+
+;***
+;InvokeCdecl
+;
+;extern "C" SCODE CDECL
+;InvokeCdecl
+; void FAR* _this,
+; unsigned int oVft,
+; unsigned int vtReturn,
+; unsigned int cActuals,
+; VARTYPE FAR* rgvt,
+; VARIANTARG FAR* rgpvarg,
+; VARIANTARG FAR* pvargResult)
+;
+;Purpose:
+; see InvokeStdCall
+;
+;Entry:
+; see InvokeStdCall
+;
+;Exit:
+; see InvokeStdCall
+;
+;Uses:
+; esi, edi
+;
+;Preserves:
+; UNDONE
+;
+;***********************************************************************
+
+InvokeCdecl PROC C PUBLIC USES esi edi ebx,
+ _this : PTR,
+ oVft : DWORD,
+ vtReturn : DWORD,
+ cActuals : DWORD,
+ rgvt : PTR,
+ rgpvarg : PTR,
+ pvargResult : PTR
+
+LOCAL savedSP : DWORD,
+ vargHiddenParam : VARIANTARG
+
+ mov savedSP, esp
+
+ ;; cannot return byRef
+ ;;
+ mov ebx, vtReturn
+ test bh, 040h
+ jnz LRetInvalidArg
+
+ ;; load number of arguments passed
+ ;;
+ mov eax, cActuals
+ cmp eax, 0
+ jz LDoCall
+
+ ;; edi = &rgpvarg[cActuals-1]
+ ;;
+ dec eax
+ mov edi, eax
+ shl edi, 2 ; (cArgs-1)*sizeof(FAR*)
+ add edi, DWORD PTR rgpvarg
+
+ ;; edx = &rgvt[cActuals-1]
+ ;;
+ mov edx, eax
+ shl edx, 1 ; ((cArgs-1)*sizeof(WORD))
+ add edx, DWORD PTR rgvt
+
+LArgsTop:
+
+ ;; bx = rgvt[i]
+ ;;
+ movzx ebx, WORD PTR [edx]
+
+ ;; load the VARIANTARG* in preparation for pushing
+ ;;
+ mov esi, [edi]
+
+ test bh, 060h ; VT_BYREF | VT_ARRAY
+ jnz LPush4 ; all ByRefs are sizeof(FAR*)
+
+ ;; lookup size of the param in rgcbVtSize table
+ ;;
+ and bh, 00h ; ~(mode bits)
+ mov al, BYTE PTR rgcbVtSize[bx]
+
+ cmp al, 0
+ jl LRetInvalidArg
+ jz LNextArg
+ sub al, 2
+ jz LPush2
+ sub al, 2
+ jz LPush4
+ sub al, 4
+ jz LPush8
+ sub al, 8
+ jz LPush16
+ jmp LRetInvalidArg
+
+ Align 2
+LPush16: ; push the entire variant
+ push DWORD PTR [esi+12]
+ push DWORD PTR [esi+8]
+ push DWORD PTR [esi+4]
+ push DWORD PTR [esi]
+ jmp LNextArg
+
+ Align 2
+LPush8: ; 8 bytes of data
+ push (VARIANTARG PTR [esi]).dw3
+ push (VARIANTARG PTR [esi]).dw2
+
+LPush4: ; 4 bytes of data
+ push (VARIANTARG PTR [esi]).dw1
+ push (VARIANTARG PTR [esi]).dw0
+ jmp LNextArg
+
+LPush2: ; 2 bytes of data
+ mov ax, (VARIANTARG PTR [esi]).dw0
+ push eax
+
+LNextArg:
+ sub edx, 2 ; sizeof(VARTYPE)
+ sub edi, 4 ; sizeof(VARIANTARG FAR*)
+ cmp edi, DWORD PTR rgpvarg
+ jae LArgsTop
+
+LDoCall:
+ ;; if its a structure return, we must push a 'hidden' argument
+ ;;
+ mov ebx, vtReturn
+IF 0
+ and bh, 00h ; ~(mode bits)
+ELSE
+ test bh, 060h ; VT_BYREF | VT_ARRAY
+ jnz LPushThis ; no hidden parm if byref or
+ ; array return
+ENDIF
+ mov al, BYTE PTR rgfStructReturn[bx]
+ cmp al, 0
+ jz LPushThis
+
+ ;; push the address of the struct return hidden param
+ ;;
+ ;; Note: the hidparam is passed as a FAR* because we
+ ;; explicitly declare all of our structs FAR.
+ ;;
+ lea eax, vargHiddenParam;
+ push eax
+
+LPushThis:
+
+ ;; push the this pointer.
+ ;;
+ mov ebx, _this
+ push ebx
+
+ ;; load the vtable offset
+ ;;
+ mov esi, oVft
+
+ mov ebx, [ebx] ; @ vtable*
+ call dWORD PTR [ebx][esi]
+ mov esp, savedSP
+
+ ;; CONSIDER: verify that the callee adjusted the stack the way
+ ;; we expected. something like,
+ ;;
+ ;; if(sp != savedSP){
+ ;; sp = savedSP;
+ ;; return DISP_E_SomeError
+ ;; }
+ ;;
+
+ ;; Grab the return value.
+ ;; We are going to grab the value based on the VARTYPE in
+ ;; the given vtReturn. This VARTYPE is used as a description
+ ;; of the return value, not a desired target type. ie, no
+ ;; coercions are performed. See the function header for a
+ ;; description of the Pascal member function return value
+ ;; convention.
+ ;;
+
+
+ mov edi, pvargResult
+
+ mov ebx, vtReturn
+ mov (VARIANTARG PTR [edi]).vt, bx
+
+ test bh, 060h ; VT_BYREF | VT_ARRAY
+ jnz LRetPtr
+
+ ; Assert((bh & VT_ARRAY) == 0);
+
+ cmp bx, VT_UI1
+ je ValidVartype
+ cmp bx, VT_MAX
+ jae LRetInvalidArg
+
+ValidVartype:
+ shl bx, 2
+ jmp LRetValJmpTabCdecl[bx]
+
+ Align 2
+LRetValJmpTabCdecl LABEL dword
+ DWORD LDone ; VT_EMPTY
+ DWORD LRetI4 ; VT_NULL
+ DWORD LRetI2 ; VT_I2
+ DWORD LRetI4 ; VT_I4
+ DWORD LRetR4 ; VT_R4
+ DWORD LRetR8 ; VT_R8
+ DWORD LRetCy ; VT_CY
+ DWORD LRetR8 ; VT_DATE
+ DWORD LRetPtr ; VT_BSTR
+ DWORD LRetPtr ; VT_DISPATCH
+ DWORD LRetI4 ; VT_ERROR
+ DWORD LRetI2 ; VT_BOOL
+ DWORD LRetVar ; VT_VARIANT
+ DWORD LRetPtr ; VT_UNKNOWN
+ DWORD LRetInvalidArg ; unused
+ DWORD LRetInvalidArg ; unused
+ DWORD LRetInvalidArg ; VT_I1
+ DWORD LRetUI1 ; VT_UI1
+
+ Align 2
+LRetVar:
+ mov esi, eax
+ movsd
+ movsd
+ movsd
+ movsd
+ jmp LDone
+
+
+ Align 2
+LRetR4:
+ add edi, VARIANT_DATA_OFFSET
+ fstp DWORD PTR [edi]
+ jmp LDone
+
+ Align 2
+LRetR8:
+ add edi, VARIANT_DATA_OFFSET
+ fstp QWORD PTR [edi]
+ jmp LDone
+
+ Align 2
+LRetCy:
+ add edi, VARIANT_DATA_OFFSET
+IF 1 ; CY return in C++ is via hidden parm
+ mov edx, eax
+ mov ebx, DWORD PTR [edx]
+ mov DWORD PTR [edi], ebx
+ mov ebx, DWORD PTR 4[edx]
+ mov DWORD PTR [edi+4], ebx
+ELSE ; CY return in C is via registers
+ mov DWORD PTR [edi], eax
+ mov DWORD PTR [edi+4], edx
+ENDIF
+ jmp LDone
+
+ Align 2
+LRetI4:
+LRetPtr:
+ add edi, VARIANT_DATA_OFFSET
+ mov DWORD PTR [edi], eax
+ jmp LDone
+
+ Align 2
+LRetI2:
+LRetUI1:
+ mov (VARIANTARG PTR [edi]).dw0, ax
+
+LDone:
+ mov eax, DWORD PTR g_S_OK
+ ret
+
+
+LRetInvalidArg:
+ mov eax, DWORD PTR g_E_INVALIDARG
+ mov esp, savedSP
+ ret
+
+InvokeCdecl ENDP
+
+
+
+;***
+;InvokeStdCall
+;
+;extern "C" SCODE
+;InvokeStdCall(
+; void FAR* pvMethod,
+; unsigned int oVft,
+; unsigned int vtReturn,
+; unsigned int cActuals,
+; VARTYPE FAR* rgvt,
+; VARIANTARG FAR* rgpvarg,
+; VARIANTARG FAR* pvargResult)
+;
+;Purpose:
+;
+; Invoke a virtual StdCall method using the given this pointer,
+; method index and array of parameters.
+;
+; The StdCall member function calling convention (MSC v8.0)
+; --------------------------------------------------------
+; - arguments pushed right to left
+; - callee clean (ie, the callee adjusts the sp on return)
+; - model specific this* always pushed last
+;
+; return values are handled as follows,
+;
+; vartype fundamental return location
+; ------------------------------------------------
+; VT_UI1 unsigned char al
+; VT_I2 short ax
+; VT_I4 long eax
+; VT_R4 float float-return(1)
+; VT_R8 double float-return
+; VT_DATE double float-return
+; VT_CY struct struct-return(2)
+; VT_BSTR char FAR* eax
+; VT_UNKNOWN void FAR* eax
+; VT_DISPATCH void FAR* eax
+; VT_ERROR long eax
+; VT_BOOL short ax
+; VT_VARIANT VARIANTARG struct-return
+; VT_WBSTR WCHAR FAR* eax
+; VT_DISPATCHW void FAR* eax
+;
+; 1. floating point returns
+;
+; Floating point values are returned in a caller allocated buffer.
+; a *near* pointer to this buffer is passed as a hidden parameter,
+; and is pushed as the last (ie, rightmost) parameter. This means
+; that it is always located immediately before the 'this' pointer.
+;
+; A model specific pointer to this caller allocated buffer is
+; passed back in ax[:dx]. All this means is that the callee returns
+; the address we passed in as the hidden param, and sticks SS into
+; DX if the callee is large model (see following note).
+;
+; Note: the compiler *assumes* that this caller allocated buffer
+; is SS relative (hence the reason it only passes a near pointer),
+; so the following code is careful to ensure this.
+;
+; 2. structure returns
+;
+; Structures are returned in a caller allocated buffer, and are
+; handled exactly the same as float returns except that the pointer
+; to the buffer is always pushed as the first (leftmost) param. This
+; is opposite of the location it is passed for float returns (I
+; have no idea why there different).
+;
+;
+; Limitations & assumptions
+; -------------------------
+; Only supports far calls.
+;
+;Entry:
+; pvMethod = ptr to the method to invoke
+; cArgs = count of the number of actuals
+; rgvt = array of VARTYPES describing the methods formals
+; rgpvarg = array of VARIANTARG*s, which map the actuals by position
+; vtReturn = the VARTYPE of the return value
+;
+;Exit:
+; pvargResult = VARIANTARG containing the method return value
+;
+;Uses:
+; bx, si, di
+;
+;Preserves:
+;
+;
+;***********************************************************************
+InvokeStdCall PROC C PUBLIC USES esi edi ebx,
+ _this : PTR,
+ oVft : DWORD,
+ vtReturn : DWORD,
+ cActuals : DWORD,
+ rgvt : PTR,
+ rgpvarg : PTR,
+ pvargResult : PTR
+
+LOCAL savedSP : DWORD,
+ vargHiddenParam : VARIANTARG
+
+
+ mov savedSP, esp
+
+ ;; cannot return byRef
+ ;;
+ mov ebx, vtReturn
+ test bh, 040h
+ jnz LRetInvalidArg
+
+ ;; load number of arguments passed
+ ;;
+ mov eax, cActuals
+ cmp eax, 0
+ jz LDoCall
+
+ ;; edi = &rgpvarg[cActuals-1]
+ ;;
+ dec eax
+ mov edi, eax
+ shl edi, 2 ; (cArgs-1)*sizeof(FAR*)
+ add edi, DWORD PTR rgpvarg
+
+ ;; edx = &rgvt[cActuals-1]
+ ;;
+ mov edx, eax
+ shl edx, 1 ; ((cArgs-1)*sizeof(WORD))
+ add edx, DWORD PTR rgvt
+
+LArgsTop:
+
+ ;; bx = rgvt[i]
+ ;;
+ movzx ebx, WORD PTR [edx]
+
+ ;; load the VARIANTARG* in preparation for pushing
+ ;;
+ mov esi, [edi]
+
+ test bh, 060h ; VT_BYREF | VT_ARRAY
+ jnz LPush4 ; all ByRefs are sizeof(FAR*)
+
+ ;; lookup size of the param in rgcbVtSize table
+ ;;
+ and bh, 00h ; ~(mode bits)
+ mov al, BYTE PTR rgcbVtSize[bx]
+
+ cmp al, 0
+ jl LRetInvalidArg
+ jz LNextArg
+ sub al, 2
+ jz LPush2
+ sub al, 2
+ jz LPush4
+ sub al, 4
+ jz LPush8
+ sub al, 8
+ jz LPush16
+ jmp LRetInvalidArg
+
+ Align 2
+LPush16: ; push the entire variant
+ push DWORD PTR [esi+12]
+ push DWORD PTR [esi+8]
+ push DWORD PTR [esi+4]
+ push DWORD PTR [esi]
+ jmp LNextArg
+
+ Align 2
+LPush8: ; 8 bytes of data
+ push (VARIANTARG PTR [esi]).dw3
+ push (VARIANTARG PTR [esi]).dw2
+
+LPush4: ; 4 bytes of data
+ push (VARIANTARG PTR [esi]).dw1
+ push (VARIANTARG PTR [esi]).dw0
+ jmp LNextArg
+
+LPush2: ; 2 bytes of data
+ mov ax, (VARIANTARG PTR [esi]).dw0
+ push eax
+
+LNextArg:
+ sub edx, 2 ; sizeof(VARTYPE)
+ sub edi, 4 ; sizeof(VARIANTARG FAR*)
+ cmp edi, DWORD PTR rgpvarg
+ jae LArgsTop
+
+LDoCall:
+ ;; if its a structure return, we must push a 'hidden' argument
+ ;;
+ mov ebx, vtReturn
+
+IF 0
+ and bh, 00h ; ~(mode bits)
+ELSE
+ test bh, 060h ; VT_BYREF | VT_ARRAY
+ jnz LPushThis ; no hidden parm if byref or
+ ; array return
+ENDIF
+
+ mov al, BYTE PTR rgfStructReturn[bx]
+ cmp al, 0
+ jz LPushThis
+
+ ;; push the address of the struct return hidden param
+ ;;
+ ;; Note: the hidparam is passed as a FAR* because we
+ ;; explicitly declare all of our structs FAR.
+ ;;
+ lea eax, vargHiddenParam;
+ push eax
+
+LPushThis:
+
+ ;; push the this pointer.
+ ;;
+ mov ebx, _this
+ push ebx
+
+ ;; load the vtable offset
+ ;;
+ mov esi, oVft
+
+ mov ebx, [ebx] ; @ vtable*
+ call dWORD PTR [ebx][esi]
+
+ ;; CONSIDER: verify that the callee adjusted the stack the way
+ ;; we expected. something like,
+ ;;
+ ;; if(sp != savedSP){
+ ;; sp = savedSP;
+ ;; return DISP_E_SomeError
+ ;; }
+ ;;
+
+ ;; Grab the return value.
+ ;; We are going to grab the value based on the VARTYPE in
+ ;; the given vtReturn. This VARTYPE is used as a description
+ ;; of the return value, not a desired target type. ie, no
+ ;; coercions are performed. See the function header for a
+ ;; description of the Pascal member function return value
+ ;; convention.
+ ;;
+
+
+ mov edi, pvargResult
+
+ mov ebx, vtReturn
+ mov (VARIANTARG PTR [edi]).vt, bx
+
+ test bh, 060h ; VT_BYREF | VT_ARRAY
+ jnz LRetPtr
+
+ ; Assert((bh & VT_ARRAY) == 0);
+
+ cmp bx, VT_UI1
+ je ValidVartype
+ cmp bx, VT_MAX
+ jae LRetInvalidArg
+
+ValidVartype:
+ shl bx, 2
+ jmp LRetValJmpTabStdCall[bx]
+
+ Align 2
+LRetValJmpTabStdCall LABEL dword
+ DWORD LDone ; VT_EMPTY
+ DWORD LRetI4 ; VT_NULL
+ DWORD LRetI2 ; VT_I2
+ DWORD LRetI4 ; VT_I4
+ DWORD LRetR4 ; VT_R4
+ DWORD LRetR8 ; VT_R8
+ DWORD LRetCy ; VT_CY
+ DWORD LRetR8 ; VT_DATE
+ DWORD LRetPtr ; VT_BSTR
+ DWORD LRetPtr ; VT_DISPATCH
+ DWORD LRetI4 ; VT_ERROR
+ DWORD LRetI2 ; VT_BOOL
+ DWORD LRetVar ; VT_VARIANT
+ DWORD LRetPtr ; VT_UNKNOWN
+ DWORD LRetInvalidArg ; unused
+ DWORD LRetInvalidArg ; unused
+ DWORD LRetInvalidArg ; VT_I1
+ DWORD LRetUI1 ; VT_UI1
+
+ Align 2
+LRetVar:
+ mov esi, eax
+ movsd
+ movsd
+ movsd
+ movsd
+ jmp LDone
+
+
+ Align 2
+LRetR4:
+ add edi, VARIANT_DATA_OFFSET
+ fstp DWORD PTR [edi]
+ jmp LDone
+
+ Align 2
+LRetR8:
+ add edi, VARIANT_DATA_OFFSET
+ fstp QWORD PTR [edi]
+ jmp LDone
+
+ Align 2
+LRetCy:
+ add edi, VARIANT_DATA_OFFSET
+IF 1 ; CY return in C++ is via hidden parm
+ mov edx, eax
+ mov ebx, DWORD PTR [edx]
+ mov DWORD PTR [edi], ebx
+ mov ebx, DWORD PTR 4[edx]
+ mov DWORD PTR [edi+4], ebx
+ELSE ; CY return in C is via registers
+ mov DWORD PTR [edi], eax
+ mov DWORD PTR [edi+4], edx
+ENDIF
+ jmp LDone
+
+ Align 2
+LRetI4:
+LRetPtr:
+ add edi, VARIANT_DATA_OFFSET
+ mov DWORD PTR [edi], eax
+ jmp LDone
+
+ Align 2
+LRetI2:
+LRetUI1:
+ mov (VARIANTARG PTR [edi]).dw0, ax
+
+LDone:
+ mov eax, DWORD PTR g_S_OK
+ ret
+
+
+LRetInvalidArg:
+ mov eax, DWORD PTR g_E_INVALIDARG
+ mov esp, savedSP
+ ret
+
+InvokeStdCall ENDP
+
+
+
+
+;***
+;Universal Method
+;
+;extern "C" _stdcall HRESULT
+;UMx( // UM3 upto UM512
+; CProxUniv FAR* pProx,
+; ...)
+;
+;Purpose:
+;
+; The Win32 Universal Method is called with _stdcall calling convention
+; (callee cleans up), but the UM takes a variable number of arguments,
+; so it must decide at runtime how much stack to clean up and hence cannot
+; be written in C.
+;
+;
+;Entry:
+; pProx = ptr to CProxUniv instance
+; ... = argumnents to the method (decoded in CProxUniv)
+;
+;Exit:
+; returns HRESULT = result of the method call
+;
+;Uses:
+;
+;Preserves:
+;
+;
+;***********************************************************************
+UMTemplate MACRO X:REQ
+PUBLIC @CatStr(UM,X)
+@CatStr(UM,X):
+ mov edx, X
+ jmp lblUmCommon
+ENDM ; UMTemplate
+
+; Generate 510 UMxxx functions, starting with UM2
+Count = 3
+WHILE Count LE 512
+ UMTemplate %Count
+ Count=Count+1
+ENDM
+
+PUBLIC lblUmCommon
+lblUmCommon:
+ ; at entry, EDX = Method index, stack contains params for the
+ ; method
+
+ push ebp
+ mov ebp, esp
+ push eax ; LOCAL: int cbStackCleanup
+
+ pProx EQU DWORD PTR [ebp+08h]
+ pEllipses EQU DWORD PTR [ebp+0ch]
+ cbStackCleanup EQU DWORD PTR [ebp-04h]
+
+ ; va_start(args, pProx)
+ lea eax, pEllipses ; eax = args
+
+ mov ecx, esp ; push &cbStackCleanup
+ push ecx
+ push eax ; push args
+ push edx ; push method index
+ push pProx ; push pProx
+ call ProxyMethod ; ProxyMethod(pProx,X,args,&cbStackCleanup)
+ ; eax = HRESULT
+
+ mov edx, cbStackCleanup
+ leave ; clean up the local var, esp and ebp
+ pop ecx ; pop the return address
+ add esp, edx ; do the _stdcall argument cleanup
+ jmp ecx ; then return
+; end lblUmCommon
+
+END
diff --git a/private/oleauto/src/dispatch/win32/i386/oleconva.asm b/private/oleauto/src/dispatch/win32/i386/oleconva.asm
new file mode 100644
index 000000000..77468b69d
--- /dev/null
+++ b/private/oleauto/src/dispatch/win32/i386/oleconva.asm
@@ -0,0 +1,675 @@
+;***
+;oleconva.a - Machine-specific conversion helpers
+;
+; Copyright (C) 1993, Microsoft Corporation. All Rights Reserved.
+; Information Contained Herein Is Proprietary and Confidential.
+;
+;Purpose:
+; Type conversion helper functions.
+;
+;Revision History:
+;[nnn] dd-mmm-yy alias___ Comment
+;
+; [] 18-Mar-93 timp Module created.
+;[001] 31-May-93 bradlo Added overflow checking.
+;
+;******************************************************************************
+
+
+ .386
+ .MODEL FLAT, STDCALL
+
+ ; Since this code will be linked with C code, the symbols
+ ; should be case sensitive.
+
+ OPTION CASEMAP:NONE
+
+ extern ReportOverflow@0:far
+
+; HRESULT error return code
+DISP_E_OVERFLOW equ 8002000aH
+
+ .CODE
+
+
+; max and min floating point values that can fit in a currency
+; scale by 10,000
+g_dblMaxPosCy dq 9.223372036854775807e+18
+g_dblMaxNegCy dq -9.223372036854775808e+18
+
+
+; floating point <-> currency scaling factor
+CYFACTOR equ 10000
+g_wCyFactor dw CYFACTOR
+g_fltCyFactor dd 10000.0
+
+TenTo18 dt 1.0E18
+
+g_CwStd dw 137fH ;Mask all errors, 64-bit, round near
+CwTrunc dw 1F7fH ;Mask all errors, 64-bit, chop
+
+FPERR equ 0DH ;Overflow, zero divide, invalid errs
+
+
+SETUP87 MACRO CwSave, cw:=<g_CwStd>
+ fstcw CwSave ;;Save existing environment
+ fldcw cw ;;Use our own CW
+ ENDM
+
+
+RESTORE87 MACRO CwSave
+ fclex ;;Prevent 486 bug on FLDCW
+ fldcw CwSave ;;Restore original CW
+ ENDM
+
+
+CHKERR87 MACRO CwSave, ErrLoc
+ fstsw ax ;;Get error flags
+ fclex ;;Don't let caller see errors
+ test al,FPERR ;;See if any errors
+ fldcw CwSave ;;Restore original CW
+ jnz ErrLoc ;;Go handle error if bit set
+ ENDM
+
+
+;******************************************************************************
+;
+;PUBLIC HRESULT ErrCyFromI2(short sIn, CY *pcyOut)
+;
+;Purpose:
+; Convert Integer to Currency
+;
+;Entry:
+; sIn = Integer to convert
+;
+;Exit:
+; return value = HRESULT
+;
+;*****
+
+ErrCyFromI2 PROC STDCALL PUBLIC, sIn:SWORD, pcyOut:PTR QWORD
+
+ movsx eax,sIn
+ imul eax,CYFACTOR ;Scale the I2
+ cdq ;Extend through edx
+ mov ecx,pcyOut
+ mov [ecx],eax
+ mov [ecx+4],edx
+
+ sub eax,eax ;NOERROR
+ ret
+
+ErrCyFromI2 ENDP
+
+
+;******************************************************************************
+;
+;PUBLIC HRESULT ErrCyFromI4(long lIn, CY *pcyOut)
+;
+;Purpose:
+; Convert Long to Currency
+;
+;Entry:
+; lIn = Long to convert
+;
+;Exit:
+; return value = HRESULT
+;
+;*****
+
+ErrCyFromI4 PROC STDCALL PUBLIC, lIn:SDWORD, pcyOut:PTR QWORD
+
+ mov eax,lIn
+ mov edx,CYFACTOR
+;Multiply by immediate leaves only a 32-bit result in eax.
+;The following instruction leaves a 64-bit result in edx:eax.
+ imul edx ;Scale the I4
+
+ mov ecx,pcyOut
+ mov [ecx],eax
+ mov [ecx+4],edx
+
+ sub eax,eax ;NOERROR
+ ret
+
+ErrCyFromI4 ENDP
+
+
+;******************************************************************************
+;
+;PRIVATE BOOL CkOvflCy
+;
+;Purpose:
+; Check to see if the given floating point value will fit in a currency.
+;
+;Entry:
+; st(0) = the floating point value to check
+;
+;Exit:
+; return value = BOOL, TRUE if the value will overflow
+;
+;*****
+
+CkOvflCy PROC
+
+ fld st(0)
+ fcom g_dblMaxPosCy
+ fnstsw ax
+ sahf
+ jae LOvfl
+
+ fcom g_dblMaxNegCy
+ fnstsw ax
+ sahf
+ jbe LOvfl
+
+ fstp st(0)
+ sub eax,eax
+ ret
+
+LOvfl:
+ fstp st(0)
+ mov eax,1
+ ret
+
+CkOvflCy ENDP
+
+;******************************************************************************
+;
+;PUBLIC HRESULT ErrCyFromR4(float FAR* pfltIn, CY *pcyOut)
+;
+;Purpose:
+; Convert Single to Currency
+;
+;Entry:
+; pfltIn = Single to convert
+; pcyOut = pointer to Currency to hold result
+;
+;Exit:
+; return value = HRESULT
+;
+;*****
+
+ErrCyFromR4 PROC STDCALL PUBLIC, pfltIn:PTR REAL4, pcyOut:PTR QWORD
+
+ mov eax,pfltIn
+ fld dword ptr [eax] ;Load R4
+ fimul g_wCyFactor ;Scale it
+
+ call CkOvflCy
+ or eax,eax
+ jnz LOvfl
+
+
+ mov eax,pcyOut
+ fistp qword ptr [eax] ;Store CY result
+
+ sub eax,eax ;NOERROR
+ ret
+
+LOvfl:
+ fstp st(0)
+ ;call ReportOverflow@0 ;DISP_E_OVERFLOW
+ mov eax,DISP_E_OVERFLOW
+ ret
+
+ErrCyFromR4 ENDP
+
+
+;******************************************************************************
+;
+;PUBLIC HRESULT ErrCyFromR8(double FAR* pdblIn, CY *pcyOut)
+;
+;Purpose:
+; Convert Double to Currency
+;
+;Entry:
+; pdblIn = Double to convert
+; pcyOut = pointer to Currency to hold result
+;
+;Exit:
+; return value = HRESULT
+;
+;*****
+
+ErrCyFromR8 PROC STDCALL PUBLIC, pdblIn:PTR REAL8, pcyOut:PTR QWORD
+
+ mov eax,pdblIn
+ fld qword ptr [eax]
+ fimul g_wCyFactor ;Scale it
+
+ call CkOvflCy
+ or eax,eax
+ jnz LOvfl
+
+
+ mov eax,pcyOut
+ fistp qword ptr [eax] ;Store CY result
+
+ sub eax,eax ;NOERROR
+ ret
+
+LOvfl:
+ fstp st(0)
+ ;call ReportOverflow@0 ;DISP_E_OVERFLOW
+ mov eax,DISP_E_OVERFLOW
+ ret
+
+ErrCyFromR8 ENDP
+
+
+;******************************************************************************
+;
+;PUBLIC HRESULT ErrI2FromCy(CY cyIn, short *psOut)
+;
+;Purpose:
+; Convert Currency to Integer
+;
+;Entry:
+; cyIn = Currency to convert
+; psOut = pointer to Integer to hold result
+;
+;Exit:
+; return value = HRESULT
+;
+;*****
+
+ErrI2FromCy PROC STDCALL PUBLIC, cyIn:QWORD, psOut:PTR SWORD
+
+LOCAL cyTmp:QWORD
+
+ fild cyIn ;Load CY
+ fidiv g_wCyFactor ;Remov scaling
+ fistp cyTmp
+
+ mov eax,dword ptr cyTmp
+ cwde ;sign extend ax->eax
+ cdq ;sign extend eax->edx
+ cmp eax,dword ptr cyTmp
+ jne LOvfl
+ cmp edx,dword ptr cyTmp+4
+ jne LOvfl
+
+ mov ecx,psOut
+ mov word ptr [ecx],ax
+
+ sub eax,eax ;NOERROR
+ ret
+
+LOvfl:
+ ;call ReportOverflow@0 ;DISP_E_OVERFLOW
+ mov eax,DISP_E_OVERFLOW
+ ret
+
+ErrI2FromCy ENDP
+
+
+;******************************************************************************
+;
+;PUBLIC HRESULT ErrI4FromCy(CY cyIn, long *plOut)
+;
+;Purpose:
+; Convert Currency to Long
+;
+;Entry:
+; cyIn = Currency to convert
+; plOut = pointer to Long to hold result
+;
+;Exit:
+; return value = HRESULT
+;
+;*****
+
+ErrI4FromCy PROC STDCALL PUBLIC, cyIn:QWORD, plOut:PTR SDWORD
+
+LOCAL cyTmp:QWORD
+
+ fild cyIn ;Load CY
+ fidiv g_wCyFactor ;Remov scaling
+ fistp cyTmp
+
+ mov eax,dword ptr cyTmp
+ cdq
+ cmp edx,dword ptr cyTmp+4
+ jne LOvfl
+
+ mov edx,plOut
+ mov [edx],eax
+
+ sub eax,eax ;NOERROR
+ ret
+
+LOvfl:
+ ;call ReportOverflow@0 ;DISP_E_OVERFLOW
+ mov eax,DISP_E_OVERFLOW
+ ret
+
+ErrI4FromCy ENDP
+
+
+;******************************************************************************
+;
+;PUBLIC HRESULT ErrR4FromCy(CY cyIn, float *pfltOut)
+;
+;Purpose:
+; Convert Currency to Single
+;
+;Entry:
+; cyIn = Currency to convert
+;
+;Exit:
+; return value = HRESULT
+;
+;*****
+ErrR4FromCy PROC STDCALL PUBLIC, cyIn:QWORD, pfltOut:PTR REAL4
+
+ fild cyIn ;Load CY
+ fidiv g_wCyFactor ;Remov scaling
+ mov eax,pfltOut
+ fstp dword ptr [eax]
+ ;fwait
+
+ sub eax,eax ;NOERROR
+ ret
+
+ErrR4FromCy ENDP
+
+
+;******************************************************************************
+;
+;PUBLIC HRESULT ErrR8FromCy(CY cyIn, double *pdblOut)
+;
+;Purpose:
+; Convert Currency to Double
+;
+;Entry:
+; cyIn = Currency to convert
+;
+;Exit:
+; return value = HRESULT.
+;
+;*****
+
+ErrR8FromCy PROC STDCALL PUBLIC, cyIn:QWORD, pdblOut:PTR REAL8
+
+ fild cyIn ;Load CY
+ fidiv g_wCyFactor ;Remov scaling
+ mov eax,pdblOut
+ fstp qword ptr [eax]
+ ;fwait
+
+ sub eax,eax ;NOERROR
+ ret
+
+ErrR8FromCy ENDP
+
+
+;******************************************************************************
+;
+;PUBLIC HRESULT ErrMultCyI4(CY cyIn, long lIn, CY *pcyOut);
+;
+;Purpose:
+; Multiply Currency by Long with Currency result
+;
+;Entry:
+; cyIn = Currency multiplicand
+; lIn = Long multiplier
+; pcyOut = Pointer to result Currency location
+;
+;Outputs:
+; return value = HRESULT
+;
+;*****
+
+ErrMultCyI4 PROC STDCALL PUBLIC, cyIn:QWORD, lIn:DWORD, pcyOut:PTR QWORD
+
+if 0 ; - don't use FP unit
+
+ fild cyIn
+ fild lIn
+ fmul ;Product
+ mov eax,pcyOut ;Get pointer to result location
+ fistp qword ptr es:[eax] ;Save result
+
+ sub eax,eax ;UNDONE: no error
+
+else ;0 - don't use FP unit
+
+;This routine uses Booth's algorithm for a twos-complement signed
+;multiply. This algorithm says to compute the product with unsigned
+;arithmetic. Then correct the result by looking at the signs of the
+;original operands: for each operand that is negative, subtract the
+;other operand from the high half of the product. (The mathematical
+;proof is a fun 15-minute exercise. Go for it.)
+
+;Note: multiplications are optimized by having operand with the most
+;leading zeros in eax.
+ mov eax,lIn ;Get I4
+ mul dword ptr cyIn ;Multiply by low half of CY
+ push eax
+ xchg ecx,edx ;Save high result in ecx
+ mov eax,dword ptr cyIn+4 ;Get high half of CY
+ mul lIn
+ add eax,ecx ;Combine partial products
+ adc edx,0
+;Result in edx:eax:[sp] needs Booth's sign correction
+ cmp byte ptr cyIn+7,0 ;Is cyIn positive?
+ jns PosCy
+ sub edx,lIn
+PosCy:
+ cmp byte ptr lIn+3,0 ;Is lIn positive?
+ jns PosI4
+ sub eax,dword ptr cyIn
+ sbb edx,dword ptr cyIn+4
+PosI4:
+;Signed result in edx:eax:[sp]. Check for overflow.
+ mov ecx,edx ;Save highest dword of product
+ cdq ;Sign-extend eax
+ cmp ecx,edx ;Is it just the sign extension of eax?
+ pop ecx ;Get low dword of product
+ jnz LOvfl
+;64-bit product in eax:ecx
+ mov edx,pcyOut ;Get result ptr
+ mov [edx],ecx ;Save result
+ mov [edx+4],eax
+
+endif ;don't use FP unit
+
+ sub eax,eax ;NOERROR
+ ret
+
+LOvfl:
+ ;call ReportOverflow@0
+ mov eax,DISP_E_OVERFLOW
+ ret
+
+ErrMultCyI4 ENDP
+
+
+;******************************************************************************
+;
+;void PASCAL DoFbstp(CY *pcyIn, DIGARY *pdigOut);
+;
+;Purpose:
+; Do x87 FBSTP instruction on currency type. Check to see if CY is too
+; big first and compute 19th digit separately.
+;
+;Entry:
+; pcyIn = Type currency to convert
+; pdigOut = pointer to result packed BCD digits
+;
+;Outputs:
+; None.
+;
+;*****
+
+;This constant is the upper bits of the 64-bit integer representation
+;of 10^18. CY values at or above this will overflow FBSTP.
+
+MAX18CY equ 0DE0B6B3H
+
+DoFbstp proc stdcall public, pcyIn:ptr qword, pdigOut:ptr tbyte
+
+LOCAL cw:WORD, iTemp:DWORD
+
+ mov ecx,pcyIn
+ fild qword ptr [ecx]
+ mov eax,[ecx+4]
+ mov ecx,pdigOut
+ cmp eax,MAX18CY
+ jge Get19
+ cmp eax,-MAX18CY
+ jle Get19
+ fbstp tbyte ptr [ecx]
+ fwait
+ ret
+
+Get19:
+ SETUP87 cw,CwTrunc
+ fld TenTo18
+ fld st(1) ;Copy input
+ fdiv st,st(1) ;Compute last digit
+ frndint ;Chop to integer
+ fist iTemp ;Get value of MSD
+ fmul
+ fsub ;Remove MSD
+ fbstp tbyte ptr [ecx]
+ mov eax,[iTemp]
+;Take absolute value
+ cdq ;Extend sign through edx
+ xor eax,edx ;NOT if negative
+ sub eax,edx ;INC if negative
+ RESTORE87 cw
+ and dl,80h ;set sign bit in AL
+ or al, dl
+ mov [ecx+9],al ;Set 19th digit
+ ret
+
+DoFbstp endp
+
+
+;******************************************************************************
+;
+;int ConvFloatToAscii(double dblIn, DIGARY *pdigOut)
+;
+;Purpose:
+; Convert double to packed BCD digit string plus base-10 exponent.
+;
+;Entry:
+; dblIn = Type double to convert
+; pdigOut = pointer to result packed BCD digits
+;
+;Outputs:
+; return value = power of 10 of the 18-digit integer.
+;
+;*****
+
+ConvFloatToAscii PROC STDCALL PUBLIC, dblIn:QWORD, pdigOut:PTR
+
+LOCAL cw:WORD, temp:TBYTE
+
+ SETUP87 cw
+ fld dblIn ;Put double on x87
+
+;What we want now is equivalent to FXTRACT, but it's faster just
+;to store the tbyte and look at it directly. The reasone we don't
+;use the double's exponent is in case it's denormal.
+;
+ fld st ;Make a copy
+ fstp temp
+ movzx eax,word ptr [temp+8] ;Get word with exponent
+ and ah,not 80H ;Zero out sign
+
+;2^59 = 5.7E17 (18 digits). A 59-bit integer could be 2^59 - 1.
+;Our goal now is to find a power of ten to multiply by that will give us
+;a 55- to 59-bit integer. We'll target 58 bits so the multiply can carry
+;to 59, and truncate while figuring the power so we never exceed it.
+
+ sub eax,16382 + 58 ;Remove bias and 58 bits
+
+;Find power of 10 by multiplying base 2 exponent by log10(2)
+
+ imul eax,19728 ;log10(2) * 2^16 = .30103 * 65536
+ add eax,0FFFFH ;Round up
+ sar eax,16 ;Only use high half
+ call MulPower10 ;ax preserved
+ mov ebx,pdigOut
+ fbstp tbyte ptr [ebx]
+ RESTORE87 cw
+ ret
+
+ConvFloatToAscii endp
+
+
+MulPower10:
+;eax = negative of power of 10 required
+ or eax,eax
+ jz NoPower
+ push ebx
+ mov edx,eax
+ mov ecx,offset tNegPower
+ jns GetPower
+ mov ecx,offset tPosPower
+ neg edx
+GetPower:
+ mov ebx,edx
+ and ebx,0FH ;Use low 4 exponent bits
+ jz NoMul
+ dec ebx
+ imul ebx,size tbyte ;Index into table of powers
+ fld tbyte ptr [ebx+ecx]
+ fmul
+NoMul:
+ add ecx,15 * size tbyte ;Advance to next table
+ shr edx,4 ;Get next exponent bits
+ jnz GetPower
+ pop ebx
+NoPower:
+ ret
+
+
+;******************************************************************************
+;
+;Power of 10 tables
+;
+;Two tables: one positive powers, the other negative. Each table is broken
+;into three groups: 10^1 to 10^15 by 1, 10^16 to 10^240 by 16, and
+;(theoretically) 10^256 to ... by 256. However, because the maximum value
+;is about 10^309, only one entry in the last group is needed (10^256), so
+;it is slipped on to the end of the previous group.
+
+
+SetPower10 macro Power
+ dt 1.0E&Power
+ ENDM
+
+
+tPosPower label Tbyte
+
+Power = 1
+ REPT 15
+ SetPower10 %Power
+Power = Power + 1
+ ENDM
+
+ REPT 16
+ SetPower10 %Power
+Power = Power + 16
+ ENDM
+
+
+tNegPower label Tbyte
+
+Power = 1
+ REPT 15
+ SetPower10 -%Power
+Power = Power + 1
+ ENDM
+
+ REPT 16
+ SetPower10 -%Power
+Power = Power + 16
+ ENDM
+
+
+ END
diff --git a/private/oleauto/src/dispatch/win32/mips/invoke.s b/private/oleauto/src/dispatch/win32/mips/invoke.s
new file mode 100644
index 000000000..c68cb9220
--- /dev/null
+++ b/private/oleauto/src/dispatch/win32/mips/invoke.s
@@ -0,0 +1,725 @@
+// TITLE("invoke.s for OLE Automation")
+//++
+//
+// Copyright (c) 1993 Microsoft Corporation
+//
+// Module Name:
+//
+// invoke.s
+//
+// Abstract:
+//
+// This module implements the low-level dispatching support for
+// the default implementation of IDispatch::Invoke().
+//
+// Author:
+//
+// tomteng 12-Sep-93 Derived from initial cut by HoiV (Cario)
+//
+// Environment:
+//
+// User mode.
+//
+// Revision History:
+//
+//--
+
+#include "ksmips.h"
+
+ .extern g_S_OK 4
+ .extern g_E_INVALIDARG 4
+
+
+// Note: the following must match the definition of VARIANT in variant.h
+
+#define VT_EMPTY 0
+#define VT_NULL 1
+#define VT_I2 2
+#define VT_I4 3
+#define VT_R4 4
+#define VT_R8 5
+#define VT_CY 6
+#define VT_DATE 7
+#define VT_BSTR 8
+#define VT_DISPATCH 9
+#define VT_ERROR 10
+#define VT_BOOL 11
+#define VT_VARIANT 12
+#define VT_UNKNOWN 13
+#define VT_MAX 14
+// 14 is unused
+// 15 is unused
+//#define VT_I1 16
+#define VT_UI1 17
+
+#define VT_BYREF 0x4000
+#define VT_ARRAY 0x2000
+#define VT_NOMODE 0x00ff
+
+
+ .struct 0
+vt: .space 2
+wReserved1: .space 2
+wReserved2: .space 2
+wReserved3: .space 2
+dw0: .space 2
+dw1: .space 2
+dw2: .space 2
+dw3: .space 2
+VariantArg:
+
+#define VARIANT_DATA_OFFSET 8 // offset to union of data
+
+
+ .text
+ .align 2
+rgcbVtStackSize:
+ .byte 0 // VT_EMPTY
+ .byte 4 // VT_NULL
+ .byte 4 // VT_I2
+ .byte 4 // VT_I4
+ .byte 4 // VT_R4
+ .byte 8 // VT_R8
+ .byte 8 // VT_CY
+ .byte 8 // VT_DATE
+ .byte 4 // VT_BSTR
+ .byte 4 // VT_DISPATCH
+ .byte 4 // VT_ERROR
+ .byte 4 // VT_BOOL
+ .byte 16 // VT_VARIANT
+ .byte 4 // VT_UNKNOWN
+ .byte 0 // unused
+ .byte 0 // unused
+ .byte 4 // VT_I1
+ .byte 4 // VT_UI1
+
+
+ .align 2
+rgfStructReturn:
+ .byte 0 // VT_EMPTY
+ .byte 0 // VT_NULL
+ .byte 0 // VT_I2
+ .byte 0 // VT_I4
+ .byte 0 // VT_R4
+ .byte 0 // VT_R8
+ .byte 1 // VT_CY
+ .byte 0 // VT_DATE
+ .byte 0 // VT_BSTR
+ .byte 0 // VT_DISPATCH
+ .byte 0 // VT_ERROR
+ .byte 0 // VT_BOOL
+ .byte 1 // VT_VARIANT
+ .byte 0 // VT_UNKNOWN
+ .byte 0 // unused
+ .byte 0 // unused
+ .byte 0 // VT_I1
+ .byte 0 // VT_UI1
+
+
+ .align 4
+LPushValJmpTab:
+ .word LNextArg // VT_EMPTY [0]
+ .word LPush4 // VT_NULL [4]
+ .word LPush2 // VT_I2 [2]
+ .word LPush4 // VT_I4 [4]
+ .word LPush4 // VT_R4 [4]
+ .word LPushR8 // VT_R8 [8]
+ .word LPush8 // VT_CY [8]
+ .word LPushR8 // VT_DATE [8]
+ .word LPush4 // VT_BSTR [4]
+ .word LPush4 // VT_DISPATCH [4]
+ .word LPush4 // VT_ERROR [4]
+ .word LPush2 // VT_BOOL [2]
+ .word LPushVar // VT_VARIANT [16]
+ .word LPush4 // VT_UNKNOWN [4]
+ .word 0 // unused
+ .word 0 // unused
+ .word LPush2 // VT_I1 [2]
+ .word LPush2 // VT_UI1 [2]
+
+ .align 4
+LRetValJmpTab:
+ .word LDone // VT_EMPTY
+ .word LRetI4 // VT_NULL
+ .word LRetI2 // VT_I2
+ .word LRetI4 // VT_I4
+ .word LRetR4 // VT_R4
+ .word LRetR8 // VT_R8
+ .word LRetCy // VT_CY
+ .word LRetR8 // VT_DATE
+ .word LRetPtr // VT_BSTR
+ .word LRetPtr // VT_DISPATCH
+ .word LRetI4 // VT_ERROR
+ .word LRetI2 // VT_BOOL
+ .word LRetVar // VT_VARIANT
+ .word LRetPtr // VT_UNKNOWN
+ .word 0 // unused
+ .word 0 // unused
+ .word 0 // unused (VT_I1)
+ .word LRetUI1 // VT_UI1
+
+
+
+
+ SBTTL("InvokeStdCall")
+//++
+//
+// ULONG // HRESULT
+// InvokeStdCall (
+// IN PVOID _this, // void FAR*
+// IN DWORD oVft, // unsigned int
+// IN DWORD vtReturn, // unsigned int
+// IN DWORD cActuals, // unsigned int
+// IN PVOID rgvt, // VARTYPE FAR*
+// IN PVOID rgpvarg, // VARIANTARG FAR* FAR*
+// OUT PVOID pvargResult // VARIANT FAR*
+// )
+//
+// Routine Description:
+//
+// Invoke a virtual StdCall method using the given _this pointer,
+// method index and array of parameters.
+//
+// Arguments:
+//
+// _this (a0) - Supplies a pointer to the method to invoke.
+//
+// oVft (a1) - vTable offset into _this ptr
+//
+// vtReturn (a2) - the VARTYPE of the return value.
+//
+// cActuals (a3) - count of the number of actuals.
+//
+// rgvt 4*4(sp) - array of VARTYPES describing the methods formals.
+//
+// rgpvarg 5*4(sp) - array of VARIANTARG*s, which map the actuals by
+// position.
+//
+// pvargResult 6*4(sp) - VARIANTARG containing the method return value.
+//
+// Return Value:
+//
+// v0 - g_S_OK (extern value)
+// g_E_INVALIDARG (extern value)
+//
+// Implementation Note:
+//
+// MIPS StdCall method arguments are push on the stack left to right.
+// The stack grows downward (pushing decrements stack address). Data
+// alignment on the stack starts from arg1 upward. Callee cleans.
+//
+// Per MIPS calling conventions used by the Centuar compiler (mcl),
+// the following rules are followed:
+//
+// 1. Stack frame must be DWORD (8-bytes) aligned. The argument
+// build part of the stack frame must be a minimum of 16 bytes,
+// even if no arguments are passed.
+//
+// 2. VT_I2 (16-bits) are push on the stack as a WORD (32-bits).
+//
+// 3. Double precision floating point numbers (VT_R8, VT_DATE)
+// must be push on the stack on a DWORD boundary.
+//
+// 4. Structures are pushed on the stack by value. They need to be
+// DWORD aligned on the stack if the struct contains a R8 type
+// (e.g., VARIANT is DWORD aligned, where as, CY isn't).
+// They are returned in the v0 register which contains the address
+// of a hidden argument (vargHiddenParm) allocated by the caller and
+// pushed as the second argument [a1] on the stack (1st argument [a0]
+// for non-vtable calls).
+//
+// 5. On vtable-based calls, _this is passed as the first argument [a0].
+//
+// 6. Registers [a0 - a3] must be set before calling, if used.
+// Some registers aren't used either when there are less than
+// 4 arguments or the space between 0(sp) to 16(sp) is used
+// for filler because of a double precision argument alignment.
+//
+// 7. Registers [f12, f14] are set before calling, if used.
+// It isn't used for vtable-based dispatching.
+//
+// 8. Return values are handled as follows:
+//
+// vartype fundamental return register
+// ---------------------------------------------------
+// VT_UI1 unsigned char a0
+// VT_I2 short a0
+// VT_I4 long a0
+// VT_R4 float f0
+// VT_R8 double f0
+// VT_DATE double f0
+// VT_CY struct a0 (address of struct return)
+// VT_BSTR char FAR* a0
+// VT_UNKNOWN void FAR* a0
+// VT_DISPATCH void FAR* a0
+// VT_ERROR long a0
+// VT_BOOL short a0
+// VT_VARIANT VARIANTARG a0 (address of struct return)
+//
+//
+// NOTES: NO support for VT_ARRAY
+//
+//--
+
+
+// Stack Frame
+ .struct 0
+
+SavedS0: .space 4
+SavedS1: .space 4
+SavedSP: .space 4
+SavedRA: .space 4
+
+vargHiddenParm: .space 8*4 // temporary for struct return
+
+StackFrameLength:
+
+_this: .space 4 // a0 0*4(sp)
+oVft: .space 4 // a1 1*4(sp) arg only takes 2 bytes
+vtReturn: .space 4 // a2 2*4(sp) arg only takes 2 bytes
+cActuals: .space 4 // a3 3*4(sp)
+rgvt: .space 4 // 4*4(sp)
+rgpvarg: .space 4 // 5*4(sp)
+pvargResult: .space 4 // 6*4(sp)
+
+
+ .text
+ .align 4
+ .globl InvokeStdCall
+ .ent InvokeStdCall, 0
+
+InvokeStdCall:
+
+ .set noreorder
+ .set at
+
+ subu sp, StackFrameLength // Setup our stack frame
+
+ .frame sp, StackFrameLength, ra
+
+ sw ra, SavedRA(sp) // Save $ra
+ sw s0, SavedS0(sp) // Save our current s1
+ sw s1, SavedS1(sp) // Save our current s1
+ sw sp, SavedSP(sp) // Save our current sp
+
+ sw a0, _this(sp) // Save
+ sw a1, oVft(sp) // all
+ sw a2, vtReturn(sp) // arg
+ sw a3, cActuals(sp) // regs
+
+
+ // cannot return byRef
+ //
+ andi a2, VT_BYREF // Isolate VT_Mode bits
+ bne a2, zero, LRetInvalidArg // Check VT_Type
+ nop //*
+
+
+ // Setup arguments if any
+ //
+ bne a3, zero, LCalcStackSize
+ nop
+
+
+ // if no arguments, still adjust stack per MIPS convention
+ // and call directly
+ addiu s1, sp, -16 // s1 = adjusted stack pointer
+ b LPushThis
+ move s0, s1 // s0 = arg loc
+
+
+LCalcStackSize:
+
+ // calculate space need for pushing arguments on stack
+
+ lw t3, rgvt(sp) // t3 = &rgvt[0]
+
+ li s1, 4 // add 4 for _this
+
+ lhu t1, vtReturn(sp) // add 4 if struct return
+ nop
+
+#if 0
+ andi t1, VT_NOMODE
+#else
+ andi t0, t1, VT_BYREF | VT_ARRAY // Isolate mode bits
+ bne t0, zero, LCalcStackLoop // ByRefs don't return structs
+ nop
+#endif
+ la t0, rgfStructReturn
+ add t0, t0, t1
+ lbu t0, 0(t0)
+ nop
+ beq t0, zero, LCalcStackLoop
+ nop
+ addiu s1, s1, 4
+
+
+LCalcStackLoop:
+
+ lhu t6, (t3) // t6 = rgvt[i]
+ nop
+
+ andi t0, t6, VT_BYREF | VT_ARRAY // Isolate mode bits
+ bne t0, zero, LCalcAdd // all ByRefs are sizeof(FAR*)
+ li t1, 4
+
+ andi t6, VT_NOMODE // Turn off mode bits
+ beq t6, VT_UI1, LValidVartype1
+ bge t6, VT_MAX, LRetInvalidArg // Error if Max or above
+ nop
+
+LValidVartype1:
+ la t0, rgcbVtStackSize
+ add t0, t0, t6
+ lbu t1, (t0) // t1 = rgcbVtSize[i]
+
+ beq t6, VT_R8, LAddFiller // Special Alignment for R8
+ nop
+ beq t6, VT_DATE, LAddFiller
+ nop
+ b LCalcAdd
+ nop
+
+
+LAddFiller:
+
+ move t0, s1 // check DWORD boundary
+ andi t0, 0x7
+ beq t0, zero, LCalcAdd
+ nop
+
+ addiu s1, s1, 4 // aligned stack
+
+
+LCalcAdd:
+
+ add s1, s1, t1 // increment stack size
+
+ addiu t3, t3, 2 // &rgvt[i++]
+ addiu a3, a3, -1 // cActual--
+ bne a3, zero, LCalcStackLoop // If more args, go again
+ nop
+
+ move t0, s1 // make sure new 0(sp)
+ andi t0, 0x7 // at DWORD boundary
+ beq t0, zero, LSetupParms
+ nop
+
+ addiu s1, s1, 4 // aligned stack
+
+
+LSetupParms:
+
+ neg s1
+ add s1, sp, s1 // s1 = adjusted stack pointer
+ move s0, s1 // s0 = arg stack loc
+
+ lw a3, cActuals(sp) // a3 = cActuals
+ lw t2, rgpvarg(sp) // t2 = &rgpvarg[0]
+ lw t3, rgvt(sp) // t3 = &rgvt[0]
+ addiu t0, a3, -1
+ sll t0, 2
+ nop
+ addu t9, t2, t0 // t9 = &rgpvarg[cArgs - 1]
+
+
+
+LPushThis:
+
+ lw t1, _this(sp)
+ nop
+ sw t1, 0(s1)
+ addiu s0, s0, 4 // adjust arg loc
+
+
+LPushHiddenArg:
+
+ // Check if we need to return a structure, if so
+ // move the address of the vargHiddenParm as
+ // the second (hidden) argument
+ //
+
+ lhu t1, vtReturn(sp)
+ nop // ********** FILL ***********
+#if 0
+ andi t1, VT_NOMODE // Turn off mode bits
+#else
+ andi t0, t1, VT_BYREF | VT_ARRAY // Isolate mode bits
+ bne t0, zero, LCheckArgs // ByRefs don't return structs
+ nop
+#endif
+
+ la t0, rgfStructReturn // t0 = &rgfStructReturn
+ add t0, t0, t1 // t0 = &rgfStructReturn[i]
+ lbu t0, 0(t0) // t0 = rgfStructReturn[i]
+ nop // ********** FILL ***********
+
+ beq t0, zero, LCheckArgs // Jmp if no struc to be ret
+ nop //*
+
+ la t1, vargHiddenParm(sp) // Have to push an extra parm
+ sw t1, 4(s1)
+ addiu s0, s0, 4 // adjust arg loc
+
+LCheckArgs:
+
+ beq a3, zero, LDoCall
+ nop
+
+LPushArgs:
+
+ lw t5, (t2) // t5 = rgpvarg[i]
+ lhu t6, (t3) // t6 = rgvt[i]
+ nop // ********** FILL ***********
+
+ andi t6, t6, VT_BYREF | VT_ARRAY // Isolate mode bits
+ bne t6, zero, LPush4 // all ByRefs are sizeof(FAR*)
+ nop // ********** FILL ***********
+
+ lhu t6, (t3) // t6 = rgvt[i]
+ nop // ********** FILL ***********
+ andi t6, VT_NOMODE // Turn off mode bits
+ beq t6, VT_UI1, LValidVartype2
+ bge t6, VT_MAX, LRetInvalidArg // Error if Max or above
+ nop
+
+LValidVartype2:
+ move t1, t6
+ sll t1, 2 // WORD offset
+ la t0, LPushValJmpTab // Get Address of ret table
+ addu t0, t1, t0 // Get Address of ret routine
+ lw t0, 0(t0)
+ nop // ********** FILL ***********
+ j t0 // Go execute the push code
+ nop
+
+ b LRetInvalidArg // Invalid arg if still here
+ nop //*
+
+
+LPushVar: // 16 bytes of data
+
+ move t1, s0
+ andi t1, 0x7
+ beq t1, zero, LAlignedVar
+ nop
+
+ addiu s0, s0, 4 // aligned stack
+
+LAlignedVar:
+
+ lw t1, 0(t5) // Push 1st WORD
+ nop // ********** FILL ***********
+ sw t1, 0(s0)
+
+ lw t1, 4(t5) // Push 2nd WORD
+ nop // ********** FILL ***********
+ sw t1, 4(s0)
+
+ lw t1, 8(t5) // Push 3rd WORD
+ nop // ********** FILL ***********
+ sw t1, 8(s0)
+
+ lw t1, 12(t5) // Push 4rd WORD
+ nop // ********** FILL ***********
+ sw t1, 12(s0) //*
+
+ b LNextArg
+ addiu s0, s0, 16 // adjust arg loc
+
+
+LPushR8: // 8 bytes of R8 data
+
+ move t1, s0
+ andi t1, 0x7
+ beq t1, zero, LAlignedR8
+ nop
+
+ addiu s0, s0, 4 // aligned stack
+
+LAlignedR8:
+
+ l.d f16, dw0(t5)
+ nop
+ s.d f16, 0(s0)
+
+ b LNextArg
+ addiu s0, s0, 8 // adjust arg loc
+
+
+LPush8: // 8 bytes of R8 data
+
+ lw t1, dw0(t5) // Push 1st WORD
+ nop // ********** FILL ***********
+ sw t1, 0(s0)
+
+ lw t1, dw2(t5) // Push 2nd WORD
+ nop
+ sw t1, 4(s0) //*
+
+ b LNextArg
+ addiu s0, s0, 8 // adjust arg loc
+
+
+LPush4: // 4 bytes of data
+
+ lw t1, dw0(t5) // Push 1st WORD
+ nop
+ sw t1, 0(s0)
+
+ addiu s0, s0, 4 // adjust arg loc
+ b LNextArg
+ nop
+
+
+LPush2: // 4 bytes of data
+
+ lh t1, dw0(t5) // Push HWORD (as 32-bit)
+ nop
+ sw t1, 0(s0)
+
+ b LNextArg
+ addiu s0, s0, 4 // adjust arg loc
+
+
+LNextArg:
+ addiu t2, t2, 4 // &rgpvarg[i++]
+ addiu t3, t3, 2 // &rgvt[i++]
+ ble t2, t9, LPushArgs // If more args, go again
+ nop
+
+
+LDoCall:
+
+ // load registers
+ //
+ lw a0 , 0(s1) // Set a0-a3
+ lw a1, 4(s1)
+ lw a2, 8(s1)
+ lw a3, 12(s1)
+
+
+ // load the vtable offset
+ //
+ lw t0, _this(sp) // this
+ nop // ********** FILL ***********
+ lw t0, 0(t0) // address of vtable
+
+ lw t1, oVft(sp) // Get the vtable offset
+ nop // ********** FILL ***********
+ addu t0, t0, t1 // Get addr of ptr to func
+ lw t0, (t0) // Get ptr to func in vtable
+
+
+ // call virtual member function
+ //
+ addiu s0, sp, 0 // s0 = sp
+ jal t0 // Invoke the Idispatch func
+ addiu sp, s1, 0 // sp = new sp
+ addiu sp, s0, 0 // Restore our SP
+
+
+ // Get return argument
+ //
+
+ lhu t1, vtReturn(sp) // t1 = vtType to return
+ lw t3, pvargResult(sp) // Get RetData Area
+ nop // ********** FILL ***********
+ sh t1, vt(t3) // varResult->vt
+
+ andi t2, t1, VT_BYREF | VT_ARRAY // Check ret mode
+ bne t2, zero, LRetPtr // If !0 -> go ret a ptr
+ nop //*
+
+ andi t1, VT_NOMODE // Turn off mode bits
+ beq t1, VT_UI1, LValidVartype3
+ bge t1, VT_MAX, LRetInvalidArg // Error if Max or above
+ nop //*
+
+LValidVartype3:
+ sll t1, 2 // WORD offset
+ la t2, LRetValJmpTab // Get Address of ret table
+ addu t2, t1, t2 // Get Address of ret routine
+ lw t2, 0(t2)
+ nop // ********** FILL ***********
+ j t2 // Go execute the ret code
+ nop
+
+LRetVar:
+ lw t1, 0(v0) // Get 1st DWORD
+ nop // ********** FILL ***********
+ sw t1, 0(t3) // Save it in pvArgResult
+
+ lw t1, 4(v0) // Get 2nd DWORD
+ nop // ********** FILL ***********
+ sw t1, 4(t3) // Store 2nd DWORD
+
+ lw t1, 8(v0) // Get 3rd DWORD
+ nop // ********** FILL ***********
+ sw t1, 8(t3) // Store 3rd DWORD
+
+ lw t1, 12(v0) // Get 4th DWORD
+
+
+ b LDone // Done
+ sw t1, 12(t3) //*Store 4th DWORD
+
+
+LRetR4:
+ addiu t3, t3, VARIANT_DATA_OFFSET // Bump saved area
+ b LDone // Done
+ swc1 f0, 0(t3) //*
+
+
+LRetR8:
+ addiu t3, t3, VARIANT_DATA_OFFSET // Bump saved area
+ b LDone // Done
+ sdc1 f0, 0(t3) //*
+
+
+LRetCy:
+ addiu t3, t3, VARIANT_DATA_OFFSET // Bump saved area
+
+ lw t1, 0(v0) // cy.Lo
+ nop // ********** FILL ***********
+ sw t1, 0(t3)
+
+ lw t1, 4(v0) // cy.Hi
+
+ b LDone // Done
+ sw t1, 4(t3) //*
+
+
+LRetI4:
+LRetPtr:
+ addiu t3, t3, VARIANT_DATA_OFFSET // Bump saved area
+ b LDone // Done
+ sw v0, 0(t3) //*
+
+
+LRetUI1:
+LRetI2:
+ sh v0, dw0(t3)
+
+LDone:
+ la t0, g_S_OK //*v0 = g_S_OK
+ b ExitInvoke
+ lw v0, 0(t0)
+
+
+LRetInvalidArg:
+ la t0, g_E_INVALIDARG // v0 = g_E_INVALIDARG
+ lw v0, 0(t0)
+
+ExitInvoke:
+ lw s0, SavedS0(sp) // Restore s0
+ lw s1, SavedS1(sp) // Restore s1
+ lw ra, SavedRA(sp) // reload ra
+ lw sp, SavedSP(sp) // Restore sp to be sure
+ nop // ********** FILL ***********
+ addu sp, StackFrameLength
+ j ra // jump back to parent routine
+ nop
+
+ .end InvokeStdCall
diff --git a/private/oleauto/src/dispatch/win32/mips/invtest.cpp b/private/oleauto/src/dispatch/win32/mips/invtest.cpp
new file mode 100644
index 000000000..7add928e4
--- /dev/null
+++ b/private/oleauto/src/dispatch/win32/mips/invtest.cpp
@@ -0,0 +1,413 @@
+#define CALLCONV __stdcall
+
+#include "invtest.h"
+
+class Foo
+{
+ public:
+ virtual void empty();
+ virtual short i2(short, short*);
+ virtual long i4(short, long, long*);
+ virtual float r4(short, long, float, float, float*);
+ virtual float r4x(float, float, float*);
+ virtual double r8(short, long, float, double, double, double*);
+ virtual double r8x(double, double, double*);
+ virtual double r8x2(short, float, double);
+ virtual VARIANT_BOOL bool(short, long, float, double, VARIANT_BOOL);
+ virtual SCODE scode(short, long, float, double, VARIANT_BOOL, SCODE);
+ virtual CY cy(short, long, float, double, VARIANT_BOOL, SCODE, CY, CY*);
+ virtual CY cyx(CY, CY*);
+ virtual CY cyx2(short, CY);
+ virtual void cyx3(CY);
+ virtual DATE date(short, long, float, double, VARIANT_BOOL,
+ SCODE, CY, DATE, DATE*);
+ virtual BSTR bstr(short, long, float, double, VARIANT_BOOL,
+ SCODE, CY, DATE, BSTR, BSTR*);
+ virtual IUnknown* interface(short, long, float, double, VARIANT_BOOL,
+ SCODE, CY, DATE, BSTR, IUnknown*, IUnknown**);
+ virtual VARIANT variant(short, long, float, double, VARIANT_BOOL,
+ SCODE, CY, DATE, BSTR, IUnknown*, VARIANT, VARIANT*);
+ virtual VARIANT variantx(VARIANT, VARIANT*);
+ virtual VARIANT variantx2(short, VARIANT);
+};
+
+void Foo::empty()
+{
+ int i, i2;
+ i += 100;
+ i2 = 200;
+}
+
+short Foo::i2(short i, short* i2)
+{
+ i += 100;
+ *i2 = 200;
+ return i;
+}
+
+
+long Foo::i4(short i, long l, long* l2)
+{
+ i += 100;
+ l += 2000;
+ *l2 = 5000;
+ return l;
+}
+
+
+float Foo::r4(short i, long l, float f, float f2, float* f3)
+{
+ i += 100;
+ l += 2000;
+ f += 3000.345;
+ f2 += 34232.43242;
+ *f3 = 5432.232;
+ return f;
+}
+
+float Foo::r4x(float f, float f2, float* f3)
+{
+ f += 3000.345;
+ f2 += 34232.43242;
+ *f3 = 5432.232;
+ return f;
+}
+
+
+double Foo::r8(short i, long l, float f, double d, double d2, double* d3)
+{
+ i += 100;
+ l += 2000;
+ f += 3000.345;
+ d += 4000.888;
+ d2 += 8000.333;
+ *d3 = 5000.0;
+ return d;
+}
+
+double Foo::r8x(double d, double d2, double* d3)
+{
+ d += 4000.888;
+ d2 += 8000.333;
+ *d3 = 5000.0;
+ return d;
+}
+
+double Foo::r8x2(short i, float f, double d)
+{
+ i += 100;
+ f += 3000.345;
+ d += 4000.888;
+ return d;
+}
+
+
+VARIANT_BOOL Foo::bool(short i, long l, float f, double d, VARIANT_BOOL b)
+{
+ i += 100;
+ l += 2000;
+ f += 3000.345;
+ d += 4000.888;
+ b = b ? 0 : 1;
+ return b;
+}
+
+SCODE Foo::scode(short i, long l, float f, double d, VARIANT_BOOL b, SCODE s)
+{
+ i += 100;
+ l += 2000;
+ f += 3000.345;
+ d += 4000.888;
+ b = 1;
+ s = 0x80001;
+ return s;
+}
+
+CY Foo::cy(short i, long l, float f, double d, VARIANT_BOOL b, SCODE s,
+ CY c, CY* c2)
+{
+ i += 100;
+ l += 2000;
+ f += 3000.345;
+ d += 4000.888;
+ b = 1;
+ s = 0x80001;
+ c.Lo = 10;
+ c.Hi = 20;
+ c2->Lo = 30;
+ c2->Hi = 40;
+ return c;
+}
+
+CY Foo::cyx(CY c, CY* c2)
+{
+ c.Lo = 10;
+ c.Hi = 20;
+ c2->Lo = 30;
+ c2->Hi = 40;
+ return c;
+}
+
+CY Foo::cyx2(short i, CY c)
+{
+ i += 100;
+ c.Lo = 10;
+ c.Hi = 20;
+ return c;
+}
+
+
+void Foo::cyx3(CY c)
+{
+ c.Lo = 10;
+ c.Hi = 20;
+}
+
+
+DATE Foo::date(short i, long l, float f, double d, VARIANT_BOOL b, SCODE s,
+ CY c, DATE date, DATE* date2)
+{
+ i += 100;
+ l += 2000;
+ f += 3000.345;
+ d += 4000.888;
+ b = 1;
+ s = 0x80001;
+ c.Lo = 10;
+ c.Hi = 20;
+ date += 10.34340;
+ *date2 = 23232.01;
+ return date;
+}
+
+BSTR Foo::bstr(short i, long l, float f, double d, VARIANT_BOOL b, SCODE s,
+ CY c, DATE date, BSTR bstr, BSTR* bstr2)
+{
+ i += 100;
+ l += 2000;
+ f += 3000.345;
+ d += 4000.888;
+ b = 1;
+ s = 0x80001;
+ c.Lo = 10;
+ c.Hi = 20;
+ date += 10.34340;
+ bstr = "bar";
+ *bstr2 = "foo";
+ return bstr;
+}
+
+IUnknown* Foo::interface(short i, long l, float f, double d,
+ VARIANT_BOOL b, SCODE s, CY c,
+ DATE date, BSTR bstr,
+ IUnknown* punk, IUnknown** punk2)
+{
+ i += 100;
+ l += 2000;
+ f += 3000.345;
+ d += 4000.888;
+ b = 1;
+ s = 0x80001;
+ c.Lo = 10;
+ c.Hi = 20;
+ date += 10.34340;
+ bstr = "bar";
+ punk = (IUnknown*) this;
+ *punk2 = (IUnknown*) 0;
+ return punk;
+}
+
+
+VARIANT Foo::variant(short i, long l, float f, double d,
+ VARIANT_BOOL b, SCODE s, CY c,
+ DATE date, BSTR bstr, IUnknown* punk,
+ VARIANT v, VARIANT* v2)
+{
+ i += 100;
+ l += 2000;
+ f += 3000.345;
+ d += 4000.888;
+ b = 1;
+ s = 0x80001;
+ c.Lo = 10;
+ c.Hi = 20;
+ date += 10.34340;
+ bstr = "bar";
+ punk = (IUnknown*) this;
+ v.vt = 4;
+ v.iVal = 30;
+ v2->vt = 5;
+ v2->fltVal = 232.03;
+ return v;
+}
+
+VARIANT Foo::variantx(VARIANT v, VARIANT* v2)
+{
+ v.vt = 4;
+ v.iVal = 30;
+ v2->vt = 5;
+ v2->fltVal = 232.03;
+ return v;
+}
+
+
+VARIANT Foo::variantx2(short i, VARIANT v)
+{
+ i += 100;
+ v.vt = 4;
+ v.iVal = 30;
+ return v;
+}
+
+
+extern "C"
+short CALLCONV I2(short _i2, long _l, float _f, double _d)
+{
+ short i2;
+ long l, l2;
+
+ i2 = _i2 + _l + _f + _d;
+ return i2;
+}
+
+extern "C"
+long CALLCONV I4(long _i4, long _t1)
+{
+ short i4;
+
+ i4 = _i4 + 2;
+ return i4;
+}
+
+extern "C"
+float CALLCONV R4(float _r4, float _t1, float _t2)
+{
+ float r4;
+
+ r4 = _r4 + 3.0;
+ return r4;
+}
+
+extern "C"
+double CALLCONV R8(double _r8, double _t1, double _t2, double _t3)
+{
+ double r8;
+
+ r8 = _r8 + 4.0;
+ return r8;
+}
+
+extern "C"
+CY CALLCONV Cy(CY _cy)
+{
+ CY cy;
+
+ cy.Lo = _cy.Lo + 0;
+ cy.Hi = _cy.Hi + 1;
+
+ return cy;
+}
+
+extern "C"
+BSTR CALLCONV Bstr(BSTR _bstr)
+{
+ BSTR bstr;
+
+ bstr = _bstr;
+ return bstr;
+}
+
+extern "C"
+VARIANT CALLCONV Multi(VARIANT v, short i, long l, float f, double d, VARIANT_BOOL bool, SCODE scode, CY cy, DATE date, BSTR bstr, IUnknown* punk)
+{
+ v.iVal = i;
+ v.lVal = l;
+ v.fltVal = f;
+ v.dblVal = d;
+ v.bool = bool;
+ v.scode = scode;
+ v.cyVal = cy;
+ v.date = date;
+ v.bstrVal = bstr;
+ v.punkVal = punk;
+ return v;
+}
+
+
+extern "C"
+void main()
+{
+ short i, i2;
+ long l, l2;
+ float f, f2, f3;
+ double d, d2, d3;
+ VARIANT_BOOL bool;
+ SCODE scode;
+ CY cy, cy2;
+ DATE date, date2;
+ BSTR bstr, bstr2;
+ IUnknown* punk, *punk2;
+ VARIANT v, v2;
+
+ Foo* foo;
+
+ i = 1;
+ i2 = 100;
+ l = 2;
+ l2 = 232;
+ f = 3.0;
+ f2 = 3.1;
+ f3 = 3.2;
+ d = 4.0;
+ d2 = 4.2;
+ d3 = 4.3;
+ bool = 0;
+ scode = 0;
+ cy.Lo = 50;
+ cy.Hi = 100;
+ cy2.Lo = 200;
+ cy2.Hi = 300;
+ date = 1000.000;
+ date2 = 3000.000;
+ bstr = "bstr";
+ bstr2 = "bstr2";
+ punk = (IUnknown*) 0;
+ punk2 = (IUnknown*) 0;
+ v.vt = 2;
+ v.iVal = 5000;
+ v2.vt = 4;
+ v2.fltVal = 232.9032;
+
+ foo = new Foo();
+
+ foo->empty();
+ i = foo->i2(i, &i2);
+ l = foo->i4(i, l, &l2);
+ f = foo->r4(i, l, f, f2, &f3);
+ f2 = foo->r4x(f, f2, &f3);
+ d = foo->r8(i, l, f, d, d2, &d3);
+ d2 = foo->r8x(d, d2, &d3);
+ d2 = foo->r8x2(i, f, d);
+ bool = foo->bool(i, l, f, d, bool);
+ scode = foo->scode(i, l, f, d, bool, scode);
+ cy = foo->cy(i, l, f, d, bool, scode, cy, &cy2);
+ cy2 = foo->cyx(cy, &cy2);
+ cy2 = foo->cyx2(i, cy);
+ foo->cyx3(cy);
+ date = foo->date(i, l, f, d, bool, scode, cy, date, &date2);
+ bstr = foo->bstr(i, l, f, d, bool, scode, cy, date, bstr, &bstr2);
+ punk = foo->interface(i, l, f, d, bool, scode, cy,
+ date, bstr, punk, &punk2);
+ v = foo->variant(i, l, f, d, bool, scode, cy,
+ date, bstr, punk, v, &v2);
+ v2 = foo->variantx(v, &v2);
+ v2 = foo->variantx2(i, v);
+
+ i = I2(i, l, f, d);
+ l = I4(l, l2);
+ f = R4(f, f2, f3);
+ d = R8(d, d2, d3, d3);
+ cy = Cy(cy2);
+ bstr = Bstr(bstr2);
+ v2 = Multi(v, i, l, f, d, bool, scode, cy, date, bstr, punk);
+}
diff --git a/private/oleauto/src/dispatch/win32/mips/invtest.h b/private/oleauto/src/dispatch/win32/mips/invtest.h
new file mode 100644
index 000000000..5298c3fce
--- /dev/null
+++ b/private/oleauto/src/dispatch/win32/mips/invtest.h
@@ -0,0 +1,72 @@
+typedef short VARIANT_BOOL;
+
+typedef long SCODE;
+
+typedef struct tagCY {
+ unsigned long Lo;
+ long Hi;
+} CY;
+
+typedef double DATE;
+
+typedef char* BSTR;
+
+class IUnknown;
+class IDispatch;
+
+typedef struct tagSAFEARRAYBOUND {
+ unsigned long cElements;
+ long lLbound;
+} SAFEARRAYBOUND;
+
+typedef struct tagSAFEARRAY {
+ unsigned short cDims;
+ unsigned short fFeatures;
+ unsigned short cbElements;
+ unsigned short cLocks;
+ unsigned long handle;
+ void* pvData;
+ SAFEARRAYBOUND rgsabound[1];
+} SAFEARRAY;
+
+
+typedef unsigned short VARTYPE;
+typedef struct tagVARIANT VARIANT;
+
+struct tagVARIANT {
+ VARTYPE vt;
+ unsigned short wReserved1;
+ unsigned short wReserved2;
+ unsigned short wReserved3;
+ union {
+ short iVal; /* VT_I2 */
+ long lVal; /* VT_I4 */
+ float fltVal; /* VT_R4 */
+ double dblVal; /* VT_R8 */
+ VARIANT_BOOL bool; /* VT_BOOL */
+ SCODE scode; /* VT_ERROR */
+ CY cyVal; /* VT_CY */
+ DATE date; /* VT_DATE */
+ BSTR bstrVal; /* VT_BSTR */
+ IUnknown * punkVal; /* VT_UNKNOWN */
+ IDispatch * pdispVal; /* VT_DISPATCH */
+ SAFEARRAY * parray; /* VT_ARRAY|* */
+
+ short * piVal; /* VT_BYREF|VT_I2 */
+ long * plVal; /* VT_BYREF|VT_I4 */
+ float * pfltVal; /* VT_BYREF|VT_R4 */
+ double * pdblVal; /* VT_BYREF|VT_R8 */
+ VARIANT_BOOL * pbool; /* VT_BYREF|VT_BOOL */
+ SCODE * pscode; /* VT_BYREF|VT_ERROR */
+ CY * pcyVal; /* VT_BYREF|VT_CY */
+ DATE * pdate; /* VT_BYREF|VT_DATE */
+ BSTR * pbstrVal; /* VT_BYREF|VT_BSTR */
+ IUnknown * * ppunkVal; /* VT_BYREF|VT_UNKNOWN */
+ IDispatch * * ppdispVal; /* VT_BYREF|VT_DISPATCH */
+ SAFEARRAY * * pparray; /* VT_BYREF|VT_ARRAY|* */
+ VARIANT * pvarVal; /* VT_BYREF|VT_VARIANT */
+
+ void * byref; /* Generic ByRef */
+ };
+};
+
diff --git a/private/oleauto/src/dispatch/win32/oleconva.cpp b/private/oleauto/src/dispatch/win32/oleconva.cpp
new file mode 100644
index 000000000..2fbc01c60
--- /dev/null
+++ b/private/oleauto/src/dispatch/win32/oleconva.cpp
@@ -0,0 +1,549 @@
+/***
+*oleconva.cpp
+*
+* Copyright (C) 1993, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This module contains the low level VARTYPE coersion API.
+* On RISC platforms go for portability, hence C/C++.
+*
+*Revision History:
+*
+* [00] 7-Sept-93 tomteng: Created from silver\rt\oleconv.c
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+
+#include <stdio.h>
+#include <math.h>
+#include <float.h>
+#include <ctype.h>
+#include <stdlib.h>
+
+ASSERTDATA
+
+extern "C" {
+
+// Note: the floating point IN params on the following utilities are
+// passed byref, because mpw and wings pass floating point values
+// differently byval, and we need to interface these asm routines
+// with both compilers.
+
+INTERNAL_(HRESULT) ErrCyFromI2(short sIn, CY FAR* pcyOut);
+INTERNAL_(HRESULT) ErrCyFromI4(long lIn, CY FAR* pcyOut);
+INTERNAL_(HRESULT) ErrCyFromR4(float FAR* pfltIn, CY FAR* pcyOut);
+INTERNAL_(HRESULT) ErrCyFromR8(double FAR* pdlbIn, CY FAR* pcyOut);
+INTERNAL_(HRESULT) ErrI2FromCy(CY cyIn, short FAR* psOut);
+INTERNAL_(HRESULT) ErrI4FromCy(CY cyIn, long FAR* plOut);
+INTERNAL_(HRESULT) ErrR4FromCy(CY cyIn, float FAR* pfltOut);
+INTERNAL_(HRESULT) ErrR8FromCy(CY cyIn, double FAR* pdblOut);
+INTERNAL_(HRESULT) ErrMultCyI4(CY cyIn, long lIn, CY FAR* pcyOut);
+
+
+PRIVATE_(int) FMakePosCy (CY *pcyValue);
+PRIVATE_(void) PackCy (CY *pcy, unsigned long *plValues);
+PRIVATE_(void) UnpackCy (CY *pcy, unsigned long *plValues);
+
+#define C2TO32TH 4294967296.0
+
+/***
+* ErrCyFromI2 - convert I2 to currency
+* Purpose:
+* The specified two-byte integer value is multiplied by 10000
+* and returned in a currency value.
+*
+* Entry:
+* sIn - two-byte integer input value
+*
+* Exit:
+* pcyOut - pointer to currency result
+* returns error:
+* DISP_E_OVERFLOW - result is outside currency range.
+* NOERROR - no error
+*
+***********************************************************************/
+INTERNAL_(HRESULT)
+ErrCyFromI2(short sIn, CY FAR* pcyOut)
+{
+ return ErrCyFromI4((long)sIn, pcyOut);
+}
+
+/***
+* ErrCyFromI4 - convert I4 to currency
+* Purpose:
+* The specified four-byte integer value is multiplied by 10000
+* and returned in a currency value.
+*
+* Entry:
+* lIn - four-byte integer input value
+*
+* Exit:
+* pcyOut - pointer to currency result
+* returns error:
+* DISP_E_OVERFLOW - result is outside currency range.
+* NOERROR - no error
+*
+***********************************************************************/
+INTERNAL_(HRESULT)
+ErrCyFromI4(long lInput, CY FAR* pcyOut)
+{
+ BOOL fNegative = lInput < 0;
+
+ unsigned long templow;
+ unsigned long tempmid;
+
+ if (fNegative)
+ lInput = -lInput;
+
+ templow = ((unsigned long)lInput & 0xffff) * 10000;
+ tempmid = ((unsigned long)lInput >> 16) * 10000;
+
+ pcyOut->Hi = tempmid >> 16;
+ pcyOut->Lo = templow + (tempmid << 16);
+ if (pcyOut->Lo < templow)
+ pcyOut->Hi++;
+
+ if (fNegative) {
+ pcyOut->Hi = ~pcyOut->Hi;
+ if ((pcyOut->Lo = (unsigned long)(-(long)pcyOut->Lo)) == 0)
+ pcyOut->Hi++;
+ }
+
+ return NOERROR;
+}
+
+INTERNAL_(HRESULT)
+ErrCyFromR4(float FAR* pfltIn, CY FAR* pcyOut)
+{
+ double dbl = (double) *pfltIn;
+ return ErrCyFromR8(&dbl, pcyOut);
+}
+
+/***
+* ErrCyFromR8 - return error for double-real to currency conversion
+* Purpose:
+* Convert an eight-byte real value to a currency and return
+* any error status.
+*
+* Entry:
+* pdblIn - pointer to an eight-byte input value
+*
+* Exit:
+* pcyOut - pointer to currency result
+* returns error:
+* DISP_E_OVERFLOW - result is outside currency range.
+* NOERROR - no error
+*
+***********************************************************************/
+INTERNAL_(HRESULT)
+ErrCyFromR8(double FAR* pdlbIn, CY FAR* pcyOut)
+{
+ BOOL fNegative = FALSE;
+ double dblInput = *pdlbIn;
+ double dblHi, dblLo;
+ float flt;
+ double dblDif;
+
+ // test for overflow first
+ // [Note: We are counting on the compiler rounding the following numbers
+ // correctly (by IEEE rules to the nearest R8). The magnitude of these
+ // numbers are rounded up and, thus, are always outside the legal range
+ // for currency.
+ if (dblInput >= 922337203685477.58 ||
+ dblInput <= -922337203685477.58)
+ return RESULT(DISP_E_OVERFLOW);
+
+ // if negative, set flag and make positive
+ if (dblInput < 0.0) {
+ fNegative = TRUE;
+ dblInput = -dblInput;
+ }
+
+ // In order to maintain the necessary precision when multiplying
+ // by 10000 (i.e., going from 53-bit to 64-bit), split the
+ // input value into two different doubles and perform calcs using
+ // them:
+ //
+ // dblHi = has low bits 0
+ // dblLo = has high bits 0
+ //
+
+ // split input into two parts
+ // Note: compiler doesn't do the right thing with this:
+ // "dblHi = (double) (float) dblInput"
+ flt = (float) dblInput;
+ dblHi = (double) flt; // input rounded to 24-bit precision
+ dblLo = dblInput - dblHi; // diff between 24- and 53-bit input value
+
+ // bias for currency
+
+ dblHi = dblHi * 10000;
+ dblLo = dblLo * 10000;
+
+ // calculate cy.Hi
+ pcyOut->Hi = (long) ((dblLo + dblHi) / C2TO32TH);
+
+ // calculate cy.Lo
+ dblHi -= (((double) pcyOut->Hi) * C2TO32TH);
+ pcyOut->Lo = (unsigned long) (dblLo + dblHi);
+
+ // round as necessary
+ dblDif = (dblLo + dblHi) - (double)(pcyOut->Lo);
+ if ( (dblDif > 0.5) || ((dblDif == 0.5) && (pcyOut->Lo & 1)) ) {
+ pcyOut->Lo++;
+ if (pcyOut->Lo == 0)
+ pcyOut->Hi++;
+ }
+
+ // negate the result if input was negative
+ if (fNegative) {
+ pcyOut->Hi = ~pcyOut->Hi;
+ if ((pcyOut->Lo = (unsigned long)(-(long)pcyOut->Lo)) == 0)
+ pcyOut->Hi++;
+ }
+
+ return NOERROR;
+}
+
+
+/***
+* ErrI2FromCy - return error for currency to two-byte integer conversion
+***********************************************************************/
+INTERNAL_(HRESULT)
+ErrI2FromCy(CY cyIn, short FAR* psOut)
+{
+ long lValue;
+ HRESULT hresult;
+
+ hresult = ErrI4FromCy(cyIn, &lValue);
+ if (hresult == NOERROR) {
+ if (lValue < -32768L || lValue > 32767L)
+ hresult = RESULT(DISP_E_OVERFLOW);
+ else
+ *psOut = (short)lValue;
+ }
+
+ return hresult;
+}
+
+/***
+* ErrI4FromCy - return error for currency to four-byte integer conversion
+* Purpose:
+* Convert a currency value to a four-byte integer and return
+* any error status.
+*
+* Entry:
+* cyInput - currency input value
+*
+* Exit:
+* plOut - pointer to four-byte integer result
+* returns error:
+* DISP_E_OVERFLOW - result is outside currency range.
+* NOERROR - no error
+*
+***********************************************************************/
+INTERNAL_(HRESULT)
+ErrI4FromCy(CY cyIn, long FAR* plOut)
+{
+ BOOL fNegative;
+ int index;
+
+ unsigned long lValue[4];
+ short sRemainder;
+
+ // convert value to a positive sign
+ fNegative = FMakePosCy(&cyIn);
+
+ // unpack the input currency into four long words
+ // least significant in [0] to most in [3].
+ UnpackCy(&cyIn, lValue);
+
+ // divide the unpacked value by 10000 and get remainder.
+ // process from most to least significant part and leave
+ // the remainder in the extra fifth part.
+ for (index = 3; index > 0; index--) {
+ lValue[index - 1] |= (lValue[index] % 10000) << 16;
+ lValue[index] /= 10000;
+ }
+
+ sRemainder = (short)(lValue[0] % 10000);
+ lValue[0] /= 10000;
+
+ // pack the values back into a CY
+ PackCy(&cyIn, lValue);
+
+ // round value up if:
+ // remainder is greater than 5000, or
+ // remainder is equal to 5000 and unrounded result is odd.
+ if (sRemainder > 5000 || (sRemainder == 5000 && (cyIn.Lo & 1))) {
+ cyIn.Lo++;
+ if (cyIn.Lo == 0)
+ cyIn.Hi++;
+ }
+
+ // test for overflow - high part must be zero and
+ // lower part must not be greater than 0x7fffffff
+ // for a positive value and 0x80000000 for negative.
+ if (cyIn.Hi != 0 ||
+ cyIn.Lo > (0x7fffffff + (unsigned long)fNegative))
+ return RESULT(DISP_E_OVERFLOW);
+
+ // if negative, convert only the low part
+ if (fNegative)
+ cyIn.Lo = (unsigned long)(-(long)cyIn.Lo);
+
+ *plOut = (long)cyIn.Lo;
+
+ return NOERROR;
+}
+
+
+/***
+* rtR4FromCy - convert currency to R4
+* Purpose:
+* The specified currency value is scaled to a
+* single-precision real value.
+*
+* Entry:
+* cyInput - currency input value
+*
+* Exit:
+* Returns a four-byte real number.
+*
+* Exceptions:
+*
+***********************************************************************/
+
+INTERNAL_(HRESULT)
+ErrR4FromCy(CY cyInput, float FAR* pfltOut)
+{
+ *pfltOut = (float) (((double)cyInput.Hi * C2TO32TH + (double)cyInput.Lo)
+ / 10000.0);
+ return NOERROR;
+}
+
+
+/***
+* rtR8FromCy - convert currency to R8
+* Purpose:
+* The specified currency value is scaled to a
+* double-precision real value.
+*
+* Entry:
+* cyInput - currency input value
+*
+* Exit:
+* Returns a eight-byte real number.
+*
+* Exceptions:
+*
+***********************************************************************/
+
+INTERNAL_(HRESULT)
+ErrR8FromCy(CY cyInput, double FAR* pdblOut)
+{
+ *pdblOut = ((double)cyInput.Hi * C2TO32TH + (double)cyInput.Lo) / 10000.0;
+ return NOERROR;
+}
+
+
+INTERNAL_(HRESULT)
+ErrMultCyI4(CY cyIn, long lInput, CY FAR* pcyOut)
+{
+ CY cyI4;
+
+ BOOL fNegative = FALSE;
+ BOOL fRound = FALSE;
+ BOOL fScale = FALSE;
+ int outIndex;
+ int inIndex;
+ CY cyProduct;
+
+ unsigned long lValue1[4];
+ unsigned long lValue2[4];
+ unsigned long lProduct[8];
+
+
+ // create an unscaled currency value by setting
+ // the low part to the input value and sign-extending
+ // to the high part
+ cyI4.Lo = lInput;
+ cyI4.Hi = -(lInput < 0);
+
+ // convert both input values to positive and set
+ // the negative flag if either, but not both, were
+ // negative.
+ fNegative = FMakePosCy(&cyIn) ^ FMakePosCy(&cyI4);
+
+ // build the unpacked arrays from the positive values
+ UnpackCy(&cyIn, lValue1);
+ UnpackCy(&cyI4, lValue2);
+
+ // initialize the product array to zero
+ MEMSET(lProduct, 0, sizeof(lProduct));
+
+ // outer loop - for each value in lValue1, add the
+ // partial product with the array lValue2 into the
+ // lProduct array.
+ for (outIndex = 0; outIndex < 4; outIndex++) {
+
+ // only bother to form partial product if the
+ // value is nonzero
+ if (lValue1[outIndex] != 0) {
+
+ // add the product to the product array value
+ for (inIndex = 0; inIndex < 4; inIndex++)
+ lProduct[inIndex + outIndex] +=
+ lValue1[outIndex] * lValue2[inIndex];
+
+ // propagate any high-word value to the next product
+ // array element and clear the high-word value
+ for (inIndex = outIndex; inIndex < outIndex + 4; inIndex++) {
+ lProduct[inIndex + 1] += lProduct[inIndex] >> 16;
+ lProduct[inIndex] &= 0x0000ffffL;
+ }
+ }
+ }
+
+ // product is now in the lProduct array. If fScale is set
+ // for the CY * CY case, divide the array values by 10000
+ // and set the fRound flag if greater or equal to 5000.
+ if (fScale) {
+ for (outIndex = 7; outIndex > 0; outIndex--)
+ if (lProduct[outIndex] != 0) {
+ lProduct[outIndex - 1] |= (lProduct[outIndex] % 10000) << 16;
+ lProduct[outIndex] /= 10000;
+ }
+
+ fRound = (lProduct[0] % 10000) >= 5000;
+ lProduct[0] /= 10000;
+ }
+
+ // overflow has occurred if any of the high four product array
+ // values are nonzero.
+ if ((lProduct[7] | lProduct[6] | lProduct[5] | lProduct[4]) != 0)
+ return RESULT(DISP_E_OVERFLOW);
+
+ // pack the last four array values into the returned CY structure;
+ PackCy(&cyProduct, lProduct);
+
+ // process rounding if needed
+ if (fRound) {
+
+ // do special overflow check that would be lost
+ // when incrementing (0xffffffff|ffffffff -> 0x0)
+ if ((cyProduct.Hi & cyProduct.Lo) == 0xffffffffL)
+ return RESULT(DISP_E_OVERFLOW);
+
+ // increment the value
+ if (++cyProduct.Lo == 0)
+ cyProduct.Hi++;
+ }
+
+ // negate the value if needed
+ if (fNegative) {
+ cyProduct.Hi = ~cyProduct.Hi;
+
+ // if the negation produces a zero value, clear the negative
+ // flag so the overflow test will work correctly
+ if ((cyProduct.Lo = (unsigned long)(-(long)cyProduct.Lo)) == 0 &&
+ ++cyProduct.Hi == 0)
+ fNegative = FALSE;
+ }
+
+ // do final overflow check - test sign expected against
+ // actual sign of result
+ if (fNegative == (cyProduct.Hi >= 0))
+ return RESULT(DISP_E_OVERFLOW);
+
+ // done - return product
+ *pcyOut = cyProduct;
+
+ return NOERROR;
+}
+
+
+/***
+* FMakePosCy - make a positive currency value and return sign
+* Purpose:
+* Return the positive value of the input currency value and a
+* flag with the sign of the original value.
+*
+* Entry:
+* pcyValue - pointer to currency input value
+*
+* Exit:
+* pcyValue - pointer to positive currency value
+* returns: 0 if positive, 1 if negative
+*
+* Note:
+* A maximum negative value input is returned unchanged, but
+* treated as an unsigned value by the calling routines.
+*
+***********************************************************************/
+PRIVATE_(int)
+FMakePosCy (CY *pcyValue)
+{
+ int fNegative = 0;
+
+ if (pcyValue->Hi < 0) {
+ pcyValue->Hi = ~pcyValue->Hi;
+ if ((pcyValue->Lo = (unsigned long)(-(long)pcyValue->Lo)) == 0)
+ pcyValue->Hi++;
+ fNegative = 1;
+ }
+
+ return fNegative;
+}
+
+
+/***
+* UnpackCy - separate currency value into four two-byte integers
+* Purpose:
+* Unpack the currency value input into the lower half of the
+* specified pointer to an array of unsigned longs. The array
+* goes from least- to most-significant values.
+*
+* Entry:
+* pcy - pointer to currency input value
+*
+* Exit:
+* plValues - pointer to start of unsigned long array
+*
+***********************************************************************/
+PRIVATE_(void)
+UnpackCy (CY *pcy, unsigned long *plValues)
+{
+ *plValues++ = pcy->Lo & 0xffff;
+ *plValues++ = pcy->Lo >> 16;
+ *plValues++ = (unsigned long)pcy->Hi & 0xffff;
+ *plValues = (unsigned long)pcy->Hi >> 16;
+}
+
+/***
+* PackCy - build currency value from four two-byte integers
+* Purpose:
+* Pack the lower half of the array of unsigned long into a
+* currency value. This routine complements UnpackCy.
+*
+* Entry:
+* plValues - pointer to start of unsigned long array input
+*
+* Exit:
+* pcy - pointer to currency result
+*
+***********************************************************************/
+PRIVATE_(void)
+PackCy (CY *pcy, unsigned long *plValues)
+{
+ pcy->Lo = *plValues++;
+ pcy->Lo |= *plValues++ << 16;
+ pcy->Hi = *plValues++;
+ pcy->Hi |= *plValues++ << 16;
+}
+
+}
diff --git a/private/oleauto/src/dispatch/win32/oledisp.cpp b/private/oleauto/src/dispatch/win32/oledisp.cpp
new file mode 100644
index 000000000..b4dbbda1c
--- /dev/null
+++ b/private/oleauto/src/dispatch/win32/oledisp.cpp
@@ -0,0 +1,119 @@
+/***
+*oledisp.cpp
+*
+* Copyright (C) 1993, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+
+* Win32 DLL initailization/termination routine for oledisp.dll.
+*
+*Revision History:
+*
+* [00] 20-Feb-93 tomteng: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "oledisp.h"
+#include "oautil.h"
+
+ASSERTDATA
+
+
+extern "C"
+{
+
+#ifdef _X86_
+// TRUE if were running on Chicago
+BOOL g_fChicago = FALSE;
+
+// TRUE if were running on win32s
+BOOL g_fWin32s = FALSE;
+#endif
+
+// oleaut32.dll instance handle
+HINSTANCE g_hinstDLL = NULL;
+
+// in TYPELIB
+extern "C" void InitMbString(void);
+
+}
+
+STDAPI CoSetState(IUnknown FAR *punk);
+
+/***
+*BOOL DllMain
+*Purpose:
+* Win32 DLL Entry/Exit routine.
+*
+*Entry:
+* hinst = The DLL's instance handle.
+* dwReason = the reason the entry point was called.
+*
+*Exit:
+* return value = BOOL.
+*
+***********************************************************************/
+BOOL APIENTRY
+DllMain(HINSTANCE hinstDLL, DWORD dwReason, LPVOID pvReserved)
+{
+ BOOL fRet = TRUE;
+
+ g_hinstDLL = hinstDLL;
+
+ switch(dwReason){
+ case DLL_THREAD_ATTACH:
+ break;
+
+ case DLL_THREAD_DETACH:
+ if (Pappdata() != NULL) {
+ // Safety net. If we've been initialized and are going away, but
+ // nobody has called OleUninitialize yet, then call back into OLE now
+ // to have it free it's pointer to us (we are going away), and call
+ // ReleaseAppData().
+ CoSetState(NULL);
+ }
+ break;
+
+ case DLL_PROCESS_DETACH:
+ if (Pappdata() != NULL) {
+ // Safety net. If we've been initialized and are going away, but
+ // nobody has called OleUninitialize yet, then call back into OLE now
+ // to have it free it's pointer to us (we are going away), and call
+ // ReleaseAppData().
+ CoSetState(NULL);
+ }
+ ReleaseProcessData(); // Delete cached per-process data.
+ break;
+
+ case DLL_PROCESS_ATTACH:
+#ifdef _X86_
+ // code for Chicago detection (taken from MSDN News March 94)
+ DWORD dwVersion = GetVersion();
+ if (dwVersion < 0x80000000) {
+ // NT
+ }
+ else if (LOBYTE(LOWORD(dwVersion)) < 4) {
+ // WIN32s -- no Wide API's, just like Chicago, also
+ // need HOLDER marshalling hack.
+ //
+ g_fWin32s = g_fChicago = TRUE;
+ }
+ else {
+ g_fChicago = TRUE;
+ }
+#endif
+
+ InitMbString(); // init multibyte helpers for TYPELIB
+ fRet = SUCCEEDED(InitProcessData()); // initilize per-process data.
+#if 0
+ if (fRet) {
+ fRet = SUCCEEDED(InitAppData());
+ }
+#endif // 0
+ break;
+ }
+ return fRet;
+}
diff --git a/private/oleauto/src/dispatch/win32/ppc/invoke.s b/private/oleauto/src/dispatch/win32/ppc/invoke.s
new file mode 100644
index 000000000..ed46f8312
--- /dev/null
+++ b/private/oleauto/src/dispatch/win32/ppc/invoke.s
@@ -0,0 +1,853 @@
+//****************************************************************************/
+// invoke.s - OLE Automation v-table based Invoke (POWERPC)
+//
+// Copyright (C) 1994, Microsoft Corporation. All Rights Reserved.
+// Information Contained Herein Is Proprietary and Confidential.
+//
+// Purpose:
+//
+// This module implements the low-level v-table based dispatching
+// support for the default implementation of IDispatch::Invoke()
+// on PowerPC hardware.
+//
+// Revision History:
+//
+// 28-Mar-94 tomteng: Created POWERPC version
+//
+// Implementation Notes:
+//
+// (1) The POWERPC documentation indicates that you can load values
+// into FP registers without causing exceptions if they are illegal
+// FP values. Thus, we can use the 8-byte FP load/store instructions
+// for moving non-FP values efficiently. NOTE: this will fail if
+// the data is not mod-8 (i.e. 3 least-significant-bits of address
+// are 0). A data alignment fault will occur.
+//
+// (2) On POWERPC stdcall, the caller allocates space for the arguments
+// (which is normal) but also REMOVES that space. That is, stdcall on
+// POWERPC is "caller clear" (not callee).
+//
+// (3) POWERPC stack layout is as follows:
+//
+// +-----------------------+
+// | Link Area |
+// | (6*4 = 24 bytes) |
+// +-----------------------+ <= SP on entry
+// | Caller-saved Regs | |
+// | (as needed) | |
+// +-----------------------+ V
+// | Locals | Stack
+// | (as needed) | Grows
+// +-----------------------+ Down
+// | Parameters | |
+// | (8 * 4 = 32 bytes for | |
+// | reg arg homing area, | V
+// | + additional params |
+// | as needed) |
+// +-----------------------+
+// | Link Area |
+// | (6*4 = 24 bytes) |
+// +-----------------------+ <= SP on call out
+//
+//
+// (4) Register conventions:
+//
+// R0 = Scratch, used in glue & prologs
+// R1 = Stack Pointer
+// R2 = TOC pointer (RTOC)
+// R3-R10 = arg passing and retval registers, R3 used fo non-float return
+// R11/R12 = scratch regs (trashed across calls) used in glue & prologs
+// R13-R31 = must be preserved by callee, non-volatile local
+//
+// FR0 = scratch FP reg
+// f1-f13 = FP arg passing and retval registers, first 13 FP registers
+// f14-FR31 = must be preserved by callee, non-volatile local storage
+//
+// Our conventions are as follows:
+//
+// R29 = address of DLL target function location (Declare templates only)
+// R30 = virtual stack (vs) memory pointer
+// R31 = address of the virtual stack (vs) pointer in ebthread
+// R11/R12 = temps for intermediate values
+// FR0 = temp for intermediate FP value
+//
+// (5) Keep SP 8-byte aligned (even if values within stack are only 4-byte
+// aligned)!
+//
+// (6) TOC: The TOC (Table Of Contents) scheme for cross-fragment data/code
+// access is somewhat complicated and cumbersome to adhere to in asm code
+// that is generated dynamically on the fly. [See appropriate documentation
+// and compiler-generated code. In particular, the Apple "PowerPC Native
+// Runtime Architecture" (draft 6, 7/27/92) and the readme.txt that comes
+// with asmppc.exe are both helpful.]
+//
+//****************************************************************************/
+
+#include "ksppc.h"
+
+//
+// imported symbols
+//
+ .extern g_S_OK
+ .extern g_E_INVALIDARG
+
+//
+// TOC block offsets
+.set TOC_ADDR, 0 // address of target function
+.set TOC_RTOC, 4 // target TOC register value
+.set TOC_ENV, 8 // environment value
+
+//
+// register alias
+//
+
+.set t0, r19 // temporary registers
+.set t1, r20
+.set t2, r21
+.set t3, r22
+.set t4, r23
+.set t5, r24
+.set t6, r25
+.set t7, r26
+.set t8, r27
+.set t9, r28
+.set s0, r30
+.set s1, r31 // new stack pointer
+
+
+// Variant Layout
+.set vt, 0
+.set wReserved1, 2
+.set wReserved2, 4
+.set wReserved3, 6
+.set dw0, 8
+.set dw1, 10
+.set dw2, 12
+.set dw3, 14
+
+//
+// constants
+//
+
+.set VT_EMPTY, 0
+.set VT_NULL, 1
+.set VT_I2, 2
+.set VT_I4, 3
+.set VT_R4, 4
+.set VT_R8, 5
+.set VT_CY, 6
+.set VT_DATE, 7
+.set VT_BSTR, 8
+.set VT_DISPATCH, 9
+.set VT_ERROR, 10
+.set VT_BOOL, 11
+.set VT_VARIANT, 12
+.set VT_UNKNOWN, 13
+.set VT_MAX, 14
+// 14 is unused
+// 15 is unused
+//.set VT_I1, 16
+.set VT_UI1, 17
+
+
+.set VT_BYREF, 0x4000
+.set VT_ARRAY, 0x2000
+.set VT_NOMODE, 0x00ff
+
+// stupid asmppc GPF's on OR'ed constants in the source code enclosed
+// in parens, and ignored the 2nd half when not in parens
+.set VT_BYREF_OR_VT_ARRAY, 0x6000
+
+//***
+//
+//HRESULT
+//InvokeStdCall (
+// IN PVOID _this, //void FAR*
+// IN DWORD oVft, //unsigned int
+// IN DWORD vtReturn, //unsigned int
+// IN DWORD cActuals, //unsigned int
+// IN PVOID rgvt, //VARTYPE FAR*
+// IN PVOID rgpvarg, //VARIANTARG FAR* FAR*
+// OUT PVOID pvargResult //VARIANT FAR*
+// )
+//
+//Routine Description:
+//
+// Invoke a virtual StdCall method using the given _this pointer,
+// method index and array of parameters.
+//
+//Arguments:
+//
+// _this - Supplies a pointer to the method to invoke.
+//
+// oVft - vTable offset into _this ptr
+//
+// vtReturn - the VARTYPE of the return value.
+//
+// cActuals - count of the number of actuals.
+//
+// rgvt - array of VARTYPES describing the methods formals.
+//
+// rgpvarg - array of VARIANTARG*s, which map the actuals by position.
+//
+// pvargResult - VARIANTARG containing the method return value.
+//
+//Return Value:
+//
+// g_S_OK (extern value)
+// g_E_INVALIDARG (extern value)
+//
+//Implementation Note:
+//
+// PowerPC StdCall method arguments are push on the stack left to right.
+// The stack grows downward (pushing decrements stack address). Data
+// alignment on the stack starts from arg1 upward. Caller cleans.
+//
+// Per PowerPC calling conventions, the following rules are followed:
+//
+// 1. Stack frame must be QUADWORD (64-bits) aligned.
+//
+//
+// 2. Structures are pushed on the stack by value. They are returned in
+// the r3 register which contains the address of a hidden argument
+// (vargHiddenParm) allocated by the caller and pushed as the first
+// argument [r3] on the stack (*before* the this pointer)
+//
+// 3. On vtable-based calls, _this is passed as the first argument [r3],
+// *unless* there is a structure return, in which case it is pased in
+// r4.
+//
+// 4. Eight integer/floating registers [r3 - r10] & [f1 - f13] must be
+// set before calling, if used. Type and order of arguments determine
+// the registers used. (int1, float1, int2, int3, float2) means that:
+// r3 <- int1// f1 <- float1)// r5 <- int2// r6 <- int3// fr2 <- float2)//
+//
+//
+// 5. Return values are handled as follows:
+//
+// vartype fundamental return register
+// ---------------------------------------------------
+// VT_UI1 unsigned char r3
+// VT_I2 short r3
+// VT_I4 long r3
+// VT_R4 float f1
+// VT_R8 double f1
+// VT_DATE double f1
+// VT_CY struct r3 (address of struct return)
+// VT_BSTR char FAR* r3
+// VT_UNKNOWN void FAR* r3
+// VT_DISPATCH void FAR* r3
+// VT_ERROR long r3
+// VT_BOOL short r3
+// VT_VARIANT VARIANTARG r3 (address of struct return)
+//
+//
+//
+//--
+
+
+//Stack Frame
+//
+
+//
+
+
+// StackFrameHeaderLength is 56
+// SSIZE is 184
+
+.set SSIZE, StackFrameHeaderLength+128
+.set STKROOM, StackFrameHeaderLength
+
+// Arguments
+.set _this, STKROOM+76 // stack offset to parameter 0
+.set oVft, STKROOM+80 // stack offset to parameter 1
+.set vtReturn, STKROOM+84 // stack offset to parameter 2
+.set cActuals, STKROOM+88 // stack offset to parameter 3
+.set rgvt, STKROOM+92 // stack offset to parameter 4
+.set rgpvarg, STKROOM+96 // stack offset to parameter 5
+.set pvargResult, STKROOM+100 // stack offset to parameter 6
+.set vargHiddenParm, STKROOM+104 // 16-byte temporary for struct return
+
+ // We want to save off 19
+ // non-volatile registers.
+NESTED_ENTRY( InvokeStdCall, SSIZE, 0, 0 )
+PROLOGUE_END( InvokeStdCall )
+
+// This does an swtu sp, -184(sp)
+// stw r0, 180(sp)
+ // entry code
+
+ // Save non-volatile registers...
+ stw r13,STKROOM+0(sp)
+ stw r14,STKROOM+4(sp)
+ stw r15,STKROOM+8(sp)
+ stw r16,STKROOM+12(sp)
+ stw r17,STKROOM+16(sp)
+ stw r18,STKROOM+20(sp)
+ stw r19,STKROOM+24(sp)
+ stw r20,STKROOM+28(sp)
+ stw r21,STKROOM+32(sp)
+ stw r22,STKROOM+36(sp)
+ stw r23,STKROOM+40(sp)
+ stw r24,STKROOM+44(sp)
+ stw r25,STKROOM+48(sp)
+ stw r26,STKROOM+52(sp)
+ stw r27,STKROOM+56(sp)
+ stw r28,STKROOM+60(sp)
+ stw r29,STKROOM+64(sp)
+ stw r30,STKROOM+68(sp)
+ stw r31,STKROOM+72(sp)
+
+ // Save parameter passing register
+
+ stw r3, _this(sp)
+ stw r4, oVft(sp)
+ stw r5, vtReturn(sp)
+ stw r6, cActuals(sp)
+ stw r7, rgvt(sp)
+ stw r8, rgpvarg(sp)
+ stw r9, pvargResult(sp)
+
+ // cannot return byRef
+ //
+ mr t0, r5
+ andi. t0, t0, VT_BYREF // Isolate VT_Mode bits
+ bne LRetInvalidArg // Check VT_Type
+
+ // Setup arguments if any
+ //
+
+LCalcStackSize:
+
+ // calculate space need for pushing arguments on stack
+
+ lwz t3, rgvt(sp) // t3 = &rgvt[0]
+ li t9, 4 // t9 = running arg count of
+ // # of bytes needed.
+ // starts at 4 due to the
+ // implicit _this pointer
+ li t7, 0 // fStructReturn = FALSE
+
+ lwz t1, vtReturn(sp) // check if struct return
+ andi. t0, t1, VT_BYREF_OR_VT_ARRAY // Byref's aren't struct's
+ bne LCalcStackLoop
+
+ lwz t0, [toc]rgfStructReturn(rtoc) // t0 = &rgfStructReturn
+ add t0, t1, t0 // t0 = &rgfStructReturn[i]
+ add t0, t1, t0
+ lhz t0, 0(t0) // t0 = rgfStructReturn[i]
+ andi. t0, t0, 0xff
+ beq LCalcStackLoop
+
+ addi t9, t9, 4 // one more for struct return
+ addi t7, t7, 1 // fStructReturn = TRUE
+
+
+// CONSIDER: re-work to eliminate this first loop, looping backwards over the
+// CONSIDER: args, and just decrementing SP as we go.
+
+LCalcStackLoop:
+ cmpi 0, 0, r6, 0 // go if zero parms
+ beq LCalcStackLoopDone
+
+ lhz t1, 0(t3) // t6 = rgvt[i]
+ andi. t1, t1, VT_NOMODE // Turn off mode bits
+ cmpi 0, 0, t1, VT_UI1 // VT_UI1
+ beq LValidVarType1 // branch if so
+ cmpi 0, 0, t1, VT_MAX
+ bge LRetInvalidArg // Error if Max or above
+
+LValidVarType1:
+ lwz t0, [toc]rgcbVtSize(rtoc) // t0 = &rgcbVtSize
+ add t0, t1, t0 // t0 = &rgcbVtSize[i]
+ add t0, t1, t0
+ lhz t0, 0(t0) // t0 = rgcbVtSize[i]
+ add t9, t9, t0 // bump byte count
+
+ cmpi 0, 0, t1, VT_VARIANT // requires 8 byte alignment?
+ beq AlignIt //
+ cmpi 0, 0, t1, VT_R8 //
+ bne NoAlignment //
+AlignIt:
+ li t0, 7 // align it
+ add t9, t9, t0
+ andc t9, t9, t0
+NoAlignment:
+
+ addi t3, t3, 2 // &rgvt[i++]
+ addi r6, r6, -1 // cActual--
+ b LCalcStackLoop // If more args, go again
+
+LCalcStackLoopDone:
+
+// UNDONE: is there a minimum parameter block size??? If so then need to
+// UNDONE: check t9 against that and possibly bump it.
+
+ mr s1, sp // s1 = old stack pointer
+ subf sp, t9, sp // sp = new stack pointer
+ li t9, 0xfffffff8 // make sure stack is still
+ and sp, sp, t9 // 8-byte aligned.
+ // All errors after this point
+ // must clean up the stack right
+ mr s0, sp // s0 = temporary stack loc
+
+ lwz t2, rgpvarg(s1) // t2 = &rgpvarg[0]
+ lwz t3, rgvt(s1) // t3 = &rgvt[0]
+ lwz t4, cActuals(s1) // t4 = cActuals
+
+ li t1, 2 // t0 = cArgs * 4
+ slw t0, t4, t1
+ add t8, t0, t2 // t8 = &rgpvarg[cArgs]
+
+ li t9, 0 // t9 = running FP argument count
+
+
+#if 0 // UNDONE: turn on once the PPC compiler is fixed to
+ // UNDONE: have the right calling convention here.
+LPushHiddenArg:
+
+ // Check if we need to return a structure, if so
+ // move the address of the vargHiddenParm as
+ // the first (hidden) argument
+ //
+
+ lwz t1, vtReturn(s1)
+ andi. t0, t1, VT_BYREF_OR_VT_ARRAY // Byref's aren't struct's
+ bne LPushThis
+
+ cmpi 0, 0, t7, 0 // fStructReturn == TRUE?
+ beq LPushThis // brif not
+
+ addi r0, s1, vargHiddenParm // r0 = &vargHiddenParm
+ stw r0, 0(s0) // Save on stack
+ addi s0, s0, 4 // adjust arg loc
+
+ // This pointer pushed after hidden struct return parm, if any
+LPushThis:
+
+ stw r3, 0(s0) // Save 'this' on stack
+ addi s0, s0, 4 // adjust arg loc
+#else //0
+
+ // In the broken compiler, the 'this' pointer is the first hidden parm
+ stw r3, 0(s0) // Save 'this' on stack
+ addi s0, s0, 4 // adjust arg loc
+
+
+ // Check if we need to return a structure, if so
+ // move the address of the vargHiddenParm as
+ // the second hidden argument
+ //
+
+ lwz t1, vtReturn(s1)
+ andi. t0, t1, VT_BYREF_OR_VT_ARRAY // Byref's aren't struct's
+ bne NoHiddenArg
+
+ cmpi 0, 0, t7, 0 // fStructReturn == TRUE?
+ beq NoHiddenArg // brif not
+
+ addi r0, s1, vargHiddenParm // r0 = &vargHiddenParm
+ stw r0, 0(s0) // Save on stack
+ addi s0, s0, 4 // adjust arg loc
+NoHiddenArg:
+
+
+#endif //0
+
+
+ cmpi 0, 0, t4, 0 // any args?
+ beq LDoCall // brif not
+
+
+LPushArgs:
+
+ lwz t5, 0(t2) // t5 = rgpvarg[i]
+ lhz t6, 0(t3) // t6 = rgvt[i]
+
+ andi. t0, t6, VT_BYREF_OR_VT_ARRAY // Isolate mode bits
+ bne LPush4 // all ByRefs are sizeof(FAR*)
+
+
+ andi. t1, t6, VT_NOMODE // Turn off mode bits
+ li t0, 2
+ slw t1, t1, t0 // ADDRESS offset
+ lwz t0, [toc]LPushValJmpTab(rtoc) // Get Address of push table
+ add t0, t1, t0 // Get Address of push routine
+ lwz t0, 0(t0)
+#if 0 // only for 68k mac
+ add t0, t0, rtoc // don't ask why
+ lwz t0, 0(t0)
+#endif //0
+ mtctr t0
+ bcctr 20, 0 // Go execute the push code
+
+
+LPush1: // 1 byte of data
+ lbz t0, dw0(t5) // Push HWORD (as 32-bit)
+ stw t0, 0(s0) // Save on stack
+ addi s0, s0, 4 // adjust arg loc
+ b LNextArg
+
+LPush2: // 2 bytes of data
+
+ lhz t0, dw0(t5) // Push HWORD (as 32-bit)
+ stw t0, 0(s0) // Save on stack
+ addi s0, s0, 4 // adjust arg loc
+ b LNextArg
+
+
+LPush4: // 4 bytes of data
+
+ lwz t0, dw0(t5) // Push 1st WORD
+ stw t0, 0(s0)
+ addi s0, s0, 4 // adjust arg loc
+ b LNextArg
+
+
+LPushR4:
+
+ lfs f14, dw0(t5)
+ stfs f14, 0(s0)
+ addi s0, s0, 4 // adjust arg loc
+ b LPushFPValue
+
+
+LPushR8: // 8 bytes of R8 data
+ li t0, 7 // first 8-byte align it
+ add s0, s0, t0
+ andc s0, s0, t0
+
+ lfd f14, dw0(t5)
+ stfd f14, 0(s0)
+ addi s0, s0, 8 // adjust arg loc
+LPushFPValue:
+ cmpi 0, 0, t9, 13 // pass by register?
+ bne LNextArg // brif not
+
+ mr t0, t9 // t0 = current FP register count
+ addi t9, t9, 1 // one more FP register used
+ mulli t0, t0, 8
+
+ lwz t1, [toc]LVSetFpReg(rtoc)
+ add t1, t1, t0
+
+ mtctr t1
+ bcctr 20, 0 // go execute reg setting code
+
+
+LVSetFpReg:
+ fmr f1, f14
+ b LNextArg
+ fmr f2, f14
+ b LNextArg
+ fmr f3, f14
+ b LNextArg
+ fmr f4, f14
+ b LNextArg
+ fmr f5, f14
+ b LNextArg
+ fmr f6, f14
+ b LNextArg
+ fmr f7, f14
+ b LNextArg
+ fmr f8, f14
+ b LNextArg
+ fmr f9, f14
+ b LNextArg
+ fmr f10, f14
+ b LNextArg
+ fmr f11, f14
+ b LNextArg
+ fmr f12, f14
+ b LNextArg
+ fmr f13, f14
+ b LNextArg
+
+
+LPush8: // 8 bytes of data
+#if 0
+ li t0, 7 // first 8-byte align it
+ add s0, s0, t0
+ andc s0, s0, t0
+#endif //0
+
+ lwz t0, dw0(t5)
+ lwz t1, dw2(t5)
+ stw t0, 0(s0)
+ stw t1, 4(s0)
+ addi s0, s0, 8 // adjust arg loc
+ b LNextArg
+
+
+LPushVar: // 16 bytes of data
+ li t0, 7 // first 8-byte align it
+ add s0, s0, t0
+ andc s0, s0, t0
+
+ lwz t0, 0(t5)
+ lwz t1, 4(t5)
+ stw t0, 0(s0)
+ stw t1, 4(s0)
+ lwz t0, 8(t5)
+ lwz t1, 12(t5)
+ stw t0, 8(s0)
+ stw t1, 12(s0)
+
+ addi s0, s0, 16 // adjust arg loc
+
+LNextArg:
+
+ addi t2, t2, 4 // &rgpvarg[i++]
+ addi t3, t3, 2 // &rgvt[i++]
+
+ cmp 0, 0, t2, t8
+ bne LPushArgs // If more args, go again
+
+
+LDoCall:
+ // R3 is current this pointer
+ // load the vtable offset
+ //
+ lwz t0, 0(r3) // address of vtable
+
+ // now set up R3-R10, in case they are used
+ // CONSIDER: better way to do this???
+// UNDONE: must handle parms where we added alignment padding (variant & R8)
+ lwz r3, 0(sp) // this or struct return
+ lwz r4, 4(sp) // arg1 or this
+ lwz r5, 8(sp)
+ lwz r6, 12(sp)
+ lwz r7, 16(sp)
+ lwz r8, 20(sp)
+ lwz r9, 24(sp)
+ lwz r10, 28(sp)
+
+
+ lwz t1, oVft(s1) // Get the vtable offset
+ add t0, t1, t0 // Get addr of ptr to func
+ lwz t0, 0(t0) // Get ptr to func in vtable
+
+
+ // call virtual member function
+ //
+ addi sp, sp, -24 // space for link area
+ mr t1, rtoc // save rtoc
+ lwz r0,TOC_ADDR(t0) // r0 = target address
+ lwz rtoc,TOC_RTOC(t0) // new rtoc value
+ lwz r11,TOC_ENV(t0) // r11 = new environment
+
+ mtctr r0 // here we go!!!!
+ bcctrl 20,0
+
+ mr rtoc, t1 // restore rtoc
+ mr sp, s1 // Restore SP
+
+
+ // Get return argument
+ //
+
+ lwz t1, vtReturn(sp) // t1 = vtType to return
+ lwz t3, pvargResult(sp) // Get RetData Area
+ sth t1, vt(t3) // varResult->vt
+
+ mr t2, t1
+ andi. t2, t2, VT_BYREF_OR_VT_ARRAY // Check ret mode
+ bne LRetPtr // If !0 -> go ret a ptr
+
+ andi. t1, t1, VT_NOMODE // Turn off mode bits
+ cmpi 0, 0, t1, VT_UI1 // VT_UI1
+ beq LValidVarType2 // branch if so
+ cmpi 0, 0, t1, VT_MAX
+ bge LRetInvalidArg // Error if Max or above
+
+LValidVarType2:
+ li t0, 2
+ slw t1, t1, t0 // ADDRESS offset
+ lwz t0, [toc]LRetValJmpTab(rtoc) // Get Address of ret table
+ add t0, t1, t0 // Get Address of ret routine
+ lwz t0, 0(t0)
+#if 0 // only for 68k mac
+ add t0, t0, rtoc // don't ask why
+ lwz t0, 0(t0)
+#endif //0
+ mtctr t0
+ bcctr 20, 0 // Go execute the ret code
+
+LRetUI1:
+ stb r3, dw0(t3)
+ b LDone // Done
+
+LRetI2:
+
+ sth r3, dw0(t3)
+ b LDone // Done
+
+
+LRetI4:
+LRetPtr:
+
+ stw r3, dw0(t3)
+ b LDone // Done
+
+
+LRetR4:
+
+ stfs f1, dw0(t3)
+ b LDone // Done
+
+
+
+LRetR8:
+
+ stfd f1, dw0(t3)
+ b LDone // Done
+
+
+
+LRetCy:
+
+ lwz t1, 0(r3) // cy.Lo
+ stw t1, dw0(t3)
+ lwz t1, 4(r3) // cy.Hi
+ stw t1, dw2(t3)
+ b LDone // Done
+
+
+LRetVar:
+ lwz t1, 0(r3) // store 16-bytes in pvArgResult
+ stw t1, 0(t3)
+ lwz t1, 4(r3)
+ stw t1, 4(t3)
+ lwz t1, 8(r3)
+ stw t1, 8(t3)
+ lwz t1, 12(r3)
+ stw t1, 12(t3)
+ b LDone // Done
+
+LRetInvalidArg:
+
+ lwz r3, [toc]g_E_INVALIDARG(rtoc) // r3 = *g_E_INVALIDARG
+ b ExitInvoke
+
+
+LDone:
+
+ lwz r3, [toc]g_S_OK(rtoc) // r3 = *g_S_OK
+
+
+ExitInvoke:
+ lwz r3, 0(r3) // set return value
+
+ // Restore 19 registers
+ lwz r13,STKROOM+0(sp)
+ lwz r14,STKROOM+4(sp)
+ lwz r15,STKROOM+8(sp)
+ lwz r16,STKROOM+12(sp)
+ lwz r17,STKROOM+16(sp)
+ lwz r18,STKROOM+20(sp)
+ lwz r19,STKROOM+24(sp)
+ lwz r20,STKROOM+28(sp)
+ lwz r21,STKROOM+32(sp)
+ lwz r22,STKROOM+36(sp)
+ lwz r23,STKROOM+40(sp)
+ lwz r24,STKROOM+44(sp)
+ lwz r25,STKROOM+48(sp)
+ lwz r26,STKROOM+52(sp)
+ lwz r27,STKROOM+56(sp)
+ lwz r28,STKROOM+60(sp)
+ lwz r29,STKROOM+64(sp)
+ lwz r30,STKROOM+68(sp)
+ lwz r31,STKROOM+72(sp)
+
+ // and pray...
+NESTED_EXIT( InvokeStdCall, SSIZE, 0, 0 )
+
+
+
+ .align 4
+LPushValJmpTab:
+ .word LNextArg //VT_EMPTY [0]
+ .word LPush4 //VT_NULL [4]
+ .word LPush2 //VT_I2 [2]
+ .word LPush4 //VT_I4 [4]
+ .word LPushR4 //VT_R4 [4]
+ .word LPushR8 //VT_R8 [8]
+ .word LPush8 //VT_CY [8]
+ .word LPushR8 //VT_DATE [8]
+ .word LPush4 //VT_BSTR [4]
+ .word LPush4 //VT_DISPATCH [4]
+ .word LPush4 //VT_ERROR [4]
+ .word LPush2 //VT_BOOL [2]
+ .word LPushVar //VT_VARIANT [16]
+ .word LPush4 //VT_UNKNOWN [4]
+ .word 0 //unused
+ .word 0 //unused
+ .word LPush1 //VT_I1 [1]
+ .word LPush1 //VT_UI1 [1]
+
+
+ .align 4
+LRetValJmpTab:
+ .word LDone //VT_EMPTY
+ .word LRetI4 //VT_NULL
+ .word LRetI2 //VT_I2
+ .word LRetI4 //VT_I4
+ .word LRetR4 //VT_R4
+ .word LRetR8 //VT_R8
+ .word LRetCy //VT_CY
+ .word LRetR8 //VT_DATE
+ .word LRetPtr //VT_BSTR
+ .word LRetPtr //VT_DISPATCH
+ .word LRetI4 //VT_ERROR
+ .word LRetI2 //VT_BOOL
+ .word LRetVar //VT_VARIANT
+ .word LRetPtr //VT_UNKNOWN
+ .word 0 //unused
+ .word 0 //unused
+ .word 0 //unused (VT_I1)
+ .word LRetUI1 //VT_UI1
+
+ .align 2
+rgcbVtSize:
+ .half 0 //VT_EMPTY
+ .half 4 //VT_NULL
+ .half 4 //VT_I2
+ .half 4 //VT_I4
+ .half 4 //VT_R4
+ .half 8 //VT_R8
+ .half 8 //VT_CY
+ .half 8 //VT_DATE
+ .half 4 //VT_BSTR
+ .half 4 //VT_DISPATCH
+ .half 4 //VT_ERROR
+ .half 4 //VT_BOOL
+ .half 16 //VT_VARIANT
+ .half 4 //VT_UNKNOWN
+ .half 0 //unused
+ .half 0 //unused
+ .half 4 //VT_I1
+ .half 4 //VT_UI1
+
+
+ .align 2
+rgfStructReturn:
+ .half 0 //VT_EMPTY
+ .half 0 //VT_NULL
+ .half 0 //VT_I2
+ .half 0 //VT_I4
+ .half 0 //VT_R4
+ .half 0 //VT_R8
+ .half 1 //VT_CY
+ .half 0 //VT_DATE
+ .half 0 //VT_BSTR
+ .half 0 //VT_DISPATCH
+ .half 0 //VT_ERROR
+ .half 0 //VT_BOOL
+ .half 1 //VT_VARIANT
+ .half 0 //VT_UNKNOWN
+ .half 0 //unused
+ .half 0 //unused
+ .half 0 //VT_I1
+ .half 0 //VT_UI1
+
+
diff --git a/private/oleauto/src/inc/dispatch.h b/private/oleauto/src/inc/dispatch.h
new file mode 100644
index 000000000..1ba77f7b4
--- /dev/null
+++ b/private/oleauto/src/inc/dispatch.h
@@ -0,0 +1,1412 @@
+/***
+*dispatch.h - OLE Automation definitions.
+*
+* Copyright (C) 1992-1995, Microsoft Corporation. All Rights Reserved.
+*
+*Purpose:
+* This file defines the Ole Automation interfaces and APIs.
+*
+*Implementation Notes:
+* This file requires ole2.h
+*
+*****************************************************************************/
+
+#ifndef _DISPATCH_H_
+#define _DISPATCH_H_
+
+#include "variant.h"
+
+#ifndef BEGIN_INTERFACE
+# define BEGIN_INTERFACE
+#endif
+
+#if defined(NONAMELESSUNION) || (defined(_MAC) && !defined(__cplusplus) && !defined(_MSC_VER))
+# define UNION_NAME(X) X
+#else
+# define UNION_NAME(X)
+#endif
+
+
+DEFINE_OLEGUID(IID_IDispatch, 0x00020400L, 0, 0);
+DEFINE_OLEGUID(IID_IEnumVARIANT, 0x00020404L, 0, 0);
+DEFINE_OLEGUID(IID_ITypeInfo, 0x00020401L, 0, 0);
+DEFINE_OLEGUID(IID_ITypeLib, 0x00020402L, 0, 0);
+DEFINE_OLEGUID(IID_ITypeComp, 0x00020403L, 0, 0);
+DEFINE_OLEGUID(IID_ICreateTypeInfo, 0x00020405L, 0, 0);
+DEFINE_OLEGUID(IID_ICreateTypeLib, 0x00020406L, 0, 0);
+
+DEFINE_OLEGUID(IID_StdOle, 0x00020430L, 0, 0);
+#define STDOLE_MAJORVERNUM 0x1
+#define STDOLE_MINORVERNUM 0x0
+#define STDOLE_LCID 0x0000
+
+// {1CF2B120-547D-101B-8E65-08002B2BD119}
+DEFINE_GUID(IID_IErrorInfo,
+ 0x1CF2B120L, 0x547D, 0x101B, 0x8E, 0x65, 0x08, 0x00, 0x2B, 0x2B, 0xD1, 0x19);
+
+// {22F03340-547D-101B-8E65-08002B2BD119}
+DEFINE_GUID(IID_ICreateErrorInfo,
+ 0x22F03340L, 0x547D, 0x101B, 0x8E, 0x65, 0x08, 0x00, 0x2B, 0x2B, 0xD1, 0x19);
+
+// {DF0B3D60-548F-101B-8E65-08002B2BD119}
+DEFINE_GUID(IID_ISupportErrorInfo,
+ 0xDF0B3D60L, 0x548F, 0x101B, 0x8E, 0x65, 0x08, 0x00, 0x2B, 0x2B, 0xD1, 0x19);
+
+
+/* forward declarations */
+#ifdef __cplusplus
+
+ interface IDispatch;
+ interface IEnumVARIANT;
+ interface ITypeInfo;
+ interface ITypeLib;
+ interface ITypeComp;
+ interface ICreateTypeInfo;
+ interface ICreateTypeLib;
+ interface IErrorInfo;
+ interface ICreateErrorInfo;
+ interface ISupportErrorInfo;
+
+#else
+
+ typedef interface IDispatch IDispatch;
+ typedef interface IEnumVARIANT IEnumVARIANT;
+ typedef interface ITypeInfo ITypeInfo;
+ typedef interface ITypeLib ITypeLib;
+ typedef interface ITypeComp ITypeComp;
+ typedef interface ICreateTypeInfo ICreateTypeInfo;
+ typedef interface ICreateTypeLib ICreateTypeLib;
+ typedef interface IErrorInfo IErrorInfo;
+ typedef interface ICreateErrorInfo ICreateErrorInfo;
+ typedef interface ISupportErrorInfo ISupportErrorInfo;
+
+#endif
+
+
+/* OLE Automation error codes */
+
+#define DISP_ERROR(X) MAKE_SCODE(SEVERITY_ERROR, FACILITY_DISPATCH, X)
+
+#define DISP_E_UNKNOWNINTERFACE DISP_ERROR(1)
+#define DISP_E_MEMBERNOTFOUND DISP_ERROR(3)
+#define DISP_E_PARAMNOTFOUND DISP_ERROR(4)
+#define DISP_E_TYPEMISMATCH DISP_ERROR(5)
+#define DISP_E_UNKNOWNNAME DISP_ERROR(6)
+#define DISP_E_NONAMEDARGS DISP_ERROR(7)
+#define DISP_E_BADVARTYPE DISP_ERROR(8)
+#define DISP_E_EXCEPTION DISP_ERROR(9)
+#define DISP_E_OVERFLOW DISP_ERROR(10)
+#define DISP_E_BADINDEX DISP_ERROR(11)
+#define DISP_E_UNKNOWNLCID DISP_ERROR(12)
+#define DISP_E_ARRAYISLOCKED DISP_ERROR(13)
+#define DISP_E_BADPARAMCOUNT DISP_ERROR(14)
+#define DISP_E_PARAMNOTOPTIONAL DISP_ERROR(15)
+#define DISP_E_BADCALLEE DISP_ERROR(16)
+#define DISP_E_NOTACOLLECTION DISP_ERROR(17)
+
+
+#define TYPE_ERROR(X) MAKE_SCODE(SEVERITY_ERROR, FACILITY_DISPATCH, X)
+
+#define TYPE_E_BUFFERTOOSMALL TYPE_ERROR(32790)
+#define TYPE_E_INVDATAREAD TYPE_ERROR(32792)
+#define TYPE_E_UNSUPFORMAT TYPE_ERROR(32793)
+#define TYPE_E_REGISTRYACCESS TYPE_ERROR(32796)
+#define TYPE_E_LIBNOTREGISTERED TYPE_ERROR(32797)
+#define TYPE_E_UNDEFINEDTYPE TYPE_ERROR(32807)
+#define TYPE_E_QUALIFIEDNAMEDISALLOWED TYPE_ERROR(32808)
+#define TYPE_E_INVALIDSTATE TYPE_ERROR(32809)
+#define TYPE_E_WRONGTYPEKIND TYPE_ERROR(32810)
+#define TYPE_E_ELEMENTNOTFOUND TYPE_ERROR(32811)
+#define TYPE_E_AMBIGUOUSNAME TYPE_ERROR(32812)
+#define TYPE_E_NAMECONFLICT TYPE_ERROR(32813)
+#define TYPE_E_UNKNOWNLCID TYPE_ERROR(32814)
+#define TYPE_E_DLLFUNCTIONNOTFOUND TYPE_ERROR(32815)
+#define TYPE_E_BADMODULEKIND TYPE_ERROR(35005)
+#define TYPE_E_SIZETOOBIG TYPE_ERROR(35013)
+#define TYPE_E_DUPLICATEID TYPE_ERROR(35014)
+#define TYPE_E_INVALIDID TYPE_ERROR(35023)
+#define TYPE_E_TYPEMISMATCH TYPE_ERROR(36000)
+#define TYPE_E_OUTOFBOUNDS TYPE_ERROR(36001)
+#define TYPE_E_IOERROR TYPE_ERROR(36002)
+#define TYPE_E_CANTCREATETMPFILE TYPE_ERROR(36003)
+#define TYPE_E_CANTLOADLIBRARY TYPE_ERROR(40010)
+#define TYPE_E_INCONSISTENTPROPFUNCS TYPE_ERROR(40067)
+#define TYPE_E_CIRCULARTYPE TYPE_ERROR(40068)
+
+
+/* if not already picked up from olenls.h */
+#ifndef _LCID_DEFINED
+typedef unsigned long LCID;
+# define _LCID_DEFINED
+#endif
+
+
+
+/*---------------------------------------------------------------------*/
+/* BSTR API */
+/*---------------------------------------------------------------------*/
+
+STDAPI_(BSTR) SysAllocString(const OLECHAR FAR*);
+STDAPI_(int) SysReAllocString(BSTR FAR*, const OLECHAR FAR*);
+STDAPI_(BSTR) SysAllocStringLen(const OLECHAR FAR*, unsigned int);
+STDAPI_(int) SysReAllocStringLen(BSTR FAR*, const OLECHAR FAR*, unsigned int);
+STDAPI_(void) SysFreeString(BSTR);
+STDAPI_(unsigned int) SysStringLen(BSTR);
+
+#ifdef WIN32
+STDAPI_(unsigned int) SysStringByteLen(BSTR bstr);
+STDAPI_(BSTR) SysAllocStringByteLen(const char FAR* psz, unsigned int len);
+#endif
+
+
+/*---------------------------------------------------------------------*/
+/* Time API */
+/*---------------------------------------------------------------------*/
+
+STDAPI_(int)
+DosDateTimeToVariantTime(
+ unsigned short wDosDate,
+ unsigned short wDosTime,
+ double FAR* pvtime);
+
+STDAPI_(int)
+VariantTimeToDosDateTime(
+ double vtime,
+ unsigned short FAR* pwDosDate,
+ unsigned short FAR* pwDosTime);
+
+
+/*---------------------------------------------------------------------*/
+/* SafeArray API */
+/*---------------------------------------------------------------------*/
+
+STDAPI
+SafeArrayAllocDescriptor(unsigned int cDims, SAFEARRAY FAR* FAR* ppsaOut);
+
+STDAPI SafeArrayAllocData(SAFEARRAY FAR* psa);
+
+STDAPI_(SAFEARRAY FAR*)
+SafeArrayCreate(
+ VARTYPE vt,
+ unsigned int cDims,
+ SAFEARRAYBOUND FAR* rgsabound);
+
+STDAPI SafeArrayDestroyDescriptor(SAFEARRAY FAR* psa);
+
+STDAPI SafeArrayDestroyData(SAFEARRAY FAR* psa);
+
+STDAPI SafeArrayDestroy(SAFEARRAY FAR* psa);
+
+STDAPI SafeArrayRedim(SAFEARRAY FAR* psa, SAFEARRAYBOUND FAR* psaboundNew);
+
+STDAPI_(unsigned int) SafeArrayGetDim(SAFEARRAY FAR* psa);
+
+STDAPI_(unsigned int) SafeArrayGetElemsize(SAFEARRAY FAR* psa);
+
+STDAPI
+SafeArrayGetUBound(SAFEARRAY FAR* psa, unsigned int nDim, long FAR* plUbound);
+
+STDAPI
+SafeArrayGetLBound(SAFEARRAY FAR* psa, unsigned int nDim, long FAR* plLbound);
+
+STDAPI SafeArrayLock(SAFEARRAY FAR* psa);
+
+STDAPI SafeArrayUnlock(SAFEARRAY FAR* psa);
+
+STDAPI SafeArrayAccessData(SAFEARRAY FAR* psa, void HUGEP* FAR* ppvData);
+
+STDAPI SafeArrayUnaccessData(SAFEARRAY FAR* psa);
+
+STDAPI
+SafeArrayGetElement(
+ SAFEARRAY FAR* psa,
+ long FAR* rgIndices,
+ void FAR* pv);
+
+STDAPI
+SafeArrayPutElement(
+ SAFEARRAY FAR* psa,
+ long FAR* rgIndices,
+ void FAR* pv);
+
+STDAPI
+SafeArrayCopy(
+ SAFEARRAY FAR* psa,
+ SAFEARRAY FAR* FAR* ppsaOut);
+
+STDAPI
+SafeArrayPtrOfIndex(
+ SAFEARRAY FAR* psa,
+ long FAR* rgIndices,
+ void HUGEP* FAR* ppvData);
+
+
+/*---------------------------------------------------------------------*/
+/* VARIANT API */
+/*---------------------------------------------------------------------*/
+
+STDAPI_(void)
+VariantInit(VARIANTARG FAR* pvarg);
+
+STDAPI
+VariantClear(VARIANTARG FAR* pvarg);
+
+STDAPI
+VariantCopy(
+ VARIANTARG FAR* pvargDest,
+ VARIANTARG FAR* pvargSrc);
+
+STDAPI
+VariantCopyInd(
+ VARIANT FAR* pvarDest,
+ VARIANTARG FAR* pvargSrc);
+
+STDAPI
+VariantChangeType(
+ VARIANTARG FAR* pvargDest,
+ VARIANTARG FAR* pvarSrc,
+ unsigned short wFlags,
+ VARTYPE vt);
+
+STDAPI
+VariantChangeTypeEx(
+ VARIANTARG FAR* pvargDest,
+ VARIANTARG FAR* pvarSrc,
+ LCID lcid,
+ unsigned short wFlags,
+ VARTYPE vt);
+
+#define VARIANT_NOVALUEPROP 1
+
+
+/*---------------------------------------------------------------------*/
+/* VARTYPE Coercion API */
+/*---------------------------------------------------------------------*/
+
+/* Note: The routines that convert *from* a string are defined
+ * to take a OLECHAR* rather than a BSTR because no allocation is
+ * required, and this makes the routines a bit more generic.
+ * They may of course still be passed a BSTR as the strIn param.
+ */
+
+
+/* Any of the coersion functions that converts either from or to a string
+ * takes an additional lcid and dwFlags arguments. The lcid argument allows
+ * locale specific parsing to occur. The dwFlags allow additional function
+ * specific condition to occur. All function that accept the dwFlags argument
+ * can include either 0 or LOCALE_NOUSEROVERRIDE flag. In addition, the
+ * VarDateFromStr functions also accepts the VAR_TIMEVALUEONLY and
+ * VAR_DATEVALUEONLY flags
+ */
+
+#define VAR_TIMEVALUEONLY 0x0001 /* return time value */
+#define VAR_DATEVALUEONLY 0x0002 /* return date value */
+
+
+STDAPI VarUI1FromI2(short sIn, unsigned char FAR* pbOut);
+STDAPI VarUI1FromI4(long lIn, unsigned char FAR* pbOut);
+STDAPI VarUI1FromR4(float fltIn, unsigned char FAR* pbOut);
+STDAPI VarUI1FromR8(double dblIn, unsigned char FAR* pbOut);
+STDAPI VarUI1FromCy(CY cyIn, unsigned char FAR* pbOut);
+STDAPI VarUI1FromDate(DATE dateIn, unsigned char FAR* pbOut);
+STDAPI VarUI1FromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, unsigned char FAR* pbOut);
+STDAPI VarUI1FromDisp(IDispatch FAR* pdispIn, LCID lcid, unsigned char FAR* pbOut);
+STDAPI VarUI1FromBool(VARIANT_BOOL boolIn, unsigned char FAR* pbOut);
+
+STDAPI VarI2FromUI1(unsigned char bIn, short FAR* psOut);
+STDAPI VarI2FromI4(long lIn, short FAR* psOut);
+STDAPI VarI2FromR4(float fltIn, short FAR* psOut);
+STDAPI VarI2FromR8(double dblIn, short FAR* psOut);
+STDAPI VarI2FromCy(CY cyIn, short FAR* psOut);
+STDAPI VarI2FromDate(DATE dateIn, short FAR* psOut);
+STDAPI VarI2FromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, short FAR* psOut);
+STDAPI VarI2FromDisp(IDispatch FAR* pdispIn, LCID lcid, short FAR* psOut);
+STDAPI VarI2FromBool(VARIANT_BOOL boolIn, short FAR* psOut);
+
+STDAPI VarI4FromUI1(unsigned char bIn, long FAR* plOut);
+STDAPI VarI4FromI2(short sIn, long FAR* plOut);
+STDAPI VarI4FromR4(float fltIn, long FAR* plOut);
+STDAPI VarI4FromR8(double dblIn, long FAR* plOut);
+STDAPI VarI4FromCy(CY cyIn, long FAR* plOut);
+STDAPI VarI4FromDate(DATE dateIn, long FAR* plOut);
+STDAPI VarI4FromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, long FAR* plOut);
+STDAPI VarI4FromDisp(IDispatch FAR* pdispIn, LCID lcid, long FAR* plOut);
+STDAPI VarI4FromBool(VARIANT_BOOL boolIn, long FAR* plOut);
+
+STDAPI VarR4FromUI1(unsigned char bIn, float FAR* pfltOut);
+STDAPI VarR4FromI2(short sIn, float FAR* pfltOut);
+STDAPI VarR4FromI4(long lIn, float FAR* pfltOut);
+STDAPI VarR4FromR8(double dblIn, float FAR* pfltOut);
+STDAPI VarR4FromCy(CY cyIn, float FAR* pfltOut);
+STDAPI VarR4FromDate(DATE dateIn, float FAR* pfltOut);
+STDAPI VarR4FromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, float FAR* pfltOut);
+STDAPI VarR4FromDisp(IDispatch FAR* pdispIn, LCID lcid, float FAR* pfltOut);
+STDAPI VarR4FromBool(VARIANT_BOOL boolIn, float FAR* pfltOut);
+
+STDAPI VarR8FromUI1(unsigned char bIn, double FAR* pdblOut);
+STDAPI VarR8FromI2(short sIn, double FAR* pdblOut);
+STDAPI VarR8FromI4(long lIn, double FAR* pdblOut);
+STDAPI VarR8FromR4(float fltIn, double FAR* pdblOut);
+STDAPI VarR8FromCy(CY cyIn, double FAR* pdblOut);
+STDAPI VarR8FromDate(DATE dateIn, double FAR* pdblOut);
+STDAPI VarR8FromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, double FAR* pdblOut);
+STDAPI VarR8FromDisp(IDispatch FAR* pdispIn, LCID lcid, double FAR* pdblOut);
+STDAPI VarR8FromBool(VARIANT_BOOL boolIn, double FAR* pdblOut);
+
+STDAPI VarDateFromUI1(unsigned char bIn, DATE FAR* pdateOut);
+STDAPI VarDateFromI2(short sIn, DATE FAR* pdateOut);
+STDAPI VarDateFromI4(long lIn, DATE FAR* pdateOut);
+STDAPI VarDateFromR4(float fltIn, DATE FAR* pdateOut);
+STDAPI VarDateFromR8(double dblIn, DATE FAR* pdateOut);
+STDAPI VarDateFromCy(CY cyIn, DATE FAR* pdateOut);
+STDAPI VarDateFromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, DATE FAR* pdateOut);
+STDAPI VarDateFromDisp(IDispatch FAR* pdispIn, LCID lcid, DATE FAR* pdateOut);
+STDAPI VarDateFromBool(VARIANT_BOOL boolIn, DATE FAR* pdateOut);
+
+STDAPI VarCyFromUI1(unsigned char bIn, CY FAR* pcyOut);
+STDAPI VarCyFromI2(short sIn, CY FAR* pcyOut);
+STDAPI VarCyFromI4(long lIn, CY FAR* pcyOut);
+STDAPI VarCyFromR4(float fltIn, CY FAR* pcyOut);
+STDAPI VarCyFromR8(double dblIn, CY FAR* pcyOut);
+STDAPI VarCyFromDate(DATE dateIn, CY FAR* pcyOut);
+STDAPI VarCyFromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, CY FAR* pcyOut);
+STDAPI VarCyFromDisp(IDispatch FAR* pdispIn, LCID lcid, CY FAR* pcyOut);
+STDAPI VarCyFromBool(VARIANT_BOOL boolIn, CY FAR* pcyOut);
+
+STDAPI VarBstrFromUI1(unsigned char bVal, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut);
+STDAPI VarBstrFromI2(short iVal, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut);
+STDAPI VarBstrFromI4(long lIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut);
+STDAPI VarBstrFromR4(float fltIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut);
+STDAPI VarBstrFromR8(double dblIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut);
+STDAPI VarBstrFromCy(CY cyIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut);
+STDAPI VarBstrFromDate(DATE dateIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut);
+STDAPI VarBstrFromDisp(IDispatch FAR* pdispIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut);
+STDAPI VarBstrFromBool(VARIANT_BOOL boolIn, LCID lcid, unsigned long dwFlags, BSTR FAR* pbstrOut);
+
+STDAPI VarBoolFromUI1(unsigned char bIn, VARIANT_BOOL FAR* pboolOut);
+STDAPI VarBoolFromI2(short sIn, VARIANT_BOOL FAR* pboolOut);
+STDAPI VarBoolFromI4(long lIn, VARIANT_BOOL FAR* pboolOut);
+STDAPI VarBoolFromR4(float fltIn, VARIANT_BOOL FAR* pboolOut);
+STDAPI VarBoolFromR8(double dblIn, VARIANT_BOOL FAR* pboolOut);
+STDAPI VarBoolFromDate(DATE dateIn, VARIANT_BOOL FAR* pboolOut);
+STDAPI VarBoolFromCy(CY cyIn, VARIANT_BOOL FAR* pboolOut);
+STDAPI VarBoolFromStr(OLECHAR FAR* strIn, LCID lcid, unsigned long dwFlags, VARIANT_BOOL FAR* pboolOut);
+STDAPI VarBoolFromDisp(IDispatch FAR* pdispIn, LCID lcid, VARIANT_BOOL FAR* pboolOut);
+
+
+/* Mac Note: On the Mac, the coersion functions support the
+ * Symantec C++ calling convention for float/double. To support
+ * float/double arguments compiled with the MPW C compiler,
+ * use the following APIs to move MPW float/double values into
+ * a VARIANT.
+ */
+
+#ifdef _MAC
+STDAPI MPWVarFromR4(float FAR* pfltIn, VARIANT FAR* pvarOut);
+STDAPI MPWVarFromR8(double FAR* pdblIn, VARIANT FAR* pvarOut);
+STDAPI MPWR4FromVar(VARIANT FAR* pvarIn, float FAR* pfltOut);
+STDAPI MPWR8FromVar(VARIANT FAR* pvarIn, double FAR* pdblOut);
+#endif
+
+
+
+/*---------------------------------------------------------------------*/
+/* ITypeLib */
+/*---------------------------------------------------------------------*/
+
+
+typedef long DISPID;
+typedef DISPID MEMBERID;
+
+#define MEMBERID_NIL DISPID_UNKNOWN
+#define ID_DEFAULTINST -2
+
+typedef enum tagSYSKIND {
+ SYS_WIN16
+ , SYS_WIN32
+ , SYS_MAC
+#ifdef _MAC
+ , SYS_FORCELONG = 2147483647
+#endif
+} SYSKIND;
+
+typedef enum tagLIBFLAGS {
+ LIBFLAG_FRESTRICTED = 0x01
+ , LIBFLAG_FCONTROL = 0x02
+ , LIBFLAG_FHIDDEN = 0x04
+#ifdef _MAC
+ , LIBFLAG_FORCELONG = 2147483647
+#endif
+} LIBFLAGS;
+
+typedef struct FARSTRUCT tagTLIBATTR {
+ GUID guid; /* globally unique library id */
+ LCID lcid; /* locale of the TypeLibrary */
+ SYSKIND syskind;
+ unsigned short wMajorVerNum;/* major version number */
+ unsigned short wMinorVerNum;/* minor version number */
+ unsigned short wLibFlags; /* library flags */
+} TLIBATTR, FAR* LPTLIBATTR;
+
+typedef enum tagTYPEKIND {
+ TKIND_ENUM = 0
+ , TKIND_RECORD
+ , TKIND_MODULE
+ , TKIND_INTERFACE
+ , TKIND_DISPATCH
+ , TKIND_COCLASS
+ , TKIND_ALIAS
+ , TKIND_UNION
+ , TKIND_MAX /* end of enum marker */
+#ifdef _MAC
+ , TKIND_FORCELONG = 2147483647
+#endif
+} TYPEKIND;
+
+#undef INTERFACE
+#define INTERFACE ITypeLib
+
+DECLARE_INTERFACE_(ITypeLib, IUnknown)
+{
+ BEGIN_INTERFACE
+
+ /* IUnknown methods */
+ STDMETHOD(QueryInterface)(THIS_ REFIID riid, void FAR* FAR* ppvObj) PURE;
+ STDMETHOD_(unsigned long, AddRef)(THIS) PURE;
+ STDMETHOD_(unsigned long, Release)(THIS) PURE;
+
+ /* ITypeLib methods */
+ STDMETHOD_(unsigned int,GetTypeInfoCount)(THIS) PURE;
+
+ STDMETHOD(GetTypeInfo)(THIS_
+ unsigned int index, ITypeInfo FAR* FAR* pptinfo) PURE;
+
+ STDMETHOD(GetTypeInfoType)(THIS_
+ unsigned int index, TYPEKIND FAR* ptypekind) PURE;
+
+ STDMETHOD(GetTypeInfoOfGuid)(THIS_
+ REFGUID guid, ITypeInfo FAR* FAR* pptinfo) PURE;
+
+ STDMETHOD(GetLibAttr)(THIS_
+ TLIBATTR FAR* FAR* pptlibattr) PURE;
+
+ STDMETHOD(GetTypeComp)(THIS_
+ ITypeComp FAR* FAR* pptcomp) PURE;
+
+ STDMETHOD(GetDocumentation)(THIS_
+ int index,
+ BSTR FAR* pbstrName,
+ BSTR FAR* pbstrDocString,
+ unsigned long FAR* pdwHelpContext,
+ BSTR FAR* pbstrHelpFile) PURE;
+
+ STDMETHOD(IsName)(THIS_
+ OLECHAR FAR* szNameBuf,
+ unsigned long lHashVal,
+ int FAR* lpfName) PURE;
+
+ STDMETHOD(FindName)(THIS_
+ OLECHAR FAR* szNameBuf,
+ unsigned long lHashVal,
+ ITypeInfo FAR* FAR* rgptinfo,
+ MEMBERID FAR* rgmemid,
+ unsigned short FAR* pcFound) PURE;
+
+ STDMETHOD_(void, ReleaseTLibAttr)(THIS_ TLIBATTR FAR* ptlibattr) PURE;
+};
+
+typedef ITypeLib FAR* LPTYPELIB;
+
+
+
+/*---------------------------------------------------------------------*/
+/* ITypeInfo */
+/*---------------------------------------------------------------------*/
+
+typedef unsigned long HREFTYPE;
+
+
+typedef struct FARSTRUCT tagTYPEDESC {
+ union {
+ /* VT_PTR - the pointed-at type */
+ struct FARSTRUCT tagTYPEDESC FAR* lptdesc;
+
+ /* VT_CARRAY */
+ struct FARSTRUCT tagARRAYDESC FAR* lpadesc;
+
+ /* VT_USERDEFINED - this is used to get a TypeInfo for the UDT */
+ HREFTYPE hreftype;
+
+ }UNION_NAME(u);
+ VARTYPE vt;
+} TYPEDESC;
+
+typedef struct FARSTRUCT tagARRAYDESC {
+ TYPEDESC tdescElem; /* element type */
+ unsigned short cDims; /* dimension count */
+ SAFEARRAYBOUND rgbounds[1]; /* variable length array of bounds */
+} ARRAYDESC;
+
+typedef struct FARSTRUCT tagIDLDESC {
+#if defined(WIN32) || defined(_MAC)
+ unsigned long dwReserved;
+#else
+ BSTR bstrIDLInfo; /* reserved, but original name retained for
+ compatibilty */
+#endif
+ unsigned short wIDLFlags; /* IN, OUT, etc */
+} IDLDESC, FAR* LPIDLDESC;
+
+
+#define IDLFLAG_NONE 0
+#define IDLFLAG_FIN 0x1
+#define IDLFLAG_FOUT 0x2
+#define IDLFLAG_FLCID 0x4
+#define IDLFLAG_FRETVAL 0x8
+
+typedef struct FARSTRUCT tagELEMDESC {
+ TYPEDESC tdesc; /* the type of the element */
+ IDLDESC idldesc; /* info for remoting the element */
+} ELEMDESC, FAR* LPELEMDESC;
+
+
+typedef struct FARSTRUCT tagTYPEATTR {
+ GUID guid; /* the GUID of the TypeInfo */
+ LCID lcid; /* locale of member names and doc strings */
+ unsigned long dwReserved;
+ MEMBERID memidConstructor; /* ID of constructor, MEMBERID_NIL if none */
+ MEMBERID memidDestructor; /* ID of destructor, MEMBERID_NIL if none */
+ OLECHAR FAR* lpstrSchema; /* reserved for future use */
+ unsigned long cbSizeInstance;/* the size of an instance of this type */
+ TYPEKIND typekind; /* the kind of type this typeinfo describes */
+ unsigned short cFuncs; /* number of functions */
+ unsigned short cVars; /* number of variables / data members */
+ unsigned short cImplTypes; /* number of implemented interfaces */
+ unsigned short cbSizeVft; /* the size of this types virtual func table */
+ unsigned short cbAlignment; /* the alignment for an instance of this type */
+ unsigned short wTypeFlags;
+ unsigned short wMajorVerNum;/* major version number */
+ unsigned short wMinorVerNum;/* minor version number */
+ TYPEDESC tdescAlias; /* if typekind == TKIND_ALIAS this specifies
+ the type for which this type is an alias */
+ IDLDESC idldescType; /* IDL attributes of the described type */
+} TYPEATTR, FAR* LPTYPEATTR;
+
+typedef struct FARSTRUCT tagDISPPARAMS{
+ VARIANTARG FAR* rgvarg;
+ DISPID FAR* rgdispidNamedArgs;
+ unsigned int cArgs;
+ unsigned int cNamedArgs;
+} DISPPARAMS;
+
+typedef struct FARSTRUCT tagEXCEPINFO {
+ unsigned short wCode; /* An error code describing the error. */
+ /* Either (but not both) the wCode or */
+ /* scode fields must be set */
+ unsigned short wReserved;
+
+ BSTR bstrSource; /* A textual, human readable name of the
+ source of the exception. It is up to the
+ IDispatch implementor to fill this in.
+ Typically this will be an application name. */
+
+ BSTR bstrDescription; /* A textual, human readable description of the
+ error. If no description is available, NULL
+ should be used. */
+
+ BSTR bstrHelpFile; /* Fully qualified drive, path, and file name
+ of a help file with more information about
+ the error. If no help is available, NULL
+ should be used. */
+
+ unsigned long dwHelpContext;
+ /* help context of topic within the help file. */
+
+ void FAR* pvReserved;
+
+ /* Use of this field allows an application to defer filling in
+ the bstrDescription, bstrHelpFile, and dwHelpContext fields
+ until they are needed. This field might be used, for example,
+ if loading the string for the error is a time-consuming
+ operation. If deferred fill-in is not desired, this field should
+ be set to NULL. */
+#ifdef _MAC
+# ifdef _MSC_VER
+ HRESULT (STDAPICALLTYPE FAR* pfnDeferredFillIn)(struct tagEXCEPINFO FAR*);
+# else
+ STDAPICALLTYPE HRESULT (FAR* pfnDeferredFillIn)(struct tagEXCEPINFO FAR*);
+# endif
+#else
+ HRESULT (STDAPICALLTYPE FAR* pfnDeferredFillIn)(struct tagEXCEPINFO FAR*);
+#endif
+
+ SCODE scode; /* An SCODE describing the error. */
+
+} EXCEPINFO, FAR* LPEXCEPINFO;
+
+typedef enum tagCALLCONV {
+ CC_CDECL = 1
+ , CC_MSCPASCAL
+ , CC_PASCAL = CC_MSCPASCAL
+ , CC_MACPASCAL
+ , CC_STDCALL
+ , CC_RESERVED
+ , CC_SYSCALL
+ , CC_MPWCDECL
+ , CC_MPWPASCAL
+ , CC_MAX /* end of enum marker */
+#ifdef _MAC
+ , CC_FORCELONG = 2147483647
+#endif
+} CALLCONV;
+
+typedef enum tagFUNCKIND {
+ FUNC_VIRTUAL
+ , FUNC_PUREVIRTUAL
+ , FUNC_NONVIRTUAL
+ , FUNC_STATIC
+ , FUNC_DISPATCH
+#ifdef _MAC
+ , FUNC_FORCELONG = 2147483647
+#endif
+} FUNCKIND;
+
+/* Flags for IDispatch::Invoke */
+#define DISPATCH_METHOD 0x1
+#define DISPATCH_PROPERTYGET 0x2
+#define DISPATCH_PROPERTYPUT 0x4
+#define DISPATCH_PROPERTYPUTREF 0x8
+
+typedef enum tagINVOKEKIND {
+ INVOKE_FUNC = DISPATCH_METHOD
+ , INVOKE_PROPERTYGET = DISPATCH_PROPERTYGET
+ , INVOKE_PROPERTYPUT = DISPATCH_PROPERTYPUT
+ , INVOKE_PROPERTYPUTREF = DISPATCH_PROPERTYPUTREF
+#ifdef _MAC
+ , INVOKE_FORCELONG = 2147483647
+#endif
+} INVOKEKIND;
+
+typedef struct FARSTRUCT tagFUNCDESC {
+ MEMBERID memid;
+ SCODE FAR* lprgscode;
+ ELEMDESC FAR* lprgelemdescParam; /* array of parameter types */
+ FUNCKIND funckind;
+ INVOKEKIND invkind;
+ CALLCONV callconv;
+ short cParams;
+ short cParamsOpt;
+ short oVft;
+ short cScodes;
+ ELEMDESC elemdescFunc;
+ unsigned short wFuncFlags;
+} FUNCDESC, FAR* LPFUNCDESC;
+
+typedef enum tagVARKIND {
+ VAR_PERINSTANCE
+ , VAR_STATIC
+ , VAR_CONST
+ , VAR_DISPATCH
+#ifdef _MAC
+ , VAR_FORCELONG = 2147483647
+#endif
+} VARKIND;
+
+typedef struct FARSTRUCT tagVARDESC {
+ MEMBERID memid;
+ OLECHAR FAR* lpstrSchema; /* reserved for future use */
+ union {
+ /* VAR_PERINSTANCE - the offset of this variable within the instance */
+ unsigned long oInst;
+
+ /* VAR_CONST - the value of the constant */
+ VARIANT FAR* lpvarValue;
+
+ }UNION_NAME(u);
+ ELEMDESC elemdescVar;
+ unsigned short wVarFlags;
+ VARKIND varkind;
+} VARDESC, FAR* LPVARDESC;
+
+typedef enum tagTYPEFLAGS {
+ TYPEFLAG_FAPPOBJECT = 0x01
+ , TYPEFLAG_FCANCREATE = 0x02
+ , TYPEFLAG_FLICENSED = 0x04
+ , TYPEFLAG_FPREDECLID = 0x08
+ , TYPEFLAG_FHIDDEN = 0x10
+ , TYPEFLAG_FCONTROL = 0x20
+ , TYPEFLAG_FDUAL = 0x40
+ , TYPEFLAG_FNONEXTENSIBLE = 0x80
+ , TYPEFLAG_FOLEAUTOMATION = 0x100
+#ifdef _MAC
+ , TYPEFLAG_FORCELONG = 2147483647
+#endif
+} TYPEFLAGS;
+
+typedef enum tagFUNCFLAGS {
+ FUNCFLAG_FRESTRICTED= 1
+ , FUNCFLAG_FSOURCE= 0x2
+ , FUNCFLAG_FBINDABLE= 0x4
+ , FUNCFLAG_FREQUESTEDIT= 0x8
+ , FUNCFLAG_FDISPLAYBIND= 0x10
+ , FUNCFLAG_FDEFAULTBIND= 0x20
+ , FUNCFLAG_FHIDDEN= 0x40
+#ifdef _MAC
+ , FUNCFLAG_FORCELONG = 2147483647
+#endif
+} FUNCFLAGS;
+
+typedef enum tagVARFLAGS {
+ VARFLAG_FREADONLY = 1
+ , VARFLAG_FSOURCE= 0x2
+ , VARFLAG_FBINDABLE= 0x4
+ , VARFLAG_FREQUESTEDIT= 0x8
+ , VARFLAG_FDISPLAYBIND= 0x10
+ , VARFLAG_FDEFAULTBIND= 0x20
+ , VARFLAG_FHIDDEN = 0x40
+#ifdef _MAC
+ , VARFLAG_FORCELONG = 2147483647
+#endif
+} VARFLAGS;
+
+/* IMPLTYPE Flags */
+#define IMPLTYPEFLAG_FDEFAULT 0x1
+#define IMPLTYPEFLAG_FSOURCE 0x2
+#define IMPLTYPEFLAG_FRESTRICTED 0x4
+
+#undef INTERFACE
+#define INTERFACE ITypeInfo
+
+DECLARE_INTERFACE_(ITypeInfo, IUnknown)
+{
+ BEGIN_INTERFACE
+
+ /* IUnknown methods */
+ STDMETHOD(QueryInterface)(THIS_ REFIID riid, void FAR* FAR* ppvObj) PURE;
+ STDMETHOD_(unsigned long, AddRef)(THIS) PURE;
+ STDMETHOD_(unsigned long, Release)(THIS) PURE;
+
+ /* ITypeInfo methods */
+ STDMETHOD(GetTypeAttr)(THIS_ TYPEATTR FAR* FAR* pptypeattr) PURE;
+
+ STDMETHOD(GetTypeComp)(THIS_ ITypeComp FAR* FAR* pptcomp) PURE;
+
+ STDMETHOD(GetFuncDesc)(THIS_
+ unsigned int index, FUNCDESC FAR* FAR* ppfuncdesc) PURE;
+
+ STDMETHOD(GetVarDesc)(THIS_
+ unsigned int index, VARDESC FAR* FAR* ppvardesc) PURE;
+
+ STDMETHOD(GetNames)(THIS_
+ MEMBERID memid,
+ BSTR FAR* rgbstrNames,
+ unsigned int cMaxNames,
+ unsigned int FAR* pcNames) PURE;
+
+ STDMETHOD(GetRefTypeOfImplType)(THIS_
+ unsigned int index, HREFTYPE FAR* phreftype) PURE;
+
+ STDMETHOD(GetImplTypeFlags)(THIS_
+ unsigned int index, int FAR* pimpltypeflags) PURE;
+
+ STDMETHOD(GetIDsOfNames)(THIS_
+ OLECHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ MEMBERID FAR* rgmemid) PURE;
+
+ STDMETHOD(Invoke)(THIS_
+ void FAR* pvInstance,
+ MEMBERID memid,
+ unsigned short wFlags,
+ DISPPARAMS FAR *pdispparams,
+ VARIANT FAR *pvarResult,
+ EXCEPINFO FAR *pexcepinfo,
+ unsigned int FAR *puArgErr) PURE;
+
+ STDMETHOD(GetDocumentation)(THIS_
+ MEMBERID memid,
+ BSTR FAR* pbstrName,
+ BSTR FAR* pbstrDocString,
+ unsigned long FAR* pdwHelpContext,
+ BSTR FAR* pbstrHelpFile) PURE;
+
+ STDMETHOD(GetDllEntry)(THIS_
+ MEMBERID memid,
+ INVOKEKIND invkind,
+ BSTR FAR* pbstrDllName,
+ BSTR FAR* pbstrName,
+ unsigned short FAR* pwOrdinal) PURE;
+
+ STDMETHOD(GetRefTypeInfo)(THIS_
+ HREFTYPE hreftype, ITypeInfo FAR* FAR* pptinfo) PURE;
+
+ STDMETHOD(AddressOfMember)(THIS_
+ MEMBERID memid, INVOKEKIND invkind, void FAR* FAR* ppv) PURE;
+
+ STDMETHOD(CreateInstance)(THIS_
+ IUnknown FAR* punkOuter,
+ REFIID riid,
+ void FAR* FAR* ppvObj) PURE;
+
+ STDMETHOD(GetMops)(THIS_ MEMBERID memid, BSTR FAR* pbstrMops) PURE;
+
+ STDMETHOD(GetContainingTypeLib)(THIS_
+ ITypeLib FAR* FAR* pptlib, unsigned int FAR* pindex) PURE;
+
+ STDMETHOD_(void, ReleaseTypeAttr)(THIS_ TYPEATTR FAR* ptypeattr) PURE;
+ STDMETHOD_(void, ReleaseFuncDesc)(THIS_ FUNCDESC FAR* pfuncdesc) PURE;
+ STDMETHOD_(void, ReleaseVarDesc)(THIS_ VARDESC FAR* pvardesc) PURE;
+};
+
+typedef ITypeInfo FAR* LPTYPEINFO;
+
+
+/*---------------------------------------------------------------------*/
+/* ITypeComp */
+/*---------------------------------------------------------------------*/
+
+typedef enum tagDESCKIND {
+ DESCKIND_NONE = 0
+ , DESCKIND_FUNCDESC
+ , DESCKIND_VARDESC
+ , DESCKIND_TYPECOMP
+ , DESCKIND_IMPLICITAPPOBJ
+ , DESCKIND_MAX /* end of enum marker */
+#ifdef _MAC
+ , DESCKIND_FORCELONG = 2147483647
+#endif
+} DESCKIND;
+
+typedef union tagBINDPTR {
+ FUNCDESC FAR* lpfuncdesc;
+ VARDESC FAR* lpvardesc;
+ ITypeComp FAR* lptcomp;
+} BINDPTR, FAR* LPBINDPTR;
+
+
+#undef INTERFACE
+#define INTERFACE ITypeComp
+
+DECLARE_INTERFACE_(ITypeComp, IUnknown)
+{
+ BEGIN_INTERFACE
+
+ /* IUnknown methods */
+ STDMETHOD(QueryInterface)(THIS_ REFIID riid, void FAR* FAR* ppvObj) PURE;
+ STDMETHOD_(unsigned long, AddRef)(THIS) PURE;
+ STDMETHOD_(unsigned long, Release)(THIS) PURE;
+
+ /* ITypeComp methods */
+ STDMETHOD(Bind)(THIS_
+ OLECHAR FAR* szName,
+ unsigned long lHashVal,
+ unsigned short wflags,
+ ITypeInfo FAR* FAR* pptinfo,
+ DESCKIND FAR* pdesckind,
+ BINDPTR FAR* pbindptr) PURE;
+
+ STDMETHOD(BindType)(THIS_
+ OLECHAR FAR* szName,
+ unsigned long lHashVal,
+ ITypeInfo FAR* FAR* pptinfo,
+ ITypeComp FAR* FAR* pptcomp) PURE;
+};
+
+typedef ITypeComp FAR* LPTYPECOMP;
+
+
+
+/*---------------------------------------------------------------------*/
+/* ICreateTypeLib */
+/*---------------------------------------------------------------------*/
+
+
+#undef INTERFACE
+#define INTERFACE ICreateTypeLib
+
+DECLARE_INTERFACE_(ICreateTypeLib, IUnknown)
+{
+ BEGIN_INTERFACE
+
+ /* IUnknown methods */
+ STDMETHOD(QueryInterface)(THIS_ REFIID riid, void FAR* FAR* ppvObj) PURE;
+ STDMETHOD_(unsigned long, AddRef)(THIS) PURE;
+ STDMETHOD_(unsigned long, Release)(THIS) PURE;
+
+ /* ICreateTypeLib methods */
+ STDMETHOD(CreateTypeInfo)(THIS_
+ OLECHAR FAR* szName,
+ TYPEKIND tkind,
+ ICreateTypeInfo FAR* FAR* lplpictinfo) PURE;
+
+ STDMETHOD(SetName)(THIS_ OLECHAR FAR* szName) PURE;
+
+ STDMETHOD(SetVersion)(THIS_
+ unsigned short wMajorVerNum, unsigned short wMinorVerNum) PURE;
+
+ STDMETHOD(SetGuid) (THIS_ REFGUID guid) PURE;
+
+ STDMETHOD(SetDocString)(THIS_ OLECHAR FAR* szDoc) PURE;
+
+ STDMETHOD(SetHelpFileName)(THIS_ OLECHAR FAR* szHelpFileName) PURE;
+
+ STDMETHOD(SetHelpContext)(THIS_ unsigned long dwHelpContext) PURE;
+
+ STDMETHOD(SetLcid)(THIS_ LCID lcid) PURE;
+
+ STDMETHOD(SetLibFlags)(THIS_ unsigned int uLibFlags) PURE;
+
+ STDMETHOD(SaveAllChanges)(THIS) PURE;
+};
+
+typedef ICreateTypeLib FAR* LPCREATETYPELIB;
+
+
+
+/*---------------------------------------------------------------------*/
+/* ICreateTypeInfo */
+/*---------------------------------------------------------------------*/
+
+#undef INTERFACE
+#define INTERFACE ICreateTypeInfo
+
+DECLARE_INTERFACE_(ICreateTypeInfo, IUnknown)
+{
+ BEGIN_INTERFACE
+
+ /* IUnknown methods */
+ STDMETHOD(QueryInterface)(THIS_ REFIID riid, void FAR* FAR* ppvObj) PURE;
+ STDMETHOD_(unsigned long, AddRef)(THIS) PURE;
+ STDMETHOD_(unsigned long, Release)(THIS) PURE;
+
+ /* ICreateTypeInfo methods */
+ STDMETHOD(SetGuid)(THIS_ REFGUID guid) PURE;
+
+ STDMETHOD(SetTypeFlags)(THIS_ unsigned int uTypeFlags) PURE;
+
+ STDMETHOD(SetDocString)(THIS_ OLECHAR FAR* pstrDoc) PURE;
+
+ STDMETHOD(SetHelpContext)(THIS_ unsigned long dwHelpContext) PURE;
+
+ STDMETHOD(SetVersion)(THIS_
+ unsigned short wMajorVerNum, unsigned short wMinorVerNum) PURE;
+
+ STDMETHOD(AddRefTypeInfo)(THIS_
+ ITypeInfo FAR* ptinfo, HREFTYPE FAR* phreftype) PURE;
+
+ STDMETHOD(AddFuncDesc)(THIS_
+ unsigned int index, FUNCDESC FAR* pfuncdesc) PURE;
+
+ STDMETHOD(AddImplType)(THIS_
+ unsigned int index, HREFTYPE hreftype) PURE;
+
+ STDMETHOD(SetImplTypeFlags)(THIS_
+ unsigned int index, int impltypeflags) PURE;
+
+ STDMETHOD(SetAlignment)(THIS_ unsigned short cbAlignment) PURE;
+
+ STDMETHOD(SetSchema)(THIS_ OLECHAR FAR* lpstrSchema) PURE;
+
+ STDMETHOD(AddVarDesc)(THIS_
+ unsigned int index, VARDESC FAR* pvardesc) PURE;
+
+ STDMETHOD(SetFuncAndParamNames)(THIS_
+ unsigned int index, OLECHAR FAR* FAR* rgszNames, unsigned int cNames) PURE;
+
+ STDMETHOD(SetVarName)(THIS_
+ unsigned int index, OLECHAR FAR* szName) PURE;
+
+ STDMETHOD(SetTypeDescAlias)(THIS_
+ TYPEDESC FAR* ptdescAlias) PURE;
+
+ STDMETHOD(DefineFuncAsDllEntry)(THIS_
+ unsigned int index, OLECHAR FAR* szDllName, OLECHAR FAR* szProcName) PURE;
+
+ STDMETHOD(SetFuncDocString)(THIS_
+ unsigned int index, OLECHAR FAR* szDocString) PURE;
+
+ STDMETHOD(SetVarDocString)(THIS_
+ unsigned int index, OLECHAR FAR* szDocString) PURE;
+
+ STDMETHOD(SetFuncHelpContext)(THIS_
+ unsigned int index, unsigned long dwHelpContext) PURE;
+
+ STDMETHOD(SetVarHelpContext)(THIS_
+ unsigned int index, unsigned long dwHelpContext) PURE;
+
+ STDMETHOD(SetMops)(THIS_
+ unsigned int index, BSTR bstrMops) PURE;
+
+ STDMETHOD(SetTypeIdldesc)(THIS_
+ IDLDESC FAR* pidldesc) PURE;
+
+ STDMETHOD(LayOut)(THIS) PURE;
+};
+
+typedef ICreateTypeInfo FAR* LPCREATETYPEINFO;
+
+
+
+/*---------------------------------------------------------------------*/
+/* TypeInfo APIs */
+/*---------------------------------------------------------------------*/
+/* compute a 32bit hash value for the given name based on the lcid and system kind
+ */
+#ifdef WIN32
+STDAPI_(unsigned long)
+LHashValOfNameSysA(SYSKIND syskind, LCID lcid, const char FAR* szName);
+#endif //WIN32
+
+STDAPI_(unsigned long)
+LHashValOfNameSys(SYSKIND syskind, LCID lcid, const OLECHAR FAR* szName);
+
+/* Macro to compute a 32bit hash value for the given name based on the LCID
+ */
+#ifdef _MAC
+#define LHashValOfName(lcid, szName) \
+ LHashValOfNameSys(SYS_MAC, lcid, szName)
+#else
+#define LHashValOfName(lcid, szName) \
+ LHashValOfNameSys(SYS_WIN32, lcid, szName)
+#endif
+
+/* compute a 16bit hash value from 32 bit hash value
+ */
+#define WHashValOfLHashVal(lhashval) \
+ ((unsigned short) (0x0000ffff & (lhashval)))
+
+/* Check if the hash values are compatible.
+*/
+#define IsHashValCompatible(lhashval1, lhashval2) \
+ ((BOOL) ((0x00ff0000 & (lhashval1)) == (0x00ff0000 & (lhashval2))))
+
+/* load the typelib from the file with the given filename
+ */
+STDAPI
+LoadTypeLib(const OLECHAR FAR* szFile, ITypeLib FAR* FAR* pptlib);
+
+/* load registered typelib
+ */
+STDAPI
+LoadRegTypeLib(
+ REFGUID rguid,
+ unsigned short wVerMajor,
+ unsigned short wVerMinor,
+ LCID lcid,
+ ITypeLib FAR* FAR* pptlib);
+
+/* get path to registered typelib
+ */
+STDAPI
+QueryPathOfRegTypeLib(
+ REFGUID guid,
+ unsigned short wMaj,
+ unsigned short wMin,
+ LCID lcid,
+ LPBSTR lpbstrPathName);
+
+/* add typelib to registry
+ */
+STDAPI
+RegisterTypeLib(
+ ITypeLib FAR* ptlib,
+ OLECHAR FAR* szFullPath,
+ OLECHAR FAR* szHelpDir);
+
+STDAPI
+CreateTypeLib(SYSKIND syskind, const OLECHAR FAR* szFile, ICreateTypeLib FAR* FAR* ppctlib);
+
+#ifdef _MAC
+/* load the typelib from the file with the given FSSPEC
+ */
+STDAPI
+LoadTypeLibFSp(const FSSpec *pfsspec, ITypeLib FAR* FAR* pptlib);
+
+/* register the location of the standard typelib folder
+ */
+STDAPI
+RegisterTypeLibFolder(OLECHAR FAR* szFullPath);
+
+/* obtain the path to the registered typelib folder
+ */
+STDAPI
+QueryTypeLibFolder(LPBSTR pbstr);
+#endif // _MAC
+
+
+/*---------------------------------------------------------------------*/
+/* IEnumVARIANT */
+/*---------------------------------------------------------------------*/
+
+#undef INTERFACE
+#define INTERFACE IEnumVARIANT
+
+DECLARE_INTERFACE_(IEnumVARIANT, IUnknown)
+{
+ BEGIN_INTERFACE
+
+ /* IUnknown methods */
+ STDMETHOD(QueryInterface)(THIS_ REFIID riid, void FAR* FAR* ppvObj) PURE;
+ STDMETHOD_(unsigned long, AddRef)(THIS) PURE;
+ STDMETHOD_(unsigned long, Release)(THIS) PURE;
+
+ /* IEnumVARIANT methods */
+ STDMETHOD(Next)(
+ THIS_ unsigned long celt, VARIANT FAR* rgvar, unsigned long FAR* pceltFetched) PURE;
+ STDMETHOD(Skip)(THIS_ unsigned long celt) PURE;
+ STDMETHOD(Reset)(THIS) PURE;
+ STDMETHOD(Clone)(THIS_ IEnumVARIANT FAR* FAR* ppenum) PURE;
+};
+
+typedef IEnumVARIANT FAR* LPENUMVARIANT;
+
+
+/*---------------------------------------------------------------------*/
+/* IDispatch */
+/*---------------------------------------------------------------------*/
+
+
+#undef INTERFACE
+#define INTERFACE IDispatch
+
+DECLARE_INTERFACE_(IDispatch, IUnknown)
+{
+ BEGIN_INTERFACE
+
+ /* IUnknown methods */
+ STDMETHOD(QueryInterface)(THIS_ REFIID riid, void FAR* FAR* ppvObj) PURE;
+ STDMETHOD_(unsigned long, AddRef)(THIS) PURE;
+ STDMETHOD_(unsigned long, Release)(THIS) PURE;
+
+ /* IDispatch methods */
+ STDMETHOD(GetTypeInfoCount)(THIS_ unsigned int FAR* pctinfo) PURE;
+
+ STDMETHOD(GetTypeInfo)(
+ THIS_
+ unsigned int itinfo,
+ LCID lcid,
+ ITypeInfo FAR* FAR* pptinfo) PURE;
+
+ STDMETHOD(GetIDsOfNames)(
+ THIS_
+ REFIID riid,
+ OLECHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ LCID lcid,
+ DISPID FAR* rgdispid) PURE;
+
+ STDMETHOD(Invoke)(
+ THIS_
+ DISPID dispidMember,
+ REFIID riid,
+ LCID lcid,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pdispparams,
+ VARIANT FAR* pvarResult,
+ EXCEPINFO FAR* pexcepinfo,
+ unsigned int FAR* puArgErr) PURE;
+};
+
+typedef IDispatch FAR* LPDISPATCH;
+
+
+/* DISPID reserved for the standard "value" property */
+#define DISPID_VALUE 0
+
+/* DISPID reserved to indicate an "unknown" name */
+#define DISPID_UNKNOWN -1
+
+/* The following DISPID is reserved to indicate the param
+ * that is the right-hand-side (or "put" value) of a PropertyPut
+ */
+#define DISPID_PROPERTYPUT -3
+
+/* DISPID reserved for the standard "NewEnum" method */
+#define DISPID_NEWENUM -4
+
+/* DISPID reserved for the standard "Evaluate" method */
+#define DISPID_EVALUATE -5
+
+#define DISPID_CONSTRUCTOR -6
+#define DISPID_DESTRUCTOR -7
+#define DISPID_COLLECT -8
+
+
+//---------------------------------------------------------------------
+// IErrorInfo, et al
+//---------------------------------------------------------------------
+
+#undef INTERFACE
+#define INTERFACE IErrorInfo
+DECLARE_INTERFACE_(IErrorInfo, IUnknown)
+{
+ BEGIN_INTERFACE
+
+ /* IUnknown methods */
+ STDMETHOD(QueryInterface)(THIS_ REFIID riid, void FAR* FAR* ppvObj) PURE;
+ STDMETHOD_(unsigned long, AddRef)(THIS) PURE;
+ STDMETHOD_(unsigned long, Release)(THIS) PURE;
+
+ /* IErrorInfo methods */
+ STDMETHOD(GetGUID)(THIS_ GUID FAR* pguid) PURE;
+ STDMETHOD(GetSource)(THIS_ BSTR FAR* pbstrSource) PURE;
+ STDMETHOD(GetDescription)(THIS_ BSTR FAR* pbstrDescription) PURE;
+ STDMETHOD(GetHelpFile)(THIS_ BSTR FAR* pbstrHelpFile) PURE;
+ STDMETHOD(GetHelpContext)(THIS_ unsigned long FAR* pdwHelpContext) PURE;
+};
+
+#undef INTERFACE
+#define INTERFACE ICreateErrorInfo
+DECLARE_INTERFACE_(ICreateErrorInfo, IUnknown)
+{
+ BEGIN_INTERFACE
+
+ /* IUnknown methods */
+ STDMETHOD(QueryInterface)(THIS_ REFIID riid, void FAR* FAR* ppvObj) PURE;
+ STDMETHOD_(unsigned long, AddRef)(THIS) PURE;
+ STDMETHOD_(unsigned long, Release)(THIS) PURE;
+
+ /* ICreateErrorInfo methods */
+ STDMETHOD(SetGUID)(THIS_ REFGUID rguid) PURE;
+ STDMETHOD(SetSource)(THIS_ LPOLESTR szSource) PURE;
+ STDMETHOD(SetDescription)(THIS_ LPOLESTR szDescription) PURE;
+ STDMETHOD(SetHelpFile)(THIS_ LPOLESTR szHelpFile) PURE;
+ STDMETHOD(SetHelpContext)(THIS_ unsigned long dwHelpContext) PURE;
+};
+
+#undef INTERFACE
+#define INTERFACE ISupportErrorInfo
+DECLARE_INTERFACE_(ISupportErrorInfo, IUnknown)
+{
+ BEGIN_INTERFACE
+
+ /* IUnknown methods */
+ STDMETHOD(QueryInterface)(THIS_ REFIID riid, void FAR* FAR* ppvObj) PURE;
+ STDMETHOD_(unsigned long, AddRef)(THIS) PURE;
+ STDMETHOD_(unsigned long, Release)(THIS) PURE;
+
+ /* ISupportErrorInfo methods */
+ STDMETHOD(InterfaceSupportsErrorInfo)(THIS_ REFIID riid) PURE;
+};
+
+STDAPI SetErrorInfo(unsigned long dwReserved, IErrorInfo FAR* perrinfo);
+STDAPI GetErrorInfo(unsigned long dwReserved, IErrorInfo FAR* FAR* pperrinfo);
+STDAPI CreateErrorInfo(ICreateErrorInfo FAR* FAR* pperrinfo);
+
+
+/*---------------------------------------------------------------------*/
+/* IDispatch implementation support */
+/*---------------------------------------------------------------------*/
+
+typedef struct FARSTRUCT tagPARAMDATA {
+ OLECHAR FAR* szName; /* parameter name */
+ VARTYPE vt; /* parameter type */
+} PARAMDATA, FAR* LPPARAMDATA;
+
+typedef struct FARSTRUCT tagMETHODDATA {
+ OLECHAR FAR* szName; /* method name */
+ PARAMDATA FAR* ppdata; /* pointer to an array of PARAMDATAs */
+ DISPID dispid; /* method ID */
+ unsigned int iMeth; /* method index */
+ CALLCONV cc; /* calling convention */
+ unsigned int cArgs; /* count of arguments */
+ unsigned short wFlags; /* same wFlags as on IDispatch::Invoke() */
+ VARTYPE vtReturn;
+} METHODDATA, FAR* LPMETHODDATA;
+
+typedef struct FARSTRUCT tagINTERFACEDATA {
+ METHODDATA FAR* pmethdata; /* pointer to an array of METHODDATAs */
+ unsigned int cMembers; /* count of members */
+} INTERFACEDATA, FAR* LPINTERFACEDATA;
+
+
+
+/* Locate the parameter indicated by the given position, and
+ * return it coerced to the given target VARTYPE (vtTarg).
+ */
+STDAPI
+DispGetParam(
+ DISPPARAMS FAR* pdispparams,
+ unsigned int position,
+ VARTYPE vtTarg,
+ VARIANT FAR* pvarResult,
+ unsigned int FAR* puArgErr);
+
+/* Automatic TypeInfo driven implementation of IDispatch::GetIDsOfNames()
+ */
+STDAPI
+DispGetIDsOfNames(
+ ITypeInfo FAR* ptinfo,
+ OLECHAR FAR* FAR* rgszNames,
+ unsigned int cNames,
+ DISPID FAR* rgdispid);
+
+/* Automatic TypeInfo driven implementation of IDispatch::Invoke()
+ */
+STDAPI
+DispInvoke(
+ void FAR* _this,
+ ITypeInfo FAR* ptinfo,
+ DISPID dispidMember,
+ unsigned short wFlags,
+ DISPPARAMS FAR* pparams,
+ VARIANT FAR* pvarResult,
+ EXCEPINFO FAR* pexcepinfo,
+ unsigned int FAR* puArgErr);
+
+/* Construct a TypeInfo from an interface data description
+ */
+STDAPI
+CreateDispTypeInfo(
+ INTERFACEDATA FAR* pidata,
+ LCID lcid,
+ ITypeInfo FAR* FAR* pptinfo);
+
+/* Create an instance of the standard TypeInfo driven IDispatch
+ * implementation.
+ */
+STDAPI
+CreateStdDispatch(
+ IUnknown FAR* punkOuter,
+ void FAR* pvThis,
+ ITypeInfo FAR* ptinfo,
+ IUnknown FAR* FAR* ppunkStdDisp);
+
+
+/*---------------------------------------------------------------------*/
+/* Active Object Registration API */
+/*---------------------------------------------------------------------*/
+
+/* flags for RegisterActiveObject */
+#define ACTIVEOBJECT_STRONG 0x0
+#define ACTIVEOBJECT_WEAK 0x1
+
+STDAPI
+RegisterActiveObject(
+ IUnknown FAR* punk,
+ REFCLSID rclsid,
+ unsigned long dwFlags,
+ unsigned long FAR* pdwRegister);
+
+STDAPI
+RevokeActiveObject(
+ unsigned long dwRegister,
+ void FAR* pvReserved);
+
+STDAPI
+GetActiveObject(
+ REFCLSID rclsid,
+ void FAR* pvReserved,
+ IUnknown FAR* FAR* ppunk);
+
+
+#undef UNION_NAME
+
+/*---------------------------------------------------------------------*/
+/* MISC API */
+/*---------------------------------------------------------------------*/
+
+STDAPI_(unsigned long) OaBuildVersion(void);
+
+#endif /* _DISPATCH_H_ */
+
diff --git a/private/oleauto/src/inc/oautil.h b/private/oleauto/src/inc/oautil.h
new file mode 100644
index 000000000..9e85b21b2
--- /dev/null
+++ b/private/oleauto/src/inc/oautil.h
@@ -0,0 +1,283 @@
+/***
+*oautil.h - OLE Automation component-wide utility functions.
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* OA-wide utility function headers.
+*
+*Revision History:
+* 08-Nov-94 andrewso: Create
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#ifndef OAUTIL_H_INCLUDED
+#define OAUTIL_H_INCLUDED
+
+#if !OE_WIN32
+#error "Only valid in WIN32."
+#endif // !OE_WIN32
+
+#if ID_DEBUG
+
+// Declare a common assertion macro.
+#if defined(ASSERTSZ)
+
+#define OAASSERT(x,y) { if (x) ; else DispAssert(y, __FILE__, __LINE__); }
+#define OAHALT(x) DispAssert(x, __FILE__, __LINE__)
+
+#elif defined(DebAssert)
+
+#define OAASSERT(x,y) DebAssert(x, y)
+#define OAHALT(x) DebHalt(x)
+
+#else
+#error "No assertion code".
+#endif // ASSERT
+
+#else // !ID_DEBUG
+#define OAASSERT(x,y)
+#define OAHALT(x)
+#endif // !ID_DEBUG
+
+typedef DWORD TID;
+typedef DWORD ITLS;
+#define TID_EMPTY 0xFFFFFFFF
+#define ITLS_EMPTY 0xFFFFFFFF
+
+class OLE_TYPEMGR;
+
+// Per-app data structure
+struct APP_DATA
+{
+ OLE_TYPEMGR *m_poletmgr;
+ IMalloc *m_pimalloc; // cache a pointer to the IMalloc
+ USHORT m_cTypeLib;
+
+ IErrorInfo * m_perrinfo;
+
+ DWORD m_cbFreeBlock;
+ BSTR m_pbFreeBlock;
+ ITypeLib *m_ptlibStdole; // cache a pointer to the stdole32 typelib
+
+#if ID_DEBUG
+ // Used in the assertion code.
+ LPSTR m_szLoc;
+ LPSTR m_szMsg;
+#endif // ID_DEBUG
+
+ APP_DATA()
+ {
+ m_poletmgr = NULL;
+ m_pimalloc = NULL;
+ m_cTypeLib = 0;
+ m_perrinfo = NULL;
+ m_cbFreeBlock = 0;
+ m_pbFreeBlock = NULL;
+ m_ptlibStdole = NULL;
+
+#if ID_DEBUG
+ m_szLoc = NULL;
+ m_szMsg = NULL;
+#endif // ID_DEBUG
+ }
+};
+
+typedef ULONG HTINFO;
+#define HTINFO_Nil 0xFFFFFFFF
+
+// AppObjectTable node
+struct AOTABLE_NODE {
+ CLSID m_clsid;
+ VOID **m_ppv;
+ USHORT m_cRefs;
+};
+
+/***
+*class AppObjectTable - 'aotable'
+*Purpose:
+* Map between all instance of a typeinfo in a process and their shared
+* appobject.
+*
+***********************************************************************/
+
+class AppObjectTable
+{
+public:
+ VOID Release();
+
+ HRESULT AddTypeInfo(CLSID *pclsid,
+ HTINFO *phtinfo);
+
+ VOID RemoveTypeInfo(HTINFO htinfo);
+
+ VOID AddressOfAppObject(HTINFO htinfo, VOID **ppv);
+
+#if ID_DEBUG
+ VOID DebIsTableEmpty();
+#endif // ID_DEBUG
+
+ AppObjectTable()
+ {
+ m_cNodes = 0;
+ m_rgaotbl = NULL;
+ InitializeCriticalSection(&m_criticalsection);
+ }
+
+private:
+ ULONG m_cNodes;
+ AOTABLE_NODE *m_rgaotbl;
+ CRITICAL_SECTION m_criticalsection;
+};
+
+
+HRESULT InitProcessData();
+VOID ReleaseProcessData();
+
+HRESULT InitAppData();
+VOID ReleaseAppData();
+
+
+// Globals declaration.
+extern "C" {
+extern BOOL g_fWin32s;
+};
+
+extern AppObjectTable g_AppObjectTable;
+extern ITLS g_itlsAppData;
+
+// Inlined accessor functions.
+/***
+*APP_DATA *Pappdata()
+*
+*Purpose:
+* Returns per-app struct shared by typelib and obrun.
+*
+*Inputs:
+*
+*Outputs:
+* APP_DATA *
+*
+******************************************************************************/
+
+inline APP_DATA *Pappdata()
+{
+ OAASSERT(g_itlsAppData != ITLS_EMPTY, "Not initialized");
+
+ return((APP_DATA *)TlsGetValue(g_itlsAppData));
+}
+
+/***
+* Pmalloc()
+*
+*Purpose:
+* Returns cached IMalloc.
+*
+*Inputs:
+*
+*Outputs:
+* IMalloc *
+*
+******************************************************************************/
+
+inline IMalloc *Pmalloc()
+{
+ return Pappdata()->m_pimalloc;
+}
+
+/***
+* Poletmgr()
+*
+*Purpose:
+* Returns cached IMalloc.
+*
+*Inputs:
+*
+*Outputs:
+* OLE_TYPEMGR *
+*
+******************************************************************************/
+
+inline OLE_TYPEMGR *Poletmgr()
+{
+ return Pappdata()->m_poletmgr;
+}
+
+/***
+* Perrinfo()
+*
+*Purpose:
+* Returns cached errinfo.
+*
+*Inputs:
+*
+*Outputs:
+* IErrorInfo *
+*
+******************************************************************************/
+
+inline IErrorInfo *Perrinfo()
+{
+ return Pappdata()->m_perrinfo;
+}
+
+
+/***
+* HRESULT GetAppData()
+*
+*Purpose:
+* Returns the appdata, creatiing it if it doesn't exist.
+*
+*Inputs:
+*
+*Outputs:
+* AppData.
+* returns HRESULT.
+*
+******************************************************************************/
+
+inline HRESULT GetAppData(APP_DATA **ppappdata)
+{
+ if ((*ppappdata = Pappdata()) == NULL) {
+ HRESULT hresult;
+
+ if (FAILED(hresult = InitAppData())) {
+ return hresult;
+ }
+
+ *ppappdata = Pappdata();
+ }
+
+ return NOERROR;
+}
+
+
+/***
+* HRESULT GetMalloc()
+*
+*Purpose:
+* Returns cached IMalloc.
+*
+*Inputs:
+*
+*Outputs:
+* IMalloc and NOERROR.
+*
+******************************************************************************/
+
+inline HRESULT GetMalloc(IMalloc **ppmalloc)
+{
+ APP_DATA *pappdata;
+ HRESULT hresult;
+
+ if (FAILED(hresult = GetAppData(&pappdata))) {
+ return hresult;
+ }
+
+ *ppmalloc = Pmalloc();
+ return NOERROR;
+}
+#endif // ! OAUTIL_H_INCLUDED
diff --git a/private/oleauto/src/inc/olenls.h b/private/oleauto/src/inc/olenls.h
new file mode 100644
index 000000000..870f1f594
--- /dev/null
+++ b/private/oleauto/src/inc/olenls.h
@@ -0,0 +1,502 @@
+/***
+*olenls.h - National language support functions.
+*
+* Copyright (C) 1992-1995, Microsoft Corporation. All Rights Reserved.
+*
+*Purpose:
+* This describes the NLSAPI functions for Win16 and Mac. This is a subset
+* of Win32 NLSAPI, and is a non-Unicode version.
+*
+*Implementation Notes:
+* This files is largely ported from the Win32 header winnls.h.
+*
+*****************************************************************************/
+
+#ifndef _OLENLS_
+#define _OLENLS_
+
+#ifndef NONLS
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+
+#ifndef EXTERN_C
+# ifdef __cplusplus
+# define EXTERN_C extern "C"
+# else
+# define EXTERN_C extern
+# endif
+#endif
+
+#ifdef _MAC
+# ifndef FAR
+# define FAR
+# endif
+# ifdef _MSC_VER
+# define NLSAPI_(TYPE) EXTERN_C TYPE __pascal
+# else
+# define NLSAPI_(TYPE) EXTERN_C pascal TYPE
+# endif
+#else
+# define NLSAPI_(TYPE) EXTERN_C TYPE WINAPI
+#endif
+
+
+/***************************************************************************\
+* Constants
+*
+* Define all constants for the NLS component here.
+\***************************************************************************/
+
+/*
+ * Character Type Flags.
+ */
+#define CT_CTYPE1 0x00000001 /* ctype 1 information */
+#define CT_CTYPE2 0x00000002 /* ctype 2 information */
+#define CT_CTYPE3 0x00000004 /* ctype 3 information */
+
+/*
+ * CType 1 Flag Bits.
+ */
+#define C1_UPPER 0x0001 /* upper case */
+#define C1_LOWER 0x0002 /* lower case */
+#define C1_DIGIT 0x0004 /* decimal digits */
+#define C1_SPACE 0x0008 /* spacing characters */
+#define C1_PUNCT 0x0010 /* punctuation characters */
+#define C1_CNTRL 0x0020 /* control characters */
+#define C1_BLANK 0x0040 /* blank characters */
+#define C1_XDIGIT 0x0080 /* other digits */
+#define C1_ALPHA 0x0100 /* any letter */
+
+/*
+ * CType 2 Flag Bits.
+ */
+#define C2_LEFTTORIGHT 0x1 /* left to right */
+#define C2_RIGHTTOLEFT 0x2 /* right to left */
+
+#define C2_EUROPENUMBER 0x3 /* European number, digit */
+#define C2_EUROPESEPARATOR 0x4 /* European numeric separator */
+#define C2_EUROPETERMINATOR 0x5 /* European numeric terminator */
+#define C2_ARABICNUMBER 0x6 /* Arabic number */
+#define C2_COMMONSEPARATOR 0x7 /* common numeric separator */
+
+#define C2_BLOCKSEPARATOR 0x8 /* block separator */
+#define C2_SEGMENTSEPARATOR 0x9 /* segment separator */
+#define C2_WHITESPACE 0xA /* white space */
+#define C2_OTHERNEUTRAL 0xB /* other neutrals */
+
+#define C2_NOTAPPLICABLE 0x0 /* no implicit directionality */
+
+/*
+ * CType 3 Flag Bits.
+ */
+#define C3_NONSPACING 0x0001 /* nonspacing character */
+#define C3_DIACRITIC 0x0002 /* diacritic mark */
+#define C3_VOWELMARK 0x0004 /* vowel mark */
+#define C3_SYMBOL 0x0008 /* symbols */
+
+#define C3_KATAKANA 0x0010
+#define C3_HIRAGANA 0x0020
+#define C3_HALFWIDTH 0x0040
+#define C3_FULLWIDTH 0x0080
+#define C3_IDEOGRAPH 0x0100
+#define C3_KASHIDA 0x0200
+#define C3_ALPHA 0x8000
+
+#define C3_NOTAPPLICABLE 0x0 /* ctype 3 is not applicable */
+
+
+/*
+ * String Flags.
+ */
+#define NORM_IGNORECASE 0x00000001 /* ignore case */
+#define NORM_IGNORENONSPACE 0x00000002 /* ignore nonspacing chars */
+#define NORM_IGNORESYMBOLS 0x00000004 /* ignore symbols */
+
+#define NORM_IGNOREWIDTH 0x00000008 /* ignore width */
+#define NORM_IGNOREKANATYPE 0x00000040 /* ignore kanatype */
+
+#define NORM_IGNOREKASHIDA 0x00040000 /* ignore Arabic kashida chars */
+
+
+/*
+ * Locale Dependent Mapping Flags.
+ */
+#define LCMAP_LOWERCASE 0x00000100 /* lower case letters */
+#define LCMAP_UPPERCASE 0x00000200 /* upper case letters */
+#define LCMAP_SORTKEY 0x00000400 /* WC sort key (normalize) */
+
+#define LCMAP_HALFWIDTH 0x00000800 /* narrow pitch case letters */
+#define LCMAP_FULLWIDTH 0x00001000 /* wide picth case letters */
+#define LCMAP_HIRAGANA 0x00002000 /* map katakana to hiragana */
+#define LCMAP_KATAKANA 0x00004000 /* map hiragana to katakana */
+
+
+/*
+ * Language IDs.
+ *
+ * The following two combinations of primary language ID and
+ * sublanguage ID have special semantics:
+ *
+ * Primary Language ID Sublanguage ID Result
+ * ------------------- --------------- ------------------------
+ * LANG_NEUTRAL SUBLANG_NEUTRAL Language neutral
+ * LANG_NEUTRAL SUBLANG_DEFAULT Process default language
+ * LANG_NEUTRAL SUBLANG_SYS_DEFAULT System default language
+ */
+
+/*
+ * Primary language IDs.
+ */
+#define LANG_NEUTRAL 0x00
+
+#define LANG_ALBANIAN 0x1c
+#define LANG_ARABIC 0x01
+#define LANG_BAHASA 0x21
+#define LANG_BULGARIAN 0x02
+#define LANG_CATALAN 0x03
+#define LANG_CHINESE 0x04
+#define LANG_CZECH 0x05
+#define LANG_DANISH 0x06
+#define LANG_DUTCH 0x13
+#define LANG_ENGLISH 0x09
+#define LANG_FINNISH 0x0b
+#define LANG_FRENCH 0x0c
+#define LANG_GERMAN 0x07
+#define LANG_GREEK 0x08
+#define LANG_HEBREW 0x0d
+#define LANG_HUNGARIAN 0x0e
+#define LANG_ICELANDIC 0x0f
+#define LANG_ITALIAN 0x10
+#define LANG_JAPANESE 0x11
+#define LANG_KOREAN 0x12
+#define LANG_NORWEGIAN 0x14
+#define LANG_POLISH 0x15
+#define LANG_PORTUGUESE 0x16
+#define LANG_RHAETO_ROMAN 0x17
+#define LANG_ROMANIAN 0x18
+#define LANG_RUSSIAN 0x19
+#define LANG_SERBO_CROATIAN 0x1a
+#define LANG_SLOVAK 0x1b
+#define LANG_SPANISH 0x0a
+#define LANG_SWEDISH 0x1d
+#define LANG_THAI 0x1e
+#define LANG_TURKISH 0x1f
+#define LANG_URDU 0x20
+
+/*
+ * Sublanguage IDs.
+ *
+ * The name immediately following SUBLANG_ dictates which primary
+ * language ID that sublanguage ID can be combined with to form a
+ * valid language ID.
+ */
+#define SUBLANG_NEUTRAL 0x00 /* language neutral */
+#define SUBLANG_DEFAULT 0x01 /* user default */
+#define SUBLANG_SYS_DEFAULT 0x02 /* system default */
+
+#define SUBLANG_CHINESE_SIMPLIFIED 0x02 /* Chinese (Simplified) */
+#define SUBLANG_CHINESE_TRADITIONAL 0x01 /* Chinese (Traditional) */
+#define SUBLANG_DUTCH 0x01 /* Dutch */
+#define SUBLANG_DUTCH_BELGIAN 0x02 /* Dutch (Belgian) */
+#define SUBLANG_ENGLISH_US 0x01 /* English (USA) */
+#define SUBLANG_ENGLISH_UK 0x02 /* English (UK) */
+#define SUBLANG_ENGLISH_AUS 0x03 /* English (Australian) */
+#define SUBLANG_ENGLISH_CAN 0x04 /* English (Canadian) */
+#define SUBLANG_ENGLISH_NZ 0x05 /* English (New Zealand) */
+#define SUBLANG_ENGLISH_EIRE 0x06 /* English (Irish) */
+#define SUBLANG_FRENCH 0x01 /* French */
+#define SUBLANG_FRENCH_BELGIAN 0x02 /* French (Belgian) */
+#define SUBLANG_FRENCH_CANADIAN 0x03 /* French (Canadian) */
+#define SUBLANG_FRENCH_SWISS 0x04 /* French (Swiss) */
+#define SUBLANG_GERMAN 0x01 /* German */
+#define SUBLANG_GERMAN_SWISS 0x02 /* German (Swiss) */
+#define SUBLANG_GERMAN_AUSTRIAN 0x03 /* German (Austrian) */
+#define SUBLANG_ITALIAN 0x01 /* Italian */
+#define SUBLANG_ITALIAN_SWISS 0x02 /* Italian (Swiss) */
+#define SUBLANG_NORWEGIAN_BOKMAL 0x01 /* Norwegian (Bokmal) */
+#define SUBLANG_NORWEGIAN_NYNORSK 0x02 /* Norwegian (Nynorsk) */
+#define SUBLANG_PORTUGUESE 0x02 /* Portuguese */
+#define SUBLANG_PORTUGUESE_BRAZILIAN 0x01 /* Portuguese (Brazilian) */
+#define SUBLANG_SERBO_CROATIAN_CYRILLIC 0x02 /* Serbo-Croatian (Cyrillic) */
+#define SUBLANG_SERBO_CROATIAN_LATIN 0x01 /* Croato-Serbian (Latin) */
+#define SUBLANG_SPANISH 0x01 /* Spanish */
+#define SUBLANG_SPANISH_MEXICAN 0x02 /* Spanish (Mexican) */
+#define SUBLANG_SPANISH_MODERN 0x03 /* Spanish (Modern) */
+
+
+/*
+ * Country Codes.
+ */
+#define CTRY_DEFAULT 0
+
+#define CTRY_AUSTRALIA 61 /* Australia */
+#define CTRY_AUSTRIA 43 /* Austria */
+#define CTRY_BELGIUM 32 /* Belgium */
+#define CTRY_BRAZIL 55 /* Brazil */
+#define CTRY_CANADA 2 /* Canada */
+#define CTRY_DENMARK 45 /* Denmark */
+#define CTRY_FINLAND 358 /* Finland */
+#define CTRY_FRANCE 33 /* France */
+#define CTRY_GERMANY 49 /* Germany */
+#define CTRY_ICELAND 354 /* Iceland */
+#define CTRY_IRELAND 353 /* Ireland */
+#define CTRY_ITALY 39 /* Italy */
+#define CTRY_JAPAN 81 /* Japan */
+#define CTRY_MEXICO 52 /* Mexico */
+#define CTRY_NETHERLANDS 31 /* Netherlands */
+#define CTRY_NEW_ZEALAND 64 /* New Zealand */
+#define CTRY_NORWAY 47 /* Norway */
+#define CTRY_PORTUGAL 351 /* Portugal */
+#define CTRY_PRCHINA 86 /* PR China */
+#define CTRY_SOUTH_KOREA 82 /* South Korea */
+#define CTRY_SPAIN 34 /* Spain */
+#define CTRY_SWEDEN 46 /* Sweden */
+#define CTRY_SWITZERLAND 41 /* Switzerland */
+#define CTRY_TAIWAN 886 /* Taiwan */
+#define CTRY_UNITED_KINGDOM 44 /* United Kingdom */
+#define CTRY_UNITED_STATES 1 /* United States */
+
+
+/*
+ * Locale Types.
+ *
+ * These types are used for the GetLocaleInfoA NLS API routine.
+ */
+
+#define LOCALE_NOUSEROVERRIDE 0x80000000 /* OR in to avoid user override */
+
+#define LOCALE_ILANGUAGE 0x0001 /* language id */
+#define LOCALE_SLANGUAGE 0x0002 /* localized name of language */
+#define LOCALE_SENGLANGUAGE 0x1001 /* English name of language */
+#define LOCALE_SABBREVLANGNAME 0x0003 /* abbreviated language name */
+#define LOCALE_SNATIVELANGNAME 0x0004 /* native name of language */
+#define LOCALE_ICOUNTRY 0x0005 /* country code */
+#define LOCALE_SCOUNTRY 0x0006 /* localized name of country */
+#define LOCALE_SENGCOUNTRY 0x1002 /* English name of country */
+#define LOCALE_SABBREVCTRYNAME 0x0007 /* abbreviated country name */
+#define LOCALE_SNATIVECTRYNAME 0x0008 /* native name of country */
+#define LOCALE_IDEFAULTLANGUAGE 0x0009 /* default language id */
+#define LOCALE_IDEFAULTCOUNTRY 0x000A /* default country code */
+#define LOCALE_IDEFAULTCODEPAGE 0x000B /* default oem code page */
+#define LOCALE_IDEFAULTANSICODEPAGE 0x1004 /* default ansi code page */
+
+#define LOCALE_SLIST 0x000C /* list item separator */
+#define LOCALE_IMEASURE 0x000D /* 0 = metric, 1 = US */
+
+#define LOCALE_SDECIMAL 0x000E /* decimal separator */
+#define LOCALE_STHOUSAND 0x000F /* thousand separator */
+#define LOCALE_SGROUPING 0x0010 /* digit grouping */
+#define LOCALE_IDIGITS 0x0011 /* number of fractional digits */
+#define LOCALE_ILZERO 0x0012 /* leading zeros for decimal */
+#define LOCALE_INEGNUMBER 0x1010 /* negative number mode */
+#define LOCALE_SNATIVEDIGITS 0x0013 /* native ascii 0-9 */
+
+#define LOCALE_SCURRENCY 0x0014 /* local monetary symbol */
+#define LOCALE_SINTLSYMBOL 0x0015 /* intl monetary symbol */
+#define LOCALE_SMONDECIMALSEP 0x0016 /* monetary decimal separator */
+#define LOCALE_SMONTHOUSANDSEP 0x0017 /* monetary thousand separator */
+#define LOCALE_SMONGROUPING 0x0018 /* monetary grouping */
+#define LOCALE_ICURRDIGITS 0x0019 /* # local monetary digits */
+#define LOCALE_IINTLCURRDIGITS 0x001A /* # intl monetary digits */
+#define LOCALE_ICURRENCY 0x001B /* positive currency mode */
+#define LOCALE_INEGCURR 0x001C /* negative currency mode */
+
+#define LOCALE_SDATE 0x001D /* date separator */
+#define LOCALE_STIME 0x001E /* time separator */
+#define LOCALE_SSHORTDATE 0x001F /* short date-time separator */
+#define LOCALE_SLONGDATE 0x0020 /* long date-time separator */
+#define LOCALE_STIMEFORMAT 0x1003 /* time format string */
+#define LOCALE_IDATE 0x0021 /* short date format ordering */
+#define LOCALE_ILDATE 0x0022 /* long date format ordering */
+#define LOCALE_ITIME 0x0023 /* time format specifier */
+#define LOCALE_ITIMEMARKPOSN 0x1005 /* time marker position */
+#define LOCALE_ICENTURY 0x0024 /* century format specifier */
+#define LOCALE_ITLZERO 0x0025 /* leading zeros in time field */
+#define LOCALE_IDAYLZERO 0x0026 /* leading zeros in day field */
+#define LOCALE_IMONLZERO 0x0027 /* leading zeros in month field */
+#define LOCALE_S1159 0x0028 /* AM designator */
+#define LOCALE_S2359 0x0029 /* PM designator */
+
+#define LOCALE_ICALENDARTYPE 0x1009 /* type of calendar specifier */
+#define LOCALE_IOPTIONALCALENDAR 0x100B /* additional calendar types specifier */
+
+#define LOCALE_IFIRSTDAYOFWEEK 0x100C /* first day of week specifier */
+#define LOCALE_IFIRSTWEEKOFYEAR 0x100D /* first week of year specifier */
+
+
+#define LOCALE_SDAYNAME1 0x002A /* long name for Monday */
+#define LOCALE_SDAYNAME2 0x002B /* long name for Tuesday */
+#define LOCALE_SDAYNAME3 0x002C /* long name for Wednesday */
+#define LOCALE_SDAYNAME4 0x002D /* long name for Thursday */
+#define LOCALE_SDAYNAME5 0x002E /* long name for Friday */
+#define LOCALE_SDAYNAME6 0x002F /* long name for Saturday */
+#define LOCALE_SDAYNAME7 0x0030 /* long name for Sunday */
+#define LOCALE_SABBREVDAYNAME1 0x0031 /* abbreviated name for Monday */
+#define LOCALE_SABBREVDAYNAME2 0x0032 /* abbreviated name for Tuesday */
+#define LOCALE_SABBREVDAYNAME3 0x0033 /* abbreviated name for Wednesday */
+#define LOCALE_SABBREVDAYNAME4 0x0034 /* abbreviated name for Thursday */
+#define LOCALE_SABBREVDAYNAME5 0x0035 /* abbreviated name for Friday */
+#define LOCALE_SABBREVDAYNAME6 0x0036 /* abbreviated name for Saturday */
+#define LOCALE_SABBREVDAYNAME7 0x0037 /* abbreviated name for Sunday */
+#define LOCALE_SMONTHNAME1 0x0038 /* long name for January */
+#define LOCALE_SMONTHNAME2 0x0039 /* long name for February */
+#define LOCALE_SMONTHNAME3 0x003A /* long name for March */
+#define LOCALE_SMONTHNAME4 0x003B /* long name for April */
+#define LOCALE_SMONTHNAME5 0x003C /* long name for May */
+#define LOCALE_SMONTHNAME6 0x003D /* long name for June */
+#define LOCALE_SMONTHNAME7 0x003E /* long name for July */
+#define LOCALE_SMONTHNAME8 0x003F /* long name for August */
+#define LOCALE_SMONTHNAME9 0x0040 /* long name for September */
+#define LOCALE_SMONTHNAME10 0x0041 /* long name for October */
+#define LOCALE_SMONTHNAME11 0x0042 /* long name for November */
+#define LOCALE_SMONTHNAME12 0x0043 /* long name for December */
+#define LOCALE_SMONTHNAME13 0x100E /* long name for 13th month (if exists) */
+#define LOCALE_SABBREVMONTHNAME1 0x0044 /* abbreviated name for January */
+#define LOCALE_SABBREVMONTHNAME2 0x0045 /* abbreviated name for February */
+#define LOCALE_SABBREVMONTHNAME3 0x0046 /* abbreviated name for March */
+#define LOCALE_SABBREVMONTHNAME4 0x0047 /* abbreviated name for April */
+#define LOCALE_SABBREVMONTHNAME5 0x0048 /* abbreviated name for May */
+#define LOCALE_SABBREVMONTHNAME6 0x0049 /* abbreviated name for June */
+#define LOCALE_SABBREVMONTHNAME7 0x004A /* abbreviated name for July */
+#define LOCALE_SABBREVMONTHNAME8 0x004B /* abbreviated name for August */
+#define LOCALE_SABBREVMONTHNAME9 0x004C /* abbreviated name for September */
+#define LOCALE_SABBREVMONTHNAME10 0x004D /* abbreviated name for October */
+#define LOCALE_SABBREVMONTHNAME11 0x004E /* abbreviated name for November */
+#define LOCALE_SABBREVMONTHNAME12 0x004F /* abbreviated name for December */
+#define LOCALE_SABBREVMONTHNAME13 0x100F /* abbreviated name for 13th month (if exists) */
+
+#define LOCALE_SPOSITIVESIGN 0x0050 /* positive sign */
+#define LOCALE_SNEGATIVESIGN 0x0051 /* negative sign */
+#define LOCALE_IPOSSIGNPOSN 0x0052 /* positive sign position */
+#define LOCALE_INEGSIGNPOSN 0x0053 /* negative sign position */
+#define LOCALE_IPOSSYMPRECEDES 0x0054 /* mon sym precedes pos amt */
+#define LOCALE_IPOSSEPBYSPACE 0x0055 /* mon sym sep by space from pos */
+#define LOCALE_INEGSYMPRECEDES 0x0056 /* mon sym precedes neg amt */
+#define LOCALE_INEGSEPBYSPACE 0x0057 /* mon sym sep by space from neg */
+
+
+/***************************************************************************\
+* Typedefs
+*
+* Define all types for the NLS component here.
+\***************************************************************************/
+
+/*
+ * IDs.
+ */
+typedef unsigned long LCID; /* locale ID */
+typedef unsigned short LANGID; /* language ID */
+typedef unsigned long LCTYPE; /* locale type constant */
+
+#define _LCID_DEFINED
+
+
+
+/***************************************************************************\
+* Macros
+*
+* Define all macros for the NLS component here.
+\***************************************************************************/
+
+/*
+ * A language ID is a 16 bit value which is the combination of a
+ * primary language ID and a secondary language ID. The bits are
+ * allocated as follows:
+ *
+ * +-----------------------+-------------------------+
+ * | Sublanguage ID | Primary Language ID |
+ * +-----------------------+-------------------------+
+ * 15 10 9 0 bit
+ *
+ *
+ * Language ID creation/extraction macros:
+ *
+ * MAKELANGID - construct language id from primary language id and
+ * sublanguage id.
+ * PRIMARYLANGID - extract primary language id from a language id.
+ * SUBLANGID - extract sublanguage id from a language id.
+ */
+#define MAKELANGID(p, s) ((((unsigned short)(s)) << 10) | (unsigned short)(p))
+
+#define PRIMARYLANGID(lgid) ((unsigned short)(lgid) & 0x3ff)
+
+#define SUBLANGID(lgid) ((unsigned short)(lgid) >> 10)
+
+
+/*
+ * A locale ID is a 32 bit value which is the combination of a
+ * language ID and a reserved area. The bits are allocated as follows:
+ *
+ * +-----------------------+-------------------------+
+ * | Reserved | Language ID |
+ * +-----------------------+-------------------------+
+ * 31 16 15 0 bit
+ *
+ *
+ * Locale ID creation macro:
+ *
+ * MAKELCID - construct locale id from a language id.
+ */
+#define MAKELCID(lgid) ((unsigned long)(((unsigned short)(lgid)) | (((unsigned long)((unsigned short)(0))) << 16)))
+
+
+/*
+ * Get the language id from a locale id.
+ */
+#define LANGIDFROMLCID(lcid) ((unsigned short)(lcid))
+
+
+/*
+ * Default System and User IDs for language and locale.
+ */
+#define LANG_SYSTEM_DEFAULT (MAKELANGID(LANG_NEUTRAL, SUBLANG_SYS_DEFAULT))
+#define LANG_USER_DEFAULT (MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT))
+
+#define LOCALE_SYSTEM_DEFAULT (MAKELCID(LANG_SYSTEM_DEFAULT))
+#define LOCALE_USER_DEFAULT (MAKELCID(LANG_USER_DEFAULT))
+
+
+
+/***************************************************************************\
+* Function Prototypes
+*
+* Only prototypes for the NLS APIs should go here.
+\***************************************************************************/
+
+
+NLSAPI_(int)
+CompareStringA(LCID, unsigned long, const char FAR*, int, const char FAR*, int);
+
+NLSAPI_(int)
+LCMapStringA(LCID, unsigned long, const char FAR*, int, char FAR*, int);
+
+NLSAPI_(int)
+GetLocaleInfoA(LCID, LCTYPE, char FAR*, int);
+
+NLSAPI_(int)
+GetStringTypeA(LCID, unsigned long, const char FAR*, int, unsigned short FAR*);
+
+NLSAPI_(LANGID)
+GetSystemDefaultLangID(void);
+
+NLSAPI_(LANGID)
+GetUserDefaultLangID(void);
+
+NLSAPI_(LCID)
+GetSystemDefaultLCID(void);
+
+NLSAPI_(LCID)
+GetUserDefaultLCID(void);
+
+
+#ifdef __cplusplus
+}
+#endif
+
+
+#endif /* NONLS */
+
+#endif /* _OLENLS_ */
diff --git a/private/oleauto/src/inc/variant.h b/private/oleauto/src/inc/variant.h
new file mode 100644
index 000000000..3d88aded5
--- /dev/null
+++ b/private/oleauto/src/inc/variant.h
@@ -0,0 +1,277 @@
+/***
+*variant.h
+*
+* Copyright (C) 1992-1995, Microsoft Corporation. All Rights Reserved.
+*
+*Purpose:
+* This file declares VARIANT, and related data types.
+*
+*Implementation Notes:
+* This file requires ole2.h
+*
+*****************************************************************************/
+
+#ifndef _VARIANT_H_
+#define _VARIANT_H_
+
+
+#ifndef HUGEP
+# ifdef _MAC
+# define HUGEP FAR
+# else
+# if WIN32
+# define HUGEP
+# else
+# define HUGEP _huge
+# endif
+# endif
+#endif
+
+#ifndef FAR
+# ifdef _MAC
+# define FAR
+# else
+# ifdef WIN32
+# define FAR
+# else
+# define FAR _far
+# endif
+# endif
+#endif
+
+
+/* Forward Declarations */
+
+#ifdef __cplusplus
+interface IDispatch;
+#else
+typedef interface IDispatch IDispatch;
+#endif
+
+
+#ifndef OLESTR
+#if defined(WIN32)
+typedef WCHAR OLECHAR;
+typedef LPWSTR LPOLESTR;
+typedef LPCWSTR LPCOLESTR;
+#define OLESTR(str) L##str
+#else
+typedef char OLECHAR;
+typedef OLECHAR FAR* LPOLESTR;
+typedef const OLECHAR FAR* LPCOLESTR;
+#define OLESTR(str) str
+#endif
+#endif
+
+typedef OLECHAR FAR* BSTR;
+typedef BSTR FAR* LPBSTR;
+
+
+typedef struct FARSTRUCT tagSAFEARRAYBOUND {
+ unsigned long cElements;
+ long lLbound;
+} SAFEARRAYBOUND, FAR* LPSAFEARRAYBOUND;
+
+typedef struct FARSTRUCT tagSAFEARRAY {
+ unsigned short cDims;
+ unsigned short fFeatures;
+#if defined(WIN32)
+ unsigned long cbElements;
+ unsigned long cLocks;
+#else
+ unsigned short cbElements;
+ unsigned short cLocks;
+#ifdef _MAC
+ Handle handle;
+#else
+ unsigned long handle;
+#endif
+#endif
+ void HUGEP* pvData;
+ SAFEARRAYBOUND rgsabound[1];
+} SAFEARRAY, FAR* LPSAFEARRAY;
+
+#define FADF_AUTO 0x0001 /* array is allocated on the stack */
+#define FADF_STATIC 0x0002 /* array is staticly allocated */
+#define FADF_EMBEDDED 0x0004 /* array is embedded in a structure */
+#define FADF_FIXEDSIZE 0x0010 /* array may not be resized or reallocated */
+#define FADF_BSTR 0x0100 /* an array of BSTRs */
+#define FADF_UNKNOWN 0x0200 /* an array of IUnknown* */
+#define FADF_DISPATCH 0x0400 /* an array of IDispatch* */
+#define FADF_VARIANT 0x0800 /* an array of VARIANTs */
+#define FADF_RESERVED 0xF0E8 /* bits reserved for future use */
+
+
+/* 0 == FALSE, -1 == TRUE */
+typedef short VARIANT_BOOL;
+
+
+typedef double DATE;
+
+
+/* This is a helper struct for use in handling currency. */
+typedef struct FARSTRUCT tagCY {
+#ifdef _MAC
+ long Hi;
+ unsigned long Lo;
+#else
+ unsigned long Lo;
+ long Hi;
+#endif
+} CY;
+
+
+/*
+ * VARENUM usage key,
+ *
+ * [V] - may appear in a VARIANT
+ * [T] - may appear in a TYPEDESC
+ * [P] - may appear in an OLE property set
+ * [S] - may appear in a Safe Array
+ *
+ */
+enum VARENUM
+{
+ VT_EMPTY = 0, /* [V] [P] nothing */
+ VT_NULL = 1, /* [V] SQL style Null */
+ VT_I2 = 2, /* [V][T][P][S] 2 byte signed int */
+ VT_I4 = 3, /* [V][T][P][S] 4 byte signed int */
+ VT_R4 = 4, /* [V][T][P][S] 4 byte real */
+ VT_R8 = 5, /* [V][T][P][S] 8 byte real */
+ VT_CY = 6, /* [V][T][P][S] currency */
+ VT_DATE = 7, /* [V][T][P][S] date */
+ VT_BSTR = 8, /* [V][T][P][S] binary string */
+ VT_DISPATCH = 9, /* [V][T] [S] IDispatch FAR* */
+ VT_ERROR = 10, /* [V][T] [S] SCODE */
+ VT_BOOL = 11, /* [V][T][P][S] True=-1, False=0 */
+ VT_VARIANT = 12, /* [V][T][P][S] VARIANT FAR* */
+ VT_UNKNOWN = 13, /* [V][T] [S] IUnknown FAR* */
+
+ VT_I1 = 16, /* [T] signed char */
+ VT_UI1 = 17, /* [V][T] [S] unsigned char */
+ VT_UI2 = 18, /* [T] unsigned short */
+ VT_UI4 = 19, /* [T] unsigned short */
+ VT_I8 = 20, /* [T][P] signed 64-bit int */
+ VT_UI8 = 21, /* [T] unsigned 64-bit int */
+ VT_INT = 22, /* [T] signed machine int */
+ VT_UINT = 23, /* [T] unsigned machine int */
+ VT_VOID = 24, /* [T] C style void */
+ VT_HRESULT = 25, /* [T] */
+ VT_PTR = 26, /* [T] pointer type */
+ VT_SAFEARRAY = 27, /* [T] (use VT_ARRAY in VARIANT) */
+ VT_CARRAY = 28, /* [T] C style array */
+ VT_USERDEFINED = 29, /* [T] user defined type */
+ VT_LPSTR = 30, /* [T][P] null terminated string */
+ VT_LPWSTR = 31, /* [T][P] wide null terminated string */
+
+ VT_FILETIME = 64, /* [P] FILETIME */
+ VT_BLOB = 65, /* [P] Length prefixed bytes */
+ VT_STREAM = 66, /* [P] Name of the stream follows */
+ VT_STORAGE = 67, /* [P] Name of the storage follows */
+ VT_STREAMED_OBJECT = 68, /* [P] Stream contains an object */
+ VT_STORED_OBJECT = 69, /* [P] Storage contains an object */
+ VT_BLOB_OBJECT = 70, /* [P] Blob contains an object */
+ VT_CF = 71, /* [P] Clipboard format */
+ VT_CLSID = 72 /* [P] A Class ID */
+};
+
+#define VT_VECTOR 0x1000 /* [P] simple counted array */
+#define VT_ARRAY 0x2000 /* [V] SAFEARRAY* */
+#define VT_BYREF 0x4000 /* [V] */
+#define VT_RESERVED 0x8000
+
+
+typedef unsigned short VARTYPE;
+
+typedef struct FARSTRUCT tagVARIANT VARIANT;
+typedef struct FARSTRUCT tagVARIANT FAR* LPVARIANT;
+typedef struct FARSTRUCT tagVARIANT VARIANTARG;
+typedef struct FARSTRUCT tagVARIANT FAR* LPVARIANTARG;
+
+struct FARSTRUCT tagVARIANT{
+ VARTYPE vt;
+ unsigned short wReserved1;
+ unsigned short wReserved2;
+ unsigned short wReserved3;
+ union {
+ unsigned char bVal; /* VT_UI1 */
+ short iVal; /* VT_I2 */
+ long lVal; /* VT_I4 */
+ float fltVal; /* VT_R4 */
+ double dblVal; /* VT_R8 */
+ VARIANT_BOOL bool; /* VT_BOOL */
+ SCODE scode; /* VT_ERROR */
+ CY cyVal; /* VT_CY */
+ DATE date; /* VT_DATE */
+ BSTR bstrVal; /* VT_BSTR */
+ IUnknown FAR* punkVal; /* VT_UNKNOWN */
+ IDispatch FAR* pdispVal; /* VT_DISPATCH */
+ SAFEARRAY FAR* parray; /* VT_ARRAY|* */
+
+ unsigned char FAR *pbVal; /* VT_BYREF|VT_UI1 */
+ short FAR* piVal; /* VT_BYREF|VT_I2 */
+ long FAR* plVal; /* VT_BYREF|VT_I4 */
+ float FAR* pfltVal; /* VT_BYREF|VT_R4 */
+ double FAR* pdblVal; /* VT_BYREF|VT_R8 */
+ VARIANT_BOOL FAR* pbool; /* VT_BYREF|VT_BOOL */
+ SCODE FAR* pscode; /* VT_BYREF|VT_ERROR */
+ CY FAR* pcyVal; /* VT_BYREF|VT_CY */
+ DATE FAR* pdate; /* VT_BYREF|VT_DATE */
+ BSTR FAR* pbstrVal; /* VT_BYREF|VT_BSTR */
+ IUnknown FAR* FAR* ppunkVal; /* VT_BYREF|VT_UNKNOWN */
+ IDispatch FAR* FAR* ppdispVal; /* VT_BYREF|VT_DISPATCH */
+ SAFEARRAY FAR* FAR* pparray; /* VT_BYREF|VT_ARRAY|* */
+ VARIANT FAR* pvarVal; /* VT_BYREF|VT_VARIANT */
+
+ void FAR* byref; /* Generic ByRef */
+ }
+#if defined(NONAMELESSUNION) || (defined(_MAC) && !defined(__cplusplus) && !defined(_MSC_VER))
+ u
+#endif
+ ;
+};
+
+#if defined(NONAMELESSUNION) || (defined(_MAC) && !defined(__cplusplus) && !defined(_MSC_VER))
+# define V_UNION(X, Y) ((X)->u.Y)
+#else
+# define V_UNION(X, Y) ((X)->Y)
+#endif
+
+/* Variant access macros */
+#define V_VT(X) ((X)->vt)
+#define V_ISBYREF(X) (V_VT(X)&VT_BYREF)
+#define V_ISARRAY(X) (V_VT(X)&VT_ARRAY)
+#define V_ISVECTOR(X) (V_VT(X)&VT_VECTOR)
+
+#define V_NONE(X) V_I2(X)
+#define V_UI1(X) V_UNION(X, bVal)
+#define V_UI1REF(X) V_UNION(X, pbVal)
+#define V_I2(X) V_UNION(X, iVal)
+#define V_I2REF(X) V_UNION(X, piVal)
+#define V_I4(X) V_UNION(X, lVal)
+#define V_I4REF(X) V_UNION(X, plVal)
+#define V_R4(X) V_UNION(X, fltVal)
+#define V_R4REF(X) V_UNION(X, pfltVal)
+#define V_R8(X) V_UNION(X, dblVal)
+#define V_R8REF(X) V_UNION(X, pdblVal)
+#define V_BOOL(X) V_UNION(X, bool)
+#define V_BOOLREF(X) V_UNION(X, pbool)
+#define V_ERROR(X) V_UNION(X, scode)
+#define V_ERRORREF(X) V_UNION(X, pscode)
+#define V_CY(X) V_UNION(X, cyVal)
+#define V_CYREF(X) V_UNION(X, pcyVal)
+#define V_DATE(X) V_UNION(X, date)
+#define V_DATEREF(X) V_UNION(X, pdate)
+#define V_BSTR(X) V_UNION(X, bstrVal)
+#define V_BSTRREF(X) V_UNION(X, pbstrVal)
+#define V_UNKNOWN(X) V_UNION(X, punkVal)
+#define V_UNKNOWNREF(X) V_UNION(X, ppunkVal)
+#define V_DISPATCH(X) V_UNION(X, pdispVal)
+#define V_DISPATCHREF(X) V_UNION(X, ppdispVal)
+#define V_VARIANTREF(X) V_UNION(X, pvarVal)
+#define V_ARRAY(X) V_UNION(X, parray)
+#define V_ARRAYREF(X) V_UNION(X, pparray)
+#define V_BYREF(X) V_UNION(X, byref)
+
+#endif /* _VARIANT_H_ */
+
diff --git a/private/oleauto/src/inc/verstamp.h b/private/oleauto/src/inc/verstamp.h
new file mode 100644
index 000000000..8b5620552
--- /dev/null
+++ b/private/oleauto/src/inc/verstamp.h
@@ -0,0 +1,5 @@
+#define rmj 2
+#define rmm 2
+#define rup 3011
+#define szVerName ""
+#define szVerUser "DOUGF5"
diff --git a/private/oleauto/src/mktyplib/dimalloc.cxx b/private/oleauto/src/mktyplib/dimalloc.cxx
new file mode 100644
index 000000000..6d15e3de9
--- /dev/null
+++ b/private/oleauto/src/mktyplib/dimalloc.cxx
@@ -0,0 +1,1787 @@
+/***
+*dimalloc.cxx
+*
+* Copyright (C) 1992-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file contains a debug implementation of the IMalloc interface.
+*
+* This implementation is basically a simple wrapping of the C runtime,
+* with additional work to detect memory leakage, and memory overwrite.
+*
+* Leakage is detected by tracking each allocation in an address
+* instance table, and then checking to see if the table is empty
+* when the last reference to the allocator is released.
+*
+* Memory overwrite is detected by placing a signature at the end
+* of every allocated block, and checking to make sure the signature
+* is unchanged when the block is freed.
+*
+* This implementation also has additional param validation code, as
+* well as additional check make sure that instances that are passed
+* to Free() were actually allocated by the corresponding instance
+* of the allocator.
+*
+*
+* Creating an instance of this debug allocator that uses the default
+* output interface would look like the following,
+*
+*
+* BOOL init_application_instance()
+* {
+* HRESULT hresult;
+* IMalloc FAR* pmalloc;
+*
+* pmalloc = NULL;
+*
+* if((hresult = CreateDbAlloc(DBALLOC_NONE, NULL, &pmalloc)) != NOERROR)
+* goto LReturn;
+*
+* hresult = OleInitialize(pmalloc);
+*
+* LReturn:;
+* if(pmalloc != NULL)
+* pmalloc->Release();
+*
+* return (hresult == NOERROR) ? TRUE : FALSE;
+* }
+*
+*
+* CONSIDER: could add an option to force error generation, something
+* like DBALLOC_ERRORGEN, that works along the lines of OB's
+* DebErrorNow.
+*
+* CONSIDER: add support for heap-checking. say for example,
+* DBALLOC_HEAPCHECK would do a heapcheck every free? every 'n'
+* calls to free? ...
+*
+*
+*Revision History:
+*
+* [00] 25-Feb-92 bradlo: Created.
+* [01] 03-Mar-93 rajivk: Added to ebapp.
+*
+*Implementation Notes:
+*
+* The method IMalloc::DidAlloc() is allowed to always return
+* "Dont Know" (-1). This method is called by Ole, and they take
+* some appropriate action when they get this answer. UNDONE -- elaborate.
+*
+*****************************************************************************/
+
+#ifdef DEBUG // entire file
+#if 0
+#include "pch.c"
+#pragma hdrstop(PCHNAME)
+#else //0
+#include "mktyplib.h"
+#ifdef MAC
+#define OE_MAC TRUE
+#endif
+#ifdef WIN32
+#define OE_WIN32 TRUE
+#if defined(_MIPS_) || defined(_ALPHA_) || defined(_PPC_)
+#define OE_RISC TRUE
+#endif
+#endif
+#ifdef WIN16
+#define OE_WIN16 TRUE
+#endif
+#endif //0
+
+#if OE_MAC
+#include <macos\osutils.h>
+#include <macos\sysequ.h>
+#endif // OE_MAC
+
+// Note: this file is designed to be stand-alone; it includes a
+// carefully chosen, minimal set of headers.
+//
+// For conditional compilation we use the ole2 conventions,
+// _MAC = mac
+// WIN32 = Win32 (NT really)
+// <nothing> = defaults to Win16
+#ifdef _DEBUG
+#undef _DEBUG
+#endif
+#define _DEBUG 1
+
+
+#if !OE_WIN32
+#include "ole2.h"
+#if !OE_MAC
+#include "compobj.h"
+#endif
+#endif //!OE_WIN32
+
+#if OE_MAC
+// include Mac stuff
+#include "macos\memory.h"
+#include "macos\errors.h"
+
+typedef VOID* HSYS;
+#define HSYS_Nil ((HSYS)NULL)
+
+
+#endif
+
+#include <stdio.h>
+#include <malloc.h>
+#include <string.h>
+#include <stdarg.h>
+#include <limits.h>
+
+#if 0
+#include "ebapp.h"
+#include "dimalloc.hxx"
+
+// This global is defined in bind.c and contains the name of the
+// log file specified by -o, if there is one.
+//
+extern "C" {
+ CHAR g_szLogFile[];
+}
+#else //0
+
+#if OE_RISC
+ // UNDONE: RISC [jeffrob] Currently use same alignment for ALL risc
+ // UNDONE: platforms.
+ #define cbAlign 8
+#endif // OE_RISC
+
+#if OE_MAC
+ #include "macos\menus.h"
+ #include "macos\dialogs.h"
+ #include "stdio.h"
+ #include "macos\files.h"
+ #include "macos\lists.h"
+#endif // OE_MAC
+
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+// Assertion macro.
+#define DebAssert(fExpr, szComment) \
+ if (!(fExpr)) \
+ DebAssertShow(__FILE__, __LINE__, szComment); \
+ else 0 /* useless statement */
+
+void DebAssertShow(LPSTR szFileName, UINT uLine, LPSTR szComment);
+
+
+#define DebAssertNum(fExpr, szComment, nErr) \
+ if (!(fExpr)) \
+ DebAssertShow(__FILE__, __LINE__, szComment); \
+ else 0 /* useless statement */
+
+#if 0
+// Macros for error checking:
+#define IfErrExit(s) { if (eberr = (s)) goto Exit; }
+#define IfNullExit(s) { if ( !(s) ) { eberr = EBERR_OutOfMemory; goto Exit;} }
+#define IfErrGo(s) { if (eberr = (s)) goto Error; }
+#define IfErrGoTo(s, label) { if (eberr = (s)) goto label; }
+#endif //0
+
+#ifndef WIN32
+#ifndef _INC_WINDOWS
+ #define LOWORD(l) ((WORD)(DWORD)(l))
+ #define HIWORD(l) ((WORD)((((DWORD)(l)) >> 16) & 0xFFFF))
+#endif //_INC_WINDOWS
+#endif //!WIN32
+
+#if 0
+// Maintains the hproj/docfile/project substorage relationship.
+typedef struct STGREC {
+ IStorage FAR *pstgFile;
+ IStorage FAR *pstgProj;
+ HPROJECT hproj; // The hproject associated with this storage if known.
+ LPSTR bstrName; // The name of the file.
+ BOOL isTemp; // TRUE if this is a temp file that should be deleted
+ // when closed.
+} STGREC;
+
+STGREC FAR *CreateTmpStorage(void);
+EBERR CopyTmpFileToDest(HPROJECT hproj, LPSTR lpstrFileName);
+void PASCAL FreeStorage(void);
+STGREC FAR *FindStgRecByName(LPSTR szName);
+void CloseProjectStorage(HPROJECT hproj);
+
+#if OE_WIN
+extern HINSTANCE g_hInst; // host-app instance handle
+extern HWND g_hwndSrchDlg; // modeless search dialog
+extern HWND g_hwndMDISpace; // window handle of host app's MDI space
+extern HWND g_hwndParent; // this instance's top-level window.
+extern char g_szProject[]; // project window class name
+extern char g_szDebugWnd[]; // debug window class name
+extern char g_szPolyWnd[]; // polygon window class name
+#endif //OE_WIN
+
+#if OE_MAC
+extern BOOL fMacHelpLoaded; //TRUE if the mac help file is laoded
+extern FSSpec fsHelpFile; //FSSpec for the help file
+#endif
+
+extern char *g_szTitleText; // default title bar text
+extern HWND g_hwndEbActive; // Active O.B. window.
+extern BOOL g_fAppActive; // is this application active?
+extern BOOL g_fParentActive; // is the parent (frame) window active?
+extern LPSTR g_lpszHelpFile; // help file if F1 pressed
+extern DWORD g_dwHelpContext; // help context if F1 pressed
+extern UINT g_cMsgLoop; // How many nested message loops?
+extern INT g_fNoAllocs; // Are allocations allowed?
+
+extern int g_cxScroll; // width of scrollbar
+extern int g_cyScroll; // heigth of scrollbar
+// Errros Used by Ebapp only.
+#define EBERR_IdNotFound 0xffff
+extern int g_fDbcs; // is DBCS support enabled?
+
+
+LPDISPATCH EBCALL Bind(LPVARIANT lpvarRngName);
+LPDISPATCH EBCALL NewPoint(void);
+LPDISPATCH EBCALL NewPoly(void);
+LPDISPATCH EBCALL GetProjCollection(void);
+LPDISPATCH EBCALL NewList(void);
+LPDISPATCH EBCALL GetAppObj(void);
+void AppObjTerm();
+
+void CallEbNotifyWindow(HWND hwnd, EBMSG ebmsg, LONG lparam);
+void QuitEbApp();
+void DebAssertWrite(char *szFileName, char *szMsg);
+
+LPVOID EBCALL CreateNewObject(LPSTR szProjName, LPSTR szClassName);
+BOOL GetDebIMalloc(IMalloc FAR* FAR* ppmalloc);
+
+VOID FAR* EBCALL CreateInstance(BSTR szTlibName, UINT uIndex);
+VOID FAR* CreateInst(BSTR szTlibName, UINT uIndex);
+
+BOOL GetStringDlg(char **pszString);
+BOOL RenameDlg(char **pszNewName);
+
+#if OE_MAC
+Boolean CheckMacHelpEvent(EventRecord *evtPtr);
+OSErr GetWDInfoTemp(short wdRefNum, short *pvRefNum, long *pdirid);
+BOOL MacGetFullPath(long dirid, short vRefNum, LPSTR szPath);
+void InitializeGrafport();
+BOOL FCalcTextHeight(CHAR *szText, SHORT cx, SHORT *cy);
+void RectToRECT (const Rect *prcm, RECT *prc);
+void RECTToRect (const RECT *prc, Rect *prcm);
+BOOL PaintWindow(EventRecord *pevt);
+#endif // OE_MAC
+
+DEFINE_GUID (IID_CVARCOLLECT, 0x2d736941, 0xc370, 0x1068, 0xb3, 0x69, 0x08, 0x00, 0x2b, 0x2b, 0x37, 0x87);
+#endif //0
+
+#ifdef __cplusplus
+}
+#endif
+
+#if OE_MAC
+#ifdef _fstrcpy
+#undef _fstrcpy
+#endif
+#ifdef _fstrncpy
+#undef _fstrncpy
+#endif
+#ifdef _fstrncat
+#undef _fstrncat
+#endif
+#ifdef _fstrcat
+#undef _fstrcat
+#endif
+#ifdef _fstrchr
+#undef _fstrchr
+#endif
+
+#define _fstrcpy strcpy
+#define _fstrncpy strncpy
+#define _fstrncat strncat
+#define _fstrcat strcat
+#define _fstrchr strchr
+#endif //OE_MAC
+
+#if OE_MAC
+#define STDOLE_FILE "mstdole.tlb"
+#define APPOBJ_FILE "mappobj"
+#else //!OE_MAC
+
+#if OE_WIN32
+#define STDOLE_FILE "stdole32.tlb"
+#define APPOBJ_FILE "apo"
+#else //OE_WIN16
+#define STDOLE_FILE "stdole.tlb"
+#define APPOBJ_FILE "apobj"
+#endif //OE_WIN16
+
+#endif //!OE_MAC
+
+#define VBAOLB_FILE "vba"
+
+#endif
+
+#ifndef DBALLOC_H_INCLUDED /* { */
+#define DBALLOC_H_INCLUDED
+
+
+interface IDbOutput : public IUnknown
+{
+ STDMETHOD(QueryInterface)(THIS_ REFIID riid, void FAR* FAR* ppv) PURE;
+ STDMETHOD_(ULONG, AddRef)(THIS) PURE;
+ STDMETHOD_(ULONG, Release)(THIS) PURE;
+
+ STDMETHOD_(void, Printf)(THIS_
+ char FAR* szFmt, ...) PURE;
+
+ STDMETHOD_(void, Assertion)(THIS_
+ BOOL cond,
+ char FAR* szExpr,
+ char FAR* szFile,
+ UINT uLine,
+ char FAR* szMsg) PURE;
+};
+
+
+STDAPI CreateDbAlloc(
+ ULONG options,
+ IDbOutput FAR* pdbout,
+ IMalloc FAR* FAR* ppmalloc);
+
+// dballoc option flags - these are set at create time.
+
+#define DBALLOC_NONE 0
+
+
+#endif /* } DBALLOC_H_INCLUDED */
+
+#define OOB_SELECTOROF(p) ((USHORT) ((ULONG) (p) >> 16))
+#define DIM(X) (sizeof(X)/sizeof((X)[0]))
+#define UNREACHED 0
+static char szSigMsg[] = "Signature Check Failed";
+
+
+ // This defn switches in array handling code that knows how to
+ // handle non-aligned & non-power-of-2 arrays.
+ // Defined & used in hugearry.asm, dimalloc.cxx & exvarg.cxx
+ // In dimalloc.cxx it enables signature prefixing for huge
+ // arrays thus allowing testing of the array-adjust code in VBA.
+#define ADJUST_ARRAYS 1
+
+
+#if OE_WIN16
+#define MAX_SIZE 64000
+#else
+#define MAX_SIZE UINT_MAX
+#endif
+
+#define Max
+VOID FAR * HugeAlloc(DWORD bch);
+VOID FAR *HugeRealloc(VOID FAR *pv, DWORD bchNew);
+VOID FAR *HugeFree(VOID FAR * pv);
+
+
+
+
+#if defined(WIN32)
+
+# define MEMCMP(PV1, PV2, CB) memcmp((PV1), (PV2), (CB))
+# define MEMCPY(PV1, PV2, CB) memcpy((PV1), (PV2), (CB))
+# define MEMSET(PV, VAL, CB) memset((PV), (VAL), (CB))
+# define MALLOC(CB) malloc(CB)
+# define REALLOC(PV, CB) realloc((PV), (CB))
+# define FREE(PV) free(PV)
+# define MSIZE(PV) _msize(PV)
+//UNDONE: NT has no heapmin() function?
+//# define HEAPMIN() _heapmin()
+
+#elif OE_MAC
+
+#define MEMCPY memcpy
+// #define REALLOC(PV, CB) SetPtrSize((char _near *)(PV), (CB))
+// #define MALLOC(CB) NewPtr(CB)
+// #define FREE(PV) DisposPtr((char _near *)(PV))
+#define REALLOC(PV, CB) realloc((PV), (CB))
+#define MALLOC(CB) malloc(CB)
+#define FREE(PV) free(PV)
+#define MEMCMP(PV1, PV2, CB) memcmp((PV1), (PV2), (CB))
+#define MEMSET(PV, VAL, CB) memset((PV), (VAL), (CB))
+// #define MSIZE(PV) GetPtrSize((char _near *)(PV))
+#define MSIZE(PV) _msize(PV)
+#define HEAPMIN() _heapmin()
+
+#else
+
+# define MEMCMP(PV1, PV2, CB) _fmemcmp((PV1), (PV2), (CB))
+# define MEMCPY(PV1, PV2, CB) _fmemcpy((PV1), (PV2), (CB))
+# define MEMSET(PV, VAL, CB) _fmemset((PV), (VAL), (CB))
+# define MALLOC(CB) _fmalloc(CB)
+# define REALLOC(PV, CB) _frealloc(PV, CB)
+# define FREE(PV) _ffree(PV)
+# define MSIZE(PV) _fmsize(PV)
+# define HEAPMIN() _fheapmin()
+
+#endif
+
+class FAR CStdDbOutput : public IDbOutput {
+public:
+ static IDbOutput FAR* Create();
+
+ // IUnknown methods
+
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(ULONG, AddRef)(void);
+ STDMETHOD_(ULONG, Release)(void);
+
+
+ // IDbOutput methods
+
+ STDMETHOD_(void, Printf)(char FAR* szFmt, ...);
+
+ STDMETHOD_(void, Assertion)(
+ BOOL cond,
+ char FAR* szExpr,
+ char FAR* szFile,
+ UINT uLine,
+ char FAR* szMsg);
+
+
+ void FAR* operator new(size_t cb){
+ return MALLOC(cb);
+ }
+ void operator delete(void FAR* pv){
+ FREE(pv);
+ }
+
+ CStdDbOutput(){
+ m_refs = 0;
+ }
+
+private:
+ ULONG m_refs;
+
+ char m_rgch[128]; // buffer for output formatting
+};
+
+
+
+//---------------------------------------------------------------------
+// implementation of the debug allocator
+//---------------------------------------------------------------------
+
+class FAR CAddrNode
+{
+public:
+ void FAR* m_pv; // instance
+ ULONG m_cb; // size of allocation in BYTES
+ ULONG m_nAlloc; // the allocation pass count
+ CAddrNode FAR* m_next;
+
+ void FAR* operator new(size_t cb){
+ return MALLOC(cb);
+ }
+ void operator delete(void FAR* pv){
+ FREE(pv);
+ }
+};
+
+
+class FAR CDbAlloc : public IMalloc
+{
+public:
+ static HRESULT Create(
+ ULONG options, IDbOutput FAR* pdbout, IMalloc FAR* FAR* ppmalloc);
+
+ // IUnknown methods
+
+ STDMETHOD(QueryInterface)(REFIID riid, void FAR* FAR* ppv);
+ STDMETHOD_(ULONG, AddRef)(void);
+ STDMETHOD_(ULONG, Release)(void);
+
+ // IMalloc methods
+
+ STDMETHOD_(void FAR*, Alloc)(ULONG cb);
+ STDMETHOD_(void FAR*, Realloc)(void FAR* pv, ULONG cb);
+ STDMETHOD_(void, Free)(void FAR* pv);
+ STDMETHOD_(ULONG, GetSize)(void FAR* pv);
+ STDMETHOD_(int, DidAlloc)(void FAR* pv);
+ STDMETHOD_(void, HeapMinimize)(void);
+
+ VOID IMallocHeapChecker();
+ VOID MemInstance();
+
+ void FAR* operator new(size_t cb){
+ return MALLOC(cb);
+ }
+ void operator delete(void FAR* pv){
+ FREE(pv);
+ }
+
+private:
+
+ ULONG m_refs;
+ ULONG m_cAllocCalls; // total count of allocation calls
+ IDbOutput FAR* m_pdbout; // output interface
+ CAddrNode FAR* m_rganode[64]; // address instance table
+
+
+ // instance table methods
+
+ void AddInst(void FAR* pv, ULONG nAlloc, ULONG cb);
+ void DelInst(void FAR* pv);
+ CAddrNode FAR* GetInst(void FAR* pv);
+
+ BOOL IsEmpty(void);
+ void DumpInstTable(void);
+
+ void DumpInst(CAddrNode FAR* pn);
+
+ inline UINT HashInst(void FAR* pv) const {
+ return ((UINT)((ULONG)pv >> 4)) % DIM(m_rganode);
+ }
+
+
+ // output method(s)
+
+ inline void Assertion(
+ BOOL cond,
+ char FAR* szExpr,
+ char FAR* szFile,
+ UINT uLine,
+ char FAR* szMsg)
+ {
+ m_pdbout->Assertion(cond, szExpr, szFile, uLine, szMsg);
+ }
+
+ #define ASSERT(X) Assertion(X, #X, __FILE__, __LINE__, NULL)
+
+ #define ASSERTSZ(X, SZ) Assertion(X, #X, __FILE__, __LINE__, SZ)
+
+#if OE_RISC
+ char m_rgchSig[cbAlign];
+#else
+ char m_rgchSig[4];
+#endif // !(OE_RISC)
+
+public:
+ CDbAlloc(){
+ m_refs = 1;
+ m_pdbout = NULL;
+ m_cAllocCalls = 0;
+ MEMSET(m_rganode, 0, sizeof(m_rganode));
+ m_rgchSig[0] = m_rgchSig[2] = (char)0xBA;
+ m_rgchSig[1] = m_rgchSig[3] = (char)0xBE;
+#if OE_RISC
+#if (cbAlign == 8)
+ m_rgchSig[4] = m_rgchSig[6] = (char)0xBA;
+ m_rgchSig[5] = m_rgchSig[7] = (char)0xBE;
+#else
+ #error Invalid cbAlign value.
+#endif // cbAlign
+#endif // OE_RISC
+ }
+};
+
+
+/***
+*HRESULT CreateDbAlloc(ULONG, IDbOutput*, IMalloc**)
+*Purpose:
+* Create an instance of CDbAlloc -- a debug implementation
+* of IMalloc.
+*
+*Entry:
+* pdbout = optional IDbOutput interface to use for ouput
+* (if NULL, then the default debug output interface will be used)
+* options =
+*
+*Exit:
+* return value = HRESULT
+*
+* *ppmalloc = pointer to an IMalloc interface
+*
+***********************************************************************/
+STDAPI
+CreateDbAlloc(
+ ULONG options,
+ IDbOutput FAR* pdbout,
+ IMalloc FAR* FAR* ppmalloc)
+{
+ return CDbAlloc::Create(options, pdbout, ppmalloc);
+}
+
+HRESULT
+CDbAlloc::Create(
+ ULONG options,
+ IDbOutput FAR* pdbout,
+ IMalloc FAR* FAR* ppmalloc)
+{
+ HRESULT hresult;
+ CDbAlloc FAR* pmalloc;
+
+
+ // default the instance of IDbOutput if the user didn't supply one
+ if(pdbout == NULL && ((pdbout = CStdDbOutput::Create()) == NULL)){
+ hresult = ResultFromScode(E_OUTOFMEMORY);
+ goto LError0;
+ }
+
+ pdbout->AddRef();
+
+ if((pmalloc = new FAR CDbAlloc()) == NULL){
+ hresult = ResultFromScode(E_OUTOFMEMORY);
+ goto LError1;
+ }
+
+ pmalloc->m_pdbout = pdbout;
+
+ *ppmalloc = pmalloc;
+
+ return NOERROR;
+
+LError1:;
+ pdbout->Release();
+ pmalloc->Release();
+
+LError0:;
+ return hresult;
+}
+
+STDMETHODIMP
+CDbAlloc::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ HRESULT hresult;
+#if OE_MAC
+ long a5Save = SetA5(*((long *)(long)CurrentA5));
+#endif // OE_MAC
+
+ if(riid == IID_IUnknown ){
+ *ppv = this;
+ AddRef();
+ hresult = NOERROR;
+ }
+ else
+ hresult = ResultFromScode(E_NOINTERFACE);
+
+#if OE_MAC
+ SetA5(a5Save);
+#endif // OE_MAC
+
+ return hresult;
+}
+
+STDMETHODIMP_(ULONG)
+CDbAlloc::AddRef()
+{
+ return ++m_refs;
+}
+
+STDMETHODIMP_(ULONG)
+CDbAlloc::Release()
+{
+// FILE *pfileLog; // UNDONE stevenl -- not used right now
+
+ if(--m_refs == 0){
+
+#if OE_MAC
+ long a5Save = SetA5(*((long *)(long)CurrentA5));
+#endif // OE_MAC
+
+ // check for memory leakage
+ if(!IsEmpty()){
+ m_pdbout->Printf("Memory Leak Detected,\n");
+ DumpInstTable();
+ ASSERTSZ(FALSE, "Memory leaked");
+ }
+ else {
+ // No memory has leaked. If we're running a test script,
+ // we want the line "No Memory Leaks." at the end of the
+ // script, so that there will be a baseline failure if
+ // memory has leaked. The global g_szLogFile has the name
+ // of the file, if there is one.
+ //
+#if 0
+ if (strlen(g_szLogFile)) {
+#if 0
+// UNDONE 20-May-93 stevenl:
+// This is #ifdef'ed out until we feel like
+// messing with all the baselines again.
+//
+ pfileLog = fopen(g_szLogFile,"at");
+ if (pfileLog) {
+ fprintf(pfileLog, "No Memory Leaks.");
+ fclose(pfileLog);
+ }
+#endif
+ } // if
+#endif //0
+ } // else
+
+ m_pdbout->Release();
+ delete this;
+
+#if OE_MAC
+ SetA5(a5Save);
+#endif // OE_MAC
+
+ return 0;
+ }
+
+ return m_refs;
+}
+
+STDMETHODIMP_(void FAR*)
+CDbAlloc::Alloc(ULONG cb)
+{
+ ULONG size;
+ VOID FAR* pv;
+
+#if OE_MAC
+ long a5Save = SetA5(*((long *)(long)CurrentA5));
+#endif // OE_MAC
+
+#if 0
+ // If allocations have been disabled (probably because we're in
+ // the middle of a save), just return NULL.
+ if (g_fNoAllocs)
+ return NULL;
+#endif //0
+
+ IMallocHeapChecker();
+
+ // ++m_cAllocCalls;
+ MemInstance();
+
+ size = (ULONG)cb;
+
+ // Support for Huge Arrays
+ if ((cb + 2*sizeof(m_rgchSig)) < MAX_SIZE) {
+
+ if((pv = MALLOC((size_t)(size + 2*sizeof(m_rgchSig)))) == NULL)
+ goto Error;
+ }
+ else {
+ if ((pv = (VOID FAR *)HugeAlloc(size + 2*sizeof(m_rgchSig))) == NULL)
+ goto Error;
+
+ }
+
+ // set allocated block to some non-zero value
+ MEMSET(pv, -1, (size_t)(size + 2*sizeof(m_rgchSig)));
+
+#if ADJUST_ARRAYS
+ if ((cb + 2*sizeof(m_rgchSig)) < MAX_SIZE) {
+ // put signature at end of allocated block
+ MEMCPY((char FAR*)pv + size + sizeof(m_rgchSig), m_rgchSig, (size_t)sizeof(m_rgchSig));
+ }
+
+ // put signature at the head of the allocated block
+ MEMCPY((char FAR*)pv , m_rgchSig, sizeof(m_rgchSig));
+ pv = (char FAR*)pv + sizeof(m_rgchSig);
+
+#else
+ // We do not put the signature for huge memory allocation
+ if ((cb + 2*sizeof(m_rgchSig)) < MAX_SIZE) {
+ // put signature at end of allocated block
+ MEMCPY((char FAR*)pv + size + sizeof(m_rgchSig), m_rgchSig, (size_t)sizeof(m_rgchSig));
+
+ // put signature at the head of the allocated block
+ MEMCPY((char FAR*)pv , m_rgchSig, sizeof(m_rgchSig));
+
+ }
+
+ // For Huge allocation return the pointer to the beginnig of the seg.
+ if ((cb + 2*sizeof(m_rgchSig)) < MAX_SIZE) {
+ // return the pointer to the beginning of the block to be returned
+ pv = (char FAR*)pv + sizeof(m_rgchSig);
+ }
+#endif
+
+ // save the address returned and it's size also.
+ AddInst(pv, m_cAllocCalls, size);
+
+ // FALL THROUGH!!!
+
+Error:
+
+#if OE_MAC
+ SetA5(a5Save);
+#endif // OE_MAC
+
+ return pv;
+}
+
+
+
+STDMETHODIMP_(void FAR*)
+CDbAlloc::Realloc(void FAR* pv, ULONG cb)
+{
+ ULONG size;
+ ULONG sizeToFree;
+ CAddrNode FAR* pn;
+
+ if(pv == NULL){
+ return Alloc(cb);
+ }
+
+#if OE_MAC
+ long a5Save = SetA5(*((long *)(long)CurrentA5));
+#endif // OE_MAC
+
+ // ++m_cAllocCalls;
+ MemInstance();
+
+ pn = GetInst(pv);
+
+ sizeToFree = pn->m_cb;
+ ASSERT(pn != NULL);
+
+ if(cb == 0){
+ Free(pv);
+ pv = NULL;
+ goto Done;
+ }
+
+#if 0
+ // If allocations have been disabled (probably because we're in
+ // the middle of a save) and we're trying to increase the size of
+ // the allocated block, just return NULL. We allow decreases, since
+ // that can't cause an out of memory error in a real allocator.
+ if (cb > sizeToFree && g_fNoAllocs)
+ return NULL;
+#endif //0
+
+ size = cb;
+
+ // UNDONE : This does not handle the case when we mix the huge alloc and
+ // and realloc.
+ if (((sizeToFree + 2*sizeof(m_rgchSig)) < MAX_SIZE) &&
+ ((size + 2*sizeof(m_rgchSig)) < MAX_SIZE)) {
+
+ // we delete the instance from the table using the address passed in.
+ DelInst(pv);
+
+ // get the address of the original memory allocated
+ pv = (char FAR*)pv - sizeof(m_rgchSig);
+
+ // allocte enough memory to put the signature also.
+ if ((pv = REALLOC(pv, (size_t)(size + 2*sizeof(m_rgchSig)))) == NULL)
+ goto Done;
+ }
+ else {
+ if (((sizeToFree + 2*sizeof(m_rgchSig)) >= MAX_SIZE) &&
+ ((size + 2*sizeof(m_rgchSig)) >= MAX_SIZE)) {
+
+ // we delete the instance from the table using the address passed in.
+ DelInst(pv);
+
+#if ADJUST_ARRAYS
+ // get the address of the original memory allocated
+ pv = (char FAR*)pv - sizeof(m_rgchSig);
+#endif
+ // allocte enough memory to put the signature also.
+ if ((pv = HugeRealloc(pv, size + 2*sizeof(m_rgchSig))) == NULL)
+ goto Done;
+ }
+ else {
+ VOID FAR *pvNew;
+ ULONG cbCopy;
+
+
+ if ((pvNew = Alloc(size)) == NULL) {
+ // if the memory to be free is < MAX_SIZE then adjust the pointer
+ if ((sizeToFree + 2*sizeof(m_rgchSig)) < MAX_SIZE) {
+ // get the address of the original memory allocated
+ pv = (char FAR*)pv - sizeof(m_rgchSig);
+ }
+
+ Free(pv);
+ pv = NULL;
+ goto Done;
+ }
+
+ cbCopy = (sizeToFree < size) ? sizeToFree : size;
+
+ // copy the original contents
+ MEMCPY((char FAR*)pvNew , (char FAR*)pv, (size_t)cbCopy);
+
+#if ADJUST_ARRAYS
+ pv = (char FAR*)pv - sizeof(m_rgchSig);
+#else
+ // if the memory to be free is < MAX_SIZE then adjust the pointer
+ if ((sizeToFree + 2*sizeof(m_rgchSig)) < MAX_SIZE) {
+ // get the address of the original memory allocated
+ pv = (char FAR*)pv - sizeof(m_rgchSig);
+ }
+
+#endif
+
+ Free((char FAR*)pv + sizeof(m_rgchSig));
+ pv = pvNew;
+ goto Done;
+
+ }
+
+ }
+
+ // We do not put the signature at the tail for huge memory allocation
+ if ((size + 2*sizeof(m_rgchSig)) < MAX_SIZE) {
+ // put signature at end of allocated block
+ // NOTE:- the signature for the header is already there.
+ MEMCPY((char FAR*)pv + size + sizeof(m_rgchSig), m_rgchSig, sizeof(m_rgchSig));
+ }
+
+#if ADJUST_ARRAYS
+ pv = (char FAR*)pv + sizeof(m_rgchSig);
+#else
+ // For Huge allocation return the pointer to the beginnig of the seg.
+ if ((cb + 2*sizeof(m_rgchSig)) < MAX_SIZE) {
+ // return the pointer to the beginning of the block (to be used
+ // by the caller).
+ pv = (char FAR*)pv + sizeof(m_rgchSig);
+ }
+#endif
+
+ // save the address returned and it's size also.
+ AddInst(pv, m_cAllocCalls, size);
+
+Done:
+#if OE_MAC
+ SetA5(a5Save);
+#endif // OE_MAC
+ return pv;
+}
+
+STDMETHODIMP_(void)
+CDbAlloc::Free(void FAR* pv)
+{
+ CAddrNode FAR* pn;
+ ULONG sizeToFree;
+
+#if OE_MAC
+ long a5Save = SetA5(*((long *)(long)CurrentA5));
+#endif // OE_MAC
+
+ // STORAGE.DLL Calls Free(NULL) alot
+ if (pv == NULL)
+ goto Done;
+
+ pn = GetInst(pv);
+
+ // check for attempt to free an instance we didnt allocate
+ if(pn == NULL){
+ ASSERTSZ(FALSE, "pointer freed by wrong allocator");
+ goto Done;
+ }
+
+ // We do not put the signature at the tail for huge memory allocation
+ if ((pn->m_cb + 2*sizeof(m_rgchSig)) < MAX_SIZE) {
+ // verify the signature at the tail
+ if(MEMCMP((char FAR*)pv + pn->m_cb, m_rgchSig, sizeof(m_rgchSig)) != 0){
+ m_pdbout->Printf(szSigMsg); m_pdbout->Printf("\n");
+ DumpInst(GetInst(pv));
+ ASSERTSZ(FALSE, szSigMsg);
+ }
+
+#if ADJUST_ARRAYS
+ }
+
+ {
+#endif
+ // verify the signature at the head
+ if(MEMCMP((char FAR*)pv - sizeof(m_rgchSig), m_rgchSig, sizeof(m_rgchSig)) != 0){
+ m_pdbout->Printf(szSigMsg); m_pdbout->Printf("\n");
+ DumpInst(GetInst(pv));
+ ASSERTSZ(FALSE, szSigMsg);
+ }
+
+ }
+
+
+ sizeToFree = pn->m_cb;
+
+ DelInst(pv);
+
+#if ADJUST_ARRAYS
+ pv = (char FAR*)pv - sizeof(m_rgchSig);
+#else
+ if ((sizeToFree + 2*sizeof(m_rgchSig)) < MAX_SIZE) {
+ // get the address of the original memory allocated
+ pv = (char FAR*)pv - sizeof(m_rgchSig);
+ }
+#endif
+
+ // stomp on the contents of the block
+ MEMSET(pv, 0xCC, (size_t)(sizeToFree + 2*sizeof(m_rgchSig)));
+
+ if ((sizeToFree + 2*sizeof(m_rgchSig)) < MAX_SIZE) {
+
+ FREE(pv);
+ }
+ else {
+ HugeFree(pv);
+ }
+
+Done: ;
+#if OE_MAC
+ SetA5(a5Save);
+#endif // OE_MAC
+}
+
+STDMETHODIMP_(ULONG)
+CDbAlloc::GetSize(void FAR* pv)
+{
+ CAddrNode FAR* pn;
+ ASSERT((pn = GetInst(pv)) != NULL);
+
+ // dont count extra signature bytes in size
+ return pn->m_cb;
+}
+
+VOID CDbAlloc::MemInstance()
+{
+ ++m_cAllocCalls;
+
+}
+
+
+/***
+*PUBLIC HRESULT CDbAlloc::DidAlloc
+*Purpose:
+* Answer if the given address belongs to a block allocated by
+* this allocator.
+*
+*Entry:
+* pv = the instance to lookup
+*
+*Exit:
+* return value = int
+* 1 - did alloc
+* 0 - did *not* alloc
+* -1 - dont know (according to the ole2 spec it is always legal
+* for the allocator to answer "dont know")
+*
+***********************************************************************/
+STDMETHODIMP_(int)
+CDbAlloc::DidAlloc(void FAR* pv)
+{
+ return -1; // answer "I dont know"
+}
+
+
+STDMETHODIMP_(void)
+CDbAlloc::HeapMinimize()
+{
+#if !OE_WIN32 //UNDONE: what does HeapMinimize mean for WIN32?
+#if OE_MAC
+ long a5Save = SetA5(*((long *)(long)CurrentA5));
+#endif // OE_MAC
+ HEAPMIN();
+#if OE_MAC
+ SetA5(a5Save);
+#endif // OE_MAC
+#endif
+}
+
+
+//---------------------------------------------------------------------
+// instance table methods
+//---------------------------------------------------------------------
+
+/***
+*PRIVATE CDbAlloc::AddInst
+*Purpose:
+* Add the given instance to the address instance table.
+*
+*Entry:
+* pv = the instance to add
+* nAlloc = the allocation passcount of this instance
+*
+*Exit:
+* None
+*
+***********************************************************************/
+void
+CDbAlloc::AddInst(void FAR* pv, ULONG nAlloc, ULONG cb)
+{
+ UINT hash;
+ CAddrNode FAR* pn;
+
+
+ ASSERT(pv != NULL);
+
+ pn = (CAddrNode FAR*)new FAR CAddrNode();
+
+ ASSERT(pn != NULL);
+
+ pn->m_pv = pv;
+ pn->m_cb = cb;
+ pn->m_nAlloc = nAlloc;
+
+ hash = HashInst(pv);
+ pn->m_next = m_rganode[hash];
+ m_rganode[hash] = pn;
+}
+
+
+/***
+*UNDONE
+*Purpose:
+* Remove the given instance from the address instance table.
+*
+*Entry:
+* pv = the instance to remove
+*
+*Exit:
+* None
+*
+***********************************************************************/
+void
+CDbAlloc::DelInst(void FAR* pv)
+{
+ CAddrNode FAR* FAR* ppn, FAR* pnDead;
+
+ for(ppn = &m_rganode[HashInst(pv)]; *ppn != NULL; ppn = &(*ppn)->m_next){
+ if((*ppn)->m_pv == pv){
+ pnDead = *ppn;
+ *ppn = (*ppn)->m_next;
+ delete pnDead;
+ // make sure it doesnt somehow appear twice
+ ASSERT(GetInst(pv) == NULL);
+ return;
+ }
+ }
+
+ // didnt find the instance
+ ASSERT(UNREACHED);
+}
+
+
+CAddrNode FAR*
+CDbAlloc::GetInst(void FAR* pv)
+{
+ CAddrNode FAR* pn;
+
+ for(pn = m_rganode[HashInst(pv)]; pn != NULL; pn = pn->m_next){
+ if(pn->m_pv == pv)
+ return pn;
+ }
+ return NULL;
+}
+
+
+void
+CDbAlloc::DumpInst(CAddrNode FAR* pn)
+{
+ m_pdbout->Printf("[%lp] nAlloc=%ld size=%ld\n",
+ pn->m_pv, pn->m_nAlloc, GetSize(pn->m_pv));
+}
+
+
+/***
+*PRIVATE BOOL IsEmpty
+*Purpose:
+* Answer if the address instance table is empty.
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = BOOL, TRUE if empty, FALSE otherwise
+*
+***********************************************************************/
+BOOL
+CDbAlloc::IsEmpty()
+{
+ UINT u;
+
+ for(u = 0; u < DIM(m_rganode); ++u){
+ if(m_rganode[u] != NULL) {
+#if OE_MAC
+ // UNDONE: (dougf) temporary code to work around bug in OleInitialize.
+ // UNDONE: OleInitialize in the OLE2 Beta 1 build allocs 42 bytes of
+ // UNDONE: memory in it's first alloc, and never frees it. It
+ // UNDONE: also randomly fails to dealloc 39 bytes in WriteClassStg.
+ // UNDONE: Rip this code when we upgrade to a newer Mac OLE that has
+ // UNDONE: these bugs fixed.
+ CAddrNode FAR* pn;
+ ULONG cb;
+
+ pn = m_rganode[u];
+ cb = GetSize(pn->m_pv);
+
+ if (pn->m_nAlloc == 1 && cb == 42)
+ continue; // ignore OleInitialize's memory leak
+ if (cb == 39)
+ continue; // ignore the random OLE memory leak in WriteClassStg
+ // (happens when running cl\tbmacole.scr)
+#endif //OE_MAC
+
+#if OE_WIN32 && 0
+ // UNDONE: (dougf) temporary code to work around bug in OleInitialize.
+ // UNDONE: OleInitialize allocs 320 bytes of memory in it's first
+ // UNDONE: alloc, and 60 bytes in it's 3rd alloc, and never frees them.
+ // UNDONE: OleUnitialize allocs 68 & 172 bytes and never frees them.
+ // UNDONE: Rip this code when we upgrade
+ // UNDONE: to a newer NT OLE that has these bugs fixed.
+ CAddrNode FAR* pn;
+ ULONG cb;
+
+ pn = m_rganode[u];
+ cb = GetSize(pn->m_pv);
+
+ if (pn->m_nAlloc == 1 && cb == 320)
+ continue; // ignore OleInitialize's first memory leak
+ if (pn->m_nAlloc == 3 && cb == 60)
+ continue; // ignore OleInitialize's second memory leak
+ if (cb == 68)
+ continue; // ignore OleUninitialize's first memory leak
+ if (cb == 172)
+ continue; // ignore OleUninitialize's second memory leak
+#endif //OE_WIN32
+
+#if !FV_UNICODE_OLE // UNDONE: temporary (ignore the dstrmgr leaks)
+ return FALSE; // some other leak
+#endif //!FV_UNICODE_OLE
+ }
+ }
+
+ return TRUE;
+}
+
+
+/***
+*PRIVATE CDbAlloc::Dump
+*Purpose:
+* Print the current contents of the address instance table,
+*
+*Entry:
+* None
+*
+*Exit:
+* None
+*
+***********************************************************************/
+void
+CDbAlloc::DumpInstTable()
+{
+ UINT u;
+ CAddrNode FAR* pn;
+
+ for(u = 0; u < DIM(m_rganode); ++u){
+ for(pn = m_rganode[u]; pn != NULL; pn = pn->m_next){
+ DumpInst(pn);
+ }
+ }
+}
+
+
+/***********
+* GetDebIMalloc()
+*
+* Purpose : Walks the Heap and verifies that the heap is not corrupted
+*
+**************************************************************************/
+VOID CDbAlloc::IMallocHeapChecker()
+{
+
+ UINT u;
+ CAddrNode FAR* pn;
+
+ return;
+
+ for(u = 0; u < DIM(m_rganode); ++u){
+
+ for(pn = m_rganode[u]; pn != NULL; pn = pn->m_next){
+ // Verify that the signature are the foot and the head of this
+ // instance is correct.
+
+ // We do not put the signature at the tail for huge memory allocation
+ if ((pn->m_cb + 2*sizeof(m_rgchSig)) < MAX_SIZE) {
+ // verify the signature at the tail
+ if (MEMCMP((char FAR*)pn->m_pv + pn->m_cb, m_rgchSig, sizeof(m_rgchSig)) != 0){
+ m_pdbout->Printf(szSigMsg); m_pdbout->Printf("\n");
+ DumpInst(GetInst(pn->m_pv));
+ ASSERTSZ(FALSE, szSigMsg);
+ }
+
+ // verify the signature at the head
+ if (MEMCMP((char FAR*)pn->m_pv - sizeof(m_rgchSig), m_rgchSig, sizeof(m_rgchSig)) != 0){
+ m_pdbout->Printf(szSigMsg); m_pdbout->Printf("\n");
+ DumpInst(GetInst(pn->m_pv));
+ ASSERTSZ(FALSE, szSigMsg);
+ }
+ }
+
+ } // for loop
+ } // for loop
+}
+
+//---------------------------------------------------------------------
+// implementation of CStdDbOutput
+//---------------------------------------------------------------------
+
+IDbOutput FAR*
+CStdDbOutput::Create()
+{
+ return (IDbOutput FAR*)new FAR CStdDbOutput();
+}
+
+STDMETHODIMP
+CStdDbOutput::QueryInterface(REFIID riid, void FAR* FAR* ppv)
+{
+ if(riid == IID_IUnknown){
+ *ppv = this;
+ AddRef();
+ return NOERROR;
+ }
+ return ResultFromScode(E_NOINTERFACE);
+}
+
+STDMETHODIMP_(ULONG)
+CStdDbOutput::AddRef()
+{
+ return ++m_refs;
+}
+
+STDMETHODIMP_(ULONG)
+CStdDbOutput::Release()
+{
+ if(--m_refs == 0){
+ delete this;
+ return 0;
+ }
+ return m_refs;
+}
+
+STDMETHODIMP_(void)
+CStdDbOutput::Printf(char FAR* szFmt, ...)
+{
+ va_list args;
+ char *pn, FAR* pf;
+ char rgchFmtBuf[128];
+ char rgchOutputBuf[128];
+
+ // copy the 'far' format string to a near buffer so we can use
+ // a medium model vsprintf, which only supports near data pointers.
+ //
+ pn = rgchFmtBuf, pf=szFmt;
+ while(*pf != '\0')
+ *pn++ = *pf++;
+ *pn = '\0';
+
+ va_start(args, szFmt);
+
+ vsprintf(rgchOutputBuf, rgchFmtBuf, args);
+
+
+#if !OE_MAC
+ OutputDebugString(rgchOutputBuf);
+#else
+ strcat(rgchOutputBuf, ";g");
+ DebugStr((const unsigned char *) c2pstr(rgchOutputBuf));
+#endif
+
+}
+
+STDMETHODIMP_(void)
+CStdDbOutput::Assertion(
+ BOOL cond,
+ char FAR* szExpr,
+ char FAR* szFile,
+ UINT uLine,
+ char FAR* szMsg)
+{
+ if(cond)
+ return;
+
+ // following is from compobj.dll (ole2)
+ // FnAssert(szExpr, szMsg, szFile, uLine);
+ DebAssert(0, szMsg);
+}
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/***********
+* GetDebIMalloc()
+*
+* Purpose : Creates a debug version of IMalloc
+*
+**************************************************************************/
+BOOL GetDebIMalloc(IMalloc FAR* FAR* ppmalloc)
+{
+ // For Debug version we want to provide our own implementation of
+ // IMalloc. But for release version we use the default.
+ HRESULT hresult;
+ IMalloc FAR* pmalloc;
+
+ pmalloc = NULL;
+ hresult = CreateDbAlloc(DBALLOC_NONE, NULL, &pmalloc);
+
+ if (hresult != NOERROR)
+ return FALSE;
+
+ *ppmalloc = pmalloc;
+
+ return TRUE;
+}
+
+#ifdef __cplusplus
+}
+#endif
+
+
+/***
+* HugeAlloc
+*
+* Purpose:
+* Allocate a system memblock of given size and return its handle.
+* Note: on Win16 dereferences handle and produce 32-bit
+* address = selector:offset=0.
+*
+* Inputs:
+* bch Allocation request. Can be >64K.
+*
+* Outputs:
+* Returns an HSYS. NULL if unsuccessful.
+*
+*****************************************************************************/
+
+VOID FAR * HugeAlloc(DWORD bch)
+{
+#if OE_WIN16
+
+ VOID FAR *pv;
+ HANDLE hMem;
+
+ if (((hMem = GlobalAlloc(GMEM_MOVEABLE, bch)) == NULL)) {
+ return NULL;
+ }
+ else if ((pv = (VOID FAR *) GlobalLock(hMem)) == NULL) {
+ return NULL;
+ }
+ else {
+ return (VOID FAR *)pv;
+ }
+
+#elif OE_MACNATIVE
+
+ Handle hMemBlock;
+ THz pCurrZone;
+ OSErr oserr;
+
+ //--------------------------------------------------------
+ // The following is a work-around to our bogus code that
+ // caches pointers to moveable memory. The basic idea
+ // is that we allocate all such memory out of a sub-heap
+ // inside the host application (or inside our own heap when
+ // a .DLL). The zone is switched in briefly to allocate,
+ // then switched back to avoid the OS or CODE seg loads
+ // from allocating there-in.
+ //
+ // The practice of caching pointers to moveable memory on
+ // the mac should be fixed to gain optimal use of available
+ // memory. The sub-heap scheme pools available memory
+ // and keeps it from being used for loading code when data
+ // is small. Visa-versa, we cannot flush more code out
+ // when the data expands to the heap limit. (jwc)
+ //--------------------------------------------------------
+
+ DebAssert(g_pOBZone != NULL, "OB Zone used before being allocated.");
+ pCurrZone = GetZone(); // save current heap zone.
+ SetZone(g_pOBZone); // set to OB's zone.
+
+ // Allocate moveable mac memblock.
+ hMemBlock = NewHandle(bch);
+ // get the error before calling SetZone. 'Cos SetZone can
+ // change the memory error.
+ oserr = MemError();
+
+ SetZone(pCurrZone); // always restore zone.
+
+ if (oserr) {
+ return NULL;
+ }
+ else {
+ return (HSYS)hMemBlock;
+ }
+
+#elif OE_MAC
+
+ Handle hMemBlock;
+ OSErr oserr;
+
+ // Allocate moveable mac memblock.
+ hMemBlock = NewHandle(bch);
+ oserr = MemError();
+ if (oserr) {
+ return NULL;
+ }
+ else {
+ return (VOID FAR*)hMemBlock;
+ }
+
+#elif OE_WIN32
+
+ VOID FAR *pv = NULL;
+
+ return (VOID FAR *)VirtualAlloc(pv, bch, MEM_COMMIT, PAGE_READWRITE);
+
+#else
+#error Bad OE
+#endif
+}
+
+
+/***
+* HsysReallocHsys
+*
+* Purpose:
+* Reallocate a system memblock given handle to new size.
+* Shrinking won't move block.
+*
+* Inputs:
+* hsys Handle to sys memblock they want to realloc.
+* bchNew New size they want. Can be >64K.
+*
+* Outputs:
+* Returns an HSYS. NULL if unsuccessful.
+*
+*****************************************************************************/
+
+VOID FAR *HugeRealloc(VOID FAR *pv, DWORD bchNew)
+{
+#if OE_WIN16 // TEMPORARY
+#if OE_WIN16
+
+ HANDLE hMem, hMemNew;
+ VOID FAR *pvNew;
+ USHORT usSel;
+ DWORD dwMem;
+ DWORD dwNewSize = bchNew;
+#if ID_DEBUG
+ ULONG cbOld;
+#endif // ID_DEBUG
+
+
+ // Get selector
+ usSel = OOB_SELECTOROF((void FAR*)pv);
+
+ if ((dwMem = GlobalHandle((WORD)usSel)) == NULL) {
+ return NULL;
+ }
+ else {
+ // Extract the handle.
+ hMem = (HANDLE) LOWORD(dwMem);
+
+#if ID_DEBUG
+ // get the size of the old block
+ cbOld = GlobalSize(hMem);
+#endif // ID_DEBUG
+
+ if (((hMemNew =
+ GlobalReAlloc(hMem, bchNew, GMEM_MOVEABLE)) == NULL)) {
+ return NULL;
+ }
+ else if ((pvNew = GlobalLock(hMemNew)) == NULL) {
+ return NULL;
+ }
+ else {
+ return (VOID FAR *)pvNew;
+ }
+ }
+
+#elif OE_MACNATIVE
+
+ Handle hMemBlock;
+ THz pCurrZone;
+ OSErr oserr;
+#if ID_DEBUG
+ ULONG cbOld;
+#endif // ID_DEBUG
+
+ hMemBlock = (Handle)hsys;
+
+#if ID_DEBUG
+ // get the size of the old block
+ cbOld = GetHandleSize(hMemBlock);
+#endif // ID_DEBUG
+
+ pCurrZone = GetZone(); // save current zone
+ SetZone(HandleZone((Handle)hsys)); // must set proper zone or
+ SetHandleSize(hMemBlock, bchNew); // handle will likely
+ // jump to curr zone if it moves.
+ oserr = MemError();
+ SetZone(pCurrZone); // restore current zone.
+
+
+ if (oserr == memFullErr) {
+ // Out of memory
+ return NULL;
+ }
+
+ DebAssert ((MemError() != nilHandleErr),
+ "HsysReallocHsys: NIL master pointer ");
+
+ DebAssert ((MemError() != memWZErr),
+ "HsysReallocHsys: Attempt to operate on free Block");
+
+ // anything else would be an undocumented error
+ DebAssert (MemError() == noErr,
+ "HsysReallocHsys: undocumented Mac error");
+
+ return (VOID FAR *)hMemBlock;
+
+#elif OE_MAC
+
+ Handle hMemBlock;
+ OSErr oserr;
+#if ID_DEBUG
+ ULONG cbOld;
+#endif // ID_DEBUG
+
+ hMemBlock = (Handle)hsys;
+
+#if ID_DEBUG
+ // get the size of the old block
+ cbOld = GetHandleSize(hMemBlock);
+#endif // ID_DEBUG
+
+ SetHandleSize(hMemBlock, bchNew); // realloc
+ oserr = MemError();
+
+ if (oserr == memFullErr) {
+ // Out of memory
+ return NULL;
+ }
+
+ DebAssert ((MemError() != nilHandleErr),
+ "HsysReallocHsys: NIL master pointer ");
+
+ DebAssert ((MemError() != memWZErr),
+ "HsysReallocHsys: Attempt to operate on free Block");
+
+ // anything else would be an undocumented error
+ DebAssert (MemError() == noErr,
+ "HsysReallocHsys: undocumented Mac error");
+
+ return (HSYS)hMemBlock;
+
+#elif OE_WIN32
+ // UNDONE...
+ DebHalt("HsysReallocHsys: UNDONE for OE_WIN32");
+ return NULL;
+#else
+#error Bad OE
+#endif
+#endif // TEMPORARY
+ return NULL;
+}
+
+
+
+
+/***
+* FreeHsys
+*
+* Purpose:
+* Free the sys memblock given a handle.
+* Implementation:
+* On Win16, get selector part of hsys,
+* get its handle, unlock and finally free.
+* On Mac: Just use DisposHandle
+*
+* Inputs:
+* hsys Handle to memblock they want to free.
+*
+* Outputs:
+* Returns NULL if successful, otherwise on failure
+* returns the input param.
+*
+*****************************************************************************/
+
+VOID FAR *HugeFree(VOID FAR * pv)
+{
+#if OE_WIN16
+
+ HANDLE hMem;
+ DWORD dwMem;
+ USHORT usSel = OOB_SELECTOROF((VOID FAR *)pv);
+
+ dwMem = GlobalHandle((WORD)usSel);
+ if (dwMem == NULL) {
+ // error
+ return pv;
+ }
+ else {
+ hMem = (HANDLE) LOWORD(dwMem);
+ GlobalUnlock(hMem); // Can't fail cos nondiscardable.
+ if (GlobalFree(hMem) != NULL) {
+ // error
+ return pv;
+ }
+ else {
+ // ok
+ return NULL;
+ }
+ }
+
+#elif OE_MACNATIVE
+ THz pCurrZone;
+#if ID_DEBUG
+ OSErr oserr;
+#endif
+
+ pCurrZone = GetZone(); // save current zone
+ SetZone(HandleZone((Handle)hsys)); // must set to proper zone to correctly update free list.
+
+ DisposHandle((Handle)hsys);
+
+#if ID_DEBUG
+ oserr = MemError(); // SetZone() will destroy MemError() result.
+#endif
+
+ SetZone(pCurrZone); // restore zone.
+
+ DebAssert (oserr != memWZErr,
+ "FreeHsys: attempt to operate on already free block.");
+
+ DebAssert(oserr == noErr,
+ "FreeHsys: unexpected error.");
+
+ return NULL;
+
+#elif OE_MAC
+ HSYS hsys = (HSYS) pv;
+#if ID_DEBUG
+ OSErr oserr;
+#endif
+
+ DisposHandle((Handle)hsys);
+
+#if ID_DEBUG
+ oserr = MemError(); // SetZone() will destroy MemError() result.
+
+ DebAssert (oserr != memWZErr,
+ "FreeHsys: attempt to operate on already free block.");
+
+ DebAssert(oserr == noErr,
+ "FreeHsys: unexpected error.");
+#endif
+
+ return NULL;
+
+#elif OE_WIN32
+ // UNDONE...
+ DebAssert(FALSE, "FreeHsys: UNDONE for OE_WIN32");
+ return NULL;
+#else
+#error Bad OE
+#endif // OE_WIN16
+ return NULL;
+
+}
+
+#endif //DEBUG
diff --git a/private/oleauto/src/mktyplib/errors.h b/private/oleauto/src/mktyplib/errors.h
new file mode 100644
index 000000000..90deb6036
--- /dev/null
+++ b/private/oleauto/src/mktyplib/errors.h
@@ -0,0 +1,104 @@
+// error constants -- WARNING -- must be kept in order!
+// table in INTLSTR.H depends on this order!
+
+typedef enum {
+ ERR_NONE = 0,
+
+// lexer/parser errors with file/line #/column info
+ PERR_UNTERMINATED_COMMENT,
+ PERR_UNEXP_EOF,
+ PERR_READ_ERROR,
+ PERR_UNDEF_INTER,
+ PERR_UNKNOWN_TYPE,
+ PERR_DUP_DEF,
+ PERR_DUP_UUID,
+ PERR_DUP_ID,
+ PERR_INV_COMBO,
+ PERR_ID_REQ,
+ PERR_UUID_REQ,
+ PERR_IN_OUT_REQ,
+ PERR_DLLNAME_REQ,
+ PERR_ENTRY_REQ,
+ PERR_ODL_REQ,
+ PERR_IMPLIB_NOTFIRST,
+ PERR_VOID_INV,
+ PERR_NUMBER_OV,
+ PERR_INV_ATTR_COMBO,
+ PERR_INV_ATTR,
+ PERR_INV_NUMBER,
+ PERR_INV_STRING,
+ PERR_INV_UUID,
+ PERR_INV_IDENTIFIER,
+ PERR_INV_CONSTANT,
+ PERR_INV_ID,
+ PERR_INV_LCID_USE,
+ PERR_INV_RETVAL_USE,
+ PERR_INV_VARARG_USE,
+ PERR_UNSUPP_KEYWORD,
+ PERR_EXPECTED,
+ PERR_EXP_EOF,
+ PERR_EXP_IDENTIFIER,
+ PERR_EXP_KEYWORD,
+ PERR_EXP_ATTRIBUTE,
+ PERR_EXP_OPERATOR,
+ PERR_UNSUPPORTED_OP,
+ PERR_INV_EXPRESSION,
+ PERR_EXP_NUMBER,
+ PERR_EXP_STRING,
+ PERR_EXP_INTER,
+ PERR_TWO_DISPINTER,
+ PERR_INV_CALLCONV,
+ PERR_INV_ARRAY_DECL,
+ PERR_NO_IDISPATCH,
+ PERR_NO_IUNKNOWN,
+ PERR_TYPEDEF_ATTR,
+ PERR_INV_PROPPUT,
+ PERR_INV_PROPFUNC,
+ PERR_INV_LCID,
+ PERR_INV_SOURCE_ATTR,
+ PERR_INV_OUT_PARAM,
+ PERR_INV_DUAL_BASE,
+ PERR_INV_OA_BASE,
+ PERR_INV_OA_TYPE,
+ PERR_INV_OA_FUNC_TYPE,
+
+ PERR_INV_REFERENCE,
+ PWARN_INV_IDISPATCHTYPE,
+
+ OERR_NO_DEF,
+ #define TYPELIBERR(name,string) OERR_ ## name
+ #include "typelib.err" // TYPELIB.DLL error constants
+ #undef TYPELIBERR
+ OERR_TYPEINFO,
+
+// general type library generation errors (no file/line#/column# info)
+ ERR_OM,
+ ERR_CANT_OPEN_INPUTFILE,
+#if FV_CPP
+ ERR_CPP,
+#endif //FV_CPP
+ ERR_CANT_OPEN_HFILE,
+ ERR_WRITING_HFILE,
+
+ WARN_STRANGE_ALIGNMENT,
+
+ GENERAL_ERR_LAST, // the last general error/warning
+
+ PERR_FIRST = PERR_UNTERMINATED_COMMENT,
+ PWARN_FIRST = PWARN_INV_IDISPATCHTYPE,
+ OERR_FIRST = OERR_NO_DEF,
+ ERR_FIRST = ERR_OM,
+ WARN_FIRST = WARN_STRANGE_ALIGNMENT,
+} ERR;
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+extern VOID FAR ParseError(ERR err);
+extern VOID FAR ParseErrorTokLast(ERR err);
+extern VOID FAR ItemError(CHAR * szFormat, LPSTR lpszItem, ERR err);
+
+#ifdef __cplusplus
+}
+#endif
diff --git a/private/oleauto/src/mktyplib/fileinfo.h b/private/oleauto/src/mktyplib/fileinfo.h
new file mode 100644
index 000000000..b7e374269
--- /dev/null
+++ b/private/oleauto/src/mktyplib/fileinfo.h
@@ -0,0 +1,329 @@
+// *******************************************************
+// contexts
+// *******************************************************
+#define cLIB 0x0001
+#define cTYPE 0x0002
+#define cIMPLTYPE 0x0004
+#define cFUNC 0x0008
+#define cVAR 0x0010
+#define cPARAM 0x0020
+
+// *******************************************************
+// Attributes
+// *******************************************************
+
+// bit flags indicating presence of each attribute
+#define fUUID 0x00000001L
+#define fVERSION 0x00000002L
+#define fDLLNAME 0x00000004L
+#define fENTRY 0x00000008L
+#define fRESTRICTED 0x00000010L
+#define fHELPSTRING 0x00000020L
+#define fHELPCONTEXT 0x00000040L
+#define fHELPFILE 0x00000080L
+#define fLCID 0x00000100L
+#define fPROPGET 0x00000200L
+#define fPROPPUT 0x00000400L
+#define fPROPPUTREF 0x00000800L
+#define fOPTIONAL 0x00001000L
+#define fIN 0x00002000L
+#define fOUT 0x00004000L
+#define fPUBLIC 0x00008000L
+#define fSTRING 0x00010000L
+#define fID 0x00020000L
+#define fVARARG 0x00040000L
+#define fAPPOBJECT 0x00080000L
+#define fREADONLY 0x00100000L
+#define fODL 0x00200000L
+#define fDEFAULT 0x00400000L
+#define fSOURCE 0x00800000L
+#define fBINDABLE 0x01000000L
+#define fREQUESTEDIT 0x02000000L
+#define fDISPLAYBIND 0x04000000L
+#define fDEFAULTBIND 0x08000000L
+#define fLICENSED 0x10000000L
+#define fPREDECLID 0x20000000L
+#define fHIDDEN 0x40000000L
+#define fRETVAL 0x80000000L
+
+#define fPropBits (fPROPGET | fPROPPUT | fPROPPUTREF)
+
+// *******************************************************
+// More Attributes (to be used only with fAttr2)
+// *******************************************************
+
+#define f2PASCAL 0x00000001
+#define f2CDECL 0x00000002
+#define f2STDCALL 0x00000004
+#define f2CCDEFAULTED 0x00000008
+#define f2CONTROL 0x00000010
+#define f2DUAL 0x00000020
+#define f2NONEXTENSIBLE 0x00000040
+#define f2OLEAUTOMATION 0x00000080
+ #define f2OACompatBits (f2DUAL | f2OLEAUTOMATION) // shorthand
+#define f2GotConstVal 0x00000100 // const elem's value explictly given
+#define f2VALIDDUALBASE 0x00000200 // valid for use as base interface
+ // of a dual interface
+
+// the following bits are unused at present
+#define f2Unused07 0x00000400
+#define f2Unused08 0x00000800
+#define f2Unused09 0x00001000
+#define f2Unused10 0x00002000
+#define f2Unused11 0x00004000
+#define f2Unused12 0x00008000
+#define f2Unused13 0x00010000
+#define f2Unused14 0x00020000
+#define f2Unused15 0x00040000
+#define f2Unused16 0x00080000
+#define f2Unused17 0x00100000
+#define f2Unused18 0x00200000
+#define f2Unused19 0x00400000
+#define f2Unused20 0x00800000
+#define f2Unused21 0x01000000
+#define f2Unused22 0x02000000
+#define f2Unused23 0x04000000
+#define f2Unused24 0x08000000
+#define f2Unused25 0x10000000
+#define f2Unused26 0x20000000
+#define f2Unused27 0x40000000
+#define f2Unused28 0x80000000
+
+typedef struct {
+ DWORD fAttr; // bit flags
+ DWORD fAttr2; // more bit flags
+ WORD fContext; // the context of these attributes
+ WORD wFlags; // flags associated with this item
+ // the following attributes are allowed on most items
+ GUID FAR * lpUuid;
+ WORD wVerMajor;
+ WORD wVerMinor;
+ DWORD lHelpContext;
+ LPSTR lpszHelpString;
+ // the following attributes are mutually-exclusive
+ union {
+ DWORD lLcid; // only on Library
+ LPSTR lpszDllName; // only on Module
+ LPSTR lpszProcName; // only on Module function
+ };
+ // the following attributes are mutually-exclusive
+ union {
+ LPSTR lpszHelpFile; // only on Library
+ DWORD lId; // on lots of ids (but not Library)
+ };
+} ATTR;
+
+typedef ATTR FAR * LPATTR;
+
+
+// *******************************************************
+// TYPE structures
+// *******************************************************
+
+// kind of entries in the type table
+// WARNING: rgtkind in TYPOUT.CPP depends on this order
+typedef enum {
+ tTYPEDEF = 0,
+ tSTRUCT,
+ tENUM,
+ tUNION,
+ tMODULE,
+ tINTERFACE,
+ tDISPINTER,
+ tCOCLASS,
+ // the following don't have full-size entries for them
+ tINTRINSIC,
+ tREF,
+ // tIMPORTED also doesn't have full-size entries
+
+ // the following don't have ANY entries for them
+ tANY, // no specific type
+
+ tIMPORTED=0x1000, // imported type with qualification
+ tQUAL=0x2000, // imported type with qualification
+ tFORWARD = 0x4000 // bit set if this is a forward definition
+} TENTRYKIND;
+
+// Used to describe intrinsic types, type references, and typedef [struct/enum]
+typedef struct tagTYPE {
+ struct tagTYPE FAR * pNext; // pointer to next type item
+ // MUST BE FIRST
+ TENTRYKIND tentrykind; // kind of this type item
+ LPSTR szName; // name of this type item
+ TYPEDESC tdesc; // contains:
+ // vt = one of
+ // intrinsic type ID
+ // VT_PTR ==> * to another type
+ // VT_USERDEFINED ==> typedef struct
+ // typedef enum
+ // typedef union
+ // interface,
+ // dispinterface,
+ // coclass,
+ // modules
+ // VT_SAFEARRAY ==> array of another type
+ // indexreftypeinfo (only for VT_USERDEFINED)
+ // lptdesc (only for VT_PTR, VT_SAFEARRAY)
+ ITypeInfo FAR* lptinfo; // ITypeInfo for this guy
+ // (filled in during output pass)
+ union {
+ struct { // for tINTRINSIC, (VT_xxx)
+ BOOL fUnsigned; // non-zero if this type is an UNSIGNED type
+ } intr;
+ struct { // for tREF (VT_PTR, VT_SAFEARRAY, or VT_CARRAY)
+ // not a true type, just a reference to one
+ struct tagTYPE FAR * ptypeBase; // base type
+ SHORT cIndirect; // # of levels of indirection off base type
+ // (VT_PTR only)
+ } ref;
+ struct { // for tTYPEDEF (VT_USERDEFINED)
+ struct tagTYPE FAR * ptypeAlias; // type this is an alias for
+ } td;
+ struct { // for tINTERFACE/tDISPINTER/tCOCLASS
+ // (VT_USERDEFINED)
+ struct tagINTER FAR * interList; // list of base interface(s)
+ // NULL if none
+ } inter;
+ struct { // for tSTRUCT/tENUM/tUNION (VT_USERDEFINED)
+ LPSTR szTag; // optional tag name (NULL if not present)
+ struct tagELEM FAR * elemList; // list of struct/enum/union
+ // members
+ } structenum;
+ struct { // for tIMPORTED | tXXXX, (VT_USERDEFINED)
+ WORD wTypeFlags; // flags for this type
+ } import;
+ };
+} TYPE;
+typedef TYPE FAR * LPTYPE;
+
+
+// for element of struct, enum, union, function arg, property, etc.
+typedef struct tagELEM {
+ struct tagELEM FAR * pNext;
+ ATTR attr; // element attributes
+ LPSTR szElemName; // element name
+ LPTYPE elemType; // element type
+ VARIANT FAR * lpElemVal; // element value (for constants)
+} ELEM;
+typedef ELEM FAR * LPELEM;
+
+
+// For base interface of a interface/dispinterface, or implemented interface
+// of a coclass.
+typedef struct tagINTER {
+ struct tagELEM FAR * pNext;
+ LPTYPE ptypeInter; // interface type
+ DWORD fAttr; // interface attributes (only used for COCLASS)
+ DWORD fAttr2; // don't need the entire ATTR structure here,
+ // since only valid attrs are RESTRICTED,
+ // DEFAULT, and SOURCE, and they don't have
+ // any other info in them.
+} INTER;
+typedef INTER FAR * LPINTER;
+
+
+// *******************************************************
+// Function definition structures
+// *******************************************************
+
+typedef struct tagFUNC {
+ ELEM func; // function descr. (pNext, attr, name, type)
+ // MUST BE FIRST -- folks assume that can use
+ // a FUNC as an ELEM
+ SHORT cArgs; // # of args
+ SHORT cOptArgs; // # of optional args
+ LPELEM argList; // arg info
+} FUNC;
+typedef FUNC FAR * LPFUNC;
+
+
+// *******************************************************
+// Component structures
+// *******************************************************
+
+// module <modulename> { ... }
+typedef struct {
+ LPFUNC funcList; // list of functions
+ LPELEM constList; // list of constants
+} MODULE;
+
+// interface <interfacename> : <baseinterface> { ... }
+typedef struct {
+ LPFUNC funcList; // list of interface functions
+} INTERF;
+
+// dispinterface <interfacename> { ... }
+typedef struct {
+ LPELEM propList; // list of properties
+ LPFUNC methList; // list of methods
+} DISPINTER;
+
+#if FV_PROPSET
+// property_set <propsetname> : <base propsetname> { ... }
+typedef struct {
+ LPSTR szBaseName; // base property set name, NULL if none
+ LPELEM propList; // list of properties
+} PROPSET;
+#endif //FV_PROPSET
+
+typedef struct tagENTRY {
+ TYPE type; // type of this item
+ // (contains pNext, name, etc)
+ // MUST BE FIRST
+ ATTR attr; // attributes for this item
+ struct tagENTRY FAR * lpEntryForward; // pointer to forward declaration
+ // for this item, NULL if none.
+ ICreateTypeInfo FAR* lpdtinfo; // ICreateTypeInfo for this guy
+ // (filled in during output pass)
+ union { // extra info about the item
+ MODULE module;
+ INTERF inter;
+ DISPINTER dispinter;
+#if FV_PROPSET
+ PROPSET propset;
+#endif //FV_PROPSET
+ };
+} ENTRY;
+
+typedef ENTRY FAR * LPENTRY;
+
+
+// importlib (<filename>)
+typedef struct tagIMPORTLIB {
+ struct tagIMPORTLIB FAR * pNext; // link field
+ LPSTR lpszFileName; // filename specified by user
+ LPSTR lpszLibName; // library name of this type library
+ ITypeLib FAR* lptlib; // ITypeLib for this type library
+ ITypeComp FAR* lptcomp; // ITypeComp for this type library
+ LPTLIBATTR lptlibattr; // type library attributes
+} IMPORTLIB;
+typedef IMPORTLIB FAR * LPIMPORTLIB;
+
+
+typedef struct {
+ ATTR attr; // library attributes
+ LPSTR szLibName; // library name
+ LPENTRY pEntry; // circularly-linked list of library items
+ LPIMPORTLIB pImpLib; // circularly-linked list of imported libraries
+} TYPLIB;
+
+
+// #defines that simplify linked-list management. Assumes circularly-linked lists, and
+// that all lists have the pNext field at the same position (usually first).
+
+// Given pList, returns a pointer to the last element in the list.
+#define ListLast(pList) (pList)
+
+// Given pList, returns a pointer to the first element in the list.
+// Since circularly-linked, Next(Last) points to first element.
+#define ListFirst(pList) (((LPTYPE)pList)->pNext)
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+extern VOID FAR ListInsert(LPVOID ppList, WORD cbElem);
+
+#ifdef __cplusplus
+}
+#endif
diff --git a/private/oleauto/src/mktyplib/hout.c b/private/oleauto/src/mktyplib/hout.c
new file mode 100644
index 000000000..32b7594ab
--- /dev/null
+++ b/private/oleauto/src/mktyplib/hout.c
@@ -0,0 +1,1111 @@
+#include "mktyplib.h"
+
+// .H file output for MKTYPLIB
+
+#include <stdio.h>
+
+#ifndef WIN32
+#include <ole2.h> // required for dispatch.h
+#include "dispatch.h"
+#endif //WIN32
+
+#include "errors.h"
+#include "fileinfo.h"
+#include "intlstr.h" // for szHead* definitions
+
+// external data
+extern TYPLIB typlib;
+extern FILE *hHFile;
+extern SYSKIND SysKind;
+extern int iAlignMax;
+extern int iAlignDef;
+extern BOOL fSpecifiedInterCC;
+
+
+// external functions
+extern INT FAR FCmpCaseIns(LPSTR str1, LPSTR str2);
+
+
+// private data
+static CHAR *szHeadOlePrefix0 = "#undef INTERFACE\n"
+ "#define INTERFACE ";
+static CHAR *szHeadOlePrefix1 = "DECLARE_INTERFACE";
+static CHAR *szHeadOlePrefix2 = ")\n{\n";
+static CHAR *szHeadOlePrefix3 = "\n /* ";
+static CHAR *szHeadOlePrefix4 = " methods */\n";
+static CHAR *szHeadOlePrefix5 = " properties:\n";
+static CHAR *szHeadOlePrefix6 = " methods:\n";
+static CHAR *szHeadOlePrefix7 = "#ifndef NO_BASEINTERFACE_FUNCS\n";
+static CHAR *szHeadOleFuncPrefix1 = " "; // leading spaces
+static CHAR *szHeadOleFuncPrefix2 = "STDMETHOD";
+static CHAR *szHeadOleFuncPrefix3 = ", "; // after return type
+static CHAR *szHeadOleArgPrefix1 = ")(THIS";
+static CHAR *szHeadOleArgPrefix2 = "_ "; // only if args
+static CHAR *szHeadOleArgSuffix = ") PURE;\n";
+static CHAR *szHeadOleSuffix1 = " */\n";
+static CHAR *szHeadOleSuffix2 = "};\n";
+static CHAR *szHeadOleSuffix3 = " */\n";
+static CHAR *szHeadOleSuffix7 = "#endif\n";
+
+//Hack for profiling
+//#define PROFILE
+
+#ifdef PROFILE
+static unsigned long cFuncsTotal = 0;
+static unsigned long cArgsTotal = 0;
+static unsigned long cVarsTotal = 0;
+#endif //PROFILE
+
+// stuff dealing with non-default interface calling conventions
+static CHAR *szUndefCallType = "#undef STDMETHODCALLTYPE\n";
+static CHAR *szResetCallType =
+"#if defined(WIN32)\n"
+"#define STDMETHODCALLTYPE STDMETHODSTDCALL\n"
+"#else\n"
+"#define STDMETHODCALLTYPE STDMETHODCDECL\n"
+"#endif\n";
+
+static CHAR *szDefCallTypePrefix = "#define STDMETHODCALLTYPE STDMETHOD";
+
+static CHAR *rgszCallType[] = {
+ "CDECL",
+ "PASCAL",
+ "STDCALL"
+};
+
+typedef enum {
+ CALL_CDECL,
+ CALL_PASCAL,
+ CALL_STDCALL,
+ CALL_DEFAULT
+} CALLINGCONV;
+
+static CALLINGCONV ccInterCurrent = CALL_DEFAULT;
+
+// user-specified calling conventions for all platforms
+static CHAR * szCCHeader =
+"\n"
+"/* Macros for redefining the STDMETHOD calling convention\n"
+" * (STDMETHODCALLTYPE).\n"
+" */\n"
+"\n"
+"#if defined(_MAC)\n"
+"\n"
+"#if !defined(_MSC_VER)\n"
+"#define STDMETHODCDECL\n"
+"#define STDMETHODPASCAL\n"
+"#define STDMETHODSTDCALL\n"
+"#else\n"
+"#define STDMETHODCDECL FAR CDECL\n"
+"#define STDMETHODPASCAL FAR PASCAL\n"
+"#define STDMETHODSTDCALL FAR STDCALL\n"
+"#endif\n"
+"\n"
+"#elif defined(WIN32)\n"
+"\n"
+"#define STDMETHODCDECL EXPORT __cdecl\n"
+"#define STDMETHODPASCAL EXPORT __pascal\n"
+"#define STDMETHODSTDCALL EXPORT __stdcall\n"
+"\n"
+"#else /* WIN16 */\n"
+"\n"
+"#define STDMETHODCDECL __export FAR CDECL\n"
+"#define STDMETHODPASCAL __export FAR PASCAL\n"
+"#define STDMETHODSTDCALL __export FAR STDCALL\n"
+"\n"
+"#endif\n"
+"\n";
+
+
+// canned definition of IUnknown
+static CHAR * szHeadIUnknown =
+"\n"
+" /* IUnknown methods */\n"
+" STDMETHOD(QueryInterface)(THIS_ REFIID riid, LPVOID FAR* ppvObj) PURE;\n"
+" STDMETHOD_(ULONG, AddRef)(THIS) PURE;\n"
+" STDMETHOD_(ULONG, Release)(THIS) PURE;\n";
+
+// canned definition of IDispatch
+static CHAR * szHeadIDispatch =
+"\n"
+" /* IDispatch methods */\n"
+" STDMETHOD(GetTypeInfoCount)(THIS_ UINT FAR* pctinfo) PURE;\n"
+"\n"
+" STDMETHOD(GetTypeInfo)(\n"
+" THIS_\n"
+" UINT itinfo,\n"
+" LCID lcid,\n"
+" ITypeInfo FAR* FAR* pptinfo) PURE;\n"
+"\n"
+" STDMETHOD(GetIDsOfNames)(\n"
+" THIS_\n"
+" REFIID riid,\n"
+" OLECHAR FAR* FAR* rgszNames,\n"
+" UINT cNames,\n"
+" LCID lcid,\n"
+" DISPID FAR* rgdispid) PURE;\n"
+"\n"
+" STDMETHOD(Invoke)(\n"
+" THIS_\n"
+" DISPID dispidMember,\n"
+" REFIID riid,\n"
+" LCID lcid,\n"
+" WORD wFlags,\n"
+" DISPPARAMS FAR* pdispparams,\n"
+" VARIANT FAR* pvarResult,\n"
+" EXCEPINFO FAR* pexcepinfo,\n"
+" UINT FAR* puArgErr) PURE;\n";
+
+static CHAR *szHeadGuidPrefix = "\nDEFINE_GUID(";
+static CHAR *szHeadGuidLIBID = "LIBID_";
+static CHAR *szHeadGuidCLSID = "CLSID_";
+static CHAR *szHeadGuidIID = "IID_";
+static CHAR *szHeadGuidDIID = "DIID_";
+
+// prototypes
+VOID FAR OutputHFile (CHAR * szHFile);
+VOID NEAR HOutTypedef(LPTYPE pType);
+VOID NEAR HOutEnum(LPTYPE pType);
+VOID NEAR HOutStructUnion(LPTYPE pType);
+VOID NEAR HOutModule(LPENTRY pEntry);
+VOID NEAR HOutInterface(LPENTRY pEntry);
+VOID NEAR HOutCoclass(LPENTRY pEntry);
+VOID NEAR HOutBaseInter(LPENTRY pEntry, BOOL fRecurse);
+
+VOID NEAR HOutFuncs(LPFUNC pFuncList, TENTRYKIND tentryKind);
+VOID NEAR HOutElems(LPELEM pElemList, CHAR * szPrefix, CHAR * szSep, CHAR * szSepLast, BOOL fEnum);
+VOID NEAR HOutType(LPTYPE pType);
+VOID NEAR HOutShortNum(SHORT num, BOOL fHex);
+VOID NEAR HOutLongNum(LONG num, BOOL fHex);
+VOID NEAR HOutPropPrefix(LPFUNC pFunc);
+VOID NEAR HOutGuid(LPATTR pAttr, CHAR * szGuidPrefix, LPSTR lpszName);
+
+#ifdef PROFILE
+VOID NEAR XOutF(LPSTR lpszData);
+VOID NEAR XOut(CHAR * szData);
+#else //PROFILE
+#define XOutF HOutF
+#define XOut HOut
+#endif //PROFILE
+VOID NEAR HOutF(LPSTR lpszData);
+VOID NEAR HOut(CHAR * szData);
+VOID NEAR SetCallType(CALLINGCONV cc);
+
+
+VOID FAR OutputHFile
+(
+ CHAR * szHFile
+)
+{
+ LPENTRY pEntry;
+
+#ifdef WIN16
+ // convert szHFile in-place to OEM char set
+ AnsiToOem(szHFile, szHFile);
+
+ // don't bother converting back since this string is not used again
+#endif // WIN16
+
+ // open the file
+ hHFile = fopen(szHFile, "w"); // open output file
+ if (hHFile == NULL)
+ ParseError(ERR_CANT_OPEN_HFILE);
+
+ Assert (SYS_WIN16 == 0 && SYS_WIN32 == 1 && SYS_MAC == 2 && SysKind <= SYS_MAX);
+
+ HOut(szHeadFile); // output file header
+ HOutF(typlib.szLibName); // output type library name
+ HOut(" */\n\n#ifndef _"); // output: #ifndef _<libname>_H_
+ HOutF(typlib.szLibName); // #define _<libname>_H_
+ HOut("_H_\n#define _");
+ HOutF(typlib.szLibName);
+ HOut("_H_\n");
+
+ HOutGuid(&typlib.attr, szHeadGuidLIBID, typlib.szLibName);
+
+ if (fSpecifiedInterCC) {
+ HOut(szCCHeader);
+ }
+
+ if (typlib.pEntry)
+ {
+ pEntry = (LPENTRY)ListFirst(typlib.pEntry); // point to first entry
+
+#pragma warning(disable:4127)
+ while (TRUE)
+#pragma warning(default:4127)
+ {
+
+ switch (pEntry->type.tentrykind & ~tFORWARD)
+ {
+ case tTYPEDEF:
+ HOutTypedef(&pEntry->type);
+ break;
+
+ case tENUM:
+ HOutEnum(&pEntry->type);
+ break;
+
+ case tSTRUCT:
+ case tUNION:
+ HOutStructUnion(&pEntry->type);
+ break;
+
+ case tMODULE:
+ HOutModule(pEntry);
+ break;
+
+ case tCOCLASS:
+ HOutCoclass(pEntry);
+ break;
+
+ case tINTERFACE:
+ case tDISPINTER:
+ HOutInterface(pEntry);
+ // fall through
+
+ case tINTRINSIC:
+ case tREF:
+ break; // nothing to output
+
+#ifdef DEBUG
+ default:
+ if (pEntry->type.tentrykind & tIMPORTED)
+ break; // noting to output for imported types
+ Assert(FALSE);
+#endif //DEBUG
+ }
+
+ // advance to next entry if not all done
+ if (pEntry == (LPENTRY)ListLast(typlib.pEntry))
+ break; // exit if all done
+ pEntry = (LPENTRY)pEntry->type.pNext;
+
+ } // WHILE
+ }
+
+ HOut("\n#endif\n");
+
+ fclose(hHFile); // done writing .H file
+ hHFile = NULL; // close done
+
+ // check for possible alignment problems
+ if (iAlignMax != iAlignDef)
+ ParseError(WARN_STRANGE_ALIGNMENT);
+
+#ifdef PROFILE
+ printf("\n\ntotal functions: %d\n", cFuncsTotal);
+ printf("total function args: %d\n", cArgsTotal);
+ printf("total variables: %d\n", cVarsTotal);
+ ParseError(ERR_OM); // bogus early quit
+#endif //PROFILE
+
+}
+
+
+VOID NEAR HOutTypedef
+(
+LPTYPE pType
+)
+{
+ XOut("\ntypedef ");
+
+ // output base type
+ HOutType(pType->td.ptypeAlias);
+ HOut(" ");
+
+ XOutF(pType->szName);
+
+ Assert(pType->td.ptypeAlias->tdesc.vt != VT_CARRAY);
+
+ XOut(";\n");
+
+}
+
+
+VOID NEAR HOutEnum
+(
+LPTYPE pType
+)
+{
+
+ XOut("\ntypedef enum ");
+
+ if (pType->structenum.szTag)
+ {
+ XOutF(pType->structenum.szTag);
+ if (pType->tentrykind & tFORWARD)
+ {
+ XOut(";\n");
+ return;
+ }
+ XOut(" ");
+ }
+
+ XOut("{\n");
+
+ HOutElems(pType->structenum.elemList, " ", ",\n", "\n", TRUE);
+
+ XOut("} ");
+ XOutF(pType->szName);
+ XOut(";\n");
+
+}
+
+VOID NEAR HOutStructUnion
+(
+LPTYPE pType
+)
+{
+
+ if ((pType->tentrykind & ~tFORWARD) == tSTRUCT)
+ XOut("\ntypedef struct ");
+ else
+ XOut("\ntypedef union ");
+
+ if (pType->structenum.szTag)
+ {
+ XOutF(pType->structenum.szTag);
+ if (pType->tentrykind & tFORWARD)
+ goto done;
+
+ XOut(" ");
+ }
+
+ XOut("{\n");
+
+ HOutElems(pType->structenum.elemList, " ", ";\n", ";\n", FALSE);
+
+ XOut("} ");
+ XOutF(pType->szName);
+
+done:
+ XOut(";\n");
+
+}
+
+VOID NEAR HOutModule
+(
+LPENTRY pEntry
+)
+{
+ XOut(szHeadModule);
+ XOutF(pEntry->type.szName);
+ XOut(szHeadOleSuffix3);
+ HOutFuncs(pEntry->module.funcList, pEntry->type.tentrykind);
+ if (pEntry->module.constList)
+ HOutElems(pEntry->module.constList, " const ", ";\n", ";\n", FALSE);
+
+}
+
+VOID NEAR HOutCoclass
+(
+LPENTRY pEntry
+)
+{
+ if ((pEntry->type.tentrykind & tFORWARD) == 0) {
+ HOutGuid(&pEntry->attr, szHeadGuidCLSID, pEntry->type.szName);
+ }
+
+ // UNDONE: I don't think this will work in C.
+
+ HOut("\n#ifdef __cplusplus\nclass ");
+ HOutF(pEntry->type.szName);
+ HOut(";\n#endif\n");
+
+}
+
+
+VOID NEAR HOutInterface
+(
+LPENTRY pEntry
+)
+{
+
+LPSTR lpszBaseName;
+TENTRYKIND tentrykind;
+LPINTER lpInterFirst; // first base interface, if any
+LPINTER lpInterLast; // second/last base interface, if any
+
+ tentrykind = pEntry->type.tentrykind;
+
+ if (tentrykind & tFORWARD)
+ {
+ // UNDONE: proper OLE format for forward declaration of interface?
+ // UNDONE: I don't think this will work in C. I think it wants:
+ // UNDONE: typedef interface <interfacename> <interfacename>;
+ HOut("\ninterface ");
+ HOutF(pEntry->type.szName);
+ HOut(";\n");
+ return;
+ }
+
+ HOutGuid(&pEntry->attr,
+ ((tentrykind == tDISPINTER) ? szHeadGuidDIID: szHeadGuidIID),
+ pEntry->type.szName);
+
+ lpszBaseName = NULL;
+ lpInterFirst = NULL;
+ if (pEntry->type.inter.interList)
+ {
+ lpInterFirst = (LPINTER)ListFirst(pEntry->type.inter.interList);
+ lpInterLast = (LPINTER)ListLast(pEntry->type.inter.interList);
+
+ // We assume there's only single inheritance at this point
+ // But in the case of a dispinterface, we could have the first
+ // base interface be IDispatch, and the 2nd base interface be
+ // the interface that we're capable of dispatching on. In any
+ // case, there can't be more than 2 interfaces in the list.
+ Assert((LPINTER)lpInterFirst->pNext == lpInterLast);
+
+ lpszBaseName = lpInterFirst->ptypeInter->szName;
+ Assert(lpszBaseName);
+ }
+
+ // first output the header comment
+ HOut((tentrykind == tDISPINTER) ? szHeadDispinter: szHeadInter);
+ HOutF(pEntry->type.szName);
+ HOut(szHeadOleSuffix3);
+
+ // then output the OLE header
+ HOut(szHeadOlePrefix0);
+ HOutF(pEntry->type.szName);
+ HOut("\n\n");
+
+ HOut(szHeadOlePrefix1);
+ if (lpszBaseName)
+ HOut("_");
+ HOut("(");
+ HOutF(pEntry->type.szName);
+ if (lpszBaseName) // if this inherits from somebody
+ { // then add ", <baseinterface>"
+ HOut(", ");
+ HOutF(lpszBaseName);
+ }
+ HOut(szHeadOlePrefix2);
+
+ if (tentrykind == tDISPINTER)
+ {
+ Assert (lpszBaseName);
+
+ HOut(szHeadOlePrefix7);
+ HOut(szHeadIUnknown);
+ HOut(szHeadIDispatch);
+ HOut(szHeadOleSuffix7);
+
+ if (lpInterFirst != lpInterLast)
+ { // specifies an interface that is dispatchable
+ HOut(szHeadDispatchable);
+ HOutF(lpInterLast->ptypeInter->szName);
+ HOut(szHeadOleSuffix3);
+ }
+
+ // first output the properties (commented out) in "struct" format
+ if (pEntry->dispinter.propList)
+ {
+ XOut(szHeadOlePrefix3);
+ XOutF(pEntry->type.szName);
+ XOut(szHeadOlePrefix5);
+ HOutElems(pEntry->dispinter.propList, " ", ";\n", ";\n", FALSE);
+ HOut(szHeadOleSuffix1);
+ }
+
+ // then output the methods (commented out) in "normal" format
+ if (pEntry->dispinter.methList)
+ {
+ XOut(szHeadOlePrefix3);
+ XOutF(pEntry->type.szName);
+ XOut(szHeadOlePrefix6);
+ HOutFuncs(pEntry->dispinter.methList, tDISPINTER);
+ HOut(szHeadOleSuffix1);
+ }
+ }
+ else
+ { // an interface
+
+ // output interface functions, and base interface functions (if any)
+ HOutBaseInter(pEntry, FALSE);
+
+ }
+
+ // lastly, output the close curly
+ HOut(szHeadOleSuffix2);
+
+}
+
+
+VOID NEAR HOutBaseInter(LPENTRY pEntry, BOOL fRecurse)
+{
+ LPINTER lpInterBase;
+
+ // hard-coded descriptions for the 2 most common
+ if (!FCmpCaseIns(pEntry->type.szName, "IUnknown"))
+ {
+ HOut(szHeadIUnknown);
+ }
+ else if (!FCmpCaseIns(pEntry->type.szName, "IDispatch"))
+ {
+ if (!fRecurse)
+ HOut(szHeadOlePrefix7);
+ HOut(szHeadIUnknown);
+ if (!fRecurse)
+ HOut(szHeadOleSuffix7);
+
+ HOut(szHeadIDispatch);
+ }
+ else if ((pEntry->type.tentrykind & ~tFORWARD) != tINTERFACE)
+ {
+ // can't deal with imported base interfaces
+ HOut(szHeadOlePrefix3);
+ HOutF(pEntry->type.szName);
+ HOut(szHeadOlePrefix4);
+ HOut(szHeadMethods);
+ }
+ else
+ {
+ if (pEntry->type.tentrykind & tFORWARD) {
+ // if this is a forward decl, follow pointer back to real
+ // interface (since base interfaces and functions aren't
+ // stored in the forward declare)
+ pEntry = pEntry->lpEntryForward;
+ }
+
+ lpInterBase = pEntry->type.inter.interList;
+ if (lpInterBase) // if this inherits from somebody,
+ { // then first describe the base interface
+ if (!fRecurse)
+ HOut(szHeadOlePrefix7);
+
+ // HACK -- assumes we can cast LPTYPE to LPENTRY, but
+ // this is always true given our above validation
+ HOutBaseInter((LPENTRY)(lpInterBase->ptypeInter), TRUE);
+
+ if (!fRecurse)
+ HOut(szHeadOleSuffix7);
+ }
+
+ // output the interface functions in OLE format
+ XOut(szHeadOlePrefix3);
+ XOutF(pEntry->type.szName);
+ XOut(szHeadOlePrefix4);
+ HOutFuncs(pEntry->inter.funcList, tINTERFACE);
+ }
+}
+
+//***********************************************************************
+
+VOID NEAR HOutFuncs
+(
+ LPFUNC pFuncList,
+ TENTRYKIND tentryKind
+)
+{
+
+ LPFUNC pFunc;
+
+ if (pFuncList == NULL) // nothing to output if no functions
+ return;
+
+ pFunc = (LPFUNC)ListFirst(pFuncList); // point to first entry
+
+#pragma warning(disable:4127)
+ while (TRUE)
+#pragma warning(default:4127)
+ {
+
+#ifndef PROFILE
+ if (tentryKind == tINTERFACE)
+ {
+ if (fSpecifiedInterCC) {
+ // set up STDMETHODCALLTYPE based on the calling
+ // convention and SYSKIND
+
+ if (pFunc->func.attr.fAttr2 & f2CCDEFAULTED)
+ SetCallType(CALL_DEFAULT);
+ else if (pFunc->func.attr.fAttr2 & f2PASCAL)
+ SetCallType(CALL_PASCAL);
+ else if (pFunc->func.attr.fAttr2 & f2STDCALL)
+ SetCallType(CALL_STDCALL);
+ else
+ {
+ Assert(pFunc->func.attr.fAttr2 & f2CDECL)
+ SetCallType(CALL_CDECL);
+ }
+ }
+
+
+ HOut(szHeadOleFuncPrefix1); // leading spaces
+ HOut(szHeadOleFuncPrefix2);
+
+ if (pFunc->func.elemType->tdesc.vt == VT_HRESULT)
+ HOut("(");
+ else
+ {
+ HOut("_(");
+ // output function return type
+ HOutType(pFunc->func.elemType);
+ HOut(szHeadOleFuncPrefix3);
+ }
+
+ HOutPropPrefix(pFunc);
+ XOutF(pFunc->func.szElemName);
+
+ HOut(szHeadOleArgPrefix1);
+
+ if (pFunc->cArgs)
+ {
+ HOut(szHeadOleArgPrefix2);
+ // output list of variables, separating them by
+ // commas, with nothing after last item
+ HOutElems(pFunc->argList, "", ", ", "", FALSE);
+ }
+ XOut(szHeadOleArgSuffix);
+ }
+ else
+#endif //!PROFILE
+ {
+ HOut(szHeadOleFuncPrefix1); // leading spaces
+ if (tentryKind == tMODULE)
+ HOut ("extern ");
+
+ // output function return type
+ HOutType(pFunc->func.elemType);
+ HOut(" ");
+
+ // output calling convention
+ if (!(pFunc->func.attr.fAttr2 & f2CCDEFAULTED)) {
+ if (pFunc->func.attr.fAttr2 & f2PASCAL)
+ HOut("__pascal ");
+ else if (pFunc->func.attr.fAttr2 & f2CDECL)
+ HOut("__cdecl ");
+ else if (pFunc->func.attr.fAttr2 & f2STDCALL)
+ HOut("__stdcall ");
+#ifdef DEBUG
+ else Assert(FALSE);
+#endif //DEBUG
+ }
+
+ HOutPropPrefix(pFunc);
+ XOutF(pFunc->func.szElemName);
+
+ Assert(pFunc->func.elemType->tdesc.vt != VT_CARRAY);
+
+ XOut("(");
+
+#ifdef PROFILE
+ cArgsTotal += pFunc->cArgs;
+ cFuncsTotal++;
+#endif //PROFILE
+ if (pFunc->cArgs == 0)
+ {
+ HOut("void");
+ }
+ else
+ {
+ // output list of variables, separating them by
+ // commas, with nothing after last item
+ HOutElems(pFunc->argList, "", ", ", "", FALSE);
+#ifdef PROFILE
+ cVarsTotal-= pFunc->cArgs; // would be counted twice
+#endif //PROFILE
+ }
+ XOut(");\n");
+ }
+
+ // advance to next entry if not all done
+ if (pFunc == (LPFUNC)ListLast(pFuncList))
+ break; // exit if all done
+ pFunc = (LPFUNC)pFunc->func.pNext;
+ }
+
+ if (fSpecifiedInterCC) {
+ SetCallType(CALL_DEFAULT); // reset to default STDMETHODCALLTYPE
+ }
+}
+
+
+VOID NEAR SetCallType
+(
+ CALLINGCONV cc
+)
+{
+ Assert (fSpecifiedInterCC); // caller should have checked
+ if (cc != ccInterCurrent)
+ { // if current different than last
+ HOut(szUndefCallType); // undefine current STDMETHODCALLTYPE
+ if (cc == CALL_DEFAULT) {
+ HOut(szResetCallType); // reset to default
+ } else {
+ HOut(szDefCallTypePrefix); // re-define to new value
+ HOut(rgszCallType[cc]);
+ HOut("\n");
+ }
+
+ ccInterCurrent = cc; // update current value
+ }
+}
+
+
+VOID NEAR HOutPropPrefix
+(
+ LPFUNC pFunc
+)
+{
+ // add a prefix to the function name if this is a property function
+ if (pFunc->func.attr.fAttr & fPROPGET)
+ HOut("get_");
+ else if (pFunc->func.attr.fAttr & fPROPPUT)
+ HOut("put_");
+ else if (pFunc->func.attr.fAttr & fPROPPUTREF)
+ HOut("putref_");
+}
+
+
+VOID NEAR HOutShortNum
+(
+ SHORT num,
+ BOOL fHex
+)
+{
+ CHAR szBuffer[30]; // space to list a number
+
+ sprintf(szBuffer,
+ fHex ? "0x%hX" : "%hd",
+ num);
+ HOut(szBuffer);
+}
+
+
+VOID NEAR HOutLongNum
+(
+ LONG num,
+ BOOL fHex
+)
+{
+ CHAR szBuffer[30]; // space to list a number
+
+ // Stupid C will choke if this number is printed in decimal
+ if (num == 0x80000000)
+ fHex = TRUE;
+
+ sprintf(szBuffer,
+ fHex ? "0x%lX" : "%ld",
+ num);
+ HOut(szBuffer);
+}
+
+VOID NEAR HOutElems
+(
+ LPELEM pElemList,
+ CHAR * szPrefix,
+ CHAR * szSep,
+ CHAR * szSepLast,
+ BOOL fEnum
+)
+{
+
+ LPELEM pElem;
+ WORD cDims;
+ ARRAYDESC FAR* lpAD;
+ BOOL fHex;
+ LPOLESTR lpch;
+ CHAR * pch;
+ CHAR buf[2];
+ UINT cch;
+
+ pElem = (LPELEM)ListFirst(pElemList); // point to first entry
+
+#pragma warning(disable:4127)
+ while (TRUE)
+#pragma warning(default:4127)
+ {
+ HOut(szPrefix);
+ if (!fEnum)
+ {
+ // output elem type, with the right number of "*'s"
+ HOutType(pElem->elemType);
+ HOut(" ");
+ }
+
+ XOutF(pElem->szElemName);
+#ifdef PROFILE
+ cVarsTotal++;
+#endif //PROFILE
+
+ if (!fEnum && pElem->elemType->tdesc.vt == VT_CARRAY)
+ { // base type already outputted before name above
+ lpAD = pElem->elemType->tdesc.lpadesc;
+ for (cDims = 0; cDims < lpAD->cDims; cDims++)
+ {
+ HOut("[");
+#if 0 // arrays of the form "a[]" aren't supported
+ if (lpAD->rgbounds[cDims].cElements)
+#endif //0
+ HOutLongNum((long)lpAD->rgbounds[cDims].cElements, FALSE);
+ HOut("]");
+ }
+
+ }
+
+ if (pElem->attr.fAttr2 & f2GotConstVal)
+ {
+ HOut(" = ");
+
+ fHex = FALSE;
+ if (!fEnum) {
+ // display all the unsigned constants in Hex form
+ switch (pElem->elemType->tdesc.vt) {
+ case VT_UI1:
+ case VT_UI2:
+ case VT_UI4:
+ case VT_UINT:
+ case VT_ERROR:
+ fHex = TRUE;
+ break;
+ default:
+ break;
+ }
+ }
+
+ // output the constant element's value
+ switch (pElem->lpElemVal->vt)
+ {
+ case VT_I2:
+ case VT_BOOL:
+ HOutShortNum(pElem->lpElemVal->iVal, fHex);
+ break;
+ case VT_I4:
+ case VT_ERROR:
+ HOutLongNum(pElem->lpElemVal->lVal, fHex);
+ break;
+ case VT_BSTR:
+ HOut("\"");
+ // output 1 char at a time, in order to handle
+ // escape sequences in strings
+ lpch = pElem->lpElemVal->bstrVal;
+ cch = SysStringLen(lpch);
+ while (cch) {
+ switch(*lpch) {
+ case 0x0:
+ pch = "\\0";
+ break;
+ case 0x7:
+ pch = "\\a";
+ break;
+ case 0x8:
+ pch = "\\b";
+ break;
+ case 0x9:
+ pch = "\\t";
+ break;
+ case 0xA:
+ if (SysKind == SYS_MAC)
+ pch = "\\r";
+ else
+ pch = "\\n";
+ break;
+ case 0xB:
+ pch = "\\v";
+ break;
+ case 0xC:
+ pch = "\\f";
+ break;
+ case 0xD:
+ if (SysKind == SYS_MAC)
+ pch = "\\n";
+ else
+ pch = "\\r";
+ break;
+ default:
+#ifdef WIN32
+ SideAssert (WideCharToMultiByte(CP_ACP,
+ 0,
+ lpch,
+ 1,
+ buf,
+ 1,
+ NULL,
+ NULL) != 0);
+#else //WIN32
+ buf[0] = *lpch;
+#endif //WIN32
+ buf[1] = '\0';
+ pch = buf;
+ break;
+ }
+ HOut(pch); // output the char
+ lpch++;
+ cch--;
+ }
+ HOut("\"");
+ break;
+ // CONSIDER: support more constant types.
+ default:
+ Assert(FALSE);
+ }
+
+ }
+
+ // advance to next entry if not all done
+ if (pElem == (LPELEM)ListLast(pElemList))
+ {
+ XOut(szSepLast);
+ break; // exit if all done
+ }
+ XOut(szSep);
+ pElem = pElem->pNext;
+ }
+
+}
+
+
+VOID NEAR HOutType
+(
+ LPTYPE pType
+)
+{
+ SHORT i;
+ CHAR * szPrefix;
+
+ switch (pType->tdesc.vt)
+ {
+ case VT_PTR:
+ // first output the base type
+ HOutType(pType->ref.ptypeBase);
+
+ // now output the proper number of "*"'s
+ Assert (pType->ref.cIndirect != 0);
+ for (i = pType->ref.cIndirect; i > 0; i--)
+ {
+ // always output "FAR" for constency (same as dispatch.h)
+ HOut(" FAR*");
+ }
+ break;
+
+ case VT_CARRAY:
+ // just output the base type -- we'll handle this stuff
+ // after we output the name
+ HOutType(pType->ref.ptypeBase);
+ break;
+
+ case VT_SAFEARRAY:
+ HOut("SAFEARRAY FAR*");
+ break;
+
+ case VT_BOOL: // special case -- "boolean" no good
+ HOut("VARIANT_BOOL");
+ break;
+
+ case VT_CY: // special case -- "CURRENCY" no good
+ HOut("CY");
+ break;
+
+ default:
+ // output "unsigned" if necessary
+ if (pType->tentrykind == tINTRINSIC && pType->intr.fUnsigned)
+ HOut("unsigned ");
+
+ switch (pType->tentrykind & ~tFORWARD)
+ {
+ case tUNION:
+ szPrefix = "union ";
+ goto outputPrefix;
+
+ case tSTRUCT:
+ szPrefix = "struct ";
+outputPrefix:
+ if (pType->structenum.szTag)
+ {
+ HOut(szPrefix);
+ HOutF(pType->structenum.szTag);
+ break;
+ }
+ // otherwise, fall into default processing
+
+ default:
+ HOutF(pType->szName);
+
+ }
+ break;
+ }
+
+}
+
+VOID NEAR HOutGuid
+(
+ LPATTR pAttr,
+ CHAR * szGuidPrefix,
+ LPSTR lpszName
+)
+{
+ CHAR szBuffer[100]; // space to list a number UNDONE: Tune
+ GUID FAR * lpGuid;
+
+ if ((pAttr->fAttr & fUUID) == 0)
+ return; // no guid to output
+
+ lpGuid = pAttr->lpUuid;
+ HOut(szHeadGuidPrefix);
+ HOut(szGuidPrefix); // prefix the user's name
+ HOutF(lpszName); // add the user's name
+ sprintf(szBuffer, ",0x%.8lX,0x%.4X,0x%.4X,0x%.2X,0x%.2X,0x%.2X,0x%.2X,0x%.2X,0x%.2X,0x%.2X,0x%.2X);\n",
+ lpGuid->Data1,
+ lpGuid->Data2,
+ lpGuid->Data3,
+ lpGuid->Data4[0],
+ lpGuid->Data4[1],
+ lpGuid->Data4[2],
+ lpGuid->Data4[3],
+ lpGuid->Data4[4],
+ lpGuid->Data4[5],
+ lpGuid->Data4[6],
+ lpGuid->Data4[7]
+ );
+ HOut(szBuffer);
+}
+
+VOID NEAR HOutF
+(
+ LPSTR lpszData
+)
+{
+ CHAR szBuffer[256];
+
+ _fstrcpy(szBuffer, lpszData); // copy data near
+
+ HOut(szBuffer); // output it
+}
+
+
+VOID NEAR HOut
+(
+ CHAR * szData
+)
+{
+ if (fputs(szData, hHFile) < 0) // write the data
+ ParseError(ERR_WRITING_HFILE);
+}
+
+#ifdef PROFILE
+VOID NEAR XOutF
+(
+ LPSTR lpszData
+)
+{
+ CHAR szBuffer[256];
+
+ _fstrcpy(szBuffer, lpszData); // copy data near
+
+ XOut(szBuffer); // output it
+}
+
+
+VOID NEAR XOut
+(
+ CHAR * szData
+)
+{
+ printf(szData); // output to console
+}
+
+#endif //PROFILE
diff --git a/private/oleauto/src/mktyplib/intlstr.c b/private/oleauto/src/mktyplib/intlstr.c
new file mode 100644
index 000000000..957cdc8b2
--- /dev/null
+++ b/private/oleauto/src/mktyplib/intlstr.c
@@ -0,0 +1,212 @@
+#include "mktyplib.h"
+
+// INTLSTR.C
+// data that should be internationalized
+// this is the only file that should be altered by localization
+//
+
+#define BETA
+
+CHAR * szBanner =
+"Microsoft (R) Type Library Generator Version 2.02"
+#if defined(BETA) || defined(DEBUG)
+#include "verstamp.h"
+#define STRING(x) #x
+#define VERSTRINGX(rev) STRING(. ## rev)
+#define VERSTRING VERSTRINGX(rup)
+ VERSTRING
+#endif //BETA || DEBUG
+#ifdef DEBUG
+ " (Debug)"
+#endif //DEBUG
+"\nCopyright (c) Microsoft Corp. 1993-1995. All rights reserved."
+;
+
+#ifdef MAC
+#define cPREFIX "-"
+#define cALIGN "\t\t "
+#define cALIGN1 "\t\t "
+#define cINDENT "\t\t "
+#define cWRAP " "
+#else //!MAC
+#ifdef WIN16
+#define cPREFIX "/"
+#define cALIGN "\t "
+#define cALIGN1 "\t "
+#define cINDENT "\t\t "
+#define cWRAP "\n" cINDENT
+#else //WIN16
+#define cPREFIX "/"
+#define cALIGN "\t "
+#define cALIGN1 " "
+#define cINDENT "\t\t "
+#define cWRAP " "
+#endif //WIN16
+#endif //!MAC
+
+CHAR * szUsage =
+"Usage: MKTYPLIB <options> [inputfile]\n"
+"Valid options are:\n"
+cPREFIX "help or " cPREFIX "?" cALIGN "Displays usage.\n"
+cPREFIX "tlb <filename>" cALIGN "Specifies type library output"
+cWRAP "filename. Defaults to input name\n"
+cINDENT "with extension replaced by \".tlb\".\n"
+cPREFIX "h [filename]" cALIGN "Specifies .H file output filename.\n"
+cPREFIX "<system>" cALIGN "Specifies kind of type library to"
+cWRAP "make (win16, win32, mac, mips, alpha, ppc or ppc32).\n"
+#ifdef WIN16
+cINDENT "Defaults to win16.\n"
+#else
+#ifdef WIN32
+#ifdef _MIPS_
+cINDENT "Defaults to mips.\n"
+//UNDONE: SYS_MAC_PPC?
+#else //_MIPS_
+#ifdef _ALPHA_
+cINDENT "Defaults to alpha.\n"
+#else //_ALPHA_
+cINDENT "Defaults to win32.\n"
+#endif //_ALPHA_
+#endif //_MIPS_
+#else
+cINDENT "Defaults to mac.\n"
+#endif
+#endif
+cPREFIX "align <#>" cALIGN "Override default alignment setting.\n"
+cPREFIX "o filename" cALIGN "Redirects output from screen to"
+cWRAP "specified file.\n"
+cPREFIX "nologo\t" cALIGN "Don't display the copyright banner.\n"
+cPREFIX "w0\t" cALIGN "Disable warnings.\n"
+#if FV_CPP
+cPREFIX "nocpp\t" cALIGN "Don't spawn the C pre-processor.\n"
+cPREFIX "cpp_cmd <path>" cALIGN "Specifies path for C pre-processor.\n"
+cINDENT "Defaults to CL.EXE.\n"
+cPREFIX "cpp_opt \"<opt>\"" cALIGN1 "Specifies options for C"
+cWRAP "pre-processor. Defaults to:\n"
+cINDENT "\"/C /E /D__MKTYPLIB__\".\n"
+cPREFIX "Ddefine[=value]" cALIGN1 "Defines value for C pre-processor.\n"
+cPREFIX "I includepath" cALIGN "Specifies path for include files.\n"
+#endif //FV_CPP
+;
+
+// for titles of message boxes
+CHAR * szAppTitle = "MkTypLib";
+
+
+// Error message strings.
+// WARNING -- must be the same order as items in ERRORS.H !!!
+CHAR * rgszErr[] = {
+ // Parser/lexer errors. These have line # and column # information.
+ "unterminated comment block", // PERR_UNTERMINATED_COMMENT
+ "unexpected end-of-file", // PERR_UNEXP_EOF
+ "error reading input file", // PERR_READ_ERROR
+ "undefined interface/dispinterface", // PERR_UNDEF_INTER
+ "unknown type", // PERR_UNKNOWN_TYPE
+ "duplicate definition", // PERR_DUP_DEF
+ "duplicate 'uuid' attribute", // PERR_DUP_UUID
+ "duplicate 'id' attribute in type", // PERR_DUP_ID
+ "attributes inconsistent with this type", // PERR_INV_COMBO
+ "missing 'id' attribute", // PERR_ID_REQ
+ "missing 'uuid' attribute", // PERR_UUID_REQ
+ "missing 'in' and/or 'out' attribute", // PERR_IN_OUT_REQ
+ "missing 'dllname' attribute", // PERR_DLLNAME_REQ
+ "missing 'entry' attribute", // PERR_ENTRY_REQ
+ "missing 'odl' attribute", // PERR_ODL_REQ
+ "'importlib' sections must be first", // PERR_IMPLIB_NOTFIRST
+ "invalid use of 'void'", // PERR_VOID_INV
+ "numeric value out of range", // PERR_NUMBER_OV
+ "invalid attribute combination", // PERR_INV_ATTR_COMBO
+ "invalid attribute for this item", // PERR_INV_ATTR
+ "invalid numeric literal", // PERR_INV_NUMBER
+ "invalid string literal", // PERR_INV_STRING
+ "invalid UUID literal", // PERR_INV_UUID
+ "invalid identifier", // PERR_INV_IDENTIFIER
+ "invalid constant definition", // PERR_INV_CONSTANT
+ "specified id is out of range", // PERR_INV_ID
+ "invalid use of 'lcid' attribute", // PERR_INV_LCID_USE
+ "invalid use of 'retval' attribute", // PERR_INV_RETVAL_USE
+ "invalid use of 'vararg' attribute", // PERR_INV_VARARG_USE
+ "unsupported keyword", // PERR_UNSUPP_KEYWORD
+ "expected: ", // PERR_EXPECTED
+ "expected: end-of-file", // PERR_EXP_EOF
+ "expected: identifier", // PERR_EXP_IDENTIFIER
+ "expected: keyword", // PERR_EXP_KEYWORD
+ "expected: attribute", // PERR_EXP_ATTRIBUTE
+ "expected: operator", // PERR_EXP_OPERATOR
+ "unsupported operator", // PERR_UNSUPPORTED_OP
+ "invalid numeric expression", // PERR_INV_EXPRESION
+ "expected: numeric expression", // PERR_EXP_NUMBER
+ "expected: string", // PERR_EXP_STRING
+ "expected: interface or dispinterface", // PERR_EXP_INTER
+ "no more than one dispinterface allowed in a coclass", // PERR_TWO_DISPINTER
+ "specified calling convention invalid here", // PERR_INV_CALLCONV
+ "invalid array declaration", // PERR_INV_ARRAY_DECL
+#ifdef WIN32
+ "missing definition of IDispatch. STDOLE32.TLB must be imported.", // PERR_NO_IDISPATCH
+ "missing definition of IUnknown. STDOLE32.TLB must be imported.", // PERR_NO_IDISPATCH
+#else //WIN32
+ "missing definition of IDispatch. STDOLE.TLB must be imported.", // PERR_NO_IDISPATCH
+ "missing definition of IUnknown. STDOLE.TLB must be imported.", // PERR_NO_IDISPATCH
+#endif //WIN32
+ "attributes must follow 'typedef' keyword", // PERR_TYPEDEF_ATTR
+ "property put function must have at least 1 argument and must have exactly one argument after any LCID argument", // PERR_INV_PROPPUT
+ "return type inconsistent with property type", // PERR_INV_PROPFUNC
+ "unknown LCID", // PERR_INV_LCID
+ "source attribute only valid on objects and VARIANTs", // PERR_INV_SOURCE_ATTR
+ "'out' parameter must be a pointer", // PERR_INV_OUT_PARAM
+ "Base interface of Dual interface must be IDispatch, or an interface that derives from IDispatch", // PERR_INV_DUAL_BASE
+ "Base interface of OleAutomation interface must be IUnknown, or an interface that derives from IUnknown", // PERR_INV_OA_BASE
+ "Type is not OleAutomation-compatible", // PERR_INV_OA_TYPE
+ "Invalid return type for OleAutomation-compatible interface", // PERR_INV_OA_FUNC_TYPE
+
+ "references to this type not allowed", // PERR_INV_REFERENCE
+ "specified type is not supported by IDispatch::Invoke", // PWARN_INV_IDISPATCHTYPE
+
+ // output errors (these also have the name of the current item)
+ "forward declaration but no definition", // OERR_NO_DEF
+
+ #define TYPELIBERR(name,string) string
+ #include "typelib.err" // TYPELIB.DLL error strings
+ #undef TYPELIBERR
+
+ // This shouldn't ever be seen if the list in TYPELIB.ERR is complete.
+ "TYPELIB.DLL returned an error",// OERR_TYPEINFO
+
+ // general errors (no line/column # information)
+ "out of memory", // ERR_OM
+ "unable to open input file", // ERR_CANT_OPEN_INPUTFILE
+#if FV_CPP
+ "unable to pre-process input file", // ERR_CPP
+#endif //FV_CPP
+ "unable to open .H output file",// ERR_CANT_OPEN_HFILE
+ "error writing .H output file", // ERR_WRITING_HFILE
+
+ // general warnings (no line/column info)
+ "using non-standard alignment - some structs in the .h file may need to be padded", // WARN_STRANGE_ALIGNMENT
+ ""
+};
+
+// strings for error display/formattting
+CHAR * szFmtSuccess = "Successfully generated type library '%s'.";
+CHAR * szFmtErrFileLineCol = "%s (%ld) : fatal error M0001: Syntax error near line %ld column %d: %s %s";
+CHAR * szFmtWarnFileLineCol = "%s (%ld) : warning M0002: Warning near line %ld column %d: %s %s";
+CHAR * szFmtErrOutput = "%s : fatal error M0003: Error creating type library while processing item '%s': %s.";
+CHAR * szFmtErrImportlib = "%s : fatal error M0004: Error processing type library '%s': %s.";
+
+// This shouldn't ever be seen if the list in TYPELIB.ERR is complete.
+CHAR * szFmtErrUnknown = "%s : fatal error M0005: Error creating type library while processing item '%s': %s (SCODE = 0x%lX).";
+
+CHAR * szFmtErrGeneral = "fatal error M0006: %s";
+CHAR * szFmtWarnGeneral = "warning M0007: %s";
+
+
+// strings for header file output
+CHAR * szHeadFile = "/* This header file machine-generated by mktyplib.exe */\n"
+ "/* Interface to type library: ";
+
+CHAR * szHeadModule = "\n/* Functions defined in module: ";
+
+CHAR * szHeadInter = "\n/* Definition of interface: ";
+CHAR * szHeadDispinter = "\n/* Definition of dispatch interface: ";
+CHAR * szHeadMethods = "/* You must describe methods for this interface here */\n";
+CHAR * szHeadDispatchable = "\n/* Capable of dispatching all the methods of interface ";
diff --git a/private/oleauto/src/mktyplib/intlstr.h b/private/oleauto/src/mktyplib/intlstr.h
new file mode 100644
index 000000000..8750790fe
--- /dev/null
+++ b/private/oleauto/src/mktyplib/intlstr.h
@@ -0,0 +1,35 @@
+// INTLSTR.H
+// interface to internationalized data
+//
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+extern CHAR * szBanner; // mktyplib banner
+extern CHAR * szUsage; // usage string
+extern CHAR * szAppTitle; // application title
+
+
+// strings for error message formatting/display
+extern CHAR * rgszErr[]; // array of error strings
+extern CHAR * szFmtSuccess; // success format string
+extern CHAR * szFmtErrFileLineCol; // error format strings
+extern CHAR * szFmtWarnFileLineCol;
+extern CHAR * szFmtErrOutput;
+extern CHAR * szFmtErrImportlib;
+extern CHAR * szFmtErrUnknown;
+extern CHAR * szFmtErrGeneral;
+extern CHAR * szFmtWarnGeneral;
+
+// strings for header file output
+extern CHAR * szHeadFile;
+extern CHAR * szHeadModule;
+extern CHAR * szHeadInter;
+extern CHAR * szHeadDispinter;
+extern CHAR * szHeadMethods;
+extern CHAR * szHeadDispatchable;
+
+#ifdef __cplusplus
+}
+#endif
diff --git a/private/oleauto/src/mktyplib/lexer.c b/private/oleauto/src/mktyplib/lexer.c
new file mode 100644
index 000000000..a81e52321
--- /dev/null
+++ b/private/oleauto/src/mktyplib/lexer.c
@@ -0,0 +1,890 @@
+#include "mktyplib.h"
+
+// LEXER for MKTYPLIB
+
+#include <malloc.h>
+#include <string.h>
+#include <ctype.h>
+#include <stdio.h>
+#ifndef WIN32
+#include <ole2.h> // required for dispatch.h
+#include "dispatch.h"
+#endif //WIN32
+
+#include "errors.h"
+#include "tokens.h"
+
+// external data
+extern TOKEN tok;
+extern SYSKIND SysKind;
+
+
+// stuff for error reporting
+extern CHAR szFileCur[]; // file name of current token
+extern DWORD lnCur; // line # of current token
+extern WORD colCur; // column # of current token
+extern DWORD lnLast; // line # of last token
+extern WORD colLast; // column # of last token
+extern CHAR * szExpected; // item for "expected: <item>"
+extern FILE *hFileInput;
+#if FV_CPP
+extern BOOL fCPP; // true if we pre-processed input file
+#endif //FV_CPP
+
+// private types
+typedef struct {
+ TOKID id;
+ CHAR * sz;
+} RWTABLE;
+
+
+#define CB_LINEBUF 1024
+#define CB_MAX_ID 255
+#define CB_MAX_STRING 255
+
+// private data
+CHAR * pLineBuf; // line buffer
+CHAR * pLine; // pointer to current char in line
+BOOL fDirectiveOK;
+
+
+// prototypes
+VOID FAR ParseInit (CHAR * szFile);
+VOID FAR ConsumeTok (TOKID id, WORD fAccept);
+VOID FAR ScanTok ( WORD fAccept);
+LPVOID FAR ParseMalloc ( WORD cbAlloc);
+
+VOID NEAR FillLine(VOID);
+VOID NEAR HandleString (VOID);
+VOID NEAR HandleId (CHAR ch, WORD fAccept);
+CHAR NEAR HandleEscape(VOID);
+TOKID NEAR RwLookup (CHAR *sz, RWTABLE *prgIds);
+VOID NEAR HandleNumericLit (CHAR ch);
+DWORD NEAR HandleHexNum (WORD cDigitsMax);
+VOID NEAR HandleDirective (VOID);
+BOOL NEAR FValidIdCh (CHAR ch, BOOL fFirst);
+
+// reserved word tables
+RWTABLE rgRws[] = {
+ RW_LIBRARY, "library",
+ RW_TYPEDEF, "typedef",
+ RW_ENUM, "enum",
+ RW_STRUCT, "struct",
+ RW_MODULE, "module",
+ RW_INTERFACE, "interface",
+ RW_DISPINTERFACE, "dispinterface",
+ RW_COCLASS, "coclass",
+ RW_PROPERTIES, "properties",
+ RW_METHODS, "methods",
+ RW_IMPORTLIB, "importlib",
+ RW_PASCAL, "pascal",
+ RW_PASCAL, "_pascal",
+ RW_PASCAL, "__pascal",
+ RW_CDECL, "cdecl",
+ RW_CDECL, "_cdecl",
+ RW_CDECL, "__cdecl",
+ RW_STDCALL, "stdcall",
+ RW_STDCALL, "_stdcall",
+ RW_STDCALL, "__stdcall",
+ RW_UNSIGNED, "unsigned",
+ RW_UNION, "union",
+ RW_EXTERN, "extern",
+ RW_FAR, "far",
+ RW_FAR, "_far",
+ RW_SAFEARRAY, "SAFEARRAY",
+ RW_SAFEARRAY, "safearray",
+ RW_CONST, "const",
+#if FV_PROPSET
+ RW_PROPERTY_SET, "property_set",
+#endif //FV_PROPSET
+ // the folllowing are only present for error reporting purposes
+ RW_LBRACKET, "[",
+ RW_RBRACKET, "]",
+ RW_LCURLY, "{",
+ RW_RCURLY, "}",
+ RW_LPAREN, "(",
+ RW_RPAREN, ")",
+ RW_SEMI, ";",
+ RW_COLON, ":",
+ RW_PERIOD, ".",
+ RW_COMMA, ",",
+ RW_ASSIGN, "=",
+ RW_POINTER, "*",
+#if 0 // CONSIDER: (V2, EXPR) activate if these operators are activated
+ OP_MINUS, "-",
+ OP_PLUS, "+",
+ OP_MUL, "*",
+ OP_DIV, "/",
+ OP_MOD, "%",
+ OP_EXP, "^",
+ OP_LOG_AND, "&&",
+ OP_LOG_OR, "||",
+ OP_LOG_NOT, "!",
+ OP_BIT_AND, "&",
+ OP_BIT_OR, "|",
+ OP_BIT_NOT, "~",
+ OP_LSHIFT, "<<",
+ OP_RSHIFT, ">>",
+ OP_EQ, "==",
+ OP_LE, "<=",
+ OP_LT, "<",
+ OP_GE, ">=",
+ OP_GT, ">",
+#endif //0
+ RW_NOTFOUND, NULL
+ };
+
+
+RWTABLE rgAttrs[] = {
+ ATTR_UUID, "uuid",
+ ATTR_VERSION, "version",
+ ATTR_DLLNAME, "dllname",
+ ATTR_ENTRY, "entry",
+ ATTR_ID, "id",
+ ATTR_HELPSTRING, "helpstring",
+ ATTR_HELPCONTEXT, "helpcontext",
+ ATTR_HELPFILE, "helpfile",
+ ATTR_LCID, "lcid",
+ ATTR_PROPGET, "propget",
+ ATTR_PROPPUT, "propput",
+ ATTR_PROPPUTREF, "propputref",
+ ATTR_OPTIONAL, "optional",
+ ATTR_IN, "in",
+ ATTR_OUT, "out",
+ ATTR_STRING, "string",
+ ATTR_VARARG, "vararg",
+ ATTR_APPOBJECT, "appobject",
+ ATTR_RESTRICTED, "restricted",
+ ATTR_PUBLIC, "public",
+ ATTR_READONLY, "readonly",
+ ATTR_ODL, "odl",
+ ATTR_DEFAULT, "default",
+ ATTR_SOURCE, "source",
+ ATTR_BINDABLE, "bindable",
+ ATTR_REQUESTEDIT, "requestedit",
+ ATTR_DISPLAYBIND, "displaybind",
+ ATTR_DEFAULTBIND, "defaultbind",
+ ATTR_LICENSED, "licensed",
+ ATTR_PREDECLID, "predeclid",
+ ATTR_HIDDEN, "hidden",
+ ATTR_RETVAL, "retval",
+ ATTR_CONTROL, "control",
+ ATTR_DUAL, "dual",
+ ATTR_NONEXTENSIBLE, "nonextensible",
+ ATTR_OLEAUTOMATION, "oleautomation",
+ RW_NOTFOUND, NULL
+ };
+
+// ************************************************************************
+// File init/term/read routines
+// ************************************************************************
+
+VOID FAR ParseInit
+(
+ CHAR * szFile
+)
+{
+ pLineBuf = (CHAR *)malloc(CB_LINEBUF+1); // alloc buffer to read lines into
+
+#ifdef WIN16
+ // convert szFile in-place to OEM char set
+ AnsiToOem(szFile, szFile);
+#endif // WIN16
+
+ hFileInput = fopen(szFile, "rb"); // open input file
+
+#ifdef WIN16
+ // convert back to ANSI
+ OemToAnsi(szFile, szFile);
+#endif // WIN16
+
+ if (hFileInput == NULL)
+#if FV_CPP
+ ParseError(fCPP ? ERR_CPP : ERR_CANT_OPEN_INPUTFILE);
+#else
+ ParseError(ERR_CANT_OPEN_INPUTFILE);
+#endif
+
+ FillLine(); // get first line
+
+ ScanTok(0); // get first token
+}
+
+
+// fill up a line buffer
+VOID NEAR FillLine()
+{
+ pLine = pLineBuf; // reset pointer to BOL
+
+ if (!fgets(pLineBuf, CB_LINEBUF, hFileInput)) // get a line
+ { // eof or error
+ if (feof(hFileInput))
+ *pLine = '\0'; // signal EOL
+ else // CONSIDER: store error code & report it
+ ParseError(PERR_READ_ERROR);
+ }
+ lnCur++; // increment current line
+
+#ifdef DEBUG
+#if 0
+ if (fDebug)
+ {
+ CHAR szDebugOut[1030];
+ if (!*pLine)
+ DebugOut("<EOF>\n");
+ else
+ {
+ sprintf(szDebugOut, "%ld: %s", lnCur, pLine);
+ DebugOut(szDebugOut); // dump input to screen
+ }
+ }
+#endif // 0
+#endif // DEBUG
+
+ fDirectiveOK = TRUE; // directives must start line
+}
+
+// ************************************************************************
+// Token scanning routines
+// ************************************************************************
+
+VOID FAR ConsumeTok
+(
+TOKID id,
+WORD fAccept
+)
+{
+ RWTABLE * prgIds;
+
+ if (tok.id != id)
+ {
+ // syntax error -- lookup expected constant/RW in rgRws, for better
+ // error reporting.
+
+ prgIds = rgRws; // just look in RW table
+ // CONSIDER: Do I need to look in rgAttrs too -- I don't think anybody is
+ // CONSIDER: looking for a specific attribute right now.
+ while (prgIds->id != id)
+ {
+ Assert(prgIds->id != RW_NOTFOUND); // had better be in the RW table
+ prgIds++;
+ }
+ szExpected = prgIds->sz;
+ Assert(szExpected); // should have found this name
+ ParseError(PERR_EXPECTED);
+ }
+ ScanTok(fAccept);
+}
+
+
+// fills token structure with next token, subject to context
+VOID FAR ScanTok
+(
+WORD fAccept
+)
+{
+ CHAR ch;
+
+ lnLast = lnCur; // save info about previous token
+ colLast = colCur;
+ // CONSIDER: add a szFileLast (might be slow, however);
+
+top:
+ ch = *pLine++; // ch = next char in line
+ colCur = (WORD)(pLine-pLineBuf); // save 1-based column # of current token
+ // for error reporting
+
+ switch (ch)
+ {
+
+ case '\0': // EOF -- quit
+ if (!(fAccept & fACCEPT_EOF))
+ ParseError(PERR_UNEXP_EOF);
+ tok.id = RW_EOF;
+ break;
+
+ case '#': // probably a #line n "filename"
+ // if not first non-blank char on line, then give error
+ if (!fDirectiveOK)
+ goto default_char;
+ HandleDirective();
+ // fall into code below, to get next line & continue
+
+ case '\n': // EOL -- advance to next line, if any
+ FillLine(); // get next line
+ goto top; // and continue
+ break;
+
+ case '[':
+ tok.id = RW_LBRACKET;
+ break;
+
+ case ']':
+ tok.id = RW_RBRACKET;
+ break;
+
+ case '{':
+ tok.id = RW_LCURLY;
+ break;
+
+ case '}':
+ tok.id = RW_RCURLY;
+ break;
+
+ case '(':
+ tok.id = RW_LPAREN;
+ break;
+
+ case ')':
+ tok.id = RW_RPAREN;
+ break;
+
+ case ';':
+ tok.id = RW_SEMI;
+ break;
+
+ case ':':
+ tok.id = RW_COLON;
+ break;
+
+ case '.':
+ tok.id = RW_PERIOD;
+ break;
+
+ case ',':
+ tok.id = RW_COMMA;
+ break;
+
+ case '=':
+ tok.id = RW_ASSIGN;
+ //CONSIDER: (V2, EXPR) handle "==" (OP_EQ) when fAccept & fACCEPT_OPERATOR
+ break;
+
+ case '*':
+ tok.id = RW_POINTER;
+ break;
+
+ case '-': // subtract operator or a hyphen (perhaps a unary minus)
+ tok.id = (WORD)((fAccept & fACCEPT_OPERATOR) ? OP_SUB : RW_HYPHEN);
+ break;
+
+ case '"': // start of string literal
+ if (!(fAccept & fACCEPT_STRING)) // if unexpected string, give
+ goto default_char; // proper error (expected number/id)
+ HandleString();
+ break;
+
+ case '/': // probably a start of a comment
+ if (*pLine == '/') // if "//"
+ {
+ FillLine(); // get next line
+ goto top; // and continue
+ break;
+ }
+ else if (*pLine == '*') // if "/*"
+ {
+ pLine++; // skip "*"
+ while (*pLine) // while not EOF
+ {
+
+ pLine = XStrChr(pLine, '*');
+
+ if (pLine == NULL) // if no "*" found on this line
+ {
+ FillLine(); // get next line
+ }
+ else
+ if (*(++pLine) == '/') // if found "*/"
+ {
+ pLine++; // skip the "/"
+ goto top; // and continue
+ }
+ }
+ ParseError(PERR_UNTERMINATED_COMMENT);
+ }
+
+ // otherwise, fall into default char processing
+
+
+ default:
+ if ((BYTE)ch <= ' ') // anything less than a space, just treat as white space
+ goto top;
+
+default_char:
+ if (fAccept & fACCEPT_UUID)
+ { // if only looking for a UUID
+ // parse 16-byte UUID constant
+ CHAR * start; // starting position
+ #define CCH_SZGUID0 39 // chars in ascii guid (including NULL)
+ CHAR buffer[CCH_SZGUID0];
+
+ tok.lpUuid = (GUID FAR *)ParseMalloc(sizeof(GUID));
+
+ start = --pLine;
+
+ // use our number parsers to help validate the UUID
+ HandleHexNum(8);
+ if (*pLine++ != '-')
+ ParseError(PERR_INV_UUID);
+ HandleHexNum(4);
+ if (*pLine++ != '-')
+ ParseError(PERR_INV_UUID);
+ HandleHexNum(4);
+ if (*pLine++ != '-')
+ ParseError(PERR_INV_UUID);
+ HandleHexNum(4);
+ if (*pLine++ != '-')
+ ParseError(PERR_INV_UUID);
+ HandleHexNum(8);
+ HandleHexNum(4);
+ if (pLine - start != (32+4)) // 32 digits + 4 hyphens
+ ParseError(PERR_INV_UUID);
+
+ // get uuid in a string of the form:
+ // {numbnumb-numb-numb-numb-numbnumbnumb} so OLE can use it.
+
+ #define chClsPrefix '{'
+ #define cbClsPrefix 1
+ #define chClsSuffix '}'
+
+ *buffer = chClsPrefix;
+ _fmemcpy(buffer+cbClsPrefix, start, 32+4);
+ *(buffer+cbClsPrefix+32+4) = chClsSuffix;
+ *(buffer+cbClsPrefix+32+5) = '\0';
+
+ // have OLE translate this into it's special UUID format
+#if FV_UNICODE_OLE
+ {
+ OLECHAR bufferW[CCH_SZGUID0];
+ SideAssert (MultiByteToWideChar(CP_ACP,
+ MB_PRECOMPOSED,
+ buffer,
+ -1,
+ bufferW,
+ CCH_SZGUID0) != 0);
+ SideAssert (!FAILED(CLSIDFromString(bufferW, (LPCLSID)tok.lpUuid)));
+ }
+#else //FV_UNICODE_OLE
+ SideAssert (!FAILED(CLSIDFromString(buffer, (LPCLSID)tok.lpUuid)));
+#endif //FV_UNICODE_OLE
+
+ tok.id = LIT_UUID;
+ break;
+ }
+
+ if (fAccept & fACCEPT_OPERATOR)
+ { // if looking for an operator
+ switch (ch)
+ {
+ case '+':
+ tok.id = OP_ADD;
+ break;
+
+ case '-':
+ tok.id = OP_SUB;
+ break;
+
+ case '*':
+ tok.id = OP_MUL;
+ break;
+
+ case '/':
+ tok.id = OP_DIV;
+ break;
+
+ case '%':
+ tok.id = OP_MOD;
+ break;
+
+ case '^':
+ tok.id = OP_EXP;
+ break;
+
+ case '!':
+ tok.id = OP_LOG_NOT;
+ break;
+
+ case '&':
+ tok.id = OP_BIT_AND;
+ //CONSIDER: (V2, EXPR) handle "&&" (OP_LOG_AND)
+ break;
+
+ case '|':
+ tok.id = OP_BIT_OR;
+ //CONSIDER: (V2, EXPR) handle "||" (OP_LOG_OR)
+ break;
+
+ case '~':
+ tok.id = OP_BIT_NOT;
+ break;
+
+ case '<':
+ tok.id = OP_LT;
+ //CONSIDER: (V2, EXPR) handle "<=" (OP_LE)
+ //CONSIDER: (V2, EXPR) handle "<<" (OP_LSHIFT)
+ break;
+
+ case '>':
+ tok.id = OP_GT;
+ //CONSIDER: (V2, EXPR) handle ">=" (OP_GE)
+ //CONSIDER: (V2, EXPR) handle ">>" (OP_RSHIFT)
+ break;
+
+ default:
+ // valid chars to end expressions (such as a
+ // right paren) should have been accepted above.
+ ParseError(PERR_EXP_OPERATOR);
+ }
+
+ break; // got an operator -- exit
+ }
+
+ if (fAccept & fACCEPT_NUMBER)
+ { // if looking for a numeric value
+ HandleNumericLit(ch);
+ break;
+ }
+
+ if (fAccept & fACCEPT_STRING) // error if looking for a string
+ ParseError(PERR_EXP_STRING); // and it wasn't found above
+
+ HandleId(ch, fAccept); // ID token of some sort
+ break; // (could be RW, ATTR, id, or type)
+
+ }
+
+ fDirectiveOK = FALSE; // pre-processor directives
+ // not allowed again until next line
+}
+
+
+
+VOID NEAR HandleString ()
+{
+ CHAR szBuffer[CB_MAX_STRING+1];
+ WORD cbsz;
+ CHAR * psz;
+ CHAR ch;
+
+ psz = szBuffer; // where to copy string
+ cbsz = 0; // no chars copied so far
+ ch = *pLine++; // ch = next char in line
+ while (ch != '\"')
+ { // while not end of string
+ // error if premature EOL\EOF or buffer overflow
+ if (ch == '\n' || ch == '\0' || ++cbsz >= sizeof(szBuffer))
+ ParseError(PERR_INV_STRING);
+ if (ch == '\\') // handle escape sequences
+ ch = HandleEscape();
+ *psz++ = ch;
+ //if ch is first byte of a DBCS char, then must copy another char
+ if (IsLeadByte(ch))
+ {
+ if (++cbsz >= sizeof(szBuffer)) // 1 more byte in string
+ ParseError(PERR_INV_STRING);
+ *psz++ = *pLine++; // copy 2nd byte
+ }
+ ch = *pLine++; // ch = next char in line
+ }
+ *psz = '\0'; // null-terminate the data
+ tok.cbsz = cbsz; // save char count (not including null term)
+ cbsz++;
+ tok.lpsz = (LPSTR)ParseMalloc(cbsz);
+ _fmemcpy(tok.lpsz, szBuffer, cbsz);
+ tok.id = LIT_STRING;
+}
+
+VOID NEAR HandleId
+(
+ CHAR ch,
+ WORD fAccept
+)
+{
+ CHAR szBuffer[CB_MAX_ID+1];
+ WORD cbsz;
+ CHAR * psz;
+
+ psz = szBuffer; // where to copy ID
+ cbsz = 0; // no chars copied so far
+ if (!FValidIdCh(ch, TRUE))
+ {
+ tok.id = RW_NOTFOUND; // not a valid id -- return
+ return;
+ }
+ do
+ {
+ if (++cbsz >= sizeof(szBuffer))
+ ParseError(PERR_INV_IDENTIFIER);
+ *psz++ = ch; // copy char
+ //if ch is first byte of a DBCS char, then
+ //copy another char and keep looping.
+ if (IsLeadByte(ch))
+ {
+ if (++cbsz >= sizeof(szBuffer))
+ ParseError(PERR_INV_IDENTIFIER);
+ *psz++ = *pLine++; // then copy 2nd byte
+
+ }
+
+ ch = *pLine++; // ch = next char in ID
+ } while (FValidIdCh(ch, FALSE)); // while more chars in id
+
+ *psz = '\0'; // null-terminate the data
+ cbsz++; // include NULL in count
+ pLine--; // back up to char that terminated id
+
+ tok.id = 0;
+ if (fAccept & fACCEPT_ATTR)
+ { // see if looking for attribute
+ // returns appropriate ATTR_xxx or 0 if not found
+ tok.id = RwLookup(szBuffer, rgAttrs);
+ }
+
+ if (tok.id == 0) // see if normal RW
+ tok.id = RwLookup(szBuffer, rgRws);
+
+ if (tok.id == 0) // if not any RW, must be an ID
+ {
+ tok.lpsz = (LPSTR)ParseMalloc(cbsz);
+ _fmemcpy(tok.lpsz, szBuffer, cbsz);
+ tok.id = LIT_ID;
+ }
+}
+
+
+// Translate escape char. The following are supported:
+// \0, \a, \b, \f, \n, \r, \t, \v
+//
+// (use hard-coded values so using mktyplib on different platforms will
+// produce identical typelibs)
+//
+CHAR NEAR HandleEscape ()
+{
+ CHAR ch;
+
+ ch = *pLine++; // get char after "\"
+
+ switch (ch)
+ {
+ case '0':
+ return 0x00;
+ case 'a':
+ return 0x07;
+ case 'b':
+ return 0x08;
+ case 'f':
+ return 0x0c;
+ case 'n':
+ if (SysKind == SYS_MAC)
+ return 0x0d;
+ else
+ return 0x0a;
+ case 'r':
+ if (SysKind == SYS_MAC)
+ return 0x0a;
+ else
+ return 0x0d;
+ case 't':
+ return 0x09;
+ case 'v':
+ return 0x0b;
+ default:
+ return ch; // otherwise, just treat as char we got
+ }
+}
+
+
+// returns TRUE if char is A-Z, a-z, underscore, or >= 128
+BOOL NEAR FValidIdCh
+(
+ CHAR ch,
+ BOOL fFirst
+)
+{
+ // Assumes all DBCS lead bytes are > 128. This seems to be true.
+
+ // NOTE: using ch < 0 instead of ch >= 128, because ch is SIGNED.
+ return (isalpha(ch) || ch < 0 || ch == '_' || (!fFirst && isdigit(ch)));
+}
+
+
+VOID NEAR HandleNumericLit
+(
+ CHAR ch
+)
+{
+ DWORD prevVal;
+
+ tok.number = 0;
+ tok.id = LIT_NUMBER; // assume valid number
+ if (ch == '0' && *pLine == 'x') // parse hex constant
+ {
+ pLine++; // advance to first hex digit
+ tok.number = HandleHexNum(8); // input up to a 8-digit hex number
+ if (isxdigit(*pLine)) // error if more digits left
+ ParseError(PERR_INV_NUMBER);
+ }
+ else if (isdigit(ch)) // parse decimal constant
+ {
+#pragma warning(disable:4127)
+ while (TRUE)
+#pragma warning(default:4127)
+ {
+ prevVal = tok.number;
+ if (prevVal > 429496729L) //error if *10 will overflow
+ ParseError(PERR_NUMBER_OV);
+ tok.number *= 10;
+ tok.number += (ch - '0');
+ if (tok.number < prevVal) // error if overflow
+ ParseError(PERR_NUMBER_OV);
+ ch = *pLine; // get next char
+ if (!isdigit(ch)) // if next char not digit, we're done
+ break;
+ pLine++; // consume digit
+ };
+ }
+
+ else if (ch == '\'')
+ { // support for numeric literals of the form: 'a' or '\0'.
+ ch = *pLine++; // ch = char after quote
+ if (ch == '\\') // handle escape sequences
+ ch = HandleEscape();
+ tok.number = (BYTE)ch; // don't sign-extend
+ if (*pLine++ != '\'') // error if no close quote
+ {
+ //CONSIDER: if we're to support 4-char literals, then code
+ //CONSIDER: must be added here. Issues with 4-char literals
+ //CONSIDER: are byte order and whether we need them or not.
+ ParseError(PERR_INV_NUMBER);
+ }
+ }
+
+ else
+ ParseError(PERR_EXP_NUMBER);
+}
+
+
+DWORD NEAR HandleHexNum
+(
+ WORD cDigitsMax
+)
+{
+ DWORD result = 0;
+ CHAR ch;
+ WORD digit;
+
+ if (!isxdigit(*pLine)) // error if no hex digits
+ ParseError(PERR_INV_NUMBER);
+
+ while (isxdigit(ch = *pLine) && cDigitsMax--)
+ {
+ pLine++;
+ result = result << 4;
+
+ digit = ch;
+ if (ch < 'A')
+ digit -= '0';
+ else if (ch < 'a')
+ digit -= ('A'-10);
+ else
+ digit -= ('a'-10);
+ result += digit;
+ }
+
+ return result;
+}
+
+
+VOID NEAR HandleDirective()
+{
+ fDirectiveOK = FALSE; // don't allow nested directives
+ if (memcmp(pLine, "line ", 5) == 0) // if got #line
+ { // handle #line <line #> "<filename>"
+ // UNDONE: (CPP) Do all pre-processors emit #line directives in
+ // UNDONE: (CPP) the above format?
+
+ pLine+= 5; // skip "line "
+ ScanTok(fACCEPT_NUMBER); // read in the new current line number
+ if (tok.id != LIT_NUMBER)
+ ParseError(PERR_EXP_NUMBER); // error
+ lnCur = tok.number - 1; // set new current line # (-1 because
+ // FillLine will increment it)
+ ScanTok(fACCEPT_STRING); // get current file name
+ if (tok.id != LIT_STRING)
+ ParseError(PERR_EXP_STRING); // error
+ _fstrcpy(szFileCur, tok.lpsz); // save current file name
+ _ffree(tok.lpsz); // free unused memory
+ }
+ // Just ignore any other directives
+ // CONSIDER: (CPP) Maybe give warning instead of ignoring other directives?
+}
+
+
+// *********************************************************************
+// utility routines
+// *********************************************************************
+
+
+// if sz in rgIds, return appropriate constant.
+TOKID NEAR RwLookup
+(
+ CHAR * psz,
+ RWTABLE * prgIds
+)
+{
+
+ TOKID id;
+
+#pragma warning(disable:4127)
+ while (TRUE)
+#pragma warning(default:4127)
+ {
+ id = prgIds->id;
+ if (prgIds->sz == NULL)
+ break; // quit if end of table
+ if (strcmp(prgIds->sz, psz) == 0)
+ break; // quit if found match
+ prgIds++;
+ }
+
+ return id;
+}
+
+// cover for fmalloc -- calls ParseError(ERR_OM) if alloc fails
+LPVOID FAR ParseMalloc
+(
+ WORD cbAlloc
+)
+{
+ LPVOID retVal;
+
+ if ((retVal = _fmalloc(cbAlloc)) == NULL)
+ ParseError(ERR_OM);
+
+ return retVal;
+}
+
+
+// XStrChr: perform strchr on SBCS or DBCS string
+extern char * FAR XStrChr
+(
+ char * xsz,
+ int ch
+)
+{
+ char * pchFind = NULL;
+
+ while(*xsz != '\0') {
+ if (*xsz == ch)
+ pchFind = xsz;
+ if (IsLeadByte(*xsz)) {
+ pchFind = NULL;
+ xsz++;
+ if (*xsz == '\0')
+ break;
+ }
+ xsz++;
+ }
+ return pchFind;
+
+}
diff --git a/private/oleauto/src/mktyplib/mktyplib.c b/private/oleauto/src/mktyplib/mktyplib.c
new file mode 100644
index 000000000..cd6175ed8
--- /dev/null
+++ b/private/oleauto/src/mktyplib/mktyplib.c
@@ -0,0 +1,1302 @@
+#include "mktyplib.h"
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#ifdef WIN16
+#include <toolhelp.h>
+#endif //WIN16
+#ifndef MAC
+#include <commdlg.h>
+#endif //!MAC
+#ifdef MAC
+#include <memory.h>
+#include <quickdra.h> // stuff for initialization
+#include <fonts.h>
+#include <windows.h>
+#include <menus.h>
+#include <dialogs.h>
+#include <script.h> // needed for ParseTable()
+#endif //MAC
+#ifndef WIN32
+#include <ole2.h>
+#include "dispatch.h"
+#endif //!WIN32
+#include "fileinfo.h"
+
+#include "errors.h"
+#include "intlstr.h" // szBanner, szUsage, rgszErr structure defs
+
+// external data
+extern TYPLIB typlib;
+
+// external routines
+extern VOID FAR ParseOdlFile(CHAR * szInputFile); // from PARSER.C
+extern VOID FAR OutputHFile(CHAR * szHFile); // from HOUT.C
+extern VOID FAR OutputTyplib(CHAR * szTypeLibFile); // from TYPOUT.C
+extern VOID FAR CleanupImportedTypeLibs(void); // from TYPOUT.C
+
+#ifdef DEBUG
+//UNDONE: (oleprog #557) can't use dimalloc because dstrmgr memory leaks
+//#define USE_DIMALLOC //catches memory leaks, etc
+#endif //DEBUG
+
+#ifdef WIN16
+#ifdef DEBUG // only disable alerts in the debug version
+#define NODEBUGALERTS // activate to disable debug windows alerts
+#endif //DEBUG
+#endif //WIN16
+
+#ifdef USE_DIMALLOC
+extern BOOL GetDebIMalloc(IMalloc FAR* FAR* ppMalloc); // from dimalloc.cxx
+#endif
+
+// local defines
+#ifdef WIN16
+#define CB_MAX_PATHNAME 127
+#else //WIN16
+#define CB_MAX_PATHNAME 255
+#endif //WIN16
+
+#define ARGS_OK 0 // FParseCl() return values
+#define GIVE_USAGE 1
+
+#ifdef WIN16
+CHAR * szBatchStart = "@echo off\n";
+CHAR * szBatchEnd = "if errorlevel 1 goto goterror\n"
+ "echo 0 >%s\n"
+ ":goterror\n";
+#endif //WIN16
+
+// public variables used for error reporting
+DWORD lnCur=0; // current line #
+WORD colCur=0; // current column number
+CHAR szFileCur[CB_MAX_PATHNAME+1]; // current file name
+DWORD lnLast; // current line #
+WORD colLast; // current column number
+SCODE scodeErrCur; // SCODE of current output error
+
+CHAR * szExpected = ""; // initially empty string
+
+
+FILE * hFileInput = NULL; // file handle for reading
+FILE * hHFile = NULL; // file handle for .H file output
+FILE * hFileOutput = NULL; // file handle for redirected output
+
+// forward decls and public data for DBCS support
+char g_rgchLeadBytes[256];
+static VOID InitLeadByteTable();
+
+// prototypes
+#ifndef NO_MPW
+VOID main (int argc, CHAR *argv[]);
+#else //NO_MPW
+VOID main (VOID);
+extern VOID FAR DumpTypeLib(CHAR * szTypeLibFile); // from TLVIWER.CPP
+#endif //NO_MPW
+#ifdef MAC
+VOID MacMessageBox(CHAR * szOutput);
+#endif
+SHORT NEAR FParseCl(int argc, CHAR * argv[]);
+VOID NEAR DoPreProcess(VOID);
+CHAR * NEAR CloneNameAddExt(CHAR * szInputFile, CHAR * szExt);
+VOID NEAR ErrorExit(VOID);
+VOID NEAR DisplaySuccess (CHAR * szTypeLibFile);
+VOID NEAR ParseErrorLnCol(ERR err, DWORD lnCur, WORD colCur);
+
+
+// local data
+#ifndef MAC
+HCURSOR hcrsWait;
+#endif //!MAC
+
+// data filled in from the command line
+CHAR * szInputFile = NULL; // filename we're inputting from
+CHAR * szTypeLibFile = NULL; // filename we're outputting to
+CHAR * szHFile = NULL; // filename for .H file output
+CHAR * szOutputFile = NULL; // filename for redirected output
+BOOL fHFile = FALSE; // TRUE ==> output a .H file
+BOOL fNologo = FALSE; // TRUE ==> don't print the header
+BOOL fGiveUsage = FALSE; // TRUE ==> give usage screen
+SYSKIND SysKind = SYS_DEFAULT; // kind of typlib to generate
+int iAlignMax = ALIGN_MAX_DEFAULT; // alignment max
+int iAlignDef = ALIGN_MAX_DEFAULT; // standard alignment for the platform
+BOOL fSuppressWarnings = FALSE; // TRUE ==> suppress warnings
+#if defined(WIN16) || (defined (MAC) && !defined(_PPCMAC))
+DWORD f2DefaultCC = f2CDECL; // default calling convention for
+ // win16 & 68k Mac
+#else
+DWORD f2DefaultCC = f2STDCALL; // default calling convention for
+ // win32 & ppc mac
+#endif
+
+#if FV_CPP
+BOOL fCPP = TRUE; // default to using the pre-processor
+CHAR * szCppExe = "cl.exe"; // default pre-processor EXE
+#ifndef WIN32
+HTASK hTaskCpp; // task notification data
+#endif
+CHAR * szCppOpts = "-C -E -D__MKTYPLIB__"; // default pre-processor opts
+CHAR * szTempFile = NULL;
+#ifdef WIN16
+#define CB_CPPDEFS 128 // bounded by max command line length on win16
+#else //WIN16
+#define CB_CPPDEFS 512 // *not* bounded by max command line length.
+ // 512 is big enough for all practical purposes.
+#endif //WIN16
+CHAR szCppDefs[CB_CPPDEFS]; // pre-processor defines/includes
+
+#endif //FV_CPP
+
+BOOL fOLEInitialized = FALSE; // TRUE ==> OLE has been initialized
+#ifdef MAC
+BOOL fAppletInitialized = FALSE; // TRUE ==> OLE has been initialized
+#endif //MAC
+
+#ifdef DEBUG
+BOOL fDebug = FALSE; // TRUE ==> dump debug info
+#endif //DEBUG
+
+
+#ifndef WIN16
+#define OLEINITIALIZE OleInitialize
+#define OLEUNINITIALIZE OleUninitialize
+#else //!WIN16
+#define OLEINITIALIZE CoInitialize // don't need all of OleInitialize
+#define OLEUNINITIALIZE CoUninitialize
+#endif //!WIN16
+
+#if 0 // doesn't seem to be necessary under WIN16, WIN32 or MAC
+VOID FAR pascal WinMain(HANDLE hInstanceCur, HANDLE hInstancePrev, LPSTR lpCmdLine, int nCmdShow)
+{
+ main(0, NULL); // doesn't return
+}
+#endif //0
+
+#ifdef WIN16
+int FAR pascal WEP(int x)
+{
+ x = x; // fix retail warning
+ return 1; // success
+}
+#endif //WIN16
+
+//#define KEEPTEMP // activate to retain temp files
+
+#ifdef KEEPTEMP
+ #define MyRemove(x) 0 // pretend no error
+#else //KEEPTEMP
+ #define MyRemove remove
+#endif //KEEPTEMP
+
+#ifdef NODEBUGALERTS
+ WINDEBUGINFO Olddebuginfo;
+#endif
+
+
+// MkTypLib entry point
+VOID main
+(
+#ifndef NO_MPW
+ int argc, /* Number of strings in array argv */
+ CHAR *argv[] /* Array of command-line argument strings */
+#endif // NO_MPW
+)
+{
+
+#ifdef USE_DIMALLOC
+ IMalloc FAR *pmalloc;
+#endif //USE_DIMALLOC
+#ifdef NO_MPW
+#define MAX_ARGS 21
+ int argc; /* Number of strings in array argv */
+ CHAR *argv[MAX_ARGS]; /* Array of command-line argument strings */
+ FILE * hFileArgs;
+#endif // NO_MPW
+
+ int fArgErr;
+ HRESULT res;
+#ifndef MAC
+ OPENFILENAME ofn;
+#endif
+
+#ifdef NODEBUGALERTS
+ WINDEBUGINFO debuginfo;
+
+ GetWinDebugInfo(&debuginfo, WDI_OPTIONS);
+ Olddebuginfo = debuginfo; // save for restoration
+ debuginfo.dwOptions |= DBO_SILENT;
+ SetWinDebugInfo(&debuginfo);
+#endif //NODEBUGALERTS
+
+ // init key fields in the main 'typlib' structure before we use them
+ typlib.pEntry = NULL; // no entries seen so far
+ typlib.pImpLib = NULL; // no imported libraries initially
+
+#ifdef MAC
+#ifdef NO_MPW
+ // Do mysterious MAC init stuff
+ MaxApplZone();
+#endif //NO_MPW
+
+ InitGraf((Ptr) &qd.thePort);
+#ifdef NO_MPW
+ InitFonts();
+ InitWindows();
+ InitMenus();
+ InitDialogs(nil);
+ InitCursor();
+#endif //NO_MPW
+
+ PPCInit(); // required by OleInitialize
+
+ // init the OLE Applet
+ if ((res = InitOleManager(0)) != NOERROR)
+ ParseError(ERR_OM); // UNDONE: correct error?
+ fAppletInitialized = TRUE;
+
+#ifdef NO_MPW
+ // If a file exists called "MKTYPLIB.ARG", load up argc, argv[] to satisfy
+ // our command line parser.
+ if (hFileArgs = fopen("mktyplib.arg", "r"))
+ {
+ argc = 1;
+ while (argc < MAX_ARGS)
+ {
+ argv[argc] = malloc(50);
+ if (fscanf(hFileArgs, " %s ", argv[argc]) == EOF)
+ break;
+ argc++;
+ }
+ fclose(hFileArgs);
+
+ }
+ else
+ {
+ // activate to output to file instead of using lame MAC MessageBox's
+ // szOutputFile = "m.log"; // redirected output
+ szInputFile = "m.odl"; // input file
+ fHFile = TRUE; // want a .H file
+
+ fArgErr = FALSE; // no arg error
+ goto ArgsParsed;
+ }
+#endif //NO_MPW
+#endif //MAC
+
+ InitLeadByteTable();
+
+ fArgErr = FParseCl(argc, argv); // parse the command line
+
+#ifdef MAC
+#ifdef NO_MPW
+ArgsParsed:
+#endif //NO_MPW
+#endif //MAC
+
+ if (szOutputFile)
+ {
+#ifdef WIN16
+ // perform in-place conversion to OEM char set
+ AnsiToOem(szOutputFile, szOutputFile);
+
+ // (don't bother converting back - this string is not used again)
+#endif // WIN16
+
+ hFileOutput = fopen(szOutputFile, "w");
+ // if problem opening output file, then just revert to normal
+ // MessageBox output.
+ // CONSIDER: give an error, too?
+ }
+
+ if (!fNologo)
+ {
+ DisplayLine(szBanner); // display the copyright banner
+ // add a blank line in some cases to make it look better
+ if (hFileOutput)
+ fputs("\n", hFileOutput);
+#ifndef WIN16
+#ifndef NO_MPW
+ else
+ printf("\n");
+#endif //NO_MPW
+#endif //!WIN16
+ }
+
+ if (fArgErr || fGiveUsage)
+ {
+GiveUsage:
+ DisplayLine(szUsage);
+ ErrorExit(); // clean up and exit(1)
+ }
+
+#ifndef MAC
+ // use common dialog to get input filename if user didn't specify one
+ if (szInputFile == NULL)
+ {
+ szInputFile = malloc(CB_MAX_PATHNAME+1);
+
+ memset(&ofn, 0, sizeof(OPENFILENAME));
+ ofn.lStructSize = sizeof(OPENFILENAME);
+// ofn.hwndOwner = g_hwndMain;
+ ofn.hwndOwner = NULL;
+ ofn.lpstrFile = szInputFile;
+ ofn.nMaxFile = CB_MAX_PATHNAME+1;
+ *szInputFile = '\0';
+ ofn.lpstrFilter = "Object Description Lang.\0*.odl\0\0";
+ ofn.nFilterIndex = 1;
+ ofn.Flags = OFN_PATHMUSTEXIST | OFN_FILEMUSTEXIST;
+
+ // if anything went wrong -- just give the usage message
+ if (GetOpenFileName(&ofn) == 0)
+ goto GiveUsage;
+ }
+#endif //!MAC
+
+ Assert(szInputFile);
+
+// now compute filenames based off the input filename
+
+ if (szTypeLibFile == NULL) // if output file not specified
+ { // use input filename with ".tlb" extension
+ szTypeLibFile = CloneNameAddExt(szInputFile, ".tlb");
+ }
+
+ if (fHFile && szHFile == NULL) // if header filename not specified
+ { // use input filename with ".h" extension
+ szHFile = CloneNameAddExt(szInputFile, ".h");
+ }
+
+
+ // If output file ends up with the same name as the input file, then
+ // the user is screwed. Just give the usage message.
+ if (!strcmp(szInputFile, szTypeLibFile))
+ goto GiveUsage;
+
+ // If .h file ends up with the same name as either the input file or output
+ // file, then the user is screwed. Just give the usage message.
+ if (szHFile && (!strcmp(szInputFile, szHFile) || !strcmp(szTypeLibFile, szHFile)))
+ goto GiveUsage;
+
+#ifdef USE_DIMALLOC
+
+ // Use the dimalloc implementation, since the default implementation
+ // doesn't work yet in mac ole.
+ if (!GetDebIMalloc(&pmalloc))
+ ParseError(ERR_OM); // UNDONE: correct error?
+
+ res = OLEINITIALIZE(pmalloc);
+ pmalloc->lpVtbl->Release(pmalloc);
+#else
+ // must init OLE
+ res = OLEINITIALIZE(NULL);
+#endif
+
+ if (FAILED(res))
+ ParseError(ERR_OM); // UNDONE: correct error?
+ fOLEInitialized = TRUE;
+
+#ifndef MAC
+ hcrsWait = LoadCursor(NULL, (LPSTR)IDC_WAIT);
+ SetCursor(hcrsWait); // turn on the hourglass cursor
+ // UNDONE: this doesn't always stay on in WIN16, nor does it seem to
+ // UNDONE: have any affect in WIN32.
+#endif //!MAC
+
+#if FV_CPP
+ if (fCPP) // if we're to pre-process input file
+ DoPreProcess();
+#endif //FV_CPP
+
+ strcpy(szFileCur, szInputFile); // init current file name (for
+ // error reporting)
+
+#if FV_CPP
+ ParseOdlFile(fCPP ? szTempFile : szInputFile); // parse the input file
+#else
+ ParseOdlFile(szInputFile); // parse the input file
+#endif
+
+#if FV_CPP
+ if (szTempFile)
+ {
+ SideAssert(MyRemove(szTempFile) == 0); // delete tmp file created above
+ szTempFile = NULL;
+ }
+#endif //FV_CPP
+
+ if (fHFile) // output .H file if desired
+ OutputHFile(szHFile);
+
+ // Now emit the type library
+ OutputTyplib(szTypeLibFile);
+
+#ifdef NO_MPW
+ // Now dump the type library
+ DumpTypeLib(szTypeLibFile);
+#endif
+
+ CleanupImportedTypeLibs(); // release any imported typelibs
+
+ OLEUNINITIALIZE(); // terminate OLE
+
+#ifdef MAC
+ UninitOleManager(); // clean up applet
+#endif //MAC
+
+ DisplaySuccess(szTypeLibFile); // holy *&*%&^%, it worked!!!
+
+ if (hFileOutput) // close redirected output file
+ fclose(hFileOutput);
+
+#ifdef NODEBUGALERTS
+ SetWinDebugInfo(&Olddebuginfo);
+#endif //NODEBUGALERTS
+ exit(0);
+
+}
+
+// helper to print the "success" message -- moved out of line to reduce
+// stack usage of main routine.
+VOID NEAR DisplaySuccess
+(
+ CHAR * szTypeLibFile
+)
+{
+ CHAR szBuf[255];
+
+ sprintf (szBuf, szFmtSuccess, szTypeLibFile);
+ DisplayLine(szBuf); // then display the message
+}
+
+
+VOID FAR ParseErrorTokLast
+(
+ ERR err
+)
+{
+ ParseErrorLnCol(err, lnLast, colLast);
+}
+
+// Cleans up, and reports an error. Doesn't return unless this is a warning.
+VOID FAR ParseError
+(
+ ERR err
+)
+{
+ ParseErrorLnCol(err, lnCur, colCur);
+}
+
+// Cleans up, and reports an error. Doesn't return unless this is a warning.
+// Reports an error. If this is a warning, returns.
+// If this is an error, cleans up and exits
+VOID NEAR ParseErrorLnCol
+(
+ ERR err,
+ DWORD lnCur,
+ WORD colCur
+)
+{
+ CHAR szError[255];
+ BOOL fWarning;
+
+ fWarning = ((err >= WARN_FIRST && err < GENERAL_ERR_LAST) ||
+ (err >= PWARN_FIRST && err < OERR_FIRST));
+
+ if (fWarning && fSuppressWarnings)
+ return;
+
+ // first figure out the error text
+ if (err < OERR_FIRST)
+ { // parser/lexer error or warning
+ Assert(err);
+ sprintf (szError,
+ (fWarning ? szFmtWarnFileLineCol : szFmtErrFileLineCol),
+ szFileCur, lnCur, lnCur, colCur, rgszErr[err-1], szExpected);
+ }
+ else
+ {
+ // output errors shoudn't come through here.
+ Assert(err >= ERR_FIRST && err < GENERAL_ERR_LAST);
+ sprintf (szError,
+ (fWarning ? szFmtWarnGeneral : szFmtErrGeneral),
+ rgszErr[err-1]);
+ }
+
+ // display error/warning
+ DisplayLine(szError);
+
+ // If not a warning, then clean up and exit(1)
+ if (!fWarning)
+ ErrorExit();
+}
+
+// Cleans up, and reports an error with an insertion string. Doesn't return.
+VOID FAR ItemError
+(
+ CHAR * szErrFormat,
+ LPSTR lpszItem,
+ ERR err
+)
+{
+ CHAR szItem[255];
+ CHAR szBuf[255];
+
+ Assert(lpszItem);
+ _fstrcpy(szItem, lpszItem); // copy item name near
+
+ // format the error
+ sprintf (szBuf, szErrFormat, szFileCur, szItem, rgszErr[err-1], scodeErrCur);
+
+ // then display the error
+ DisplayLine(szBuf);
+
+ // then clean up and exit(1)
+ ErrorExit();
+}
+
+
+VOID NEAR ErrorExit()
+{
+
+ // first clean up whatever mess we've left behind
+ if (hFileInput) // in error during reading
+ fclose(hFileInput); // then close the input file
+
+#if FV_CPP
+ if (szTempFile) // if error during pre-processing
+ { // or parsing, delete tmp file
+ MyRemove(szTempFile);
+ }
+#endif //FV_CPP
+
+ if (hHFile) // if error during write of .H file
+ {
+ fclose(hHFile); // then close the .H file
+ MyRemove(szHFile); // and delete partially-generated file
+ }
+
+ if (hFileOutput) // close redirected output file
+ fclose(hFileOutput);
+
+ CleanupImportedTypeLibs(); // release any imported typelibs
+
+ if (fOLEInitialized) // terminate OLE
+ OLEUNINITIALIZE();
+
+#ifdef MAC
+ if (fAppletInitialized) // terminate OLE
+ UninitOleManager(); // clean up applet
+#endif //MAC
+
+#ifdef NODEBUGALERTS
+ SetWinDebugInfo(&Olddebuginfo);
+#endif //NODEBUGALERTS
+ exit(1); // exit with error
+}
+
+
+// creates a new pathame string that is a dup of the input pathname, with the
+// extension (if any) replaced by the given extension.
+CHAR * NEAR CloneNameAddExt
+(
+ CHAR * szInputFile,
+ CHAR * szExt
+)
+{
+ CHAR * szFile;
+ CHAR * pExt;
+ CHAR * pch;
+
+ // CONSIDER:
+ // assumes the extension is no more than 3 bytes incl '.' (ie non-DBCS)
+ // (This is true for the moment - can it ever change???)
+
+ // alloc string with enough space for ".", extension, and null
+ szFile = malloc(strlen(szInputFile)+1+3+1);
+ strcpy(szFile, szInputFile); // start with input file name
+
+ // find "." (if present) that occurs after last \ or /.
+ pExt = NULL;
+ for (pch = szFile; *pch; NextChar(pch))
+ {
+ switch (*pch)
+ {
+#ifdef MAC
+ case ':':
+ case ' ': // start search over at a space
+#else //MAC
+ case '\\':
+ case '/':
+#endif //MAC
+ pExt = NULL;
+ break;
+ case '.':
+ pExt = pch;
+ break;
+ default:
+ ;
+ }
+ }
+ if (pExt == NULL) // if no extension after last '\', then
+ pExt = pch; // append an extension to the name.
+
+ strcpy (pExt, szExt); // replace extension (if present) with
+ // desired extension
+
+ return szFile;
+}
+
+#if FV_CPP
+
+#ifdef WIN32
+// created this from the WIN32 docs, using info on WinExec and CreateProcess
+// WARNING: the example given in the WIN32 docs on CreateProcess is bogus.
+VOID NEAR DoPreProcess
+(
+)
+{
+ char szBuffer[512];
+ BOOL fSuccess;
+ STARTUPINFO si;
+ PROCESS_INFORMATION pi;
+ SECURITY_ATTRIBUTES sa;
+ DWORD dw;
+ DWORD dwExitCode;
+ HANDLE hProcess;
+ HANDLE hOutput;
+
+ memset (&si, 0, sizeof(si));
+ memset (&pi, 0, sizeof(pi));
+ memset (&sa, 0, sizeof(sa));
+
+ szTempFile = strdup(tempnam(".", "~mki")); // for pre-processed output
+
+ sa.nLength = sizeof(sa);
+ sa.bInheritHandle = TRUE;
+
+ hOutput = CreateFile(szTempFile, GENERIC_WRITE, 0, &sa,
+ CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, 0);
+
+ if (hOutput == INVALID_HANDLE_VALUE)
+ ParseError(ERR_CPP);
+
+ sprintf(szBuffer, "%s %s%s %s",
+ szCppExe, szCppOpts, szCppDefs, szInputFile);
+
+ // init si structure
+ si.cb = sizeof(si);
+ si.lpTitle = "MkTypLib: C pre-processor";
+ //si.dwX = 100; // just guessing...
+ //si.dwY = 100;
+ //si.dwXSize = 1000;
+ //si.dwYSize = 1000;
+ si.dwFlags = STARTF_USESTDHANDLES | STARTF_USESHOWWINDOW;
+ si.hStdOutput = hOutput;
+ //si.hStdError = hOutputError; // CONSIDER: show this to the user?
+ //si.wShowWindow = SW_SHOWMINIMIZED;
+ si.wShowWindow = SW_HIDE;
+
+ // Setting the Inherit Handles flag to TRUE so that it works when
+ // run under nmake with our output redirected.
+ fSuccess = CreateProcess(NULL, szBuffer, NULL, NULL, TRUE,
+ // this gives us a window'ed CL
+ //DETACHED_PROCESS,
+ 0,
+
+ NULL, NULL,
+ &si, &pi);
+
+ if (!fSuccess) {
+ CloseHandle(hOutput);
+ ParseError(ERR_CPP);
+ }
+
+ // if we were successful, now wait for it to be done
+ hProcess = pi.hProcess;
+
+ // wait for the process to complete (120 second timeoout)
+ dw = WaitForSingleObject(pi.hProcess, 120000L);
+
+#ifndef STATUS_SUCCESS
+ #define STATUS_SUCCESS 0
+#endif
+
+ if (dw == STATUS_SUCCESS)
+ fSuccess = GetExitCodeProcess(pi.hProcess, &dwExitCode);
+
+ CloseHandle(pi.hThread);
+ CloseHandle(pi.hProcess);
+ CloseHandle(hOutput);
+
+ // report any error
+ if (dw != STATUS_SUCCESS || !fSuccess || dwExitCode != 0)
+ ParseError(ERR_CPP);
+}
+
+#else //WIN32
+
+// pre-process input file, creating a tmp file
+// In order to get the return code of the C pre-processor, I'm
+// spawing a batch file that invokes CL, and creates a signal file
+// if it is successful.
+VOID NEAR DoPreProcess
+(
+)
+{
+ char szBuffer[255];
+
+ HANDLE hInstCpp;
+ TASKENTRY taskentry;
+ FILE * hFile;
+ CHAR * szTempBatch;
+ CHAR * szTempSig;
+ CHAR * szTempRoot;
+ ERR err = ERR_CPP; // assume error
+ int cbTempFilenames;
+ char * szComSpec;
+
+ // figure out the names of the temp files
+ // (note: uses OEM char set)
+ szTempRoot = tempnam(".", "~mkt"); // get base name for temp files
+ hFile = fopen(szTempRoot, "w"); // create the file now, to
+ if (hFile == NULL) // reserve this set of names
+ ParseError(ERR_CPP);
+ fclose(hFile);
+
+ cbTempFilenames = strlen(szTempRoot)+1+3+1; // base name + ext + null
+ szTempBatch = malloc(cbTempFilenames); // for .BAT file
+ strcpy(szTempBatch, szTempRoot);
+ strcat(szTempBatch, ".bat");
+
+ szTempSig = malloc(cbTempFilenames); // for .SIG file
+ strcpy(szTempSig, szTempRoot);
+ strcat(szTempSig, ".sig");
+
+ szTempFile = malloc(cbTempFilenames); // for pre-processed oupput
+ strcpy(szTempFile, szTempRoot);
+ strcat(szTempFile, ".inp");
+
+ // CONSIDER: Check for existence of any of these files, if any exist, then
+ // CONSIDER: try a different base name for the files.
+
+ // open the temp .BAT file
+ hFile = fopen(szTempBatch, "w");
+ if (hFile == NULL)
+ goto cleanup2;
+
+ // all errors after this point should go to 'cleanup'
+
+ if (fputs(szBatchStart, hFile) < 0) // write the first part
+ goto cleanup;
+
+ sprintf(szBuffer, "%s %s%s %s>",
+ szCppExe, szCppOpts, szCppDefs, szInputFile);
+
+ // convert this string to the OEM char set
+ AnsiToOem(szBuffer, szBuffer);
+
+ // append szTempFile
+ strcat(szBuffer, szTempFile);
+ strcat(szBuffer, "\n");
+
+ if (fputs(szBuffer, hFile) < 0) // write the CPP command
+ goto cleanup;
+
+ sprintf(szBuffer, szBatchEnd, szTempSig);
+ if (fputs(szBuffer, hFile) < 0) // write the error check code
+ goto cleanup;
+
+ fclose(hFile);
+ hFile = NULL; // file no longer open
+
+ szComSpec = getenv("COMSPEC");
+ if (szComSpec == NULL)
+ szComSpec = "command.com";
+
+ sprintf(szBuffer, "%s /c %s", szComSpec, szTempBatch);
+ hInstCpp = WinExec(szBuffer, SW_SHOWMINIMIZED); // shell the pre-processor
+ if (hInstCpp < 32) // if error spawning pre-processor
+ goto cleanup;
+
+ Yield(); // give it a chance to start
+
+ // find task associated with this instance. In extreme cases it may have
+ // finished even before we're executing this code.
+ taskentry.dwSize = sizeof(TASKENTRY);
+ if (TaskFirst(&taskentry) == 0) {
+ goto taskdone;
+ }
+
+ while (taskentry.hInst != hInstCpp) {
+ if (TaskNext(&taskentry) == 0) {
+ goto taskdone;
+ }
+ }
+
+ hTaskCpp = taskentry.hTask;
+
+ while (IsTask(hTaskCpp))
+ {
+ SideAssert(TaskFindHandle(&taskentry, hTaskCpp) != 0);
+ if (taskentry.hInst != hInstCpp)
+ {
+ // different hInst associated with this htask,
+ // so the app must have terminated
+ break;
+ }
+
+ Yield(); // wait until it's done
+
+ }
+
+taskdone:
+
+ // If signal file doesn't exist, then there was a problem pre-processing
+ // the input file. If it exists, then it worked.
+ if (!MyRemove(szTempSig))
+ err = ERR_NONE; // it worked!
+
+cleanup:
+ if (hFile) // close tmp batch file if
+ fclose(hFile); // error during write
+ SideAssert(MyRemove(szTempBatch) == 0); // delete tmp batch file
+
+cleanup2:
+ SideAssert(MyRemove(szTempRoot) == 0); // delete placeholder file
+
+ if (err != ERR_NONE) // report any error
+ ParseError(err);
+}
+
+#endif // WIN32
+#endif // FV_CPP
+
+
+// ******************************************************
+// FParseCl() - Commandline argument parser
+//
+// Purpose:
+// Parse the command line
+//
+// Entry:
+// None
+//
+// Exit:
+// Returns ARGS_OK or GIVE_USAGE
+// ******************************************************
+SHORT NEAR FParseCl
+(
+int argc,
+CHAR *argv[]
+)
+{
+ CHAR *arg; // pointer to current argument
+ SHORT i; // argument counter
+ BOOL fAlignSpecified = FALSE; // TRUE iff the /align switch was used
+
+#if FV_CPP
+ *szCppDefs = '\0'; // no definitions initially
+#endif //FV_CPP
+
+ for (i = 1; i < argc; i++)
+ { // while more args to get
+ arg = argv[i]; // get next argument
+
+ if (*arg == '/' || *arg == '-') // a switch
+ {
+GotArg:
+ arg++; // skip switch
+
+ if (!stricmp(arg,"?") || !(stricmp(arg, "help")))
+ fGiveUsage = TRUE; // give help
+
+ else if (!stricmp(arg,"nologo"))
+ fNologo = TRUE; // no banner
+
+ else if (!stricmp(arg,"win16"))
+ {
+ SysKind = SYS_WIN16; // make Win16 type library
+ f2DefaultCC = f2CDECL;
+ if (!fAlignSpecified)
+ iAlignMax = 1;
+ iAlignDef = 1;
+ }
+
+ else if (!stricmp(arg,"win32"))
+ {
+ SysKind = SYS_WIN32; // make Win32 type library
+ f2DefaultCC = f2STDCALL;
+ if (!fAlignSpecified)
+ iAlignMax = 4;
+ iAlignDef = 4;
+ }
+
+ else if (!stricmp(arg,"mac"))
+ {
+ SysKind = SYS_MAC; // make Mac type library
+ f2DefaultCC = f2CDECL;
+ if (!fAlignSpecified)
+ iAlignMax = 2;
+ iAlignDef = 2;
+ }
+
+ else if (!stricmp(arg,"mips"))
+ {
+ SysKind = SYS_WIN32;
+ f2DefaultCC = f2STDCALL;
+ if (!fAlignSpecified)
+ iAlignMax = 8;
+ iAlignDef = 8;
+ }
+ else if (!stricmp(arg,"alpha"))
+ {
+ SysKind = SYS_WIN32;
+ f2DefaultCC = f2STDCALL;
+ if (!fAlignSpecified)
+ iAlignMax = 8;
+ iAlignDef = 8;
+ }
+
+ else if (!stricmp(arg,"ppc32"))
+ {
+ SysKind = SYS_WIN32;
+ f2DefaultCC = f2STDCALL;
+ if (!fAlignSpecified)
+ iAlignMax = 8;
+ iAlignDef = 8;
+ }
+
+ else if (!stricmp(arg,"ppc"))
+ {
+ SysKind = SYS_MAC;
+ f2DefaultCC = f2STDCALL;
+ if (!fAlignSpecified)
+ iAlignMax = 8;
+ iAlignDef = 8;
+ }
+
+ else if (!stricmp(arg,"align")) // set alignment val
+ { // next arg is integer val
+ if (++i == argc) // no more args!
+ return GIVE_USAGE;
+ iAlignMax = atoi(argv[i]);
+ if (iAlignMax < 1)
+ return GIVE_USAGE;
+ fAlignSpecified = TRUE;
+ }
+ else if (!stricmp(arg,"w0"))
+ fSuppressWarnings = TRUE; // no warnings
+#ifdef DEBUG
+ else if (!stricmp(arg,"debug"))
+ fDebug = TRUE; // dump debug info
+#endif //DEBUG
+ else if (!stricmp(arg,"tlb"))
+ { // next arg should be filename -- get it
+ if (++i == argc) // error if no more args
+ return GIVE_USAGE;
+ szTypeLibFile = strdup(argv[i]); // save filename
+ }
+ else if (!stricmp(arg,"h"))
+ { // next arg should be filename -- get it
+ fHFile = TRUE; // want a .H file
+ if (++i == argc) // we're done if no more args
+ break;
+ arg = argv[i]; // get next argument
+
+ // if this is another arg, then just process it
+ if (*arg == '/' || *arg == '-')
+ goto GotArg;
+ szHFile = strdup(arg); // save .H filename
+ }
+ else if (!stricmp(arg,"o"))
+ { // next arg should be filename -- get it
+ if (++i == argc) // error if no more args
+ return GIVE_USAGE;
+ szOutputFile = strdup(argv[i]); // save filename
+ }
+#if FV_CPP
+ else if (*arg == 'D' || *arg == 'I')
+ { // append this /D or /I switch to szCppDefs
+
+ strcat(szCppDefs, " "); // append a space
+ strcat(szCppDefs, argv[i]); // save /D, /I switch
+
+ if (*(arg+1) == '\0')
+ { // /D or /I specified by themselves, then
+ // next arg is what's important -- append
+ // that, too
+ if (++i == argc) // error if no more args
+ return GIVE_USAGE;
+ strcat(szCppDefs, " "); // add a space
+ strcat(szCppDefs, argv[i]); // add CPP defs
+ }
+ // I don't feel like adding to ton of code to keep
+ // us from overflowing the buffer. Instead, we've
+ // got a really big buffer, so if we overwrite it,
+ // give an error & hope we don't crash on exit.
+ if (strlen(szCppDefs) >= sizeof(szCppDefs)-1) {
+ return GIVE_USAGE;
+ }
+ }
+ else if (!stricmp(arg,"cpp_cmd"))
+ { // next arg should be CPP pathname -- get it
+ if (++i == argc) // error if no more args
+ return GIVE_USAGE;
+ szCppExe = strdup(argv[i]); // save pathname
+ }
+ else if (!stricmp(arg,"cpp_opt"))
+ { // next arg should be CPP options (in quotes)
+ if (++i == argc) // error if no more args
+ return GIVE_USAGE;
+ szCppOpts = strdup(argv[i]); // get CPP options
+ }
+ else if (!stricmp(arg,"nocpp"))
+ fCPP = FALSE; // don't use C pre-processor
+#endif //FV_CPP
+ else // invalid switch
+ return GIVE_USAGE;
+ }
+ else
+ { // not a switch -- should be a filename
+ if (szInputFile) // only 1 filename allowed
+ return GIVE_USAGE;
+ szInputFile = strdup(arg); // store input filename
+ }
+ } // end for
+
+#ifndef MAC
+ // doesn't matter if filename not given -- common dialog will take care
+ // of it later.
+ return ARGS_OK;
+#else //!MAC
+ if (szInputFile) // if filename specified, then success
+ return ARGS_OK;
+
+ return GIVE_USAGE; // no file name given -- error
+#endif //!MAC
+
+}
+
+
+// display a line to the user. Assumes line doesn't end with a newline.
+VOID FAR DisplayLine(CHAR * szOutput)
+{
+ if (hFileOutput)
+ {
+#ifndef MAC
+ // convert szOutput in-place to OEM char set
+ AnsiToOem(szOutput, szOutput);
+#endif // !MAC
+
+ fputs(szOutput, hFileOutput);
+ fputs("\n", hFileOutput);
+
+#ifndef MAC
+ // convert back to ANSI in case the caller reuses this string
+ OemToAnsi(szOutput, szOutput);
+#endif // !MAC
+
+ }
+ else
+ {
+#ifdef NO_MPW
+ MacMessageBox(szOutput);
+#else //NO_MPW
+#ifndef WIN16
+
+#ifndef MAC
+ // convert szOutput in-place to OEM char set
+ AnsiToOem(szOutput, szOutput);
+#endif // !MAC
+
+ printf("%s\n", szOutput);
+
+#ifndef MAC
+ // convert back to ANSI in case the caller reuses this string
+ OemToAnsi(szOutput, szOutput);
+#endif // !MAC
+
+#else //!WIN16
+ // poor man's output under Windows
+ MessageBox(NULL, szOutput, szAppTitle, MB_OK);
+#endif //!WIN16
+#endif //NO_MPW
+ }
+}
+
+
+#ifdef DEBUG
+
+// not used in non-dimalloc versions, but it simplifies the link process
+//#ifdef USE_DIMALLOC
+/***
+*DebAssertShow - called when assertion fails
+*Purpose:
+* This function is called when an assertion fails. It prints
+* out the appropriate information and exits.
+*
+*Entry:
+* szFileName - filename where assertion failed
+* uLine - line number where assertion failed
+* szComment - reason assertion failed
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+void DebAssertShow(LPSTR lpszFileName, UINT uLine, LPSTR szComment)
+{
+ CHAR szFileName[255];
+ _fstrcpy(szFileName, lpszFileName); // copy near
+
+ AssertFail(szFileName, (WORD)uLine);
+}
+
+//#endif // USE_DIMALLOC
+
+
+
+VOID AssertFail
+(
+ CHAR * szFile,
+ WORD lineNo
+)
+{
+ CHAR szAssert[256];
+#ifndef MAC
+ int id;
+#endif //!MAC
+
+#ifdef MAC
+ *szAssert = sprintf(szAssert+1, "Typelib assertion: File %s, line %d", szFile, lineNo);
+#else //MAC
+ sprintf(szAssert, "Assertion failed. File %s, line %d.", szFile, lineNo);
+
+#endif //MAC
+
+ if (hFileOutput)
+ {
+ fputs(szAssert, hFileOutput);
+ fputs("\n", hFileOutput);
+ ErrorExit(); // clean up and exit(1)
+ }
+ else
+ {
+#ifdef MAC
+ // Can't use the the Ole2 internal assertion mechanism anymore,
+ // because if we're using the retail OLE, it doesn't assert.
+ // So we just break into macsbug ourselves.
+ //FnAssert(lpstrExpr, lpstrMsg, lpstrFileName, iLine);
+ DebugStr((const unsigned char FAR*)szAssert);
+ // ErrorExit(); // don't clean up and exit(1)
+#else
+ id = MessageBox(NULL, szAssert, "MkTypLib Assertion. OK to continue, CANCEL to quit.", MB_OKCANCEL);
+ if (id == IDCANCEL)
+ ErrorExit(); // clean up and exit(1)
+#endif //MAC
+ }
+}
+
+#if 0
+// output a string, debug version only. Assumes string ends with a newline.
+VOID DebugOut
+(
+ CHAR * szOut
+)
+{
+
+#ifndef MAC
+ int id;
+#endif //!MAC
+
+ if (hFileOutput)
+ {
+ fputs(szOut, hFileOutput);
+ fputs("\n", hFileOutput);
+ }
+ else
+ {
+#ifdef MAC
+ MacMessageBox(szOut);
+#else //MAC
+ id = MessageBox(NULL, szOut, "MkTypLib debug output. OK to continue, CANCEL to quit.", MB_OKCANCEL);
+ if (id == IDCANCEL)
+ ErrorExit(); // clean up and exit(1)
+#endif //MAC
+ }
+}
+#endif //0
+
+#endif //DEBUG
+
+#ifdef MAC
+#ifdef NO_MPW
+// UNDONE: eventually rip this & and it's resource from the MPW mktyplib build
+VOID MacMessageBox
+(
+ CHAR * szOutput
+)
+{
+ BYTE szBufTmp[256];
+
+ // convert to pascal-style string
+ *szBufTmp = (BYTE)(min(strlen(szOutput), 255));
+ strncpy(szBufTmp+1, szOutput, *szBufTmp);
+
+ // put up the alert
+ ParamText((ConstStr255Param)szBufTmp, "", "", "");
+ Alert(128, NULL);
+}
+#endif //NO_MPW
+#endif //MAC
+
+
+// initialize g_rgchLeadBytes
+//
+// use the Windows API IsDBCSLeadByte() or the Mac API ParseTable()
+//
+static VOID InitLeadByteTable()
+{
+#if MAC
+
+ // as in Silver, the font must be switched first
+
+ // preserve the old font in the current grafPort
+ short fontSave = qd.thePort->txFont;
+
+ // then set the grafPort font to 1 (Application Default) because
+ // ParseTable uses qd.thePort->txFont to determine the currect script,
+ // which in turn determines the lead byte table. We want the application
+ // default table.
+ TextFont(1);
+
+ // UNDONE: is it necessary to init this to 0?
+ memset(g_rgchLeadBytes, 0, 256);
+
+ ParseTable(g_rgchLeadBytes);
+
+ // restore the old font
+ TextFont(fontSave);
+
+#else // !MAC
+
+ int c;
+
+ memset(g_rgchLeadBytes, 0, 128);
+
+ // start at 128 since there aren't any lead bytes before that
+ for(c = 128; c < 256; c++) {
+ g_rgchLeadBytes[c] = (char)IsDBCSLeadByte((char)c);
+ }
+
+#endif // !MAC
+}
+
+// perform AnsiNext on all platforms
+extern char * XStrInc(char * pch)
+{
+ return IsLeadByte(*pch) ? pch + 2 : pch + 1;
+}
+
diff --git a/private/oleauto/src/mktyplib/mktyplib.def b/private/oleauto/src/mktyplib/mktyplib.def
new file mode 100644
index 000000000..3b5af8440
--- /dev/null
+++ b/private/oleauto/src/mktyplib/mktyplib.def
@@ -0,0 +1,7 @@
+NAME MKTYPLIB WINDOWAPI
+EXETYPE WINDOWS 3.1
+CODE PRELOAD MOVABLE DISCARDABLE
+DATA PRELOAD SINGLE
+HEAPSIZE 1024
+EXPORTS
+ WEP
diff --git a/private/oleauto/src/mktyplib/mktyplib.h b/private/oleauto/src/mktyplib/mktyplib.h
new file mode 100644
index 000000000..290e8e294
--- /dev/null
+++ b/private/oleauto/src/mktyplib/mktyplib.h
@@ -0,0 +1,162 @@
+/* single line comments and other horrid extensions are ok */
+#pragma warning(disable:4001)
+#pragma warning(disable:4201)
+#pragma warning(disable:4209)
+
+#ifdef WIN32
+
+#define __export
+#define EXPORT
+/* This line specifies widechar ctype table instead of ascii (ctype.h). */
+#define _NEWCTYPETABLE
+
+// force include of OLE2 rather than OLE1
+#define INC_OLE2
+// Yea, right...
+#define WIN32_LEAN_AND_MEAN
+#endif //WIN32
+
+#ifndef MAC
+#include <windows.h>
+#endif //!MAC
+
+// general typedef's and define's for use in MKTYPLIB
+#define TRUE 1
+#define FALSE 0
+
+// extend stuff in dispatch.h for RISC builds
+#define SYS_MAX (SYS_MAC+1)
+
+// environment-specific defines
+#ifdef MAC
+#define FAR
+#define NEAR
+#define SYS_DEFAULT SYS_MAC
+#define ALIGN_MAX_DEFAULT 2
+//UNDONE: SYS_MAC_PPC?
+#else //MAC
+#ifdef WIN32
+// defined by NT's windows.h
+#ifndef FAR
+#define FAR
+#endif
+//#define NEAR
+#define SYS_DEFAULT SYS_WIN32
+#if defined(_MIPS_) || defined(_ALPHA_) || defined(_PPC_)
+#define ALIGN_MAX_DEFAULT 8
+#else //_MIPS_ || _ALPHA_ || _PPC_
+#define ALIGN_MAX_DEFAULT 4
+#endif //_MIPS_ || _ALPHA_ || _PPC_
+#else //WIN32
+#define FAR _far
+#define NEAR _near
+#define SYS_DEFAULT SYS_WIN16
+#define ALIGN_MAX_DEFAULT 1
+#endif //WIN32
+#endif //MAC
+
+// basic types
+#undef VOID // windows.h #defines these instead of using
+#undef LONG // a typedef, but ole2.h typedef's them
+typedef void VOID;
+typedef char CHAR;
+typedef short SHORT;
+typedef int INT;
+typedef long LONG;
+typedef unsigned char BYTE;
+typedef unsigned short WORD;
+typedef unsigned long DWORD;
+typedef unsigned short USHORT;
+typedef unsigned int UINT;
+typedef unsigned long ULONG;
+typedef int BOOL;
+typedef CHAR FAR * LPSTR;
+typedef VOID FAR * LPVOID;
+
+#ifdef MAC // no windows.h -- OLE headers need the following
+//#define SIZEL LONG
+#define LPSIZE LPVOID
+#define LPRECT LPVOID
+#define Byte BYTE
+#define _MAC // for OLE include files
+#define USE_INCLUDE // for OLE include files
+#define CDECL _cdecl
+#define PASCAL _pascal
+typedef const CHAR * LPCSTR; // sz
+#include <types.h>
+#endif
+
+#ifndef WIN16
+#define _fmalloc malloc
+#define _ffree free
+#define _fmemcpy memcpy
+#define _fmemcmp memcmp
+#define _fstrcpy strcpy
+#define _fstrcmp strcmp
+#define _fstrcmpi strcmpi
+#define _fstrdup strdup
+#define _fstrcat strcat
+#endif
+
+
+// basic defines
+#ifndef WIN32 // defined by NT's windows.h
+#define LOWORD(l) ((WORD)(DWORD)(l))
+#define HIWORD(l) ((WORD)((((DWORD)(l)) >> 16) & 0xFFFF))
+#endif //WIN32
+
+// *******************************************************
+// switches
+// *******************************************************
+#define FV_PROPSET FALSE // don't allow PROPERTY_SETs
+
+#ifdef MAC
+#define FV_CPP FALSE // no C pre-processor for MAC
+#else //MAC
+#define FV_CPP TRUE // support spawning C pre-processor
+#endif //MAC
+
+// *******************************************************
+// misc types
+// *******************************************************
+
+// DBCS support
+
+extern char g_rgchLeadBytes[]; // lead byte table
+
+#define NextChar(pch) (pch = XStrInc(pch))
+#define IsLeadByte(ch) (g_rgchLeadBytes[(unsigned char)ch])
+
+#ifdef __cplusplus
+extern "C" {
+#endif // __cplusplus
+
+extern char * FAR XStrChr(char * xsz, int ch); // wrapper for strchr
+extern char * XStrInc(char * pch); // AnsiNext-like function
+
+#ifdef __cplusplus
+}
+#endif // __cplusplus
+
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+extern VOID FAR DisplayLine(CHAR * szLine); // cover for printf/messagebox
+
+// debug support
+#ifdef DEBUG
+extern VOID DebugOut(CHAR *); // cover for puts/messagebox
+extern BOOL fDebug; // TRUE if /debug specified on command line
+extern VOID AssertFail(CHAR *, WORD);
+#define Assert(expr) if (!(expr)) AssertFail(__FILE__, __LINE__);
+#define SideAssert(expr) Assert(expr)
+#else // DEBUG
+#define Assert(expr)
+#define SideAssert(expr) expr;
+#endif // DEBUG
+
+#ifdef __cplusplus
+}
+#endif
diff --git a/private/oleauto/src/mktyplib/mktyplib.ico b/private/oleauto/src/mktyplib/mktyplib.ico
new file mode 100644
index 000000000..ab9ac2165
--- /dev/null
+++ b/private/oleauto/src/mktyplib/mktyplib.ico
Binary files differ
diff --git a/private/oleauto/src/mktyplib/mktyplib.r b/private/oleauto/src/mktyplib/mktyplib.r
new file mode 100644
index 000000000..e4ab9fdf7
--- /dev/null
+++ b/private/oleauto/src/mktyplib/mktyplib.r
@@ -0,0 +1,165 @@
+#include "types.r"
+#include "systypes.r"
+//#include "ebappids.h"
+//#include "resids.h"
+#include "verstamp.h"
+
+#define STRING(x) #x
+
+
+#ifdef MKTYPLIB2 // only if special build
+
+resource 'ALRT' (128) {
+ {38, 44, 260, 438},
+ 128,
+ { /* array: 4 elements */
+ /* [1] */
+ OK, visible, sound1,
+ /* [2] */
+ OK, visible, sound1,
+ /* [3] */
+ OK, visible, sound1,
+ /* [4] */
+ OK, visible, sound1
+ }
+};
+
+resource 'DITL' (128) {
+ { /* array DITLarray: 2 elements */
+ /* [1] */
+ {194, 150, 214, 208},
+ Button {
+ enabled,
+ "Ok"
+ },
+ /* [2] */
+ {14, 17, 184, 380},
+ StaticText {
+ disabled,
+ "^0"
+ }
+ }
+};
+#endif //MKTYPLIB2
+
+
+resource 'SIZE' (-1) {
+ reserved,
+ acceptSuspendResumeEvents,
+ reserved,
+ canBackground, /* we can background; we don't currently, but our sleep value */
+ /* guarantees we don't hog the Mac while we are in the background */
+ multiFinderAware, /* this says we do our own activate/deactivate; don't fake us out */
+ backgroundAndForeground, /* this is definitely not a background-only application! */
+ dontGetFrontClicks, /* change this is if you want "do first click" behavior like the Finder */
+ ignoreChildDiedEvents, /* essentially, I'm not a debugger (sub-launching) */
+ is32BitCompatible, /* this app should not be run in 32-bit address space */
+ isHighLevelEventAware,
+ reserved,
+ reserved,
+ useTextEditServices,
+ reserved,
+ reserved,
+ reserved,
+ 2048 * 1024, // preferred size
+ 512 * 1024 // min size
+};
+
+
+#ifdef MKTYPLIB2 // only if special build
+resource 'BNDL' (1009) {
+ 'mktl',
+ 0,
+ { /* array TypeArray: 2 elements */
+ /* [1] */
+ 'FREF',
+ { /* array IDArray: 2 elements */
+ /* [1] */
+ 0, 128,
+ /* [2] */
+ 1, 129
+ },
+ /* [2] */
+ 'ICN#',
+ { /* array IDArray: 2 elements */
+ /* [1] */
+ 0, 128,
+ /* [2] */
+ 1, 129
+ }
+ }
+};
+
+data 'mktl' (0, "Owner resource") {
+ $"00" /* . */
+};
+
+resource 'FREF' (128) {
+ 'APPL',
+ 0,
+ ""
+};
+
+data 'FREF' (129) {
+ $"5445 5854 0001 7F" /* TEXT... */
+};
+
+resource 'ICN#' (128) {
+ { /* array: 2 elements */
+ /* [1] */
+ $"0000 0000 0000 0000 0000 0000 0000 0000"
+ $"0048 C000 0023 8000 0031 8003 0009 0803"
+ $"000C 1FFE 0006 03C6 0006 01EC 0006 0078"
+ $"0006 0070 00FD E050 077F F030 0DEF F870"
+ $"0B1B 1A70 1B80 04F0 1384 03F0 1A00 01F0"
+ $"1800 0030 0C80 80B0 0F80 2138 0700 FDF8"
+ $"0FF6 FFF0 3FFF FFF4 7FFF FDFC 3FFF DFFE",
+ /* [2] */
+ $"0000 0000 0000 0000 0000 0000 0000 0000"
+ $"006A C000 0033 8000 003F 8003 000F 1C07"
+ $"000E 1FFE 0006 07FE 0006 01FC 0006 00F8"
+ $"0006 0078 00FF E078 07FF F870 0FFF FC70"
+ $"0FFF FE70 1FFF FFF0 1FFF FFF0 1FFF FFF0"
+ $"1FFF FFF0 0FFF FFF8 0FFF FFF8 07FF FFF8"
+ $"0FFF FFF0 3FFF FFF4 7FFF FFFC 3FFF DFFE"
+ }
+};
+
+resource 'ICN#' (129) {
+ { /* array: 2 elements */
+ /* [1] */
+ $"0000 0000 0000 0000 01FF FF80 0100 00C0"
+ $"0100 00A0 0100 0090 0103 E088 0106 30FC"
+ $"010C 1004 0108 1004 0108 1004 0108 13E4"
+ $"0108 1634 0108 2414 010C 6C14 0107 C814"
+ $"0100 0814 0100 0FE4 0100 1864 0100 1024"
+ $"0100 2024 0100 2024 0100 6064 0100 40C4"
+ $"0100 7F84 0100 0004 0100 0004 0100 0004"
+ $"01FF FFFC",
+ /* [2] */
+ $"0000 0000 0000 0000 01FF FF80 01FF FFC0"
+ $"01FF FFE0 01FF FFF0 01FF FFF8 01FF FFFC"
+ $"01FF FFFC 01FF FFFC 01FF FFFC 01FF FFFC"
+ $"01FF FFFC 01FF FFFC 01FF FFFC 01FF FFFC"
+ $"01FF FFFC 01FF FFFC 01FF FFFC 01FF FFFC"
+ $"01FF FFFC 01FF FFFC 01FF FFFC 01FF FFFC"
+ $"01FF FFFC 01FF FFFC 01FF FFFC 01FF FFFC"
+ $"01FF FFFC"
+ }
+};
+#endif //MKTYPLIB2
+
+
+// version info
+// "MkTypLib App, (c) Microsoft Corp. 1993-1994"
+#define VERSTRINGX(maj,min,rev) STRING(maj ## . ## min ## . ## rev)
+#define VERSTRING VERSTRINGX(rmj,rmm,rup)
+resource 'vers' (1, purgeable) {
+ 0x00,
+ 0x00,
+ development,
+ 0x00,
+ verUS,
+ VERSTRING,
+ VERSTRING,
+};
diff --git a/private/oleauto/src/mktyplib/mktyplib.rc b/private/oleauto/src/mktyplib/mktyplib.rc
new file mode 100644
index 000000000..290af7f94
--- /dev/null
+++ b/private/oleauto/src/mktyplib/mktyplib.rc
@@ -0,0 +1,87 @@
+/***
+*mktyplib.rc - Resource file for MKTYPLIB.EXE
+*
+* Copyright (C) 1992 - 1993, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file is the resource file for MKTYPLIB.EXE.
+*
+*
+*Revision History:
+* [01] 23-Feb-93 dougf: added version resource.
+*
+*****************************************************************************/
+
+/* first include the icon */
+1 ICON "mktyplib.ico"
+
+/* then include all the stuff necessary for proper version information */
+#include <windows.h>
+#ifndef WIN32
+#include <ver.h>
+#endif
+
+#include "verstamp.h"
+
+/* override some stuff in verstamp.h */
+#undef rmj
+#define rmj 2
+#undef rmm
+// want version # to be 2.02.xxx
+#define rmm 02
+
+/* Define the version string with more preprocessor magic */
+#define STRING(x) #x
+#define VERSTRINGX(maj,min,rev) STRING(maj ## . ## min ## . ## rev ## \0)
+#define VERSTRING VERSTRINGX(rmj,rmm,rup)
+
+VS_VERSION_INFO VERSIONINFO
+FILEVERSION rmj,rmm,rup,01
+PRODUCTVERSION rmj,rmm,rup,01
+FILEFLAGSMASK VS_FFI_FILEFLAGSMASK
+
+#if 0
+#define BETAFLAG VS_FF_PRERELEASE
+#else //1
+#define BETAFLAG 0L
+#endif //1
+
+#ifdef _DEBUG
+FILEFLAGS BETAFLAG | VS_FF_DEBUG
+#else
+FILEFLAGS BETAFLAG
+#endif
+
+#ifdef WIN32
+FILEOS VOS_NT_WINDOWS32
+#else //WIN32
+FILEOS VOS_DOS_WINDOWS16
+#endif //WIN32
+
+FILETYPE VFT_APP
+FILESUBTYPE 0
+
+
+BEGIN
+ BLOCK "StringFileInfo"
+ BEGIN
+ BLOCK "040904E4"
+ BEGIN
+ VALUE "CompanyName", "Microsoft Corporation\0"
+ VALUE "FileDescription", "OLE Automation Type Library Generator\0"
+ VALUE "FileVersion", "2.02\0"
+ VALUE "InternalName", "MKTYPLIB.EXE\0"
+ VALUE "LegalCopyright", "Copyright \251 Microsoft Corp. 1992 - 1995\0"
+ VALUE "LegalTrademarks", "Microsoft\256 is a registered trademark of Microsoft Corporation. Windows(TM) is a trademark of Microsoft Corporation.\0"
+ VALUE "ProductName", "Microsoft OLE 2.02 for Windows\0"
+ VALUE "ProductVersion", "2.02\0"
+ VALUE "Comments", "Windows OLE Tools\0"
+ END
+ END
+
+ BLOCK "VarFileInfo"
+ BEGIN
+ VALUE "Translation", 0x409, 1252
+ END
+END
diff --git a/private/oleauto/src/mktyplib/parser.c b/private/oleauto/src/mktyplib/parser.c
new file mode 100644
index 000000000..e1d31587f
--- /dev/null
+++ b/private/oleauto/src/mktyplib/parser.c
@@ -0,0 +1,3218 @@
+#include "mktyplib.h"
+
+#include <stdio.h>
+#include <string.h>
+#include <malloc.h>
+
+#ifndef WIN32
+#include <ole2.h> // required for dispatch.h
+#include <olenls.h> // for CompareStringA
+#include "dispatch.h"
+#endif // WIN32
+
+#include "errors.h"
+#include "tokens.h"
+#include "parser.h"
+#include "fileinfo.h"
+
+// external data:
+extern FILE * hFileInput;
+
+// global variables:
+
+TYPLIB typlib; // main type structure
+TOKEN tok; // current token -- filled in by lexer
+SHORT cArgsMax = 0; // max # of args that any function has
+LCID g_lcidCompare = 0x0409; // lcid for compare purposes
+BOOL fSpecifiedInterCC = FALSE; // TRUE if an interface cc was specified
+
+// private types and data
+typedef enum {
+ FUNC_MODULE = 0,
+ FUNC_DISPINTERFACE,
+ FUNC_INTERFACE,
+ FUNC_OAINTERFACE,
+ C_FUNCTYPES
+} FUNCTYPE;
+
+static DWORD fValidFuncAttrs[C_FUNCTYPES] = {
+ VALID_MODULE_FUNC_ATTR,
+ VALID_DISPINTER_FUNC_ATTR,
+ VALID_INTERFACE_FUNC_ATTR,
+ VALID_INTERFACE_FUNC_ATTR
+};
+static DWORD fValidFuncAttrs2[C_FUNCTYPES] = {
+ VALID_MODULE_FUNC_ATTR2,
+ VALID_DISPINTER_FUNC_ATTR2,
+ VALID_INTERFACE_FUNC_ATTR2,
+ VALID_INTERFACE_FUNC_ATTR2
+};
+static DWORD fValidParmAttrs[C_FUNCTYPES] = {
+ VALID_MODULE_PARM_ATTR,
+ VALID_DISPINTER_PARM_ATTR,
+ VALID_INTERFACE_PARM_ATTR,
+ VALID_INTERFACE_PARM_ATTR
+};
+static DWORD fValidParmAttrs2[C_FUNCTYPES] = {
+ VALID_MODULE_PARM_ATTR2,
+ VALID_DISPINTER_PARM_ATTR2,
+ VALID_INTERFACE_PARM_ATTR2,
+ VALID_INTERFACE_PARM_ATTR2
+};
+
+typedef struct {
+ CHAR * szName;
+ VARTYPE vt;
+} INTRINSIC_DEF;
+
+static INTRINSIC_DEF rgIntrinsics[] = {
+// NOTE: table lookup assumes that unsigned versions follow signed versions
+ "char", VT_I1,
+ "char", VT_UI1,
+ "int", VT_INT,
+ "int", VT_UINT,
+ "short", VT_I2,
+ "short", VT_UI2,
+ "long", VT_I4,
+ "long", VT_UI4,
+ "boolean", VT_BOOL,
+ "double", VT_R8,
+ "float", VT_R4,
+ "CURRENCY", VT_CY,
+ "DATE", VT_DATE,
+ "VARIANT", VT_VARIANT,
+ "void", VT_VOID,
+ "BSTR", VT_BSTR,
+ "HRESULT", VT_HRESULT,
+ "SCODE", VT_ERROR,
+ // LPSTR is handled in InitIntrinsicTypes()
+ // wchar_t and LPWSTR are handled in InitIntrinsicTypes()
+ NULL, 0 // end of list
+};
+
+static LPTYPE lpType_LPSTR;
+static LPTYPE lpType_DISPATCH;
+static LPTYPE lpType_UNKNOWN;
+static LPTYPE lpType_LPWSTR;
+static LPTYPE lpType_wchar_t;
+
+static LPENTRY lpEntryPrev;
+static LPTYPE lpTypeIDispatch = NULL;
+static LPTYPE lpTypeIUnknown = NULL;
+
+// bit flags returned by GetTypeCompatibility
+#define COMPAT_NONE 0 // any old thing
+#define COMPAT_IDISPATCH 1 // IDispatch-compatible types
+#define COMPAT_OA 2 // OA compatible type
+#define COMPAT_DUALBASE 4 // suitable for use as base of a DUAL interface
+
+// bit to mark a type we're checking for OA compatibility as a parameter.
+#define VT_PARAM VT_VECTOR
+
+// external data
+extern SYSKIND SysKind;
+extern DWORD f2DefaultCC;
+
+// external routines
+extern VOID FAR ParseInit(CHAR * szFile);
+extern VOID FAR ConsumeTok(TOKID id, WORD fAccept);
+extern VOID FAR ScanTok(WORD fAccept);
+extern LPVOID FAR ParseMalloc(WORD cbAlloc);
+extern VOID FAR LoadExtTypeLib(LPIMPORTLIB pImpLib);
+extern LPTYPE FAR FindExtType(LPSTR szLibName, LPSTR szTypeName);
+
+// prototypes for exported routines
+VOID FAR ParseOdlFile(CHAR * szFile);
+INT FAR FCmpCaseIns(LPSTR str1, LPSTR str2);
+LPTYPE FAR lpTypePublic(LPTYPE lpType);
+
+// prototypes for internal routines
+VOID NEAR ParseLibrary(VOID);
+VOID NEAR ParseOptAttr(LPATTR pAttr, WORD wContext);
+VOID NEAR ParseNewElem(LPELEM FAR * lplpElem,
+ DWORD validElemAttr,
+ DWORD validElemAttr2,
+ LPTYPE lpType);
+VOID NEAR ParseElem(LPELEM lpElem, WORD fAllow, LPTYPE lpType);
+VOID NEAR ParseStructEnumUnion(LPENTRY lpEntry, TENTRYKIND tentrykind);
+VOID NEAR ParseNewEnumElem(LPELEM FAR * lplpElem, long * pEnumVal);
+VOID NEAR ParseTypedef(LPENTRY lpEntry);
+VOID NEAR ParseAlias(LPENTRY lpEntry);
+LPTYPE NEAR ParseKnownType(LPATTR pAttr, WORD fAllow);
+VOID NEAR ParseElemName(LPELEM lpElem, WORD fAllow);
+VOID NEAR ParseModule(VOID);
+VOID NEAR ParseInterface(VOID);
+VOID NEAR ParseDispinterface(VOID);
+VOID NEAR ParseCoclass(VOID);
+VOID NEAR ParseFunction(LPFUNC lpFunc, FUNCTYPE funcType);
+VOID NEAR ParseProperty_Set(VOID);
+VOID NEAR ParseImportlib(VOID);
+VOID NEAR CheckAttr(LPATTR pAttr, DWORD attrbit, DWORD attrbit2);
+VOID NEAR CheckAttrTokLast(LPATTR pAttr, DWORD attrbit, DWORD attrbit2);
+VOID NEAR GotAttr(LPATTR pAttr, DWORD attrbit);
+VOID NEAR GotAttr2(LPATTR pAttr2, DWORD attrbit2);
+VOID NEAR ConsumeRCurlyOptSemi(WORD fAccept);
+LPSTR NEAR ConsumeId(VOID);
+LPSTR NEAR lpszParseStringExpr();
+DWORD NEAR lParseNumericExpr(VOID);
+DWORD NEAR lParseNumber(VOID);
+VOID NEAR InitIntrinsicTypes(VOID);
+LPTYPE NEAR InitIntrinsic(CHAR * szName, VARTYPE vt);
+LPTYPE NEAR FindTypeArray(LPTYPE lpTypeBase);
+LPTYPE NEAR FindTypeInd(LPTYPE lpTypeBase, short cIndirect);
+LPTYPE NEAR FindType(LPSTR lpszName, BOOL fUnsigned, TENTRYKIND tentrykind);
+VARTYPE NEAR GetStringType(LPTYPE lpTypeBase);
+VOID NEAR EnsureNoDupEntries(LPENTRY lpEntryLast);
+VOID NEAR EnsureNoDupElem(LPELEM lpElemLast);
+BOOL NEAR IsType(LPTYPE lpType, VARTYPE vt);
+BOOL NEAR FHandleForwardDecl(LPENTRY lpEntry, TENTRYKIND tentrykind);
+VOID NEAR CheckForwardMatch(LPENTRY lpEntryLast, LPENTRY lpEntry);
+VOID NEAR InitNewEntry(LPENTRY FAR * lplpEntry);
+VOID NEAR EnsureIDispatchType(LPTYPE lpType);
+VOID NEAR EnsureOAType(LPTYPE lpType, BOOL fParam);
+WORD NEAR GetTypeCompatibility(LPTYPE lpType, WORD fRecurse);
+BOOL NEAR IsObjectType(LPTYPE lpType);
+BOOL NEAR VerifyLcid(LCID lcid);
+VOID NEAR FindIDispatch();
+
+// main parse routine
+VOID FAR ParseOdlFile
+(
+ CHAR * szFile
+)
+{
+
+ ParseInit(szFile);
+
+ ParseLibrary(); // parse library description
+ if (tok.id != RW_EOF)
+ ParseError(PERR_EXP_EOF);
+
+ fclose(hFileInput);
+ hFileInput = NULL; // we've done the close
+}
+
+
+// parse a library clause
+VOID NEAR ParseLibrary
+(
+)
+{
+
+ ParseOptAttr(&typlib.attr, cLIB); // parse attributes, if any
+
+ // ensure attributes valid in this context
+ CheckAttrTokLast(&typlib.attr, VALID_LIBRARY_ATTR, VALID_LIBRARY_ATTR2);
+
+ ConsumeTok(RW_LIBRARY, 0); // consume "library", advance to next token
+
+ // UUID required on type library
+ if (!(typlib.attr.fAttr & fUUID))
+ ParseErrorTokLast(PERR_UUID_REQ);
+
+ typlib.szLibName = ConsumeId(); // get library name
+
+ InitIntrinsicTypes(); // load type list with the intrinisc types
+
+ ConsumeTok(RW_LCURLY, 0);
+
+ // first allow any number of imported libraries
+ while (tok.id == RW_IMPORTLIB)
+ ParseImportlib();
+
+ // then allow the other sections
+ while (tok.id != RW_RCURLY)
+ {
+
+ lpEntryPrev = typlib.pEntry; // save previous entry
+
+ InitNewEntry(&typlib.pEntry); // create & init a new item
+ // in the entry list
+
+ ParseOptAttr(&(typlib.pEntry->attr), cTYPE); // parse attributes, if any
+
+ switch (tok.id)
+ {
+ case RW_TYPEDEF:
+ ParseTypedef(typlib.pEntry);
+ break;
+
+ case RW_MODULE:
+ ParseModule();
+ break;
+
+ case RW_INTERFACE:
+ ParseInterface();
+ break;
+
+ case RW_DISPINTERFACE:
+ ParseDispinterface();
+ break;
+
+ case RW_COCLASS:
+ ParseCoclass();
+ break;
+
+ case RW_IMPORTLIB:
+ ParseError(PERR_IMPLIB_NOTFIRST);
+
+ default:
+ ParseError(PERR_EXP_KEYWORD);
+ } // switch
+
+ } // while library entries
+
+ ConsumeRCurlyOptSemi(fACCEPT_EOF);
+}
+
+
+VOID NEAR InitNewEntry
+(
+ LPENTRY FAR * lplpEntryLast
+)
+{
+ LPENTRY lpEntry;
+
+ // create a new entry in list of entries
+ ListInsert(lplpEntryLast, sizeof(ENTRY));
+
+ lpEntry = *lplpEntryLast; // deref
+
+#ifdef DEBUG
+ // filled in later by the type output code (hopefully before it is used!)
+ lpEntry->lpdtinfo = (ICreateTypeInfo *)0xffffffff;
+#endif //DEBUG
+
+ lpEntry->type.tdesc.vt = VT_USERDEFINED;
+ lpEntry->type.szName = ""; // don't want this type entry to be
+ // found until we're done filling it in.
+ lpEntry->type.lptinfo = NULL;
+ lpEntry->lpEntryForward = NULL; // assume no previous forward decl
+ // for this entry
+
+ lpEntry->attr.fAttr = 0; // no attributes seen yet
+ lpEntry->attr.fAttr2 = 0;
+}
+
+
+// parses optional [<attributes>]
+// initializes 'Attr' structure with current attributes.
+VOID NEAR ParseOptAttr
+(
+ LPATTR pAttr,
+ WORD wContext
+)
+{
+ TOKID attrId;
+ DWORD lTemp;
+
+ pAttr->fAttr = 0; // no attributes seen yet
+ pAttr->fAttr2 = 0;
+ if (tok.id == RW_LBRACKET)
+ {
+ ScanTok(fACCEPT_ATTR); // consume '['
+
+ // keep going until we encounter a right bracket
+ while ((attrId = tok.id) != RW_RBRACKET)
+ {
+ ScanTok(fACCEPT_ATTR); // advance to next token
+ switch (attrId)
+ {
+
+ case ATTR_UUID: // uuid(uuid constant)
+ GotAttr(pAttr, fUUID);
+ ConsumeTok(RW_LPAREN, fACCEPT_UUID);
+ if (tok.id != LIT_UUID)
+ ParseError(PERR_INV_UUID);
+ pAttr->lpUuid = tok.lpUuid;
+ ScanTok(0); // consume UUID
+ ConsumeTok(RW_RPAREN, 0);
+ break;
+
+ case ATTR_LCID: // lcid(I4 lcid)
+ GotAttr(pAttr, fLCID);
+ // LCID attribute allowed on a param, too
+ if (wContext == cPARAM)
+ break;
+ ConsumeTok(RW_LPAREN, fACCEPT_NUMBER);
+ pAttr->lLcid = lParseNumericExpr();
+ // don't change the global if the given lcid==0
+ if (pAttr->lLcid) {
+ // make sure this is a supported lcid
+ if (!VerifyLcid(pAttr->lLcid))
+ ParseError(PERR_INV_LCID);
+ g_lcidCompare = pAttr->lLcid;
+ }
+ ConsumeTok(RW_RPAREN, 0);
+ break;
+
+ case ATTR_VERSION: // version(I2 major.I2 minor)
+ GotAttr(pAttr, fVERSION);
+ ConsumeTok(RW_LPAREN, fACCEPT_NUMBER);
+
+ lTemp = lParseNumericExpr();
+ if (HIWORD(lTemp))
+ ParseError(PERR_NUMBER_OV);
+ pAttr->wVerMajor = LOWORD(lTemp);
+
+ ConsumeTok(RW_PERIOD, fACCEPT_NUMBER);
+
+ lTemp = lParseNumericExpr();
+ if (HIWORD(lTemp))
+ ParseError(PERR_NUMBER_OV);
+ pAttr->wVerMinor = LOWORD(lTemp);
+
+ ConsumeTok(RW_RPAREN, 0);
+ break;
+
+ case ATTR_ENTRY: // entry(proc name/I2 ordinal)
+ ConsumeTok(RW_LPAREN, fACCEPT_NUMBER | fACCEPT_STRING);
+ GotAttr(pAttr, fENTRY);
+ if (tok.id == LIT_STRING)
+ {
+ pAttr->lpszProcName = tok.lpsz;
+ ScanTok(0); // consume entry string
+ }
+ else
+ { // set high word of lpszProcName to 0,
+ // to indicate call-by-ordinal
+ lTemp = lParseNumericExpr();
+ if (HIWORD(lTemp))
+ ParseError(PERR_NUMBER_OV);
+ pAttr->lpszProcName = (LPSTR)lTemp;
+ }
+
+ ConsumeTok(RW_RPAREN, 0);
+ break;
+
+ case ATTR_ID: // id(I4 id num)
+ GotAttr(pAttr, fID);
+ ConsumeTok(RW_LPAREN, fACCEPT_NUMBER);
+ pAttr->lId = lParseNumericExpr();
+
+ // We reserve the top bit for ourselves --
+ // don't let the user pick these id's except for
+ // a few special values like DISPID_NEWENUM (-4)
+ // and DISPID_EVALUATE (-5)
+ // Also allow the special range -999 to -500 for
+ // the controls folks. This range will be
+ // documented as reserved in the next version.
+ // Also allow the special range 0x80010000 to
+ // 0x8001FFFF for Control containers such as VB4.
+
+#ifndef DISPID_COLLECT // temporary until everybody upgrades header files
+#define DISPID_COLLECT (-8)
+#endif
+ // high bit == 1 ==> special negative value
+ // next bit == 1 ==> typelib.dll picked this id
+ // == 0 ==> user picked this id
+ if (pAttr->lId & 0x80000000) {
+ switch ((long)pAttr->lId) {
+ case DISPID_NEWENUM:
+ case DISPID_EVALUATE:
+ case DISPID_CONSTRUCTOR:
+ case DISPID_DESTRUCTOR:
+ case DISPID_COLLECT:
+ break;
+ default:
+ if ((long)pAttr->lId >= -999 &&
+ (long)pAttr->lId <= -500) {
+ break;
+ }
+ if (HIWORD(pAttr->lId) == 0x8001)
+ break;
+ ParseErrorTokLast(PERR_INV_ID);
+ }
+ }
+
+ ConsumeTok(RW_RPAREN, 0);
+ break;
+
+ case ATTR_HELPCONTEXT: // helpcontext(I4 context num)
+ GotAttr(pAttr, fHELPCONTEXT);
+ ConsumeTok(RW_LPAREN, fACCEPT_NUMBER);
+ pAttr->lHelpContext = lParseNumericExpr();
+ ConsumeTok(RW_RPAREN, 0);
+ break;
+
+ case ATTR_DLLNAME: // dllname("dllname string")
+ GotAttr(pAttr, fDLLNAME);
+ ConsumeTok(RW_LPAREN, fACCEPT_STRING);
+ pAttr->lpszDllName = lpszParseStringExpr();
+ ConsumeTok(RW_RPAREN, 0);
+ break;
+
+ case ATTR_HELPFILE: // helpstring("helpfile")
+ GotAttr(pAttr, fHELPFILE);
+ ConsumeTok(RW_LPAREN, fACCEPT_STRING);
+ pAttr->lpszHelpFile = lpszParseStringExpr();
+ ConsumeTok(RW_RPAREN, 0);
+ break;
+
+ case ATTR_HELPSTRING: // helpstring("help string")
+ GotAttr(pAttr, fHELPSTRING);
+ ConsumeTok(RW_LPAREN, fACCEPT_STRING);
+ pAttr->lpszHelpString = lpszParseStringExpr();
+ ConsumeTok(RW_RPAREN, 0);
+ break;
+
+ case ATTR_IN:
+ GotAttr(pAttr, fIN);
+ break;
+
+ case ATTR_OUT:
+ GotAttr(pAttr, fOUT);
+ break;
+
+ case ATTR_ODL:
+ GotAttr(pAttr, fODL);
+ break;
+
+ case ATTR_OPTIONAL:
+ GotAttr(pAttr, fOPTIONAL);
+ break;
+
+ case ATTR_PUBLIC:
+ GotAttr(pAttr, fPUBLIC);
+ break;
+
+ case ATTR_READONLY:
+ GotAttr(pAttr, fREADONLY);
+ break;
+
+ case ATTR_STRING:
+ GotAttr(pAttr, fSTRING);
+ break;
+
+ case ATTR_VARARG:
+ GotAttr(pAttr, fVARARG);
+ break;
+
+ case ATTR_APPOBJECT:
+ GotAttr(pAttr, fAPPOBJECT);
+ break;
+
+ case ATTR_PROPGET:
+ if (pAttr->fAttr & (fPROPPUT | fPROPPUTREF))
+ ParseErrorTokLast(PERR_INV_ATTR_COMBO);
+ GotAttr(pAttr, fPROPGET);
+ break;
+
+ case ATTR_PROPPUT:
+ if (pAttr->fAttr & (fPROPGET | fPROPPUTREF))
+ ParseErrorTokLast(PERR_INV_ATTR_COMBO);
+ GotAttr(pAttr, fPROPPUT);
+ break;
+
+ case ATTR_PROPPUTREF:
+ if (pAttr->fAttr & (fPROPGET | fPROPPUT))
+ ParseErrorTokLast(PERR_INV_ATTR_COMBO);
+ GotAttr(pAttr, fPROPPUTREF);
+ break;
+
+ case ATTR_RESTRICTED:
+ GotAttr(pAttr, fRESTRICTED);
+ break;
+
+ case ATTR_DEFAULT:
+ GotAttr(pAttr, fDEFAULT);
+ break;
+
+ case ATTR_SOURCE:
+ GotAttr(pAttr, fSOURCE);
+ break;
+
+ case ATTR_BINDABLE:
+ GotAttr(pAttr, fBINDABLE);
+ break;
+
+ case ATTR_REQUESTEDIT:
+ GotAttr(pAttr, fREQUESTEDIT);
+ break;
+
+ case ATTR_DISPLAYBIND:
+ GotAttr(pAttr, fDISPLAYBIND);
+ break;
+
+ case ATTR_DEFAULTBIND:
+ GotAttr(pAttr, fDEFAULTBIND);
+ break;
+
+ case ATTR_LICENSED:
+ GotAttr(pAttr, fLICENSED);
+ break;
+
+ case ATTR_PREDECLID:
+ GotAttr(pAttr, fPREDECLID);
+ break;
+
+ case ATTR_HIDDEN:
+ GotAttr(pAttr, fHIDDEN);
+ break;
+
+ case ATTR_RETVAL:
+ GotAttr(pAttr, fRETVAL);
+ break;
+
+ case ATTR_CONTROL:
+ GotAttr2(pAttr, f2CONTROL);
+ break;
+
+ case ATTR_DUAL:
+ GotAttr2(pAttr, f2DUAL);
+ break;
+
+ case ATTR_NONEXTENSIBLE:
+ GotAttr2(pAttr, f2NONEXTENSIBLE);
+ break;
+
+ case ATTR_OLEAUTOMATION:
+ GotAttr2(pAttr, f2OLEAUTOMATION);
+ break;
+
+ case RW_COMMA: // must accept blank attributes
+ continue;
+
+ default:
+ // expected attribute or ']'
+ ParseErrorTokLast(PERR_EXP_ATTRIBUTE);
+ }
+
+ if (tok.id == RW_RBRACKET)
+ break; // all done
+ // eat comma which must separate args
+ ConsumeTok(RW_COMMA, fACCEPT_ATTR);
+
+ } // while
+
+ ScanTok(0); // consume ']'
+
+ // context-insensitive attribute validations can be done here.
+
+ // 'bindable' must also be set if any other data binding attr given
+ if ((pAttr->fAttr &
+ (fREQUESTEDIT | fDISPLAYBIND | fDEFAULTBIND))
+ && !(pAttr->fAttr & fBINDABLE))
+ ParseErrorTokLast(PERR_INV_ATTR_COMBO);
+
+ } // if
+}
+
+// ******************************************************************
+// TYPEDEF-related routines
+// ******************************************************************
+
+VOID NEAR InitIntrinsicTypes()
+{
+ INTRINSIC_DEF * pIntrinsic;
+
+ // load all the intrinsic types into the type structure.
+ for (pIntrinsic = rgIntrinsics; pIntrinsic->szName; pIntrinsic++)
+ {
+ InitIntrinsic(pIntrinsic->szName, pIntrinsic->vt);
+ };
+
+ lpType_LPSTR = InitIntrinsic("LPSTR", VT_LPSTR);
+ lpType_DISPATCH = InitIntrinsic("IDispatch *", VT_DISPATCH);
+ lpType_UNKNOWN = InitIntrinsic("IUnknown *", VT_UNKNOWN);
+ lpType_LPWSTR = InitIntrinsic("LPWSTR", VT_LPWSTR);
+ // UNDONE: what VT_xxx constant to use for 'wchar_t'?
+ lpType_wchar_t = InitIntrinsic("wchar_t", VT_I2);
+}
+
+LPTYPE NEAR InitIntrinsic
+(
+ CHAR * szName,
+ VARTYPE vt
+)
+{
+ // NOTE: only need to allocate space for a TYPE item
+ ListInsert(&typlib.pEntry, sizeof(TYPE));
+ typlib.pEntry->type.szName = szName;
+ typlib.pEntry->type.tdesc.vt = vt;
+ typlib.pEntry->type.tentrykind = tINTRINSIC;
+ typlib.pEntry->type.lptinfo = NULL;
+ typlib.pEntry->type.intr.fUnsigned =
+ (vt == VT_UI1 || vt == VT_UINT ||
+ vt == VT_UI2 || vt == VT_UI4);
+
+ return (LPTYPE)typlib.pEntry;
+}
+
+
+// Start at front of type list, and find base type of the given name
+// (with 0 levels of indirection). Will also find forward declarations.
+LPTYPE NEAR FindType
+(
+ LPSTR lpszName, // name to look for
+ BOOL fUnsigned, // TRUE if unsigned keyword preceeded this
+ TENTRYKIND tentrykind // kind of thing to look for
+)
+{
+ LPTYPE lpTypeLast = (LPTYPE)ListLast(typlib.pEntry);
+ LPTYPE lpType = (LPTYPE)ListFirst(typlib.pEntry);
+
+#pragma warning(disable:4127)
+ while (TRUE)
+#pragma warning(default:4127)
+ {
+ if (tentrykind == tSTRUCT || tentrykind == tUNION)
+ { // if 'struct'/'union' keyword specified, then match tags
+ if ((lpType->tentrykind & ~tFORWARD) == tentrykind
+ && lpType->structenum.szTag
+ && !FCmpCaseIns(lpType->structenum.szTag, lpszName))
+ return lpType; // got a match
+ }
+ else if (lpType->tentrykind != tREF && !(lpType->tentrykind & tQUAL))
+ { // if type definition or intrinsic, check names
+ if (!FCmpCaseIns(lpType->szName, lpszName))
+ // if names match, check that signed/unsigned matches
+ if (fUnsigned == (lpType->tentrykind == tINTRINSIC && lpType->intr.fUnsigned))
+ return lpType; // got a match
+ }
+ if (lpType == lpTypeLast) // if end of list
+ return NULL; // return not found
+ lpType = lpType->pNext; // advance to next type
+ }
+
+}
+
+
+// find existing VT_PTR type entry (with the same base type) with same # of
+// levels of indirection, or create new entry with given indirection level.
+LPTYPE NEAR FindTypeInd
+(
+ LPTYPE lpTypeBase, // * to base type
+ short cIndirect // indirection level to look for
+)
+{
+ LPTYPE lpTypeLast = (LPTYPE)ListLast(typlib.pEntry);
+ LPTYPE lpType;
+ short cIndLast;
+ TYPEDESC FAR * lptdescPrev;
+
+ lpType = lpTypeBase; // start looking at base type
+ cIndLast = 0; // highest indirection level seen so far
+ // point to real tdesc, ignoring non-public typedef's
+ lptdescPrev = &(lpTypePublic(lpType)->tdesc);
+
+#pragma warning(disable:4127)
+ while (TRUE)
+#pragma warning(default:4127)
+ {
+ // check for a reference type with the same base type and same
+ // level of indirection
+ if (lpType->tdesc.vt == VT_PTR && lpType->ref.ptypeBase == lpTypeBase)
+ { // if base types match, check indirection levels
+ if (lpType->ref.cIndirect == cIndirect)
+ // if indirection levels match, we're done
+ return lpType;
+ Assert (lpType->ref.cIndirect > cIndLast);
+ cIndLast = lpType->ref.cIndirect; // save highest
+ // indirection level
+ // can't have a VT_PTR entry that isn't public.
+ Assert(lpTypePublic(lpType) == lpType);
+ lptdescPrev = &(lpType->tdesc);
+ }
+
+ if (lpType == lpTypeLast) // if end of list
+ break; // done -- no match found
+
+ lpType = lpType->pNext; // advance to next type
+ }
+
+ // no entry with same base type & # of levels of indirection, make new
+ // entries up to and including the current level of indirection.
+ for (cIndLast++; cIndLast <= cIndirect; cIndLast++)
+ {
+ // allocate new type list item at end of list
+ // NOTE: only need to allocate space for a TYPE item
+ ListInsert(&typlib.pEntry, sizeof(TYPE));
+
+ // set up info
+ typlib.pEntry->type.tdesc.vt = VT_PTR;
+ typlib.pEntry->type.tdesc.lptdesc = lptdescPrev;
+ lptdescPrev = &(typlib.pEntry->type.tdesc); // ready for next time
+ typlib.pEntry->type.szName = lpTypeBase->szName;
+ typlib.pEntry->type.tentrykind = tREF;
+ typlib.pEntry->type.lptinfo = NULL;
+ //CONSIDER: maybe eliminate ptypeBase now that we have the tdesc field.
+ typlib.pEntry->type.ref.ptypeBase = lpTypeBase;
+ typlib.pEntry->type.ref.cIndirect = cIndLast;
+ }
+
+ return &typlib.pEntry->type;
+}
+
+// find existing VT_SAFEARRAY type entry (with the same base type),
+// create new entry with this base type.
+LPTYPE NEAR FindTypeArray
+(
+ LPTYPE lpTypeBase // * to base type
+)
+{
+ LPTYPE lpTypeLast = (LPTYPE)ListLast(typlib.pEntry);
+ LPTYPE lpType;
+
+ lpType = lpTypeBase; // start looking at base type
+
+#pragma warning(disable:4127)
+ while (TRUE)
+#pragma warning(default:4127)
+ {
+ // check for a reference type with the same base type
+ if (lpType->tdesc.vt == VT_SAFEARRAY && lpType->ref.ptypeBase == lpTypeBase)
+ return lpType;
+
+ if (lpType == lpTypeLast) // if end of list
+ break; // done -- no match found
+
+ lpType = lpType->pNext; // advance to next type
+ }
+
+ // no entry with same base type, make new entry.
+
+ // allocate new type list item at end of list
+ // NOTE: only need to allocate space for a TYPE item
+ ListInsert(&typlib.pEntry, sizeof(TYPE));
+
+ // now create new array reference type
+ typlib.pEntry->type.tdesc.vt = VT_SAFEARRAY;
+
+ // link to real tdesc, ignoring non-public typedef's
+ typlib.pEntry->type.tdesc.lptdesc = &(lpTypePublic(lpTypeBase)->tdesc);
+
+ typlib.pEntry->type.szName = lpTypeBase->szName;
+ typlib.pEntry->type.tentrykind = tREF;
+ typlib.pEntry->type.lptinfo = NULL;
+//CONSIDER: maybe eliminate ptypeBase now that we have the tdesc field.
+ typlib.pEntry->type.ref.ptypeBase = lpTypeBase;
+
+ return &typlib.pEntry->type;
+}
+
+
+//
+// parse a type reference of the form:
+// [unsigned/struct] <name> {[far] *}
+// OR
+// SAFEARRAY(<type reference>) {[far] *}
+//
+// Also ensures that current attributes are valid in this context
+//
+LPTYPE NEAR ParseKnownType
+(
+ LPATTR pAttr,
+ WORD fAllow
+)
+{
+ short cIndirect = 0;
+ LPSTR szTypeName;
+ LPSTR szLibName = NULL;
+ LPTYPE lpType;
+ LPTYPE lpTypeBase = NULL;
+ BOOL fUnsigned = FALSE;
+ TENTRYKIND tMatchTag = tANY;
+ BOOL fFar;
+
+ if ((fAllow & fAllowSAFEARRAY) && tok.id == RW_SAFEARRAY)
+ {
+ ScanTok(0); // consume "SAFEARRAY"
+ ConsumeTok(RW_LPAREN, 0);
+ lpTypeBase = ParseKnownType(pAttr, fAllow);
+
+ if (IsType(lpTypeBase, VT_VOID)) // 'void' is no good here
+ ParseErrorTokLast(PERR_VOID_INV);
+
+ ConsumeTok(RW_RPAREN, 0);
+
+ // Now find an existing type entry that's a safearry with this
+ // base type, or create a new one if not found.
+ lpTypeBase = FindTypeArray(lpTypeBase);
+ Assert (lpTypeBase != NULL);
+ }
+ else
+ { // not a safearray
+
+ switch (tok.id)
+ {
+ // type of the form: unsigned [int, char, long, short]
+ case RW_UNSIGNED:
+ fUnsigned = TRUE;
+ goto consumeit;
+
+ // type of the form: struct <structtag>
+ case RW_STRUCT:
+ tMatchTag = tSTRUCT;
+ goto consumeit;
+
+ // type of the form: union <uniontag>
+ case RW_UNION:
+ tMatchTag = tUNION;
+consumeit:
+ ScanTok(0); // consume "unsigned"/"struct"/"union"
+
+ default:
+ ;
+ }
+
+ // get/consume typename/libraryname/tagname
+ szTypeName = ConsumeId();
+
+ if (!fUnsigned && tMatchTag == tANY && tok.id == RW_PERIOD)
+ { // if library.typename syntax
+ ScanTok(0); // consume "."
+ szLibName = szTypeName; // first id is really a lib name
+ szTypeName = ConsumeId(); // get/consume type name
+ }
+ }
+
+ // handle indirection (as many "[far] *" as are present)
+ while ((fFar = (tok.id == RW_FAR)) || tok.id == RW_POINTER)
+ {
+ cIndirect++; // one more level of indirection
+
+ ScanTok(0); // consume "*" or "far"
+
+ if (fFar) // if "far" specified, then "*" must follow
+ ConsumeTok(RW_POINTER, 0);
+
+ // CONSIDER: impose a limit on # of levels of indirection???
+ }
+
+ if (lpTypeBase == NULL) // if not a SAFEARRAY
+ {
+ // CONSIDER: (size) tQUAL entries won't get re-used
+ if (szLibName)
+ { // reference to type in a specific external type library
+ Assert(fUnsigned == FALSE);
+ Assert(tMatchTag == tANY);
+ lpTypeBase = FindExtType(szLibName, szTypeName);
+ _ffree(szLibName); // done with library name
+ }
+ else if (tMatchTag != tANY)
+ { // we're to match tag instead of name
+ Assert(szLibName == NULL);
+ Assert(fUnsigned == FALSE);
+ lpTypeBase = FindType(szTypeName, fUnsigned, tMatchTag);
+ }
+ else
+ {
+ // First perform any some special mappings before looking
+ // through all the existing types.
+ if (cIndirect)
+ {
+ // map IDispatch * to VT_DISPATCH
+ if (!FCmpCaseIns(szTypeName, "IDispatch"))
+ {
+ lpTypeBase = lpType_DISPATCH;
+ cIndirect--; // ignore the last *
+ goto FoundBaseType;
+ }
+ // map IUnknown * to VT_UNKNOWN
+ if (!FCmpCaseIns(szTypeName, "IUnknown"))
+ {
+ lpTypeBase = lpType_UNKNOWN;
+ cIndirect--; // ignore the last *
+ goto FoundBaseType;
+ }
+ }
+ // find existing type of this name with 0 levels of
+ // indirection
+ lpTypeBase = FindType(szTypeName, fUnsigned, tANY);
+
+ // if not found here, then search all external type
+ // libraries for this type definition.
+ if (lpTypeBase == NULL && !fUnsigned)
+ lpTypeBase = FindExtType(NULL, szTypeName);
+ }
+
+ if (lpTypeBase == NULL) // error if still not found
+ ParseErrorTokLast(PERR_UNKNOWN_TYPE);
+
+FoundBaseType:
+ _ffree(szTypeName); // done with type name
+ }
+
+ lpType = lpTypeBase;
+ // find existing type entry with same # of levels of indirection
+ // or create new entry with given indirection level.
+ if (cIndirect != 0)
+ lpType = FindTypeInd(lpTypeBase, cIndirect);
+
+ Assert (lpType != NULL);
+
+ // If ensure the base type of this item makes sense in this context.
+ // Typelib.dll isn't very good about catching all the errors.
+ while (lpTypeBase->tentrykind == tTYPEDEF)
+ lpTypeBase = lpTypeBase->td.ptypeAlias;
+
+ switch(lpTypeBase->tentrykind & ~(tFORWARD | tIMPORTED | tQUAL)) {
+ case tINTERFACE:
+ case tDISPINTER:
+ case tCOCLASS:
+ if (cIndirect == 0 && (fAllow & fAllowInter) == 0) {
+ // interface with no indirection -- give error
+ ParseErrorTokLast(PERR_INV_REFERENCE);
+ }
+ break;
+
+ case tMODULE:
+ if ((fAllow & fAllowMODULE) == 0) {
+ // references to module -- no good in most places
+ ParseErrorTokLast(PERR_INV_REFERENCE);
+ }
+ break;
+
+ default:
+ break; // ok
+ }
+
+ // NOTE: for MIDL compatiblity, we accept the 'string' attribute on
+ // types that mean 'char *'. We translate those type references to
+ // the intrinisc type 'LPSTR' (even in the header file).
+ // We first must validate that if 'string' is specified, then the type of
+ // the data is really a 'char *'. For types defined in external type
+ // libraries, we just accept whatever string attribute the user specified,
+ // since we can't easily check to see if it is valid. The entry in the
+ // imported type library should already be a VT_LPSTR or a VT_LPWSTR in
+ // that case anyway.
+
+ if (pAttr->fAttr & fSTRING) {
+
+ // try to figure out if it's really a string (char * or wchar_t *)
+ lpTypeBase = lpType;
+ while (lpTypeBase->tentrykind == tTYPEDEF)
+ lpTypeBase = lpTypeBase->td.ptypeAlias;
+
+ if (!(lpTypeBase->tentrykind & tIMPORTED)
+ && lpTypeBase->tdesc.vt != VT_LPSTR
+ && lpTypeBase->tdesc.vt != VT_LPWSTR
+ )
+ { // if not already a string, or an imported type -- it had
+ // better equate to "char *"
+ switch(GetStringType(lpTypeBase)) {
+ case VT_LPSTR:
+ return lpType_LPSTR;
+ case VT_LPWSTR:
+ return lpType_LPWSTR;
+ default:
+ // 'string' attr set but not char * or wchar_t *
+ ParseErrorTokLast(PERR_INV_COMBO);
+ }
+ }
+ }
+
+ return lpType;
+}
+
+
+/* returns the appropriate string type that this is, or VT_EMPTY if not a
+ string */
+VARTYPE NEAR GetStringType(LPTYPE lpTypeBase)
+{
+ if (lpTypeBase->tdesc.vt == VT_PTR && lpTypeBase->ref.cIndirect == 1) {
+ lpTypeBase = lpTypeBase->ref.ptypeBase;
+ while (lpTypeBase->tentrykind == tTYPEDEF)
+ lpTypeBase = lpTypeBase->td.ptypeAlias;
+
+ if (lpTypeBase->tentrykind == tINTRINSIC)
+ switch (lpTypeBase->tdesc.vt)
+ {
+// UNDONE: does MIDL have wchar_t???
+ // UNDONE; what VT_xxx to use here? If
+ // separate, then we can rip the 'if' stmt.
+ // and lpType_wchar_t
+ case VT_I2: // wchar_t
+ if (lpTypeBase != lpType_wchar_t)
+ break;
+ return VT_LPWSTR;
+ case VT_I1:
+ return VT_LPSTR;
+
+ default:
+ break;
+ }
+ }
+ return VT_EMPTY; // not a string
+}
+
+// parse an element name (property, struct elem, function parm, etc, handling
+// array references)
+VOID NEAR ParseElemName
+(
+ LPELEM lpElem,
+ WORD fAllow
+)
+{
+ ARRAYDESC FAR * lpAD;
+ WORD cDims;
+ DWORD cElems;
+
+ lpElem->szElemName = ConsumeId(); // get/consume/store elem name
+
+ if ((fAllow & fAllowCARRAY) && tok.id == RW_LBRACKET)
+ {
+
+#define MAX_DIMS 64 // arbitrary max # of dimensions
+
+ // allocate & load the array descriptor
+ lpAD = (ARRAYDESC FAR *)ParseMalloc(sizeof(ARRAYDESC) + ((MAX_DIMS-1) * sizeof(SAFEARRAYBOUND)));
+ cDims = 0;
+ while (tok.id == RW_LBRACKET)
+ {
+ if (cDims >= MAX_DIMS)
+ ParseError(PERR_INV_ARRAY_DECL);
+
+ ScanTok(fACCEPT_NUMBER); // consume "["
+
+ lpAD->rgbounds[cDims].lLbound = 0; // lbound always 0
+#if 0 // arrays of the form "a[]" aren't supported
+ if (cDims == 0 && tok.id == RW_RBRACKET)
+ { // array of the form "x[] or x[][2]"
+ // UN_DONE: verify that this is right
+ lpAD->rgbounds[cDims].cElements = 0;
+ }
+ else
+#endif
+ {
+ cElems = lParseNumericExpr();
+ if (cElems == 0)
+ ParseError(PERR_INV_ARRAY_DECL);
+ lpAD->rgbounds[cDims].cElements = cElems;
+ }
+ cDims++; // one more dimension
+ ConsumeTok(RW_RBRACKET, 0); // consume "]"
+ }
+ lpAD->cDims = cDims;
+
+ // get real tdesc, ignoring non-public typedef's
+ lpAD->tdescElem = lpTypePublic(lpElem->elemType)->tdesc;
+
+ // allocate new type list item at end of list
+ // NOTE: only need to allocate space for a TYPE item
+ ListInsert(&typlib.pEntry, sizeof(TYPE));
+
+ // now create new array reference type
+ typlib.pEntry->type.tdesc.vt = VT_CARRAY;
+ typlib.pEntry->type.tdesc.lpadesc = lpAD;
+ typlib.pEntry->type.szName = lpElem->elemType->szName;
+ typlib.pEntry->type.tentrykind = tREF;
+ typlib.pEntry->type.lptinfo = NULL;
+ //CONSIDER: maybe eliminate ptypeBase now that we have tdesc.
+ typlib.pEntry->type.ref.ptypeBase = lpElem->elemType;
+
+ // change type to point to this new type
+ lpElem->elemType = (LPTYPE)typlib.pEntry;
+ }
+
+}
+
+
+// ensure last element in element list isn't duplicated
+// or is in some way inconsistent with other elements
+VOID NEAR EnsureNoDupElem
+(
+ LPELEM lpElemLast
+)
+{
+ LPELEM lpElem;
+ LPSTR szElemLast = lpElemLast->szElemName;
+ BOOL fIdLast = ((lpElemLast->attr.fAttr & fID) != 0);
+ DWORD idElemLast = lpElemLast->attr.lId;
+ DWORD propBitsLast = (lpElemLast->attr.fAttr & fPropBits);
+ DWORD propFuncBitsLast = (lpElemLast->attr.fAttr & (fPropFuncBits | fRESTRICTED));
+ DWORD propBitsCur;
+ BOOL fDefaultBindLast = ((lpElemLast->attr.fAttr & fDEFAULTBIND) != 0);
+
+ for (lpElem = (LPELEM)ListFirst(lpElemLast); lpElem != lpElemLast; lpElem = lpElem->pNext)
+ {
+ // ensure names not duplicated in this element list
+ if (!FCmpCaseIns(szElemLast, lpElem->szElemName))
+ { // names match
+ // if names match, reject this if they have the same
+ // propget/put/putref bits (or one of them doesn't have
+ // a property bit set).
+ propBitsCur = (lpElem->attr.fAttr & fPropBits);
+ if (!propBitsLast || !propBitsCur || propBitsLast == propBitsCur)
+ ParseErrorTokLast(PERR_DUP_DEF);
+
+ // better both have the same id, if specified
+ if ( (fIdLast != ((lpElem->attr.fAttr & fID) != 0)) ||
+ (fIdLast && idElemLast != lpElem->attr.lId) )
+ ParseErrorTokLast(PERR_DUP_DEF);
+
+ // better have the same attributes
+ if ((lpElem->attr.fAttr & (fPropFuncBits | fRESTRICTED)) != propFuncBitsLast) {
+ ParseErrorTokLast(PERR_DUP_DEF);
+ }
+ }
+ else
+ { // names don't match
+ // better not both have the same id
+ if (fIdLast && (lpElem->attr.fAttr & fID))
+ if (idElemLast == lpElem->attr.lId)
+ ParseErrorTokLast(PERR_DUP_ID);
+
+ // better not both be marked as 'defaultbind'
+ if (fDefaultBindLast && (lpElem->attr.fAttr & fDEFAULTBIND))
+ ParseErrorTokLast(PERR_DUP_DEF);
+ }
+ }
+}
+
+// add and parse a new element to a list of elements.
+// if lpType is non-null, disallows elements of this type.
+// Assumes that the element can handle Array types.
+VOID NEAR ParseNewElem
+(
+ LPELEM FAR * lplpElem,
+ DWORD validElemAttr,
+ DWORD validElemAttr2,
+ LPTYPE lpType
+)
+{
+ LPELEM lpElem;
+
+ ListInsert(lplpElem, sizeof(ELEM)); // allocate new list item
+ lpElem = *lplpElem;
+
+ ParseOptAttr(&lpElem->attr, cVAR); // parse attributes, if any
+
+ CheckAttr(&lpElem->attr, validElemAttr, validElemAttr2);
+
+ ParseElem(lpElem, fAllowArray, lpType);
+}
+
+
+VOID NEAR ParseElem
+(
+ LPELEM lpElem,
+ WORD fAllow,
+ LPTYPE lpType
+)
+{
+ // parse element type
+ lpElem->elemType = ParseKnownType(&lpElem->attr, fAllow);
+ Assert(lpElem->elemType);
+
+ if (IsType(lpElem->elemType, VT_VOID)) // 'void' is no good here
+ ParseErrorTokLast(PERR_VOID_INV);
+
+ // disallow self-referencing types (not including pointers to those types)
+ // CONSIDER: This check isn't sufficient now that we have forward declares:
+ // CONSIDER: typedef struct foo;
+ // CONSIDER: typedef struct foo {
+ // CONSIDER: struct foo bar; // makes it by this check
+ // CONSIDER: } str;
+ // CONSIDER: The error DOES get caught during LayOut(), but it would be
+ // CONSIDER: nicer to catch it sooner if we could. The correct check is
+ // CONSIDER: is to disallow any non-pointer to a forward declare for which
+ // CONSIDER: there is no real definition.
+ if (lpElem->elemType == lpType)
+ ParseErrorTokLast(PERR_UNKNOWN_TYPE);
+
+ // parse element name, allowing arrays where appropriate
+ ParseElemName(lpElem, fAllow);
+
+ EnsureNoDupElem(lpElem); // ensure no duplicate elements now
+
+}
+
+
+
+// given a type, returns a pointer to the underlying public type.
+// This is used to ignore non-public Typedef's where desired.
+// Any typedef with an attribute is considered to be public.
+LPTYPE FAR lpTypePublic
+(
+ LPTYPE lpType
+)
+{
+ while (lpType->tentrykind == tTYPEDEF
+ && (((LPENTRY)lpType)->attr.fAttr) == 0
+ && (((LPENTRY)lpType)->attr.fAttr2) == 0)
+ lpType = lpType->td.ptypeAlias;
+
+ return lpType;
+}
+
+
+// Handle forward declarations. Ensures that there isn't already a "real"
+// definition before this definiton. Then updates the name/tag in the type
+// structure, and sees if this is a forward definition (<name> followed by ';')
+// returns TRUE if this is a forward declaration, FALSE otherwise.
+BOOL NEAR FHandleForwardDecl
+(
+ LPENTRY lpEntry,
+ TENTRYKIND tentrykind
+)
+{
+ LPSTR lpszName;
+ LPENTRY pEntryForward = NULL;
+
+ lpEntry->type.tentrykind = tentrykind; // store information in record
+ lpszName = ConsumeId(); // get/consume interface/tag name
+
+ Assert (lpEntry->lpEntryForward == NULL); // caller should have zero'ed
+
+ // find a previous forward declaration, if any
+ if ((pEntryForward = (LPENTRY)FindType(lpszName, FALSE, tentrykind)) != NULL)
+ {
+ // no good if entry found isn't a forward declaration
+ if ((pEntryForward->type.tentrykind & tFORWARD) == 0)
+ ParseError(PERR_DUP_DEF);
+ lpEntry->lpEntryForward = pEntryForward; // save * to forward
+ // declaration
+ pEntryForward->lpEntryForward = lpEntry; // also save pointer
+ // from forward decl
+ // back to real entry
+ }
+
+ if (tentrykind == tSTRUCT || tentrykind == tENUM || tentrykind == tUNION)
+ lpEntry->type.structenum.szTag = lpszName; // store tag name
+ else
+ lpEntry->type.szName = lpszName; // store interface name
+
+ // important to actually store szTag now, so that we can match type
+ // references of the form "struct tagname" from within the struct.
+ // (and from later references if this is a forward declaration).
+
+ // see if this a forward declaration
+ // NOTE: we don't support forward declares of enums, because there is
+ // no syntax that works for referencing them.
+ if (tentrykind != tENUM && tok.id == RW_SEMI)
+ {
+ //can't have any attributes on forward declarations.
+ if (lpEntry->attr.fAttr || lpEntry->attr.fAttr2)
+ ParseError(PERR_INV_ATTR); //CONSIDER: better error?
+
+ // mark this as a forward declaration and quit. We'll fill
+ // in the rest of the info later when we get the real def.
+ lpEntry->type.tentrykind |= tFORWARD;
+ ScanTok(0); // consume the semicolon
+
+ EnsureNoDupEntries(lpEntry); // check for dup def
+
+ return TRUE;
+ }
+ return FALSE;
+}
+// end common code
+
+
+// parses a TypeDef section (3 forms)
+VOID NEAR ParseTypedef
+(
+ LPENTRY lpEntry
+)
+{
+
+ // attributes must follow 'typedef' keyword for MIDL compatibility
+ if (lpEntry->attr.fAttr || lpEntry->attr.fAttr2)
+ ParseErrorTokLast(PERR_TYPEDEF_ATTR);
+
+ Assert(tok.id == RW_TYPEDEF);
+ ScanTok(0); // consume "TypeDef", advance to next token
+
+ ParseOptAttr(&(lpEntry->attr), cTYPE); // parse attrs, if any
+
+ switch (tok.id)
+ {
+ case RW_ENUM:
+ ParseStructEnumUnion(lpEntry, tENUM);
+ break;
+
+ case RW_STRUCT:
+ ParseStructEnumUnion(lpEntry, tSTRUCT);
+ break;
+
+ case RW_UNION:
+ ParseStructEnumUnion(lpEntry, tUNION);
+ break;
+
+ default: // a regular typedef
+ ParseAlias(lpEntry);
+ break;
+ }
+}
+
+
+
+
+// parse typedef <basename> <aliasname>;
+VOID NEAR ParseAlias
+(
+ LPENTRY lpEntry
+)
+{
+ lpEntry->type.tentrykind = tTYPEDEF;
+
+ // ensure attributes valid in this context
+ CheckAttr(&lpEntry->attr, VALID_TYPEDEF_ATTR, VALID_TYPEDEF_ATTR2);
+
+ // parse base type
+ lpEntry->type.td.ptypeAlias = ParseKnownType(&lpEntry->attr,
+ fAllowInter |
+ fAllowMODULE);
+
+ lpEntry->type.szName = ConsumeId(); // get/consume type name
+
+ EnsureNoDupEntries(lpEntry); // check for dup def
+
+ ConsumeTok(RW_SEMI, 0); // ends with a semicolon
+}
+
+
+// ParseStructEnumUnion()
+// parses:
+// typedef struct/enum/union [tagname] { <items> } <name>;
+// typedef struct tagname; // forward declare of a struct
+// typedef union tagname; // forward declare of a union
+// doesn't support the following syntax:
+// typedef struct/enum/union tagname typedefname;
+VOID NEAR ParseStructEnumUnion
+(
+ LPENTRY lpEntry,
+ TENTRYKIND tentrykind
+)
+{
+ long EnumVal = -1L; // enums start at 0 by default
+
+ // ensure attributes valid in this context
+ CheckAttrTokLast(&lpEntry->attr,
+ VALID_STRUCT_ENUM_UNION_ATTR,
+ VALID_STRUCT_ENUM_UNION_ATTR2);
+
+ ScanTok(0); // consume "struct/enum/union"
+
+ lpEntry->type.tentrykind = tentrykind;
+ lpEntry->type.structenum.elemList = NULL; // no struct/enum/union elements
+ lpEntry->type.structenum.szTag = NULL; // assume no tag name
+
+ if (tok.id == LIT_ID) // if got an (optional) tag name
+ {
+ // Note -- we allow forward declares of structs, enums, & unions
+ if (FHandleForwardDecl(lpEntry, tentrykind))
+ return; // if THIS is a forward decl
+ }
+
+ ConsumeTok(RW_LCURLY, 0);
+
+ if (tentrykind == tENUM)
+ {
+ // parse first enum item
+ ParseNewEnumElem(&lpEntry->type.structenum.elemList, &EnumVal);
+ while (tok.id == RW_COMMA) // enum items are comma-separated
+ {
+ ScanTok(0); // consume the comma
+ if (tok.id == RW_RCURLY) // OK to end in a comma
+ break;
+ ParseNewEnumElem(&lpEntry->type.structenum.elemList, &EnumVal);
+ }
+ }
+ else // a struct or a union
+ {
+ do
+ {
+ ParseNewElem(&lpEntry->type.structenum.elemList,
+ VALID_STRUCT_UNION_ELEM_ATTR,
+ VALID_STRUCT_UNION_ELEM_ATTR2,
+ &(lpEntry->type));
+ ConsumeTok(RW_SEMI, 0); // ends with a semicolon
+ } while (tok.id != RW_RCURLY);
+ }
+
+ ConsumeTok(RW_RCURLY, 0); // advance to struct/enum/union name
+
+ lpEntry->type.szName = ConsumeId(); // get/consume type name
+
+ EnsureNoDupEntries(lpEntry); // check for dup def
+
+ ConsumeTok(RW_SEMI, 0); // ends with a semicolon
+}
+
+
+VOID NEAR ParseNewEnumElem
+(
+ LPELEM FAR * lplpElem,
+ long * pEnumVal
+)
+{
+ long enumVal;
+ LPELEM lpElem;
+ VARIANT FAR * lpElemVal;
+
+ ListInsert(lplpElem, sizeof(ELEM));
+ lpElem = *lplpElem;
+
+ ParseOptAttr(&lpElem->attr, cVAR); // parse attributes, if any
+ // ensure attributes valid in this context
+ CheckAttrTokLast(&lpElem->attr,
+ VALID_ENUM_ELEM_ATTR,
+ VALID_ENUM_ELEM_ATTR2);
+
+ ParseElemName(lpElem, 0); // parse enum element name
+
+ if (tok.id == RW_ASSIGN) // got a value
+ {
+ ScanTok(fACCEPT_NUMBER);
+ enumVal = (long)lParseNumericExpr(); // enum's are signed
+ // enums in win16 must be in the range of an I2.
+ if (SysKind == SYS_WIN16 && (enumVal > 32767L || enumVal < -32768L))
+ ParseErrorTokLast(PERR_NUMBER_OV);
+ *pEnumVal = enumVal; // update current value
+ lpElem->attr.fAttr2 |= f2GotConstVal; // value explictly
+ // specified
+ }
+ else
+ {
+ enumVal = ++(*pEnumVal); // one more than the last one
+ // if we just overflowed then give error
+ if (SysKind == SYS_WIN16) {
+ if (enumVal == 32768L)
+ ParseErrorTokLast(PERR_NUMBER_OV);
+ } else if (enumVal == 0x80000000L)
+ ParseErrorTokLast(PERR_NUMBER_OV);
+ }
+
+ // now create a variant that contains the value (typlib generator
+ // needs it in the form of a variant).
+ lpElemVal = (VARIANT FAR *)ParseMalloc(sizeof(VARIANT));
+ lpElem->lpElemVal = lpElemVal;
+
+#ifdef DEBUG
+ lpElem->elemType = NULL; // not referenced -- element type is INT.
+#endif
+
+ // type of an enum element's value is I2 in WIN16 typelibs, I4 otherwise
+ // can't just always set lVal field, due to MAC byte-swapping issues
+ if (SysKind == SYS_WIN16)
+ {
+ lpElemVal->vt = VT_I2;
+ lpElemVal->iVal = LOWORD(enumVal);
+ }
+ else
+ {
+ lpElemVal->vt = VT_I4;
+ lpElemVal->lVal = enumVal;
+ }
+ EnsureNoDupElem(lpElem); // ensure no duplicate elements now
+}
+
+
+VOID NEAR ParseConstant
+(
+ LPELEM lpElem
+)
+{
+
+ LPTYPE lpType;
+ long constVal;
+ WORD vt;
+ LPSTR lpszConstVal;
+ WORD cbszConstVal;
+ BSTR bstrVal;
+
+ // ensure attributes valid in this context
+ CheckAttrTokLast(&lpElem->attr,
+ VALID_MODULE_CONST_ATTR,
+ VALID_MODULE_CONST_ATTR2);
+
+ ParseElem(lpElem, 0, NULL);
+
+ // get the type the user said this is.
+ lpType = lpElem->elemType;
+ while (lpType->tentrykind == tTYPEDEF)
+ lpType = lpType->td.ptypeAlias;
+
+ // we don't support constants of external types
+ if (lpType->tentrykind & tIMPORTED)
+ ParseError(PERR_INV_CONSTANT);
+
+ // CONSIDER: (V2) enhance this to accept date constants. Others?
+ ConsumeTok(RW_ASSIGN, fACCEPT_NUMBER | fACCEPT_STRING);
+ if (tok.id == LIT_STRING) {
+ lpszConstVal = tok.lpsz; // save * to string constant
+ cbszConstVal = tok.cbsz; // save string length (not including null)
+ ScanTok(0); // consume entry string
+ constVal = 0; // in case of error
+ } else {
+ constVal = (long)lParseNumericExpr();
+ lpszConstVal = NULL; // not a string
+ }
+
+ // now create a variant that contains the value (typlib generator
+ // needs it in the form of a variant).
+ lpElem->lpElemVal = (VARIANT FAR *)ParseMalloc(sizeof(VARIANT));
+ lpElem->attr.fAttr2 |= f2GotConstVal; // value explictly specified
+
+ // valididate that the type the user says is compatible with the
+ // type of the constant's value.
+
+ vt = VT_I2; // assume variant value is tagged as an I2.
+ // the only variant value tags currently supported are
+ // VT_I2, VT_I4, VT_BOOL, and VT_ERROR.
+ switch (lpType->tdesc.vt)
+ {
+ case VT_I1:
+ if (constVal < -128 || constVal > 127)
+ ParseErrorTokLast(PERR_NUMBER_OV);
+ break;
+ case VT_UI1:
+ if ((DWORD)constVal > 255)
+ ParseErrorTokLast(PERR_NUMBER_OV);
+ break;
+
+ case VT_INT:
+ if (SysKind != SYS_WIN16)
+ goto GotI4; // it's an I4
+
+ case VT_BOOL:
+ vt = VT_BOOL;
+
+ case VT_I2:
+ if (constVal < -32768 || constVal > 32767)
+ ParseErrorTokLast(PERR_NUMBER_OV);
+ break;
+
+ case VT_UINT:
+ if (SysKind != SYS_WIN16)
+ goto GotI4; // it's an unsigned I4 -- no overflow
+
+ case VT_UI2:
+ if ((DWORD)constVal > 65535L)
+ ParseErrorTokLast(PERR_NUMBER_OV);
+ break;
+
+ case VT_I4: // no overflow possible
+ case VT_UI4:
+GotI4:
+ vt = VT_I4; // it's an I4
+ break;
+
+ case VT_ERROR:
+ vt = VT_ERROR; // VT_ERROR is a valid variant tag
+ break;
+
+ case VT_LPSTR:
+ vt = VT_BSTR;
+ break;
+
+#if 0
+ case VT_LPWSTR: // CONSIDER: allow unicode string literals?
+ vt = VT_BSTR;
+ break;
+#endif //0
+
+ case VT_PTR: // ensure "char *"
+ // CONSIDER: allow wchar_t *, too?
+ if (GetStringType(lpType) == VT_LPSTR) {
+ vt = VT_BSTR;
+ break;
+ }
+ // fall through to give error
+
+ // CONSIDER: (V2) enhance this to support constants of other
+ // CONSIDER: (V2) intrinsic types
+ default:
+ ParseError(PERR_INV_CONSTANT);
+ }
+ lpElem->lpElemVal->vt = vt; // store tag
+
+ if (vt == VT_BSTR) {
+ if (lpszConstVal == NULL)
+ ParseError(PERR_EXP_STRING);
+#ifdef WIN32
+ bstrVal = SysAllocStringLen(NULL, cbszConstVal);
+ if (cbszConstVal) {
+ SideAssert (MultiByteToWideChar(CP_ACP,
+ MB_PRECOMPOSED,
+ lpszConstVal,
+ cbszConstVal,
+ bstrVal,
+ cbszConstVal) != 0);
+ }
+#else //WIN32
+ bstrVal = SysAllocStringLen(lpszConstVal, cbszConstVal);
+#endif //WIN32
+
+ if (bstrVal == NULL && cbszConstVal != 0)
+ ParseError(ERR_OM);
+ lpElem->lpElemVal->bstrVal = bstrVal;
+ } else {
+ if (lpszConstVal != NULL)
+ ParseError(PERR_EXP_NUMBER);
+#ifdef MAC
+ // can't just always set lVal field, due to MAC byte-swapping issues
+ if (vt == VT_I2 || vt == VT_BOOL)
+ lpElem->lpElemVal->iVal = LOWORD(constVal); // store data
+ else
+#endif //MAC
+ lpElem->lpElemVal->lVal = constVal; // store data
+ }
+
+ ConsumeTok(RW_SEMI, 0); // ends with a semicolon
+
+}
+
+// ******************************************************************
+// FUNCTION-related routines
+// ******************************************************************
+
+VOID NEAR ParseFunction
+(
+ LPFUNC lpFunc, // pointer to where to put this function's info
+ FUNCTYPE funcType
+)
+{
+ ATTR attr; // local attribute buffer
+ SHORT cArgs; // # of args for this function
+ SHORT cOptArgs; // # of optional args for this function
+ LPTYPE lpArgType;
+ LPTYPE lpArgTypeLast;
+ LPTYPE lpTypeRetVal;
+ LPSTR szFuncName;
+ LPTYPE lpTypeBase;
+ DWORD IDLFlagsSeen;
+ DWORD IDLFlagsCur;
+ SHORT cNeedRHS;
+
+ // if 'bindable' attr specified, must be a property function
+ if ((lpFunc->func.attr.fAttr & fBINDABLE)
+ && !(lpFunc->func.attr.fAttr & fPropBits))
+ ParseErrorTokLast(PERR_INV_ATTR_COMBO);
+
+ // ensure attributes valid in this context
+ CheckAttr(&lpFunc->func.attr,
+ fValidFuncAttrs[funcType],
+ fValidFuncAttrs2[funcType]);
+
+ // parse function return type
+ lpFunc->func.elemType = ParseKnownType(&lpFunc->func.attr,
+ fAllowSAFEARRAY);
+
+ lpTypeRetVal = lpFunc->func.elemType; // store in case no retval parm
+
+ // if PROPGET specified, return type cannot be VOID
+ if ((lpFunc->func.attr.fAttr & fPROPGET)
+ && IsType(lpTypeRetVal, VT_VOID))
+ ParseErrorTokLast(PERR_INV_PROPFUNC);
+
+ if (!IsType(lpTypeRetVal, VT_VOID)) {
+ // special case of VOID return type -- allowed everywhere
+ if (!IsType(lpTypeRetVal, VT_HRESULT)) {
+ // if PROPPUT or PROPPUTREF specified, return type must be VOID/HRESULT
+ if (lpFunc->func.attr.fAttr & (fPROPPUT | fPROPPUTREF))
+ ParseErrorTokLast(PERR_INV_PROPFUNC);
+
+ // OA functions must return either VOID or HRESULT.
+ if (funcType == FUNC_OAINTERFACE)
+ ParseErrorTokLast(PERR_INV_OA_FUNC_TYPE);
+ }
+ // ensure return type is a valid IDispatch/OA type
+ if (funcType == FUNC_DISPINTERFACE)
+ EnsureIDispatchType(lpTypeRetVal);
+ }
+
+ // parse optional "far"
+ if (tok.id == RW_FAR)
+ ScanTok(0); // consume far or _far if present
+
+ // parse optional calling convention.
+ switch (tok.id)
+ {
+ case RW_CDECL: // cdecl, _cdecl or __cdecl
+ lpFunc->func.attr.fAttr2 |= f2CDECL;
+ goto CheckCallConv;
+
+ case RW_PASCAL: // pascal, _pascal or __pascal
+ lpFunc->func.attr.fAttr2 |= f2PASCAL;
+ goto CheckCallConv;
+
+ case RW_STDCALL: // stdcall, _stdcall or __stdcall
+ lpFunc->func.attr.fAttr2 |= f2STDCALL;
+CheckCallConv:
+ ScanTok(0); // consume it
+
+ // set this flag so the .h file outputs a bunch of macros
+ // for the STDMETHODCALLTYPE.
+ if (funcType == FUNC_INTERFACE || funcType == FUNC_OAINTERFACE)
+ fSpecifiedInterCC = TRUE;
+
+ // explicit calling convention illegal in dispinterfaces and
+ // oa-compatible interfaces.
+ if (funcType == FUNC_DISPINTERFACE || funcType == FUNC_OAINTERFACE)
+ ParseErrorTokLast(PERR_INV_CALLCONV);
+ break;
+
+ default:
+ lpFunc->func.attr.fAttr2 |= (f2DefaultCC | f2CCDEFAULTED);
+ break;
+ }
+
+ lpFunc->argList = NULL; // no args yet
+
+ szFuncName = ConsumeId(); // get/consume function name
+ lpFunc->func.szElemName = szFuncName; // store function name
+
+ EnsureNoDupElem((LPELEM)lpFunc); // ensure no duplicate functions
+
+ ConsumeTok(RW_LPAREN, 0); // start of parms
+
+ cArgs = 0;
+ cOptArgs = 0;
+ IDLFlagsSeen = 0;
+ cNeedRHS = 0;
+ lpArgTypeLast = NULL; // no last parm yet (in case vararg)
+ if (tok.id != RW_RPAREN) // if any parms are present
+ {
+#pragma warning(disable:4127)
+ while (TRUE)
+#pragma warning(default:4127)
+ { // parse a function parameter
+
+ // parse & validate parm attributes, if any
+ ParseOptAttr(&attr, cPARAM);
+
+ // ensure attributes valid in this context
+ CheckAttr(&attr,
+ fValidParmAttrs[funcType],
+ fValidParmAttrs2[funcType]);
+
+ IDLFlagsCur = attr.fAttr & (fRETVAL | fLCID);
+
+ // can't have both lcid & retval on the same arg
+ if (IDLFlagsCur == (fRETVAL | fLCID))
+ ParseError(PERR_INV_ATTR_COMBO);
+
+ // only parm that can come after 'lcid' is 'retval',
+ // unless we're looking for an RHS parameter, but then
+ // we only allow one parameter to follow.
+ if (IDLFlagsSeen & fLCID && !(IDLFlagsCur & fRETVAL) && cNeedRHS != 1)
+ ParseError(PERR_INV_LCID_USE);
+
+ // If we need an RHS parameter, we want an IN parameter
+ // that is not marked as RETVAL or LCID.
+ if (cNeedRHS && (!(attr.fAttr & fIN) || IDLFlagsCur))
+ ParseError(PERR_INV_PROPFUNC);
+
+ // If we're made it this far while looking for an RHS parameter,
+ // we've found it.
+ if (cNeedRHS)
+ cNeedRHS++;
+
+ // If we have an LCID parameter and are a property PUT/PUTREF,
+ // we MUST have an RHS parameter next.
+ if (IDLFlagsCur & fLCID
+ && lpFunc->func.attr.fAttr & (fPROPPUT | fPROPPUTREF))
+
+ cNeedRHS = 1;
+
+ // Retval param is supposed to be last.
+ if (IDLFlagsSeen & fRETVAL)
+ ParseErrorTokLast(PERR_INV_RETVAL_USE);
+
+ // No retval allowed on PUT/PUTREF.
+ if (IDLFlagsCur == fRETVAL
+ && lpFunc->func.attr.fAttr & (fPROPPUT | fPROPPUTREF))
+
+ ParseErrorTokLast(PERR_INV_PROPFUNC);
+
+ IDLFlagsSeen |= IDLFlagsCur;
+
+ // parse parm type
+ lpArgType = ParseKnownType(&attr, fAllowArray);
+ if (IDLFlagsSeen == 0) {
+ lpArgTypeLast = lpArgType; // save in case vararg
+ }
+
+ // special case of foo(void) ==> no args in this case.
+ // other uses of 'void' are invalid.
+ if (IsType(lpArgType, VT_VOID))
+ {
+ if (tok.id == RW_RPAREN && cArgs == 0 && attr.fAttr == 0)
+ break; // all done
+ else
+ ParseErrorTokLast(PERR_VOID_INV);
+ }
+
+ cArgs++; // got one more arg
+
+ // one (or both) 'in', 'out' must be specified if we're
+ // not a dispinterface.
+ if (funcType != FUNC_DISPINTERFACE && !(attr.fAttr & (fIN | fOUT)))
+ ParseErrorTokLast(PERR_IN_OUT_REQ);
+
+ if (attr.fAttr & fOPTIONAL)
+ {
+ // optional args & 'vararg' don't mix
+ if (lpFunc->func.attr.fAttr & fVARARG) {
+ ParseErrorTokLast(PERR_INV_VARARG_USE);
+ }
+ cOptArgs++; // one more optional arg
+ }
+ else
+ { // can't have optional args in the middle
+ if (cOptArgs)
+ if (!IDLFlagsSeen) // if we're not a LCID or RETVAL
+ ParseErrorTokLast(PERR_INV_ATTR);
+ }
+
+ ListInsert(&lpFunc->argList, sizeof(ELEM));
+ lpFunc->argList->attr = attr; // store parm attributes
+ lpFunc->argList->elemType = lpArgType; // store parm type
+
+ // parse parm name
+ ParseElemName(lpFunc->argList, fAllowArray);
+ EnsureNoDupElem(lpFunc->argList); // ensure no duplicate
+ // parm names
+
+ // ensure this is a valid IDispatch/OA type
+ if (funcType == FUNC_DISPINTERFACE)
+ EnsureIDispatchType(lpFunc->argList->elemType);
+ else if (funcType == FUNC_OAINTERFACE)
+ EnsureOAType(lpFunc->argList->elemType, TRUE);
+
+ // if 'out' specified, parameter must be a pointer type
+ if (attr.fAttr & fOUT) {
+ lpTypeBase = lpArgType;
+ while (lpTypeBase->tentrykind == tTYPEDEF)
+ lpTypeBase = lpTypeBase->td.ptypeAlias;
+ if (!(lpTypeBase->tentrykind & tIMPORTED)) {
+ // can't reliably check if an imported type
+ switch (lpTypeBase->tdesc.vt) {
+ case VT_PTR:
+ case VT_LPSTR:
+ case VT_LPWSTR:
+ case VT_SAFEARRAY:
+ break;
+ default:
+ ParseErrorTokLast(PERR_INV_OUT_PARAM);
+ }
+ }
+ }
+
+ // 'optional' only allowed on non-array VARIANT args
+ if ((attr.fAttr & fOPTIONAL) && !IsType(lpArgType, VT_VARIANT))
+ { // an optional VARIANT * is also OK
+ lpTypeBase = lpArgType;
+ while (lpTypeBase->tentrykind == tTYPEDEF)
+ lpTypeBase = lpTypeBase->td.ptypeAlias;
+ if (lpTypeBase->tdesc.vt != VT_PTR ||
+ lpTypeBase->ref.cIndirect != 1 ||
+ !IsType(lpTypeBase->ref.ptypeBase, VT_VARIANT))
+ ParseErrorTokLast(PERR_INV_ATTR);
+ }
+
+ // validate 'retval' and 'lcid' usage
+ if (IDLFlagsCur) {
+ if (IDLFlagsCur & fLCID) {
+ // 'lcid' only legal if it's a DWORD type
+ if (!IsType(lpArgType, VT_I4))
+ ParseErrorTokLast(PERR_INV_LCID_USE);
+ // must be 'in', optional not allowed
+ if ((attr.fAttr & (fIN | fOUT | fOPTIONAL)) != fIN)
+ ParseErrorTokLast(PERR_INV_LCID_USE);
+ }
+
+ if (IDLFlagsCur & fRETVAL) {
+
+ lpTypeRetVal = lpArgType; // update * return type
+
+ // 'retval' is only allowed on
+ // hresult-returning functions.
+ if (!IsType(lpFunc->func.elemType,VT_HRESULT))
+ ParseErrorTokLast(PERR_INV_ATTR);
+
+ // must be 'out', optional not allowed
+ if ((attr.fAttr & (fIN | fOUT | fOPTIONAL)) != fOUT)
+ ParseErrorTokLast(PERR_INV_RETVAL_USE);
+
+ // 'retval' only legal if it's a pointer type
+ // this is ensured by the check above that 'out'
+ // parms must be pointers
+
+ // But it can't be an alias type, either (due to
+ // a typelib.dll limitation (bug?) in the munging
+ // code in gdtinfo.cxx -- VBA2 bug #3716).
+ // That code must have a pure pointer type. We're
+ // too close to Daytona ship to fix it in typelib,
+ // so we impose the restriction here.
+ if (!(lpArgType->tentrykind & tIMPORTED)) {
+ // can't reliably check if an imported type
+ if (lpArgType->tdesc.vt != VT_PTR)
+ ParseErrorTokLast(PERR_INV_RETVAL_USE);
+ }
+ }
+
+ }
+
+ if (tok.id == RW_RPAREN) // if all done
+ break;
+
+ ConsumeTok(RW_COMMA, 0); // must have another parm
+ }
+
+ }
+
+ // if 'propput' or 'propputref' is specified, then must have at least
+ // one non-lcid argument the comes after any LCID parameter that
+ // may exist.
+ if ((lpFunc->func.attr.fAttr & (fPROPPUT | fPROPPUTREF))
+ && (cArgs == 0 || cArgs == 1 && IDLFlagsSeen & fLCID || cNeedRHS == 1))
+ ParseErrorTokLast(PERR_INV_PROPPUT);
+
+ // if SOURCE specfied, must be an object/variant return type (ignore prop
+ // put/putref when checking for this.
+ if ((lpFunc->func.attr.fAttr & fSOURCE)
+ && !(lpFunc->func.attr.fAttr & (fPROPPUT | fPROPPUTREF))
+ && !IsObjectType(lpTypeRetVal))
+ ParseErrorTokLast(PERR_INV_SOURCE_ATTR);
+
+ // if 'vararg' specified, ensure last arg is a SAFEARRAY(VARIANT) or
+ // SAFEARRAY (VARIANT) *. Note that the following code doesn't accept
+ // things that are typedef'ed to be a SAFEARRAY or SAFEARRAY *, but
+ // I don't think that is important.
+
+ // lpArgTypeLast points to the type of the last arg, not including the
+ // lcid or retval parms, if there is an arg that meets this criteria
+ if (lpFunc->func.attr.fAttr & fVARARG)
+ {
+ // error if no last arg
+ if (lpArgTypeLast == NULL)
+ ParseErrorTokLast(PERR_INV_VARARG_USE);
+
+ // if pointer type, get base type
+ if (lpArgTypeLast->tdesc.vt == VT_PTR && lpArgTypeLast->ref.cIndirect == 1)
+ lpArgTypeLast = lpArgTypeLast->ref.ptypeBase;
+
+ if (lpArgTypeLast->tdesc.vt != VT_SAFEARRAY
+ || !IsType(lpArgTypeLast->ref.ptypeBase, VT_VARIANT))
+ ParseErrorTokLast(PERR_INV_VARARG_USE);
+ cOptArgs = -1; // tell type lib generator that VARARG
+ // was specified
+ }
+
+ if (cArgs > cArgsMax) // update global max # of args
+ cArgsMax = cArgs;
+ lpFunc->cArgs = cArgs; // store cArgs
+ lpFunc->cOptArgs = cOptArgs; // store cOptArgs
+ ScanTok(0); // consume the right paren
+ ConsumeTok(RW_SEMI, 0); // ends with a semicolon
+
+}
+
+
+BOOL NEAR IsType
+(
+ LPTYPE lpType,
+ VARTYPE vt
+)
+{
+ while (lpType->tentrykind == tTYPEDEF)
+ lpType = lpType->td.ptypeAlias;
+ return (lpType->tdesc.vt == vt);
+}
+
+
+// Checks to see that a given type is compatible with IDispatch::Invoke,
+// or is "Ole Automation compatible". Gives a warning if it is not.
+VOID NEAR EnsureIDispatchType
+(
+ LPTYPE lpType
+)
+{
+ if ((GetTypeCompatibility(lpType, 0) & COMPAT_IDISPATCH) == 0) {
+ // Type not supported by IDispatch::Invoke -- give a WARNING
+ ParseErrorTokLast(PWARN_INV_IDISPATCHTYPE);
+ }
+}
+
+// Checks to see that a given type is "Ole Automation compatible".
+// Gives an error if it is not.
+VOID NEAR EnsureOAType
+(
+ LPTYPE lpType,
+ BOOL fParam
+)
+{
+ if ((GetTypeCompatibility(lpType, (WORD)(fParam ? VT_PARAM : 0)) & COMPAT_OA) == 0) {
+ ParseErrorTokLast(PERR_INV_OA_TYPE); // Type not a valid OA type
+ }
+}
+
+// Returns info about whether or not a given type is compatible with
+// IDispatch::Invoke, or is "Ole Automation compatible".
+//
+// In the case where VT_VOID and VT_HRESULT are allowed (on a function return
+// value), we depend on our caller to not call us.
+//
+// Types allowed for dispinterfaces:
+// - All basic types (<= VT_UI1)
+// | VT_USERDEFINED/tTYPEDEF (external)
+// - the above with one level of indirection.
+//
+// Types allowed for OA compatibility:
+//
+// - All basic types (<= VT_UI1)
+// | VT_USERDEFINED/tTYPEDEF,tENUM
+// | VT_PTR -> VT_USERDEFINED/tINTERFACE,tDISPATCH,tCOCLASS
+// | VT_INT
+// - the above with one additional level of indirection.
+//
+WORD NEAR GetTypeCompatibility
+(
+ LPTYPE lpType,
+ WORD fRecurse // 0 -- not being called recursively
+ // VT_BYREF -- being called for a pointer
+ // VT_ARRAY -- being called for an array
+ // VT_PARAM -- being called for a parameter
+)
+{
+ WORD wCompat;
+ UINT cInd;
+
+ // Treat an array as just another level of indirection.
+ BOOL fBYREF = fRecurse & VT_BYREF;
+ BOOL fARRAY = fRecurse & VT_ARRAY;
+ BOOL fPARAM = fRecurse & VT_PARAM;
+ BOOL fSIMPPARAM = fPARAM || !(fBYREF || fARRAY);
+
+ while (lpType->tentrykind == tTYPEDEF)
+ lpType = lpType->td.ptypeAlias;
+
+ cInd = lpType->ref.cIndirect;
+
+ // IDispatch and OA always allow the below types.
+ if (lpType->tdesc.vt <= VT_UNKNOWN || lpType->tdesc.vt == VT_UI1) {
+ // The contents of a safearray may not containg a reference, unless
+ // they're pointing to a UDT. This is not the case, so if we have
+ // both a reference AND a safearray, return NONE.
+ //
+ if (fBYREF && fARRAY) {
+ return COMPAT_NONE;
+ }
+ else {
+ return COMPAT_IDISPATCH | COMPAT_OA;
+ }
+ }
+
+ switch (lpType->tdesc.vt) {
+ case VT_PTR:
+ // Can't even consider more than 2 levels of indirection.
+ if (cInd > 2) {
+ return COMPAT_NONE;
+ }
+
+ // Let VT_USERDEFINED know if we're dealing with
+ // 2 levels of indirection (for ENUM).
+ //
+ if (!fPARAM || fARRAY || cInd == 2) {
+ fRecurse |= VT_BYREF;
+ }
+
+ wCompat = GetTypeCompatibility(lpType->ref.ptypeBase, fRecurse);
+
+ // If the base type is VT_PTR, this isn't valid for IDispatch.
+ if (cInd > 1) {
+ wCompat &= ~COMPAT_IDISPATCH;
+ }
+
+ // Legal values:
+ // cInd = 1, fPARAM = 0, VT == VT_UDT
+ // cInd = 2, fPARAM = 0, error
+ // cInd = 1, fPARAM = 1, fARRAY = 0, VT == ANY
+ // cInd = 1, fPARAM = 1, fARRAY = 1, VT == VT_USERDEFINED
+ // cInd = 2, fPARAM = 1, fARRAY = 0, VT == VT_USERDEFINED
+ // cInd = 2, fPARAM = 1, fARRAY = 1, error
+ //
+ if (lpType->ref.ptypeBase->tdesc.vt != VT_USERDEFINED
+ && (cInd == 1 && (!fPARAM || fARRAY) || cInd == 2 && fPARAM)
+ || (cInd == 2 && (!fPARAM || fARRAY))) {
+
+ wCompat &= ~COMPAT_OA;
+ }
+
+ return wCompat;
+
+ case VT_SAFEARRAY:
+ // Only one array.
+ if (fARRAY) {
+ return COMPAT_NONE;
+ }
+
+ // We allow SAFEARRAY(type)* but not SAFEARRAY (type *), unless
+ // type is a UDT. So if the fBYREF flag has been set, clear it
+ // so we can property check for byrefs in the array.
+ //
+ return GetTypeCompatibility(lpType->ref.ptypeBase,
+ (WORD)(fRecurse & ~VT_BYREF | VT_ARRAY));
+
+ // VT_INT is only allowed in OLE automation.
+ case VT_INT:
+ return COMPAT_OA;
+
+ case VT_USERDEFINED:
+ switch (lpType->tentrykind & ~(tFORWARD | tIMPORTED | tQUAL)) {
+ case tENUM:
+ // fBYREF is set if we're dealing with 2 levels of
+ // indirection.
+ //
+ if (fBYREF) {
+ return COMPAT_NONE;
+ }
+
+ return COMPAT_OA;
+
+ // Cases of the following being used without a level of indirection
+ // are caught elsewhere.
+ //
+ case tINTERFACE:
+ switch(lpType->tentrykind & ~tQUAL) {
+ case tINTERFACE:
+ if (((LPENTRY)lpType)->attr.fAttr2 & f2OACompatBits) {
+ if (((LPENTRY)lpType)->attr.fAttr2 & f2VALIDDUALBASE) {
+ return COMPAT_OA | COMPAT_DUALBASE;
+ } else {
+ return COMPAT_OA;
+ }
+ }
+ break;
+ case (tINTERFACE | tIMPORTED):
+ if ((lpType->import.wTypeFlags & TYPEFLAG_FOLEAUTOMATION))
+ // assume valid for use as a base of a dual interface
+ return COMPAT_OA | COMPAT_DUALBASE;
+ break;
+
+ case (tINTERFACE | tFORWARD):
+ if (((LPENTRY)lpType)->lpEntryForward != NULL) {
+ // if we can get at the real definition, we can check
+ if ((((LPENTRY)lpType)->lpEntryForward->attr.fAttr2 & f2OACompatBits) == 0) {
+ break; // not OA-compatible
+ }
+ }
+ // If all we have is a forward declare, we have no
+ // means of checking to see if this is any good or not,
+ // so assume it's OK.
+ return COMPAT_OA | COMPAT_DUALBASE;
+
+ default:
+ Assert(FALSE);
+ }
+ break; // not OA-compatible
+
+ case tDISPINTER:
+ return COMPAT_IDISPATCH | COMPAT_OA;
+
+ case tCOCLASS:
+ // UNDONE: What are the rules for ensuring COCLASSes
+ // UNDONE: are OA-compatible? Assume they all are for now.
+ return COMPAT_OA;
+
+ case tTYPEDEF:
+ if (lpType->tentrykind & tIMPORTED) {
+ // UNDONE: Assume external typedef's are OA-compatible for
+ // UNDONE: now, rather than walking the typeinfos to find
+ // UNDONE: the true base type & flags.
+ return (COMPAT_IDISPATCH | COMPAT_OA | COMPAT_DUALBASE);
+ }
+ default:
+ break;
+ }
+ // fall through to return COMPAT_NONE
+
+ default:
+ break;
+ // fall through to return COMPAT_NONE
+ }
+ return COMPAT_NONE;
+}
+
+
+// see if this type is (or could be) and object type.
+// this means VARIANT, VARIANT *, coclass *, dispinterface *, or interface *.
+BOOL NEAR IsObjectType
+(
+ LPTYPE lpType
+)
+{
+ while (lpType->tentrykind == tTYPEDEF)
+ lpType = lpType->td.ptypeAlias;
+
+ switch (lpType->tdesc.vt) {
+ case VT_UNKNOWN:
+ case VT_DISPATCH:
+ case VT_VARIANT:
+ return TRUE; // variant can contain an object
+
+ case VT_PTR: // maybe a pointer to an object or variant
+ lpType = lpType->ref.ptypeBase; // get true base type
+ while (lpType->tentrykind == tTYPEDEF)
+ lpType = lpType->td.ptypeAlias;
+ switch(lpType->tentrykind & ~(tFORWARD | tIMPORTED | tQUAL)) {
+ case tINTERFACE:
+ case tDISPINTER:
+ case tCOCLASS:
+ return TRUE; // pointer to an object is ok
+
+ case tINTRINSIC:
+ switch (lpType->tdesc.vt) {
+ case VT_UNKNOWN:
+ case VT_DISPATCH:
+ case VT_VARIANT:
+ return TRUE; // pointer to a variant/object is ok
+ }
+ default:
+ break;
+ }
+ // fall through
+
+ default:
+ break;
+ }
+ return FALSE; // not an object type
+}
+
+// parses a "module" section
+VOID NEAR ParseModule
+(
+)
+{
+ LPENTRY lpEntry = typlib.pEntry;
+ ATTR attr;
+
+ // ensure attributes valid in this context
+ CheckAttr(&lpEntry->attr, VALID_MODULE_ATTR, VALID_MODULE_ATTR2);
+
+ // 'dllname' attr required on a module
+ if ((lpEntry->attr.fAttr & fDLLNAME) == 0)
+ ParseError(PERR_DLLNAME_REQ);
+
+ ScanTok(0); // consume "module", advance to next token
+
+ lpEntry->type.tentrykind = tMODULE; // store information in record
+ lpEntry->type.szName = ConsumeId(); // get/consume module name
+ // no need to set rest of type structure
+
+ lpEntry->module.funcList = NULL; // no functions initially
+ lpEntry->module.constList = NULL; // no constants initially
+
+ EnsureNoDupEntries(lpEntry); // check for dup def
+
+ ConsumeTok(RW_LCURLY, 0);
+
+ while (tok.id != RW_RCURLY)
+ {
+ ParseOptAttr(&attr, cFUNC); // parse attributes, if any
+
+ if (tok.id == RW_CONST)
+ { // a constant
+ ScanTok(0); // consume "const"
+ ListInsert(&(lpEntry->module.constList), sizeof(ELEM));
+ lpEntry->module.constList->attr = attr;
+ ParseConstant(lpEntry->module.constList);
+ }
+ else
+ { // assume function
+ ListInsert(&(lpEntry->module.funcList), sizeof(FUNC));
+ lpEntry->module.funcList->func.attr = attr; // store attrs
+
+ // 'entry' attr required on a function in a module
+ if ((attr.fAttr & fENTRY) == 0)
+ ParseError(PERR_ENTRY_REQ);
+
+ ParseFunction(lpEntry->module.funcList, FUNC_MODULE);
+ }
+ }
+
+ ConsumeRCurlyOptSemi(0); // consume rcurly and optional ;
+}
+
+// parse the interface section
+VOID NEAR ParseInterface
+(
+)
+{
+ LPENTRY lpEntry = typlib.pEntry;
+ LPTYPE lpTypeBase;
+
+ // ensure attributes valid in this context
+ CheckAttr(&lpEntry->attr, VALID_INTERFACE_ATTR, VALID_INTERFACE_ATTR2);
+
+ ScanTok(0); // consume "interface", advance to next token
+
+ if (FHandleForwardDecl(lpEntry, tINTERFACE))
+ return; // if THIS is a forward decl
+
+ // UUID is now required on all interfaces
+ if (!(lpEntry->attr.fAttr & fUUID))
+ ParseErrorTokLast(PERR_UUID_REQ);
+
+ if (!(lpEntry->attr.fAttr2 & f2OACompatBits)) {
+ // 'ODL' attr required on old-style (non-OA) interfaces
+ if (!(lpEntry->attr.fAttr & fODL))
+ ParseErrorTokLast(PERR_ODL_REQ);
+ }
+
+ if ((lpEntry->attr.fAttr2 & (f2DUAL | f2NONEXTENSIBLE)) == f2NONEXTENSIBLE){
+ // 'nonextensible' attr only valid on DUAL interfaces
+ ParseErrorTokLast(PERR_INV_ATTR);
+ }
+
+ EnsureNoDupEntries(lpEntry); // check for dup def
+
+ lpEntry->inter.funcList = NULL; // no functions initially
+ lpEntry->type.inter.interList = NULL; // no base interfaces
+
+ lpTypeBase = NULL;
+ if (tok.id == RW_COLON || (lpEntry->attr.fAttr2 & f2OACompatBits))
+ {
+ ConsumeTok(RW_COLON, 0); // consume separating colon
+ if (lpEntry->attr.fAttr2 & f2OACompatBits) {
+ if (lpTypeIDispatch == NULL)
+ FindIDispatch(); // set up lpTypeIDispatch BEFORE
+ // ParseKnownType (below) so that
+ // we can find this.
+ }
+
+ lpTypeBase = ParseKnownType(&lpEntry->attr, fAllowInter);
+ if ((lpTypeBase->tentrykind & ~(tFORWARD | tIMPORTED | tQUAL)) != tINTERFACE)
+ ParseErrorTokLast(PERR_UNDEF_INTER);
+
+ // if we claim to be "Dual" or "OleAutomation"
+ if (lpEntry->attr.fAttr2 & f2OACompatBits) {
+ WORD compatFlags;
+
+ // ok to derive from IDispatch (even though it's
+ // not marked as OA-compatible).
+ if (lpTypeBase != lpTypeIDispatch) {
+ compatFlags = GetTypeCompatibility(lpTypeBase, VT_BYREF);
+ // ensure the interface we derive from is marked as
+ // Oleautomation compatible, and has the correct base
+ // interface.
+ if (lpEntry->attr.fAttr2 & f2DUAL) {
+ // must derive from IDispatch, or another OA interface
+ // that derives from IDispatch.
+ if (!(compatFlags & COMPAT_DUALBASE)) {
+ ParseErrorTokLast(PERR_INV_DUAL_BASE);
+ }
+ } else {
+ // must derive from IUnknown, or another OA interface
+ if (lpTypeBase != lpTypeIUnknown &&
+ !(compatFlags & COMPAT_OA)) {
+ ParseErrorTokLast(PERR_INV_OA_BASE);
+ }
+ }
+ } else {
+ // IDisapatch valid as a base of a dual interface
+ compatFlags = COMPAT_DUALBASE;
+ }
+
+ // mark this interface as dual-compatible if base interface
+ // is dual-compatible
+ if (compatFlags & COMPAT_DUALBASE)
+ lpEntry->attr.fAttr2 |= f2VALIDDUALBASE;
+ }
+
+ ListInsert(&(lpEntry->type.inter.interList), sizeof(INTER));
+ lpEntry->type.inter.interList->ptypeInter = lpTypeBase;
+ // store base interface type
+ lpEntry->type.inter.interList->fAttr = 0; // no flags
+ lpEntry->type.inter.interList->fAttr2 = 0;
+ }
+
+ ConsumeTok(RW_LCURLY, 0);
+
+ while (tok.id != RW_RCURLY)
+ {
+ if (tok.id == RW_TYPEDEF)
+ { // a nested TYPEDEF
+
+ Assert (lpEntryPrev != NULL);
+
+ Assert(lpEntryPrev->type.pNext == (LPTYPE)lpEntry);
+
+ // create & init new item in entry list, linked in before
+ // the entry for the interface. Sets lpEntryPrev to
+ // point to this new entry.
+ InitNewEntry(&lpEntryPrev);
+
+ // lpEntry still points to Interface entry
+ Assert(lpEntryPrev->type.pNext == (LPTYPE)lpEntry);
+
+ ParseTypedef(lpEntryPrev); // parse nested typedef
+ }
+ else
+ { // a function
+
+ ListInsert(&lpEntry->inter.funcList, sizeof(FUNC));
+
+ // parse attributes, if any
+ ParseOptAttr(&lpEntry->inter.funcList->func.attr, cFUNC);
+ ParseFunction(
+ lpEntry->inter.funcList,
+ ((lpEntry->attr.fAttr2 & f2OACompatBits)
+ ? FUNC_OAINTERFACE : FUNC_INTERFACE));
+ }
+ }
+
+ ConsumeRCurlyOptSemi(0); // consume rcurly and optional ;
+}
+
+
+// parse the dispinterface section
+//
+// Goes to extra work to parse the properties and methods into a single list,
+// and then split the list apart, so that you can't define the same name
+// and/or ID in both the properties and methods sections.
+VOID NEAR ParseDispinterface
+(
+)
+{
+ LPENTRY lpEntry = typlib.pEntry;
+ LPELEM elemList = NULL; // no entries initially
+ LPELEM propList;
+ LPELEM elemTemp;
+ LPTYPE lpTypeBase;
+
+ // ensure attributes valid in this context
+ CheckAttr(&lpEntry->attr, VALID_DISPINTER_ATTR, VALID_DISPINTER_ATTR2);
+
+ ScanTok(0); // consume "dispinterface", advance to next tok
+
+ if (FHandleForwardDecl(lpEntry, tDISPINTER))
+ return; // if THIS is a forward decl
+
+ // UUID required on dispinterface section
+ if (!(lpEntry->attr.fAttr & fUUID))
+ ParseErrorTokLast(PERR_UUID_REQ);
+
+ ConsumeTok(RW_LCURLY, 0);
+
+ EnsureNoDupEntries(lpEntry); // check for dup def
+
+ lpEntry->dispinter.propList = NULL; // assume no properties or methods
+ lpEntry->dispinter.methList = NULL;
+ lpEntry->type.inter.interList = NULL; // no base interfaces
+ ListInsert(&(lpEntry->type.inter.interList), sizeof(INTER));
+
+ if (lpTypeIDispatch == NULL)
+ FindIDispatch(); // set up lpTypeIDispatch
+
+ lpEntry->type.inter.interList->ptypeInter = lpTypeIDispatch;
+ // store base interface
+ lpEntry->type.inter.interList->fAttr = 0; // no flags
+ lpEntry->type.inter.interList->fAttr2 = 0; // no flags
+
+ if (tok.id == RW_INTERFACE)
+ { // "interface <interfacename>;
+ ScanTok(0); // consume "interface", advance to next tok
+ // CONSIDER: this code is pretty much the end of ParseClass()
+ // maybe combine this code into a single routine?
+ lpTypeBase = ParseKnownType(&lpEntry->attr, fAllowInter);
+
+ if ((lpTypeBase->tentrykind & ~(tFORWARD | tIMPORTED | tQUAL)) != tINTERFACE)
+ ParseErrorTokLast(PERR_UNDEF_INTER);
+
+ ListInsert(&(lpEntry->type.inter.interList), sizeof(INTER));
+ lpEntry->type.inter.interList->ptypeInter = lpTypeBase;
+ // save * to referenced interface
+ lpEntry->type.inter.interList->fAttr = 0; // no flags
+ lpEntry->type.inter.interList->fAttr2 = 0;
+
+ ConsumeTok(RW_SEMI, 0); // ends with a semicolon
+ goto DoneDispinter;
+ }
+
+ // Parse the properties (if any).
+ ConsumeTok(RW_PROPERTIES, 0);
+ ConsumeTok(RW_COLON, 0);
+
+ while (tok.id != RW_METHODS && tok.id != RW_RCURLY)
+ {
+ ParseNewElem(&elemList,
+ VALID_DISPINTER_PROP_ATTR,
+ VALID_DISPINTER_PROP_ATTR2,
+ NULL);
+ ConsumeTok(RW_SEMI, 0); // ends with a semicolon
+ // 'id' attribute is required on dispinterface items
+ if (!(elemList->attr.fAttr & fID))
+ ParseErrorTokLast(PERR_ID_REQ);
+
+ // if SOURCE specfied, must be an object/variant type
+ if ((elemList->attr.fAttr & fSOURCE)
+ && !IsObjectType(elemList->elemType))
+ ParseErrorTokLast(PERR_INV_SOURCE_ATTR);
+
+ // type of this var must be an IDispatch-compatible type
+ EnsureIDispatchType(elemList->elemType);
+ }
+
+ lpEntry->dispinter.propList = elemList; // set property list
+ propList = elemList; // cache
+
+ // Parse the methods (if any).
+ ConsumeTok(RW_METHODS, 0);
+ ConsumeTok(RW_COLON, 0);
+
+ // now parse the methods (if any)
+ while (tok.id != RW_RCURLY)
+ {
+ ListInsert(&elemList, sizeof(FUNC));
+ ParseOptAttr(&elemList->attr, cFUNC);
+
+ ParseFunction((LPFUNC)elemList, FUNC_DISPINTERFACE);
+ if (!(elemList->attr.fAttr & fID))
+ ParseErrorTokLast(PERR_ID_REQ);
+ }
+
+ // now split the single list into 2 separate lists
+
+ if (elemList != propList)
+ { // if got methods
+ lpEntry->dispinter.methList = (LPFUNC)elemList; // got methods
+ if (propList)
+ { // got both methods & properties -- split into 2 lists.
+ // Swap links in order to link last method to first method,
+ // last property to first property
+ elemTemp = elemList->pNext;
+ elemList->pNext = propList->pNext;
+ propList->pNext = elemTemp;
+ }
+ }
+
+DoneDispinter:
+ ConsumeRCurlyOptSemi(0); // consume rcurly and optional ;
+}
+
+// parse the coclass section
+VOID NEAR ParseCoclass
+(
+)
+{
+
+ LPENTRY lpEntry = typlib.pEntry;
+ LPTYPE lpTypeBase;
+ TENTRYKIND tag;
+ WORD fGotDispinter = 0;
+ WORD fGotDefault = 0;
+ WORD flags;
+#define BIT_NOTSOURCE 1 // flags for fGotDispinter and fGotDefault
+#define BIT_SOURCE 2
+ ATTR attr;
+ LPINTER lpinter;
+ LPINTER lpinterList;
+
+ // ensure attributes valid in this context
+ CheckAttr(&lpEntry->attr, VALID_COCLASS_ATTR, VALID_COCLASS_ATTR2);
+
+ ScanTok(0); // consume "coclass", advance to next tok
+
+ // Since a function can now return a COCLASS, we must
+ // be able to handle forward declarations to them.
+ //
+ if (FHandleForwardDecl(lpEntry, tCOCLASS))
+ return; // if THIS is a forward decl
+
+ // UUID required on coclass section
+ if (!(lpEntry->attr.fAttr & fUUID))
+ ParseError(PERR_UUID_REQ);
+
+ lpEntry->type.inter.interList = NULL; // no base interfaces
+
+ EnsureNoDupEntries(lpEntry); // check for dup def
+
+ ConsumeTok(RW_LCURLY, 0);
+
+ do {
+ // parse a COCLASS entry
+ ParseOptAttr(&attr, cIMPLTYPE); // parse attributes, if any
+
+ // ensure attributes valid in this context
+ CheckAttrTokLast(&attr, VALID_COCLASS_INTER_ATTR,
+ VALID_COCLASS_INTER_ATTR2);
+
+ flags = (WORD)((attr.fAttr & fSOURCE) ? BIT_SOURCE : BIT_NOTSOURCE);
+
+ if (attr.fAttr & fDEFAULT) {
+ if (attr.fAttr & fRESTRICTED) {
+ // default restricted makes no sense
+ ParseErrorTokLast(PERR_INV_ATTR_COMBO);
+ }
+
+ // figure out if we have too many default's or not. We're allowed
+ // at most one [default] inter, and one [source, default] inter.
+ if (fGotDefault & flags) {
+ ParseError(PERR_DUP_DEF);
+ }
+ fGotDefault |= flags;
+ }
+
+ switch (tok.id)
+ {
+ case RW_INTERFACE:
+ tag = tINTERFACE;
+ break;
+ case RW_DISPINTERFACE:
+ tag = tDISPINTER;
+
+ // figure out if we have too many dispinterface's or not.
+ // We're allowed at most one non-[source] dispinterface, but
+ // as many [source] dispinterfaces as we want.
+ if (fGotDispinter & flags == BIT_NOTSOURCE) {
+ // Error is caught at Layout(), but it's so crypitic I'm
+ // catching it at parse time instead.
+ ParseError(PERR_TWO_DISPINTER);
+ }
+ fGotDispinter |= flags;
+ break;
+ default:
+ ParseError(PERR_EXP_INTER); // expected dispinterface or interface
+ }
+ ScanTok(0); // consume "interface"/"dispinterface"
+
+ lpTypeBase = ParseKnownType(&lpEntry->attr, fAllowInter);
+
+ if ((lpTypeBase->tentrykind & ~(tFORWARD | tIMPORTED | tQUAL)) != tag)
+ ParseErrorTokLast(PERR_UNDEF_INTER);
+
+ // insert referenced interface/dispinterface into list of interfaces
+ ListInsert(&(lpEntry->type.inter.interList), sizeof(INTER));
+ lpEntry->type.inter.interList->ptypeInter = lpTypeBase;
+ lpEntry->type.inter.interList->fAttr = attr.fAttr; // save flags
+ lpEntry->type.inter.interList->fAttr2 = attr.fAttr2;
+
+ ConsumeTok(RW_SEMI, 0); // ends with a semicolon
+
+ } while (tok.id != RW_RCURLY); // while not end of list
+
+ // If we didn't get interfaces with both source and non-source default
+ // attributes, then we need to go through and set the default bit on the
+ // first source and first non-source interfaces that aren't restricted.
+ lpinterList = lpEntry->type.inter.interList;
+ lpinter = (LPINTER)ListFirst(lpinterList);
+ while (fGotDefault != (BIT_NOTSOURCE | BIT_SOURCE))
+ {
+ flags = (WORD)((lpinter->fAttr & fSOURCE) ? BIT_SOURCE : BIT_NOTSOURCE);
+ if (!(fGotDefault & flags) && !(lpinter->fAttr & fRESTRICTED)) {
+ // if we don't have a default yet for this variety
+ // (source/nonsource) of interface, and this interface isn't
+ // marked as restricted, then tag it as default.
+ lpinter->fAttr |= fDEFAULT;
+ fGotDefault |= flags;
+ }
+
+ // advance to next entry if not all done
+ if (lpinter == (LPINTER)ListLast(lpinterList))
+ break; // exit if all done
+ lpinter = (LPINTER)lpinter->pNext;
+ } // WHILE
+
+ ConsumeRCurlyOptSemi(0); // consume rcurly and optional ;
+}
+
+
+// parses: importlib (filename);
+VOID NEAR ParseImportlib
+(
+)
+{
+
+ ScanTok(0); // consume "importlib", advance to next token
+ ConsumeTok(RW_LPAREN, fACCEPT_STRING);
+
+ ListInsert(&typlib.pImpLib, sizeof(IMPORTLIB));
+
+ typlib.pImpLib->lptlib = NULL; // null out pointers in case of error
+ typlib.pImpLib->lptcomp = NULL;
+ typlib.pImpLib->lptlibattr = NULL;
+
+ typlib.pImpLib->lpszFileName = lpszParseStringExpr(); // parse filename
+
+ ConsumeTok(RW_RPAREN, 0);
+
+ //now load the type library, and fill in pImpLib->lpszLibName/lptcomp.
+ LoadExtTypeLib(typlib.pImpLib);
+
+ ConsumeTok(RW_SEMI, 0);
+}
+
+// ****************************************
+// Expression support
+// ****************************************
+
+LPSTR NEAR lpszParseStringExpr()
+{
+ LPSTR result;
+
+ // string expressions are not supported -- only accept string literals
+
+ if (tok.id != LIT_STRING) // better be a string literal
+ ParseError(PERR_EXP_STRING);
+ if (tok.cbsz == 0) // empty string not allowed here
+ ParseError(PERR_INV_STRING);
+ result = tok.lpsz;
+ ScanTok(0); // consume string token
+ return result;
+}
+
+// supports (minimal) numeric expressions
+// Current level of support is:
+// add
+// subtract
+// (numeric literals, parentheses, and unary minus are handled
+// by lParseNumber)
+DWORD NEAR lParseNumericExpr()
+{
+ DWORD result;
+ TOKID idOp;
+ DWORD nextNum;
+
+ result = lParseNumber();
+ while (tok.id >= OP_MIN && tok.id <= OP_MAX)
+ { // repeat while a binary operator follows this number
+ idOp = tok.id; // save operator ID
+ ScanTok(fACCEPT_NUMBER); // consume the operator
+
+ nextNum = lParseNumber(); // get number after this opcode
+
+ switch (idOp)
+ {
+ case OP_ADD:
+ result = result + nextNum;
+ break;
+
+ case OP_SUB:
+ result = result - nextNum;
+ break;
+
+ // CONSIDER: (V2, EXPR) Add more operators.
+ // CONSIDER: (V2, EXPR) Probably have to completely re-write this
+ // CONSIDER: (V2, EXPR) routine to deal with operator precidence.
+
+ default:
+ // CONSIDER: should probably report error on the operator,
+ // CONSIDER: not on the 2nd number
+ ParseErrorTokLast(PERR_UNSUPPORTED_OP);
+ }
+ }
+
+ return result;
+}
+
+// Parses a single number:
+// one numeric literal,
+// a unary minus followed by a single number
+// a numeric expression enclosed in parentheses
+// Rejects anything that doesn't meet the above criteria.
+DWORD NEAR lParseNumber()
+{
+ DWORD result;
+
+ switch (tok.id)
+ {
+ case RW_LPAREN:
+ ScanTok(fACCEPT_NUMBER); // consume the '('
+ result = lParseNumericExpr(); // return value of stuff
+ // inside the parens
+ ConsumeTok(RW_RPAREN, fACCEPT_OPERATOR);
+ break;
+
+ case RW_HYPHEN: // treat as unary minus
+ // just assume the expression is signed at this point
+ ScanTok(fACCEPT_NUMBER); // consume the '-'
+
+ // if negative numeric literal, ensure in range of signed I4
+ if (tok.id == LIT_NUMBER && tok.number > 0x80000000)
+ ParseError(PERR_NUMBER_OV);
+
+ result = -(long)lParseNumber();
+ break;
+
+ case LIT_NUMBER:
+ result = tok.number;
+ ScanTok(fACCEPT_OPERATOR); // consume the number
+ break;
+
+ //case LIT_STRING:
+ default:
+ ParseError(PERR_INV_EXPRESSION);
+ }
+ return result;
+}
+
+
+// ****************************************
+// Utility routines
+// ****************************************
+
+// Calls ParseError if these attributes are invalid in this context
+VOID NEAR CheckAttr
+(
+ LPATTR pAttr,
+ DWORD attrbit,
+ DWORD attrbit2
+)
+{
+ if (pAttr->fAttr & ~attrbit || pAttr->fAttr2 & ~attrbit2)
+ ParseError(PERR_INV_ATTR); // invalid in this context
+}
+
+// Calls ParseErrorTokLast if these attributes are invalid in this context
+VOID NEAR CheckAttrTokLast
+(
+ LPATTR pAttr,
+ DWORD attrbit,
+ DWORD attrbit2
+)
+{
+ if (pAttr->fAttr & ~attrbit || pAttr->fAttr2 & ~attrbit2)
+ ParseErrorTokLast(PERR_INV_ATTR); // invalid in this context
+}
+
+VOID NEAR GotAttr
+(
+ LPATTR pAttr,
+ DWORD attrbit
+)
+{
+ if (pAttr->fAttr & attrbit) // error if already specified
+ ParseErrorTokLast(PERR_INV_ATTR_COMBO);
+ pAttr->fAttr |= attrbit;
+}
+
+VOID NEAR GotAttr2
+(
+ LPATTR pAttr,
+ DWORD attrbit2
+)
+{
+ if (pAttr->fAttr2 & attrbit2) // error if already specified
+ ParseErrorTokLast(PERR_INV_ATTR_COMBO);
+ pAttr->fAttr2 |= attrbit2;
+}
+
+// consumes a close curly followed by an optional semicolon.
+VOID NEAR ConsumeRCurlyOptSemi
+(
+ WORD fAccept
+)
+{
+ ConsumeTok(RW_RCURLY, fAccept); // consume the close curly
+ if (tok.id == RW_SEMI)
+ ScanTok(fAccept); // consume the ';' if present
+}
+
+
+// consumes an identifer token.
+LPSTR NEAR ConsumeId()
+{
+ LPSTR lpszRet;
+
+ if (tok.id != LIT_ID) // ensure we've got an ID
+ ParseError(PERR_EXP_IDENTIFIER); // error if not
+ lpszRet = tok.lpsz; // save id name for return value
+ ScanTok(0); // consume ID token
+
+ return lpszRet; // return id name
+}
+
+
+// ensure last element in entry list isn't duplicated
+// Also ensures that the uuid defined by this entry (if specified) isn't
+// specified by somebody else.
+VOID NEAR EnsureNoDupEntries
+(
+ LPENTRY lpEntryLast
+)
+{
+ LPENTRY lpEntry;
+ LPSTR szNameLast;
+ LPSTR szTagLast;
+ GUID FAR * lpUuidLast;
+
+ szNameLast = lpEntryLast->type.szName; // name of last entry added
+
+ lpUuidLast = NULL; // assume no UUID
+ szTagLast = NULL; // assume no tag
+
+ // set up szTagLast and lpUuidLast, and ensure that the last entry
+ // doesn't conflict with the 'library' section.
+ switch (lpEntryLast->type.tentrykind & ~tFORWARD)
+ {
+ case tINTRINSIC:
+ case tREF:
+ break; // no attr field on these guys
+
+ case tSTRUCT:
+ case tENUM:
+ case tUNION:
+ szTagLast = lpEntryLast->type.structenum.szTag; // NULL if none
+ // fall into default processing
+
+ default:
+ if (lpEntryLast->type.tentrykind & tIMPORTED)
+ break; // no attr field on these guys
+
+ if (lpEntryLast->attr.fAttr & fUUID) // if UUID specified
+ {
+ lpUuidLast = lpEntryLast->attr.lpUuid; // get * to uuid
+ // ensure this UUID isn't duplicated with the library's uuid
+ if ((typlib.attr.fAttr & fUUID) &&
+ !_fmemcmp(lpUuidLast, typlib.attr.lpUuid, sizeof(GUID)))
+ ParseErrorTokLast(PERR_DUP_UUID);
+ }
+ };
+
+ // ensure it's not duplicated by any other entry name/uuid
+ for (lpEntry = (LPENTRY)ListFirst(typlib.pEntry); lpEntry != lpEntryLast; lpEntry = (LPENTRY)(lpEntry->type.pNext))
+ {
+ if (lpEntry->type.tentrykind & tIMPORTED) {
+ // The following check ensures that you can't have a
+ // type definition of the same name as an unqualified reference
+ // to a type in another library. While things will work, it's
+ // a bit confusing if two id's in the same file refer to
+ // to different types just because one comes before the
+ // definition of a type.
+ // Qualifed references to types in other type libraries don't
+ // present any ambiguity.
+ if (!(lpEntry->type.tentrykind & tQUAL)) {
+ // ensure name isn't duplicated (CASE-INSENSITIVE)
+ if (!FCmpCaseIns(szNameLast, lpEntry->type.szName))
+ ParseErrorTokLast(PERR_DUP_DEF); // then error
+ }
+ }
+ else {
+ switch (lpEntry->type.tentrykind & ~tFORWARD)
+ {
+ case tREF:
+ break; // no conflicts possible with these guys
+
+ case tINTRINSIC:
+ // ensure intrinsic name isn't duplicated (CASE-SENSITIVE)
+ if (!_fstrcmp(szNameLast, lpEntry->type.szName))
+ ParseErrorTokLast(PERR_DUP_DEF);
+ break;
+
+ case tSTRUCT:
+ case tENUM:
+ case tUNION:
+ // ensure tag (if given) isn't duplicated (CASE-SENSITIVE)
+ if (szTagLast && lpEntry->type.structenum.szTag &&
+ !_fstrcmp(szTagLast, lpEntry->type.structenum.szTag))
+ CheckForwardMatch(lpEntryLast, lpEntry);
+
+ if (lpEntry->type.tentrykind & tFORWARD)
+ break; // forward declares of these don't have
+ // their names filled in yet
+
+ // fall into default processing to check names
+
+ default:
+ // ensure name isn't duplicated (CASE-INSENSITIVE)
+ if (!FCmpCaseIns(szNameLast, lpEntry->type.szName))
+ CheckForwardMatch(lpEntryLast, lpEntry);
+
+ // ensure this UUID isn't duplicated
+ if (lpUuidLast && (lpEntry->attr.fAttr & fUUID) &&
+ !_fmemcmp(lpUuidLast, lpEntry->attr.lpUuid, sizeof(GUID)))
+ ParseErrorTokLast(PERR_DUP_UUID);
+ }
+ }
+ }
+}
+
+
+// called when 2 entries have the same name -- ensure these are valid
+// combinations of forward declares. If not -- then dup def error.
+VOID NEAR CheckForwardMatch
+(
+ LPENTRY lpEntryLast,
+ LPENTRY lpEntry
+)
+{
+ // if one of these isn't a forward declare
+ if ((((lpEntryLast->type.tentrykind | lpEntry->type.tentrykind) & tFORWARD) == 0) ||
+
+ // or if the type's of these forward declares don't match
+ ((lpEntryLast->type.tentrykind & ~tFORWARD) != (lpEntry->type.tentrykind & ~tFORWARD)) )
+
+ ParseErrorTokLast(PERR_DUP_DEF); // then error
+}
+
+
+INT FAR FCmpCaseIns
+(
+ LPSTR str1,
+ LPSTR str2
+)
+{
+ return !(CompareStringA(g_lcidCompare,
+ NORM_IGNOREWIDTH |
+ NORM_IGNOREKANATYPE |
+ NORM_IGNORECASE,
+ str1,
+ -1,
+ str2,
+ -1)
+ == 2);
+
+}
+
+// *************************************************************************
+// Linked list management
+// *************************************************************************
+
+// assumes all lists have a pNext field in the same position (usually first)
+// This routine will go to ParseError if it runs out of memory
+VOID FAR ListInsert
+(
+ LPVOID ppList,
+ WORD cbElem
+)
+{
+ LPTYPE pNewItem; // any type that has a pNext -- they all have
+ LPTYPE pList; // them in the same positions
+
+ pNewItem = (LPTYPE)ParseMalloc(cbElem); // new last item
+ pList = *(LPTYPE FAR *)ppList; // deref
+
+ if (pList) // if list not empty
+ {
+ pNewItem->pNext = pList->pNext; // set * to head of list
+ pList->pNext = pNewItem; // point to new last item
+ }
+ else
+ {
+ pNewItem->pNext = pNewItem; // point back to itself
+ }
+ *(LPTYPE FAR *)ppList = pNewItem; // point to last item
+}
+
+
+
+/***
+* BOOL VerifyLcid(LCID lcid) - ripped out of silver
+*
+* Purpose: Checks if the passed in lcid is valid.
+*
+* Inputs:
+* lcid : LCID that needs to be verified.
+*
+* Outputs: BOOL : return TRUE if the passed in lcid is a valid LCID
+* else return FALSE
+*
+*****************************************************************************/
+BOOL NEAR VerifyLcid(LCID lcid)
+{
+ BOOL fValidLcid;
+ INT i;
+
+ // Call the nlsapi function to compare string. If the compare
+ // succeeds then the LCID is valid or else the passed in lcid is
+ // invalid. This is because the only reason the comparision will
+ // fail is f the lcid is invalid.
+
+ char rgTest[] = "Test\0";
+
+ fValidLcid = (BOOL) (CompareStringA(lcid, NORM_IGNORECASE | NORM_IGNORENONSPACE,
+ rgTest, -1, rgTest, -1)== 2);
+
+ if (fValidLcid) {
+ // if DBCS lcid, update lead byte table appropriately
+
+#if defined(WIN32)
+ UINT CodePage;
+ CHAR szCodePage[6]; // space for an ascii integer
+
+ // Attempt to use IsDBCSLeadByteEx API to compute this. If this doesn't
+ // work, fall into the hardcoded code, to take our best shot at it.
+ if (GetLocaleInfoA(lcid,
+ LOCALE_NOUSEROVERRIDE | LOCALE_IDEFAULTANSICODEPAGE,
+ szCodePage,
+ sizeof(szCodePage)) != 0) {
+ CodePage = atoi(szCodePage);
+
+ // start at 128 since there aren't any lead bytes before that
+ for(i = 128; i < 256; i++) {
+ g_rgchLeadBytes[i] = (char)IsDBCSLeadByteEx(CodePage, (char)i);
+ }
+ goto Done;
+ }
+#endif //WIN32
+ switch (PRIMARYLANGID(lcid)) {
+ case LANG_CHINESE:
+ if (SUBLANGID(lcid) == SUBLANG_CHINESE_TRADITIONAL) {
+ g_rgchLeadBytes[0x80] = 0;
+ for (i = 0x81; i <= 0xFE; i++) {
+ g_rgchLeadBytes[i] = 1;
+ }
+ g_rgchLeadBytes[0xFF] = 0;
+ break;
+ }
+ // fall into LANG_KOREAN for SUBLANG_CHINESE_SIMPLIFIED
+ case LANG_KOREAN:
+ for (i = 0x80; i <= 0xA0; i++) {
+ g_rgchLeadBytes[i] = 0;
+ }
+ for (i = 0xA1; i <= 0xFE; i++) {
+ g_rgchLeadBytes[i] = 1;
+ }
+ g_rgchLeadBytes[0xFF] = 0;
+ break;
+ break;
+ case LANG_JAPANESE:
+ memset(g_rgchLeadBytes+128, 0, 128);
+ for (i = 0x81; i <= 0x9F; i++) {
+ g_rgchLeadBytes[i] = 1;
+ }
+ for (i = 0xE0; i <= 0xFC; i++) {
+ g_rgchLeadBytes[i] = 1;
+ }
+ break;
+ break;
+ default:
+ // not a DBCS LCID
+ memset(g_rgchLeadBytes+128, 0, 128);
+ break;
+ }
+#if defined(WIN32)
+Done: ;
+#endif //WIN32
+ }
+
+ return fValidLcid;
+}
+
+
+VOID NEAR FindIDispatch()
+{
+ char * szIDispatch = "IDispatch";
+ char * szIUnknown = "IUnknown";
+
+ // find existing type of this name with 0 levels of indirection
+ lpTypeIDispatch = FindType(szIDispatch, FALSE, tANY);
+
+ if (lpTypeIDispatch == NULL) {
+ // if not found here, then search all external type libraries for
+ // this type definition.
+ lpTypeIDispatch = FindExtType(NULL, szIDispatch);
+ }
+ if (lpTypeIDispatch == NULL) {
+ ParseError(PERR_NO_IDISPATCH);
+ }
+
+ // now do the same for IUnknown
+ // find existing type of this name with 0 levels of indirection
+ lpTypeIUnknown = FindType(szIUnknown, FALSE, tANY);
+
+ if (lpTypeIUnknown == NULL) {
+ // if not found here, then search all external type libraries for
+ // this type definition.
+ lpTypeIUnknown = FindExtType(NULL, szIUnknown);
+ }
+ if (lpTypeIUnknown == NULL) {
+ ParseError(PERR_NO_IUNKNOWN);
+ }
+}
diff --git a/private/oleauto/src/mktyplib/parser.h b/private/oleauto/src/mktyplib/parser.h
new file mode 100644
index 000000000..fd9a45bb5
--- /dev/null
+++ b/private/oleauto/src/mktyplib/parser.h
@@ -0,0 +1,93 @@
+// PARSER.H
+//
+// parser-specific data
+
+// attributes that must be the consistent among all property functions with
+// the same name
+#define fPropFuncBits (fSOURCE | fBINDABLE | fREQUESTEDIT | fDISPLAYBIND | fDEFAULTBIND | fHIDDEN)
+
+// Common bits
+#define fHelpBits (fHELPSTRING | fHELPCONTEXT)
+#define fFuncBits (fVARARG | fSTRING | fPropBits | fPropFuncBits)
+#define fParmBits (fOPTIONAL | fIN | fOUT | fSTRING)
+#define fTypeBits (fHelpBits | fHIDDEN | fUUID)
+#define fElemBits (fHelpBits | fHIDDEN)
+
+
+// *************************************
+// attributes on typelibs
+// *************************************
+#define VALID_LIBRARY_ATTR (fHelpBits | fUUID | fVERSION | fHELPFILE | fLCID | fRESTRICTED | fHIDDEN)
+#define VALID_LIBRARY_ATTR2 (f2CONTROL)
+
+// *************************************
+// attributes on typeinfos
+// *************************************
+#define VALID_TYPEDEF_ATTR (fTypeBits | fPUBLIC)
+#define VALID_TYPEDEF_ATTR2 (0)
+
+#define VALID_STRUCT_ENUM_UNION_ATTR (fTypeBits | fVERSION)
+#define VALID_STRUCT_ENUM_UNION_ATTR2 (0)
+
+#define VALID_MODULE_ATTR (fTypeBits | fVERSION | fDLLNAME)
+#define VALID_MODULE_ATTR2 (0)
+
+#define VALID_DISPINTER_ATTR (fTypeBits | fVERSION)
+#define VALID_DISPINTER_ATTR2 (f2NONEXTENSIBLE)
+
+#define VALID_INTERFACE_ATTR (fTypeBits | fVERSION | fODL)
+#define VALID_INTERFACE_ATTR2 (f2DUAL | f2NONEXTENSIBLE | f2OLEAUTOMATION)
+
+#define VALID_COCLASS_ATTR (fTypeBits | fVERSION | fAPPOBJECT | fLICENSED | fPREDECLID)
+#define VALID_COCLASS_ATTR2 (f2CONTROL)
+
+// *************************************
+// attributes on members of typeinfos
+// *************************************
+#define VALID_DISPINTER_PROP_ATTR (fElemBits | fID | fSTRING | fREADONLY | fPropFuncBits)
+#define VALID_DISPINTER_PROP_ATTR2 (0)
+
+#define VALID_MODULE_FUNC_ATTR (fElemBits | fFuncBits | fRESTRICTED | fENTRY)
+#define VALID_MODULE_FUNC_ATTR2 (0)
+
+#define VALID_MODULE_CONST_ATTR (fElemBits)
+#define VALID_MODULE_CONST_ATTR2 (0)
+
+#define VALID_INTERFACE_FUNC_ATTR (fElemBits | fFuncBits | fRESTRICTED | fID)
+#define VALID_INTERFACE_FUNC_ATTR2 (0)
+
+#define VALID_DISPINTER_FUNC_ATTR (fElemBits | fFuncBits | fID)
+#define VALID_DISPINTER_FUNC_ATTR2 (0)
+
+#define VALID_COCLASS_INTER_ATTR (fDEFAULT | fRESTRICTED | fSOURCE)
+#define VALID_COCLASS_INTER_ATTR2 (0)
+
+#define VALID_ENUM_ELEM_ATTR (fHelpBits)
+#define VALID_ENUM_ELEM_ATTR2 (0)
+
+#define VALID_STRUCT_UNION_ELEM_ATTR (fHelpBits | fSTRING)
+#define VALID_STRUCT_UNION_ELEM_ATTR2 (0)
+
+// *************************************
+// attributes on parameters
+// *************************************
+#define VALID_MODULE_PARM_ATTR (fParmBits | fLCID | fRETVAL)
+#define VALID_MODULE_PARM_ATTR2 (0)
+
+#define VALID_INTERFACE_PARM_ATTR (fParmBits | fLCID | fRETVAL)
+#define VALID_INTERFACE_PARM_ATTR2 (0)
+
+#define VALID_DISPINTER_PARM_ATTR (fParmBits)
+#define VALID_DISPINTER_PARM_ATTR2 (0)
+
+
+// Bits for ParseKnownType(), to control what special types it will accept
+#define fAllowSAFEARRAY 0x01
+#define fAllowCARRAY 0x02
+#define fAllowMODULE 0x04
+#define fAllowCOCLASS 0x08
+#define fAllowINTERFACE 0x10
+#define fAllowDISPINTER 0x20
+
+#define fAllowArray (fAllowSAFEARRAY | fAllowCARRAY)
+#define fAllowInter (fAllowINTERFACE | fAllowDISPINTER | fAllowCOCLASS)
diff --git a/private/oleauto/src/mktyplib/stdole.def b/private/oleauto/src/mktyplib/stdole.def
new file mode 100644
index 000000000..007c6d721
--- /dev/null
+++ b/private/oleauto/src/mktyplib/stdole.def
@@ -0,0 +1,15 @@
+LIBRARY STDOLE
+DESCRIPTION 'Standard OLE Type Library'
+
+EXETYPE WINDOWS
+CODE MOVEABLE DISCARDABLE
+DATA SINGLE MOVEABLE PRELOAD
+
+PROTMODE
+HEAPSIZE 512
+
+SEGMENTS _TEXT PRELOAD
+
+EXPORTS
+ WEP @0 RESIDENTNAME
+
diff --git a/private/oleauto/src/mktyplib/stdole.odl b/private/oleauto/src/mktyplib/stdole.odl
new file mode 100644
index 000000000..55b3607b4
--- /dev/null
+++ b/private/oleauto/src/mktyplib/stdole.odl
@@ -0,0 +1,117 @@
+
+#define FAR _far
+
+[
+ uuid(00020430-0000-0000-C000-000000000046),
+ lcid(0x0000), // lcid =0; locale independent.
+ helpstring("OLE Automation"),
+ version(1.0),
+ restricted
+]
+library stdole
+{
+ typedef unsigned long DWORD; // non-public typedef's
+ typedef unsigned long ULONG;
+ typedef unsigned short WORD;
+ typedef unsigned char BYTE;
+ typedef unsigned int UINT;
+ typedef DWORD LCID;
+
+ typedef struct GUID
+ {
+ DWORD Data1;
+ WORD Data2;
+ WORD Data3;
+ BYTE Data4[8];
+ } GUID;
+
+ typedef GUID IID; // non-public typedef's
+ typedef IID FAR * REFIID;
+ typedef LONG DISPID;
+
+ //UNDONE: what to do about ITypeInfo ???
+ #define ITypeInfo void
+
+ typedef VARIANT VARIANTARG;
+
+ typedef struct tagDISPPARAMS{
+ VARIANTARG FAR* rgvarg;
+ DISPID FAR* rgdispidNamedArgs;
+ UINT cArgs;
+ UINT cNamedArgs;
+ } DISPPARAMS;
+
+
+ typedef struct tagEXCEPINFO {
+ WORD wCode;
+ WORD wReserved;
+ BSTR bstrSource;
+ BSTR bstrDescription;
+ BSTR bstrHelpFile;
+ DWORD dwHelpContext;
+ void FAR* pvReserved;
+#if 0
+ // REVIEW: the current TypeInfo implementation cant represent
+ // function pointers, so we just fillin with a void* for now.
+ HRESULT (STDAPICALLTYPE FAR* pfnDeferredFillIn)(struct tagEXCEPINFO FAR*);
+#else
+ void FAR* pfnDeferredFillIn;
+#endif
+ SCODE scode;
+ } EXCEPINFO;
+
+ [uuid(00000000-0000-0000-C000-000000000046), odl]
+ interface IUnknown
+ {
+ [restricted] HRESULT QueryInterface([in] REFIID riid, [out] void FAR* FAR* ppvObj);
+ [restricted] ULONG AddRef(void);
+ [restricted] ULONG Release(void);
+ };
+
+ [uuid(00020400-0000-0000-C000-000000000046), odl]
+ interface IDispatch:IUnknown
+ {
+ [restricted] HRESULT GetTypeInfoCount([out]UINT FAR* pctinfo);
+
+ [restricted] HRESULT GetTypeInfo(
+ [in] UINT itinfo,
+ [in] LCID lcid,
+ [out] ITypeInfo FAR* FAR* pptinfo);
+
+ [restricted] HRESULT GetIDsOfNames(
+ [in] REFIID riid,
+ [in] char FAR* FAR* rgszNames,
+ [in] UINT cNames,
+ [in] LCID lcid,
+ [out] DISPID FAR* rgdispid);
+
+ [restricted] HRESULT Invoke(
+ [in] DISPID dispidMember,
+ [in] REFIID riid,
+ [in] LCID lcid,
+ [in] WORD wFlags,
+ [in] DISPPARAMS FAR* pdispparams,
+ [out] VARIANT FAR* pvarResult,
+ [out] EXCEPINFO FAR* pexcepinfo,
+ [out] UINT FAR* puArgErr);
+ };
+
+ [uuid(00020404-0000-0000-C000-000000000046), odl]
+ interface IEnumVARIANT:IUnknown
+ {
+
+ HRESULT Next(
+ [in] unsigned long celt,
+ [in] VARIANT FAR* rgvar,
+ [out] unsigned long FAR* pceltFetched);
+
+ HRESULT Skip([in] unsigned long celt);
+
+ HRESULT Reset(void);
+
+ HRESULT Clone([out] IEnumVARIANT FAR* FAR* ppenum);
+
+ };
+
+
+} // eof
diff --git a/private/oleauto/src/mktyplib/stdole.rc b/private/oleauto/src/mktyplib/stdole.rc
new file mode 100644
index 000000000..57eebf84d
--- /dev/null
+++ b/private/oleauto/src/mktyplib/stdole.rc
@@ -0,0 +1,114 @@
+/***
+*stdole.rc - Resource file for stdole.tlb
+*
+* Copyright (C) 1994-1995, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+*
+*Revision History:
+*
+*****************************************************************************/
+
+// first include the type library as a resource
+1 typelib stdole.tmp
+
+#include <windows.h>
+#include <ver.h>
+
+#include "verstamp.h"
+
+#ifndef OLEMINORVERS
+// win16 typelib.dll for Daytona will require a special build. Oh well.
+#define OLEMINORVERS 02 // assume OLE 2.02
+#endif //!OLEMINORVERS
+
+// for OLE, we want the major version # to be 2
+#undef rmj
+#define rmj 2
+#undef rmm
+#define rmm OLEMINORVERS // want version # to be 2.OLEMINORVERS.xxxx
+// keep 'rup' the same as OB's version number for simplicity
+
+// WARNING: Similar code exists in tlibutil.cxx in the implementation of
+// WARNING: OaBuildVersion -- keep the two versions in ssync!
+
+/* Define the version string with more preprocessor magic */
+#define STRING(x) #x
+#define VERSTRINGX(maj,min,rev) STRING(maj ## . ## min ## . ## rev ## \0)
+#define VERSTRING VERSTRINGX(rmj,rmm,rup)
+
+/* Version information */
+VS_VERSION_INFO VERSIONINFO
+//FILEVERSION rmj,rmm,rup,0
+//PRODUCTVERSION rmj,rmm,rup,0
+
+// WARNING: Similar code exists in tlibutil.cxx in the implementation of
+// WARNING: OaBuildVersion -- keep the two versions in ssync!
+
+// Use VBA's verstamp.h to get the file versions for now.
+FILEVERSION 2,rmm,rup,01
+PRODUCTVERSION 2,rmm,rup,01
+FILEFLAGSMASK VS_FFI_FILEFLAGSMASK
+
+#if 0
+#define BETAFLAG VS_FF_PRERELEASE
+#else //1
+#define BETAFLAG 0L
+#endif //1
+
+#ifdef _DEBUG
+FILEFLAGS VS_FF_DEBUG | BETAFLAG
+#else // !_DEBUG
+FILEFLAGS BETAFLAG
+#endif // !_DEBUG
+
+#if (OLEMINORVERS == 02)
+// re-distributable 16-bit DLL
+FILEOS VOS_DOS_WINDOWS16
+#else
+FILEOS VOS_DOS_WINDOWS32
+// non-re-distributable 16-bit DLL (shipped with the OS)
+#endif
+
+FILETYPE VFT_DLL
+FILESUBTYPE 0
+
+BEGIN
+ BLOCK "StringFileInfo"
+ BEGIN
+ BLOCK "040904E4"
+ BEGIN
+#if (OLEMINORVERS == 02)
+// re-distributable 16-bit TLB
+ VALUE "CompanyName", "Microsoft Corporation\0"
+ VALUE "FileDescription", "OLE Automation Type Library\0"
+ VALUE "FileVersion", "2.02\0"
+ VALUE "InternalName", "STDOLE.TLB\0"
+ VALUE "LegalCopyright", "Copyright \251 Microsoft Corp. 1993-1995\0"
+ VALUE "LegalTrademarks", "Microsoft\256 is a registered trademark of Microsoft Corporation. Windows(TM) is a trademark of Microsoft Corporation.\0"
+ VALUE "ProductName", "Microsoft OLE 2.02 for Windows\0"
+ VALUE "ProductVersion", "2.02\0"
+ VALUE "Comments", "Windows OLE TLB\0"
+#else
+// non-re-distributable 16-bit TLB (shipped with the OS)
+ VALUE "CompanyName", "Microsoft Corporation\0"
+ VALUE "FileDescription", "OLE 2.1 16/32 Interoperability Type Library\0"
+ VALUE "FileVersion", "2.1\0"
+ VALUE "InternalName", "STDOLE.TLB\0"
+ VALUE "LegalCopyright", "Copyright \251 Microsoft Corp. 1993-1995\0"
+ VALUE "LegalTrademarks", "Microsoft\256 is a registered trademark of Microsoft Corporation. Windows(TM) is a trademark of Microsoft Corporation.\0"
+ VALUE "ProductName", "Microsoft OLE 2.1 16/32 Interoperability for Windows NT\0"
+ VALUE "ProductVersion", "2.1\0"
+ VALUE "Comments", "Windows NT OLE 16/32 Interoperability TLB\0"
+#endif
+ END
+
+ END
+
+ BLOCK "VarFileInfo"
+ BEGIN
+ VALUE "Translation", 0x409, 1252
+ END
+END
+
diff --git a/private/oleauto/src/mktyplib/stdole32.rc b/private/oleauto/src/mktyplib/stdole32.rc
new file mode 100644
index 000000000..1b2879fd3
--- /dev/null
+++ b/private/oleauto/src/mktyplib/stdole32.rc
@@ -0,0 +1,92 @@
+/***
+*stdole32.rc - Resource file for stdole32.DLL
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+*
+*Revision History:
+*
+*****************************************************************************/
+
+// first include the type library as a resource
+1 typelib stdole32.tmp
+
+#include "windows.h"
+#include "verstamp.h" // for 'rup'
+
+#ifndef OLEMINORVERS
+#define OLEMINORVERS 10 // assume OLE 2.10
+#endif //!OLEMINORVERS
+
+/* Version information -- hardcoded */
+VS_VERSION_INFO VERSIONINFO
+FILEVERSION 2,OLEMINORVERS,rup,01
+PRODUCTVERSION 2,OLEMINORVERS,rup,01
+FILEFLAGSMASK VS_FFI_FILEFLAGSMASK
+
+#if 0
+#define BETAFLAG VS_FF_PRERELEASE
+#else //1
+#define BETAFLAG 0L
+#endif //1
+
+#ifdef _DEBUG
+FILEFLAGS VS_FF_DEBUG | BETAFLAG
+#else // !_DEBUG
+FILEFLAGS BETAFLAG
+#endif // !_DEBUG
+
+FILEOS VOS_NT_WINDOWS32
+
+FILETYPE VFT_DLL
+FILESUBTYPE 0
+
+BEGIN
+ BLOCK "StringFileInfo"
+ BEGIN
+ BLOCK "040904E4"
+ BEGIN
+ VALUE "CompanyName", "Microsoft Corporation\0"
+ VALUE "FileDescription", "Microsoft OLE 2.1 for Windows NT(TM) Operating System\0"
+ VALUE "FileVersion", "2.1\0"
+ VALUE "InternalName", "STDOLE32.TLB\0"
+ VALUE "LegalCopyright", "Copyright \251 Microsoft Corp. 1993-1995.\0"
+ VALUE "LegalTrademarks", "Microsoft\256 is a registered trademark of Microsoft Corporation. Windows NT(TM) is a trademark of Microsoft Corporation.\0"
+ VALUE "ProductName", "Microsoft OLE 2.1 for Windows NT(TM) Operating System\0"
+ VALUE "ProductVersion", "2.1\0"
+ VALUE "Comments", "Microsoft OLE 2.1 for Windows NT(TM) Operating System\0"
+ END
+
+ END
+
+ BLOCK "VarFileInfo"
+ BEGIN
+ VALUE "Translation", 0x409, 1252
+ END
+
+END
+
+#if ID_DEBUG
+// Assertion stuff for ole2disp
+#define ASSERT_ID_BREAK 5103
+#define ASSERT_ID_EXIT 5104
+#define ASSERT_ID_IGNORE 5105
+#define ASSERT_ID_LOC 5106
+#define ASSERT_ID_EXPR 5107
+#define ASSERT_ID_MSG 5108
+
+
+ASSERTFAILDLG DIALOG 72, 32, 260, 67
+STYLE DS_MODALFRAME | WS_POPUP | WS_VISIBLE | WS_CAPTION
+CAPTION "Assertion failure!"
+FONT 8, "MS Sans Serif"
+BEGIN
+ CTEXT "", ASSERT_ID_LOC, 11, 15, 240, 8
+ CTEXT "", ASSERT_ID_MSG, 11, 28, 240, 8
+ PUSHBUTTON "&Break", ASSERT_ID_BREAK, 54, 47, 40, 14
+ PUSHBUTTON "E&xit", ASSERT_ID_EXIT, 110, 47, 40, 14
+ PUSHBUTTON "&Ignore", ASSERT_ID_IGNORE, 166, 47, 40, 14
+END
+#endif // ID_DEBUG
diff --git a/private/oleauto/src/mktyplib/tlviewer.cpp b/private/oleauto/src/mktyplib/tlviewer.cpp
new file mode 100644
index 000000000..9725a5bcc
--- /dev/null
+++ b/private/oleauto/src/mktyplib/tlviewer.cpp
@@ -0,0 +1,1473 @@
+#include "mktyplib.h"
+
+#include <malloc.h>
+#include <stdio.h>
+
+#ifndef WIN32
+#include <ole2.h>
+#include "dispatch.h"
+#endif //!WIN32
+
+extern "C" {
+#include "tlviewer.hxx"
+
+extern VOID FAR DisplayLine (CHAR * lpszMsg) ;
+
+WORD fInParams = FALSE;
+char szSilent[50];
+
+VOID FAR DumpTypeLib (LPSTR szTypeLib)
+{
+ osStrCpy ( (LPSTR)&szDumpInputFile, szTypeLib);
+ osStrCpy ( (LPSTR)&szDumpOutputFile, defaultOutput ) ;
+ osStrCpy ( (LPSTR)&szSilent, "" ) ;
+ ProcessInput () ; // read input file
+}
+
+
+VOID NEAR ProcessInput(VOID)
+ {
+ HRESULT hRes ; // return code
+
+ hRes = NOERROR; // no ole initialization
+ if ( !hRes )
+ { // load the file
+ hRes = LoadTypeLib((LPSTR) szDumpInputFile, &ptLib) ;
+ OutToFile (hRes) ; // print result to the
+ // output file
+ //OleUninitialize ();
+
+ if ( osStrCmp((LPSTR)szSilent, (LPSTR)"silent") != 0 )
+ osMessage ((LPSTR)"Output is created successfully", (LPSTR)"Tlviewer") ;
+ }
+ else
+ osMessage ((LPSTR)"OleInitialize fails", (LPSTR)"Tlviewer") ;
+ }
+
+VOID NEAR OutToFile(HRESULT hRes)
+ {
+ FILE *hFile ; // file handle
+ UINT tInfoCount ; // total number of type info
+ UINT i ;
+ char szTmp[fMaxBuffer] ;
+
+#ifdef WIN16
+ // convert szDumpOutputFile in-place to OEM char set
+ AnsiToOem(szDumpOutputFile, szDumpOutputFile);
+#endif // WIN16
+
+ hFile = fopen(szDumpOutputFile, fnWrite); // open output file
+
+#ifdef WIN16
+ // convert back to ANSI
+ OemToAnsi(szDumpOutputFile, szDumpOutputFile);
+#endif // WIN16
+
+ if (hFile == NULL)
+ {
+ osStrCpy((LPSTR)&szTmp, "Fail to open input file") ;
+ osStrCat((LPSTR)&szTmp, (LPSTR)szDumpOutputFile) ;
+ osMessage ((LPSTR)szTmp, (LPSTR)"Tlviewer") ;
+ }
+ else
+ {
+ WriteOut(hFile, (LPSTR)szFileHeader) ; // output file header
+ WriteOut(hFile, (LPSTR)szDumpInputFile) ;
+ WriteOut(hFile, (LPSTR)szEndStr) ;
+
+ if ( LOWORD(hRes) ) // if it is not a valid type ****
+ WriteOut(hFile, szInputInvalid) ;// library
+ else
+ {
+ if ( fOutLibrary(hFile) )
+ {
+ tInfoCount = ptLib->GetTypeInfoCount() ;
+ for (i = 0 ; i < tInfoCount ; i++)
+ {
+ if ( LOWORD(ptLib->GetTypeInfo(i, &ptInfo)) )
+ {
+ WriteOut(hFile, (LPSTR)szReadFail) ;
+ WriteOut(hFile, (LPSTR)"type info\n\n") ;
+ }
+ else
+ {
+ if ( LOWORD(ptInfo->GetTypeAttr(&lpTypeAttr)) )
+ {
+ WriteOut(hFile, (LPSTR)szReadFail) ;
+ WriteOut(hFile, (LPSTR)"attributes of type info\n\n") ;
+ }
+ else
+ {
+ switch (lpTypeAttr->typekind)
+ {
+ case TKIND_ENUM:
+ tOutEnum(hFile, i) ;
+ break ;
+
+ case TKIND_RECORD:
+ tOutRecord(hFile, i) ;
+ break ;
+
+ case TKIND_MODULE:
+ tOutModule(hFile, i) ;
+ break ;
+
+ case TKIND_INTERFACE:
+ tOutInterface(hFile, i) ;
+ break ;
+
+ case TKIND_DISPATCH:
+ tOutDispatch(hFile, i) ;
+ break ;
+
+ case TKIND_COCLASS:
+ tOutCoclass(hFile, i) ;
+ break ;
+
+ case TKIND_ALIAS:
+ tOutAlias(hFile, i) ;
+ break ;
+
+ case TKIND_UNION:
+ tOutUnion(hFile, i) ;
+ break ;
+
+ default:
+ WriteOut(hFile, (LPSTR) "Type of definition is unknown") ;
+ } // switch
+ ptInfo->ReleaseTypeAttr(lpTypeAttr) ;
+ } // if gettypeattr
+ ptInfo->Release() ;// release the current TypeInfo
+ } // if gettypeinfo
+ } // for i
+ WriteOut(hFile, (LPSTR)"}\n") ; // output the closing }
+ // if fOutLibrary
+ ptLib->Release(); // clean up before exit
+ }
+ }
+
+ fclose(hFile); // finish writing to the output
+ hFile = NULL; // close done
+
+ }
+ }
+
+
+BOOL NEAR fOutLibrary(FILE *hFile)
+ {
+ TLIBATTR FAR *lpLibAttr ; // attributes of the library
+ char szTmp[16] ;
+ BOOL retval = FALSE ;
+
+ if ( LOWORD( ptLib->GetLibAttr(&lpLibAttr) ) ) // *****
+
+ {
+ WriteOut(hFile, (LPSTR)szReadFail) ;
+ WriteOut(hFile, (LPSTR)"attributes of library\n\n") ;
+ }
+ else
+ { // output documentational
+ tOutAttr(hFile, -1) ; // attributes first
+ // output id-related attributes
+ _ltoa((long)lpLibAttr->lcid, szTmp, 10) ; // output lcid;
+ WriteAttr(hFile, attrLcid, (LPSTR)szTmp, numValue) ; // default is 0
+ GetVerNumber (lpLibAttr->wMajorVerNum, lpLibAttr->wMinorVerNum, szTmp) ;
+ WriteAttr(hFile, attrVer, (LPSTR)szTmp, numValue) ; // output version
+ tOutUUID(hFile, lpLibAttr->guid) ;
+ if ( endAttrFlag )
+ {
+ WriteOut(hFile, fInParams ? szEndAttr : szEndAttrNl) ;
+ endAttrFlag = FALSE ;
+ }
+
+ ptLib->ReleaseTLibAttr(lpLibAttr) ; // de-allocate attribute
+
+ WriteOut(hFile, (LPSTR)"\nlibrary ") ;
+ tOutName(hFile, -1) ; // output name of library
+ WriteOut(hFile, (LPSTR)"{\n\n") ;
+ retval = TRUE ;
+ } // if GetLibAttributes
+ return (retval) ; // before exit
+ }
+
+VOID NEAR tOutEnum (FILE *hFile, UINT iTypeId)
+ {
+ WriteOut(hFile, (LPSTR) "\ntypedef\n");// output typedef first
+ tOutAttr(hFile, (int)iTypeId) ; // output attribute
+ tOutMoreAttr(hFile) ;
+ WriteOut(hFile, (LPSTR) "\nenum {\n") ;
+ tOutVar(hFile) ; // output enum members
+
+ WriteOut(hFile, (LPSTR) "} ") ; // close the definition and
+ tOutName(hFile, iTypeId) ; // output name of the enum type
+ WriteOut(hFile, (LPSTR) " ;\n\n") ;
+ }
+
+VOID NEAR tOutRecord (FILE *hFile, UINT iTypeId)
+ {
+ WriteOut(hFile, (LPSTR) "\ntypedef\n");// output typedef first
+ tOutAttr(hFile, (int)iTypeId) ; // output attribute
+ tOutMoreAttr(hFile) ;
+ WriteOut(hFile, (LPSTR) "\nstruct {\n") ;
+ tOutVar (hFile) ; // output members
+
+ WriteOut(hFile, (LPSTR) "} ") ;
+ tOutName(hFile, iTypeId) ;
+ WriteOut(hFile, (LPSTR) " ;\n\n") ;
+ }
+
+VOID NEAR tOutModule (FILE *hFile, UINT iTypeId)
+ {
+ tOutAttr(hFile, (int)iTypeId) ; // output attribute first
+ tOutMoreAttr(hFile) ;
+ WriteOut(hFile, (LPSTR) "\nmodule ") ;
+ tOutName(hFile, iTypeId) ;
+ WriteOut(hFile, " {\n") ;
+
+ tOutVar (hFile) ; // output each const
+
+ tOutFunc (hFile) ; // output each member function
+ WriteOut(hFile, (LPSTR) "}\n\n") ;
+ }
+
+VOID NEAR tOutInterface(FILE *hFile, UINT iTypeId)
+ {
+ HREFTYPE phRefType ;
+
+ tOutAttr(hFile, (int)iTypeId) ; // output attribute first
+ tOutMoreAttr(hFile) ;
+ WriteOut(hFile, (LPSTR) "\ninterface ") ;
+ tOutName(hFile, iTypeId) ;
+ // find out if the interface
+ if ( !LOWORD(ptInfo->GetRefTypeOfImplType(0, &phRefType)) )
+ {
+ isInherit = TRUE ;
+ tOutAliasName(hFile, phRefType) ; // is inherited from some other
+ isInherit = FALSE ; // interface
+ }
+ WriteOut(hFile, " {\n") ;
+
+ tOutFunc (hFile) ; // output each member function
+ WriteOut(hFile, (LPSTR) "}\n\n") ;
+ }
+
+VOID NEAR tOutDispatch (FILE *hFile, UINT iTypeId)
+ {
+ HREFTYPE phRefType ;
+
+ tOutAttr(hFile, (int)iTypeId) ; // output attribute first
+ tOutMoreAttr(hFile) ;
+ WriteOut(hFile, (LPSTR) "\ndispinterface ") ;
+ tOutName(hFile, iTypeId) ;
+
+ if ( !LOWORD(ptInfo->GetRefTypeOfImplType(0, &phRefType)) )
+ {
+ isInherit = TRUE ;
+ tOutAliasName(hFile, phRefType) ; // is inherited from some other
+ isInherit = FALSE ; // interface
+ }
+ WriteOut(hFile, (LPSTR) " {\n") ;
+
+ WriteOut(hFile, (LPSTR) "\nproperties:\n") ;
+ tOutVar (hFile) ; // output each date member
+
+ WriteOut(hFile, (LPSTR) "\nmethods:\n") ;
+ tOutFunc (hFile) ; // output each member function
+
+ WriteOut(hFile, (LPSTR) "}\n\n") ;
+ }
+
+VOID NEAR tOutCoclass (FILE *hFile, UINT iTypeId)
+ {
+
+ HREFTYPE phRefType ;
+ WORD i ;
+
+ tOutAttr(hFile, (int)iTypeId) ; // output attribute first
+ // output appobject attribute if
+ if ( lpTypeAttr->wTypeFlags == TYPEFLAG_FAPPOBJECT ) // it is set
+ WriteAttr(hFile, attrAppObj, NULL, noValue) ;
+ tOutMoreAttr(hFile) ;
+
+ WriteOut(hFile, (LPSTR) "\ncoclass ") ;
+ tOutName(hFile, iTypeId) ;
+ WriteOut(hFile, (LPSTR) " {\n") ;
+
+ for ( i = 0 ; i < lpTypeAttr->cImplTypes; i++ )
+ {
+ if ( LOWORD(ptInfo->GetRefTypeOfImplType(i, &phRefType)) )
+ {
+ WriteOut(hFile, szReadFail) ;
+ WriteOut(hFile, "GetRefTypeOfImpType\n") ;
+ }
+ else
+ tOutAliasName(hFile, phRefType) ;
+ }
+
+ WriteOut(hFile, (LPSTR) "}\n\n") ;
+ }
+
+VOID NEAR tOutAlias (FILE *hFile, UINT iTypeId)
+ {
+ char szTmp[16] ;
+
+ WriteOut(hFile, (LPSTR) "\ntypedef ") ;
+ tOutAttr(hFile, (int)iTypeId) ; // output attribute first
+ WriteAttr(hFile, attrPublic, (LPSTR)szTmp, noValue) ; // public attr
+ tOutMoreAttr(hFile) ;
+
+ tOutType(hFile, lpTypeAttr->tdescAlias) ; // output name of base-type
+
+ tOutName(hFile, iTypeId) ; // output name of new type
+ WriteOut(hFile, (LPSTR) ";\n\n") ;
+ }
+
+VOID NEAR tOutUnion (FILE *hFile, UINT iTypeId)
+ {
+ WriteOut(hFile, (LPSTR) "\ntypedef\n"); // output typedef first
+ tOutAttr(hFile, (int)iTypeId) ; // output attribute
+ tOutMoreAttr(hFile) ;
+ WriteOut(hFile, (LPSTR) "\nunion {\n") ;
+ tOutVar (hFile) ; // output members
+
+ WriteOut(hFile, (LPSTR) "} ") ;
+ tOutName(hFile, iTypeId) ;
+ WriteOut(hFile, (LPSTR) " ;\n\n") ;
+ }
+
+
+VOID NEAR tOutEncunion (FILE *hFile, UINT iTypeId)
+ {
+ WriteOut(hFile, (LPSTR) "\ntypedef\n"); // output typedef first
+ tOutAttr(hFile, (int)iTypeId) ; // output attribute
+ tOutMoreAttr(hFile) ;
+ WriteOut(hFile, (LPSTR) "\nencunion {\n") ;
+ tOutVar (hFile) ; // output members
+
+ WriteOut(hFile, (LPSTR) "} ") ;
+ tOutName(hFile, iTypeId) ;
+ WriteOut(hFile, (LPSTR) " ;\n\n") ;
+ }
+
+
+VOID NEAR tOutName (FILE *hFile, UINT iTypeId)
+ {
+ BSTR bstrName ;
+
+ if ( LOWORD(ptLib->GetDocumentation(iTypeId, &bstrName, NULL, NULL, NULL)) )
+ {
+ WriteOut(hFile, szReadFail) ;
+ WriteOut(hFile, "name of type definition") ;
+ }
+ else
+ {
+ WriteOut(hFile, (LPSTR) bstrName) ;
+ WriteOut(hFile, (LPSTR) " ") ;
+
+ if ( iTypeId == -1 ) // record name of the library
+ osStrCpy((LPSTR)&szLibName, (LPSTR)bstrName) ;
+
+ SysFreeString(bstrName) ;
+ }
+ }
+
+VOID NEAR tOutType (FILE *hFile, TYPEDESC tdesc)
+ {
+ char szTmp[40] ;
+
+ switch (tdesc.vt)
+ {
+ case VT_EMPTY:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "notSpec " ) ;
+ break ;
+ case VT_NULL:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "NULL " ) ;
+ break ;
+ case VT_I2:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "short " ) ;
+ break ;
+ case VT_I4:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "long " ) ;
+ break ;
+ case VT_R4:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "float " ) ;
+ break ;
+ case VT_R8:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "double " ) ;
+ break ;
+ case VT_CY:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "CURRENCY " ) ;
+ break ;
+ case VT_DATE:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "DATE " ) ;
+ break ;
+ case VT_BSTR:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "BSTR " ) ;
+ break ;
+ case VT_DISPATCH:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "IDispatch * (VT_DISPATCH) " ) ;
+ break ;
+ case VT_ERROR:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "scode " ) ;
+ break ;
+ case VT_BOOL:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "boolean " ) ;
+ break ;
+ case VT_VARIANT:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "VARIANT " ) ;
+ break ;
+ case VT_UNKNOWN:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "IUnknown * (VT_UNKNOWN) " ) ;
+ break ;
+ case VT_I1:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "char " ) ;
+ break ;
+ case VT_UI1:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "unsigned char " ) ;
+ break ;
+ case VT_UI2:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "unsigned short " ) ;
+ break ;
+ case VT_UI4:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "unsigned long " ) ;
+ break ;
+ case VT_I8:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "long long " ) ;
+ break ;
+ case VT_UI8:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "unsigned long long " ) ;
+ break ;
+ case VT_INT:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "int " ) ;
+ break ;
+ case VT_UINT:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "unsigned int " ) ;
+ break ;
+ case VT_VOID:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "void " ) ;
+ break ;
+ case VT_HRESULT:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "HRESULT " ) ;
+ break ;
+ case VT_PTR:
+ tOutType (hFile, *(tdesc.lptdesc)) ;
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "* " ) ;
+ break ;
+ case VT_SAFEARRAY:
+ if ( endAttrFlag )
+ {
+ WriteOut(hFile, fInParams ? szEndAttr : szEndAttrNl) ;
+ endAttrFlag = FALSE ;
+ }
+ WriteOut(hFile, (LPSTR)"SAFEARRAY ( ") ;
+ tOutType (hFile, *(tdesc.lptdesc)) ;
+ break ;
+ case VT_CARRAY:
+ cArrFlag = (SHORT)tdesc.lpadesc->cDims ; // get dimemsion of array
+ tOutType (hFile, tdesc.lpadesc->tdescElem) ;
+ break ;
+ case VT_USERDEFINED:
+ if ( endAttrFlag )
+ {
+ WriteOut(hFile, fInParams ? szEndAttr : szEndAttrNl) ;
+ endAttrFlag = FALSE ;
+ }
+ tOutAliasName (hFile, tdesc.hreftype) ;
+ break ; // output name of the user-defined type
+ case VT_LPSTR:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "LPSTR " ) ;
+ break ;
+ default:
+ osStrCpy ( (LPSTR)&szTmp, (LPSTR) "unknown type " ) ;
+ }
+
+ if ( endAttrFlag )
+ {
+ WriteOut(hFile, fInParams ? szEndAttr : szEndAttrNl) ;
+ endAttrFlag = FALSE ;
+ }
+
+ if ( tdesc.vt != VT_CARRAY && tdesc.vt != VT_USERDEFINED && tdesc.vt != VT_SAFEARRAY )
+ WriteOut(hFile, (LPSTR)szTmp) ;
+
+ if ( tdesc.vt == VT_SAFEARRAY )
+ WriteOut(hFile, ") ") ;
+
+ }
+
+VOID NEAR tOutCDim (FILE *hFile, TYPEDESC tdesc)
+ {
+ USHORT i ;
+ ULONG l ;
+ char szTmp[16] ;
+
+ for ( i = 0 ; i < cArrFlag ; i++ )
+ {
+ l = tdesc.lpadesc->rgbounds[i].cElements ;
+ _ltoa(l, szTmp, 10) ;
+ WriteOut(hFile, (LPSTR)"[") ;
+ WriteOut(hFile, (LPSTR)szTmp) ;
+ WriteOut(hFile, (LPSTR)"]") ;
+ }
+
+ cArrFlag = -1 ;
+ }
+
+VOID NEAR tOutAliasName (FILE *hFile, HREFTYPE phRefType)
+ {
+ ITypeInfo FAR *lpInfo ; // pointer to the type definition
+ ITypeLib FAR *lpLib ; // pointer to a type library
+ TYPEATTR FAR *lptAttr ;
+ BSTR bstrName ;
+ UINT iTypeId ;
+
+ if ( LOWORD(ptInfo->GetRefTypeInfo(phRefType, &lpInfo)) )
+ { // get TypeInfo of the alias
+ WriteOut(hFile, szReadFail) ;
+ WriteOut(hFile, "GetRefTypeInfo\n") ;
+ }
+ else
+ {
+ if ( lpTypeAttr->typekind == TKIND_COCLASS )
+ {
+ if ( LOWORD(lpInfo->GetTypeAttr(&lptAttr)) )
+ {
+ WriteOut(hFile, (LPSTR)szReadFail) ;
+ WriteOut(hFile, (LPSTR)"attribute of reftype\n\n") ;
+ }
+ else
+ {
+ if ( lptAttr->typekind == TKIND_INTERFACE )
+ WriteOut(hFile, (LPSTR)"interface ") ;
+ else
+ if ( lptAttr->typekind == TKIND_DISPATCH )
+ WriteOut(hFile, (LPSTR)"dispinterface ") ;
+
+ lpInfo->ReleaseTypeAttr(lptAttr) ;
+ }
+ }
+ else // output name of base-interface
+ if ( isInherit &&
+ (lpTypeAttr->typekind == TKIND_INTERFACE ||
+ lpTypeAttr->typekind == TKIND_DISPATCH) )
+ WriteOut(hFile, (LPSTR)" : ") ;
+
+
+ if ( LOWORD(lpInfo->GetContainingTypeLib(&lpLib, &iTypeId)) )
+ { // get id of the alias
+ WriteOut(hFile, (LPSTR)szReadFail) ;
+ WriteOut(hFile, (LPSTR)"GetAlias: containing typelib\n\n") ;
+ }
+ else
+ { // check origin of the alias
+ if ( LOWORD(lpLib->GetDocumentation(-1, &bstrName, NULL, NULL, NULL)) )
+ {
+ WriteOut(hFile, szReadFail) ;
+ WriteOut(hFile, "name of import library") ;
+ }
+ else
+ { // if it is not defined locally
+ if ( osStrCmp((LPSTR)szLibName, (LPSTR)bstrName) != 0 )
+ { // i.e. name of origin is diff
+ WriteOut(hFile, (LPSTR) bstrName) ;
+ WriteOut(hFile, (LPSTR)".") ;
+ } // from the name of library;
+ // output its origin
+ SysFreeString(bstrName) ;
+ }
+
+ if ( LOWORD(lpLib->GetDocumentation(iTypeId, &bstrName, NULL, NULL, NULL)) )
+ { // retrieve name of the alias
+ WriteOut(hFile, szReadFail) ;
+ WriteOut(hFile, "name of alias") ;
+ }
+ else
+ {
+ WriteOut(hFile, (LPSTR)bstrName) ;
+
+ if ( lpTypeAttr->typekind == TKIND_COCLASS )
+ WriteOut(hFile, (LPSTR)" ;\n") ;
+ else
+ WriteOut(hFile, (LPSTR)" ") ;
+
+ SysFreeString(bstrName) ;
+ }
+ }
+ }
+ }
+
+VOID NEAR tOutValue(FILE *hFile, BSTR bstrName, VARDESC FAR *lpVarDesc)
+ {
+ VARTYPE vvt ;
+ char szTmp[16] ;
+
+ if ( endAttrFlag )
+ {
+ WriteOut(hFile, fInParams ? szEndAttr : szEndAttrNl) ;
+ endAttrFlag = FALSE ;
+ }
+
+ if ( lpTypeAttr->typekind == TKIND_MODULE )
+ {
+ WriteOut(hFile, (LPSTR)"const ") ; // output the const keyword
+ tOutType(hFile, lpVarDesc->elemdescVar.tdesc) ; // output its type
+ }
+
+ WriteOut(hFile, (LPSTR)bstrName) ; // output name of member
+ WriteOut(hFile, (LPSTR)" = ") ;
+
+ vvt = lpVarDesc->lpvarValue->vt ;
+ switch ( vvt )
+ {
+ case VT_I2:
+ case VT_BOOL:
+ _itoa((int)lpVarDesc->lpvarValue->iVal, szTmp, 10) ;
+ break ;
+ default:
+ _ltoa((long)lpVarDesc->lpvarValue->lVal, szTmp, 10) ;
+ break ;
+ }
+ WriteOut(hFile, (LPSTR)szTmp) ; // output value of member
+
+ if ( lpTypeAttr->typekind == TKIND_MODULE )
+ WriteOut(hFile, (LPSTR)" ;\n") ;
+ else
+ WriteOut(hFile, (LPSTR)" ,\n") ;
+}
+
+
+VOID NEAR tOutMember(FILE *hFile, LONG idMember, BSTR bstrName, TYPEDESC tdesc)
+ {
+ char szTmp[16] ;
+
+#if 0 // UNDONE: TEMPORARY -- id's for everybody
+ if ( lpTypeAttr->typekind == TKIND_DISPATCH )
+#endif
+ {
+ szTmp[0] = '0';
+ szTmp[1] = 'x';
+ _ultoa(idMember, szTmp+2, 16) ; // output id in hex
+ WriteAttr(hFile, attrId, (LPSTR)szTmp, numValue) ;
+ }
+ // output name of base-type
+ tOutType(hFile, tdesc) ;
+ WriteOut(hFile, (LPSTR)bstrName) ; // output name of member
+ if ( cArrFlag != -1 ) // it is a c-array; output
+ tOutCDim (hFile, tdesc) ;
+ // dimensions of the array
+ WriteOut(hFile, (LPSTR)" ;\n") ;
+ }
+
+VOID NEAR tOutVar(FILE *hFile)
+ {
+ VARDESC FAR *ptVarDesc ;
+ BSTR bstrName ; // name of member
+ BSTR bstrDoc ; // file string
+ DWORD hContext ; // help context
+ char szTmp[16] ;
+ WORD i ;
+ LONG idMember ;
+ BSTR rgNames[MAX_NAMES];
+ UINT cNames, j ;
+
+ for (i = 0 ; i < lpTypeAttr->cVars; i++) // for every member
+ {
+ if ( LOWORD(ptInfo->GetVarDesc(i, &ptVarDesc)) )
+ {
+ WriteOut(hFile, szReadFail) ;
+ WriteOut(hFile, "variables\n") ;
+ }
+ else
+ {
+ idMember = ptVarDesc->memid ;
+ // this is readonly var
+ if ( ptVarDesc->wVarFlags == VARFLAG_FREADONLY )
+ WriteAttr(hFile, attrReadonly, NULL, noValue) ;
+
+ if ( LOWORD(ptInfo->GetDocumentation(idMember, &bstrName, &bstrDoc, &hContext, NULL)) )
+ {
+ WriteOut(hFile, szReadFail) ;
+ WriteOut(hFile, "attributes of variable\n") ;
+ }
+ else
+ {
+ _ltoa((long)hContext, szTmp, 10) ;// output helpcontext; default is 0
+ WriteAttr(hFile, attrHelpCont, (LPSTR)szTmp, numValue) ;
+
+ if ( bstrDoc != NULL ) // output helpstring if exists
+ WriteAttr(hFile, attrHelpStr, (LPSTR)bstrDoc, strValue) ;
+ // typedef enum or const in module
+ if ( lpTypeAttr->typekind == TKIND_ENUM || lpTypeAttr->typekind == TKIND_MODULE )
+ tOutValue (hFile, bstrName, ptVarDesc) ;
+ else // typedef struct or dispinterface
+ tOutMember (hFile, idMember, bstrName, ptVarDesc->elemdescVar.tdesc) ;
+
+ SysFreeString(bstrDoc) ; // release local bstr
+ // also checking the name
+ if ( LOWORD(ptInfo->GetNames(idMember, rgNames, MAX_NAMES, &cNames)) )
+ { // with GetNames
+ WriteOut(hFile, szReadFail) ;
+ WriteOut(hFile, "name of variable\n") ;
+ }
+ else
+ {
+ if ( cNames != 1 )
+ {
+ WriteOut(hFile, szReadFail) ;
+ WriteOut(hFile, "GetNames return more than one name\n") ;
+ }
+ else
+ {
+ if ( osStrCmp((LPSTR)rgNames[0], (LPSTR)bstrName) != 0 )
+ {
+ WriteOut(hFile, szReadFail) ;
+ WriteOut(hFile, "name of variable inconsistent\n") ;
+ }
+ }
+
+ for ( j = 0 ; j < cNames ; j++ )
+ SysFreeString(rgNames[j]) ;
+ }
+
+ SysFreeString(bstrName) ;
+ }
+ }
+ ptInfo->ReleaseVarDesc(ptVarDesc) ;
+ ptVarDesc = NULL ;
+ } // for i
+ }
+
+
+VOID NEAR tOutFuncAttr(FILE *hFile, FUNCDESC FAR *lpFuncDesc, DWORD hContext, BSTR bstrDoc)
+ {
+ char szTmp[16] ;
+
+ _ltoa((long)hContext, szTmp, 10) ; // output helpcontext; default is 0
+ WriteAttr(hFile, attrHelpCont, (LPSTR)szTmp, numValue) ;
+
+ if ( bstrDoc != NULL ) // output helpstring if exists
+ WriteAttr(hFile, attrHelpStr, (LPSTR)bstrDoc, strValue) ;
+ // output restricted attribute
+ if ( lpFuncDesc->wFuncFlags == FUNCFLAG_FRESTRICTED )
+ WriteAttr(hFile, attrRestrict, NULL, noValue) ;
+ // last parm is optional array
+ if ( lpFuncDesc->cParamsOpt == -1 ) // of Variants
+ WriteAttr(hFile, attrVar, NULL, noValue) ;
+
+#if 0 // UNDONE: TEMPORARY -- id's for everybody
+ if ( lpTypeAttr->typekind == TKIND_DISPATCH || lpTypeAttr->typekind == TKIND_INTERFACE)
+#endif
+ {
+ szTmp[0] = '0';
+ szTmp[1] = 'x';
+ _ultoa(lpFuncDesc->memid, szTmp+2, 16) ; // output id in hex
+ WriteAttr(hFile, attrId, (LPSTR)szTmp, numValue) ;
+ }
+#if 0
+ else // DISPID designates the
+ if ( lpFuncDesc->memid == DISPID_VALUE ) // default function
+ WriteAttr(hFile, attrDefault, NULL, noValue) ;
+#endif //0
+
+ switch ( lpFuncDesc->invkind ) // Note: if one of these
+ { // flag is set, name of
+ case INVOKE_FUNC: // parm can't be set: i.e.
+// WriteAttr(hFile, (LPSTR)"invoke_func", NULL, noValue) ;
+ break ; // GetNames only returns name
+ case INVOKE_PROPERTYGET: // of the function
+ WriteAttr(hFile, attrPropget, NULL, noValue) ;
+ break ;
+ case INVOKE_PROPERTYPUT:
+ WriteAttr(hFile, attrPropput, NULL, noValue) ;
+ break ;
+ case INVOKE_PROPERTYPUTREF:
+ WriteAttr(hFile, attrProppr, NULL, noValue) ;
+ break ;
+ default:
+ WriteAttr(hFile, (LPSTR)"unknown invkind", NULL, noValue) ;
+ }
+ }
+
+VOID NEAR tOutCallConv(FILE *hFile, FUNCDESC FAR *lpFuncDesc)
+ {
+ switch ( lpFuncDesc->callconv )
+ {
+ case CC_MSCPASCAL:
+ WriteOut(hFile, (LPSTR)"__pascal ") ;
+ break ;
+ case CC_MACPASCAL:
+ WriteOut(hFile, (LPSTR)"pascal ") ;
+ break ;
+ case CC_STDCALL:
+ WriteOut(hFile, (LPSTR)"__stdcall ") ;
+ break ;
+/* this has been cut
+ case CC_THISCALL:
+ WriteOut(hFile, (LPSTR)"__thiscall ") ;
+ break ;
+*/
+ case CC_CDECL:
+ WriteOut(hFile, (LPSTR)"__cdecl ") ;
+ break ;
+ default:
+ WriteOut(hFile, (LPSTR)"unknown calling convention ") ;
+ break ;
+ }
+ }
+
+VOID NEAR tOutParams(FILE *hFile, FUNCDESC FAR *lpFuncDesc, BSTR bstrName)
+ {
+ BSTR rgNames[MAX_NAMES];
+ UINT cNames ;
+ SHORT i ;
+
+ fInParams = TRUE;
+
+ WriteOut(hFile, (LPSTR)"(") ;
+
+ if ( lpFuncDesc->cParams == 0 )
+ WriteOut(hFile, (LPSTR)"void") ;
+ else
+ {
+ if ( LOWORD(ptInfo->GetNames(lpFuncDesc->memid, rgNames, MAX_NAMES, &cNames)) )
+ {
+ WriteOut(hFile, szReadFail) ;
+ WriteOut(hFile, "parm of func in definition\n") ;
+ }
+ else
+ {
+ if ( osStrCmp((LPSTR)rgNames[0], (LPSTR)bstrName) != 0 )
+ {
+ WriteOut(hFile, szReadFail) ;
+ WriteOut(hFile, "name of function inconsistent\n") ;
+ }
+ SysFreeString(rgNames[0]) ; // release name of function
+
+ for (i = 1; i <= lpFuncDesc->cParams; i++)
+ {
+ if ( i != 1 )
+ WriteOut(hFile, (LPSTR)", ") ;
+ // output in/out attribute
+ if ( lpFuncDesc->lprgelemdescParam[i-1].idldesc.wIDLFlags != 0 )
+ {
+ if ( ( lpFuncDesc->lprgelemdescParam[i-1].idldesc.wIDLFlags & IDLFLAG_FIN ) == IDLFLAG_FIN )
+ WriteAttr(hFile, attrIn, NULL, noValue) ;
+
+ if ( ( lpFuncDesc->lprgelemdescParam[i-1].idldesc.wIDLFlags & IDLFLAG_FOUT ) == IDLFLAG_FOUT )
+ WriteAttr(hFile, attrOut, NULL, noValue) ;
+ }
+ // check for optional parm
+ if ( ( lpFuncDesc->cParamsOpt + i ) > lpFuncDesc->cParams )
+ WriteAttr(hFile, attrOption, NULL, noValue) ;
+ // and output optional attr
+ // output name of base-type
+ tOutType(hFile, lpFuncDesc->lprgelemdescParam[i-1].tdesc) ;
+ if ( i < (SHORT) cNames )// output name of parm if its is
+ { // not property-accessor function
+ WriteOut(hFile, (LPSTR)rgNames[i]) ;
+ SysFreeString(rgNames[i]) ; // release name of parm's
+ }
+ else
+ WriteOut(hFile, (LPSTR)"PseudoName") ;
+
+ if ( cArrFlag != -1 ) // it is a c-array; output
+ tOutCDim (hFile, lpFuncDesc->lprgelemdescParam[i-1].tdesc) ;
+ // dimension of the array
+ } // for i = 1
+ } // GetNames
+
+ } // if (ptFunDesc->cParams)
+
+ WriteOut(hFile, (LPSTR)") ;\n") ;
+ fInParams = FALSE;
+ }
+
+
+VOID NEAR tOutFunc(FILE *hFile)
+ {
+ FUNCDESC FAR *ptFuncDesc ;
+ BSTR bstrName ; // name of member
+ BSTR bstrDoc ; // file string
+ DWORD hContext ; // help context
+ WORD i ;
+ // VOID FAR *lpvoid ;
+ char szTmp[16] ;
+
+ for (i = 0 ; i < lpTypeAttr->cFuncs; i++) // for every member function
+ {
+ if ( LOWORD(ptInfo->GetFuncDesc(i, &ptFuncDesc)) )
+ {
+ WriteOut(hFile, szReadFail) ;
+ WriteOut(hFile, "function of definition\n") ;
+ }
+ else
+ {
+ if ( LOWORD(ptInfo->GetDocumentation(ptFuncDesc->memid, &bstrName, &bstrDoc, &hContext, NULL)) )
+ {
+ WriteOut(hFile, szReadFail) ;
+ WriteOut(hFile, "attributes of function\n") ;
+ }
+ else
+ {
+ BSTR bstrDllName;
+ BSTR bstrEntryName;
+ WORD wOrdinal;
+#if 0
+ VOID FAR * lpVoid;
+#endif //0
+
+ if(!LOWORD(ptInfo->GetDllEntry(ptFuncDesc->memid,
+ ptFuncDesc->invkind,
+ &bstrDllName,
+ &bstrEntryName,
+ &wOrdinal)))
+ {
+
+#if 0 //UNDONE: TEMPORARY
+ ptInfo->AddressOfMember(ptFuncDesc->memid,
+ ptFuncDesc->invkind,
+ &lpVoid);
+#endif //1
+
+ WriteOut(hFile, szRefDll);
+ WriteOut(hFile, "DLL name = ");
+ WriteOut(hFile, (LPSTR) bstrDllName);
+ SysFreeString(bstrDllName) ;
+
+ WriteOut(hFile, "\nDLL entry point = ");
+ if ((LPSTR)bstrEntryName != NULL)
+ {
+ WriteOut(hFile, (LPSTR) bstrEntryName);
+ SysFreeString(bstrEntryName) ;
+ }
+ else
+ {
+ WriteOut(hFile, "ordinal ");
+ _itoa(wOrdinal, szTmp, 10) ;
+ WriteOut(hFile, szTmp);
+
+ }
+ WriteOut(hFile, "\n");
+ }
+ // output attr for function
+ tOutFuncAttr(hFile, ptFuncDesc, hContext, bstrDoc) ;
+ // output return type
+ tOutType(hFile, ptFuncDesc->elemdescFunc.tdesc) ;
+ // output calling convention
+ tOutCallConv(hFile, ptFuncDesc) ;
+ WriteOut(hFile, (LPSTR)bstrName) ; // output name of member function
+ tOutParams(hFile, ptFuncDesc, bstrName) ;
+ // output parameters
+ SysFreeString(bstrDoc) ; // release local bstr's
+ SysFreeString(bstrName) ;
+ }
+ }
+ ptInfo->ReleaseFuncDesc(ptFuncDesc) ;
+ ptFuncDesc = NULL ;
+ } // for i
+ }
+
+VOID NEAR tOutUUID (FILE *hFile, GUID inGuid)
+ {
+ char szTmp[50] ;
+ int i ;
+ // get a string representation
+ // for the incoming Guid value
+ if ( !(i = osRetrieveGuid ((LPSTR)szTmp, inGuid)) )
+ { WriteOut(hFile, szReadFail) ;
+ WriteOut(hFile, (LPSTR)"insufficient memory") ;
+ }
+ else
+ { // string is in {xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx}
+ szTmp[37] = '\0' ; // format, need to remove the {}
+ WriteAttr(hFile, attrUuid, (LPSTR)&szTmp[1], numValue) ;
+ }
+ }
+
+VOID NEAR tOutAttr (FILE *hFile, int iTypeId)
+ {
+ BSTR bstrDoc ; // file string
+ BSTR bstrHelp ; // name of help file
+ DWORD hContext ; // help context
+ char szTmp[16] ;
+
+
+ if ( LOWORD(ptLib->GetDocumentation(iTypeId, NULL, &bstrDoc, &hContext, &bstrHelp)) )
+ {
+ WriteOut(hFile, (LPSTR)szReadFail) ;
+ WriteOut(hFile, (LPSTR)"documentational attribute\n\n") ;
+ }
+ else
+ {
+ _ltoa((long)hContext, szTmp, 10) ;// output helpcontext; default is 0
+ WriteAttr(hFile, attrHelpCont, (LPSTR)szTmp, numValue) ;
+
+ if ( bstrDoc != NULL ) // output helpstring if exists
+ WriteAttr(hFile, attrHelpStr, (LPSTR)bstrDoc, strValue) ;
+
+ if ( bstrHelp != NULL ) // output helpfile if exists
+ WriteAttr(hFile, attrHelpFile, (LPSTR)bstrHelp, strValue) ;
+
+ SysFreeString(bstrDoc) ; // release local bstr's
+ SysFreeString(bstrHelp) ;
+ }
+ }
+
+VOID NEAR tOutMoreAttr (FILE *hFile)
+ {
+ char szTmp[16] ;
+
+ GetVerNumber (lpTypeAttr->wMajorVerNum, lpTypeAttr->wMinorVerNum, szTmp) ;
+ WriteAttr(hFile, attrVer, (LPSTR)szTmp, numValue) ; // output version
+ tOutUUID(hFile, lpTypeAttr->guid) ;
+ if ( endAttrFlag )
+ {
+ WriteOut(hFile, fInParams ? szEndAttr : szEndAttrNl) ;
+ endAttrFlag = FALSE ;
+ }
+ }
+
+
+VOID NEAR WriteAttr(FILE *hFile, LPSTR lpszAttr, LPSTR lpszStr, int ivalType)
+ {
+ BOOL firstAttr = FALSE ;
+
+ if ( !endAttrFlag )
+ {
+ if (!fInParams)
+ WriteOut(hFile, "\n") ; // output NL for readablilty
+
+ WriteOut(hFile, szBeginAttr) ; // output "[" first
+ endAttrFlag = TRUE ;
+ firstAttr = TRUE ;
+ }
+ // this is not the first
+ if ( !firstAttr ) { // attribute to be written
+ if (fInParams)
+ WriteOut(hFile, (LPSTR)", ") ; // need to put a , before
+ else
+ WriteOut(hFile, (LPSTR)",\n") ;
+ }
+
+ // output name of attribute
+ WriteOut(hFile, lpszAttr) ;
+ if ( ivalType != noValue ) // attribute has a value
+ {
+ WriteOut(hFile, (LPSTR)"(") ;
+ if ( ivalType != numValue ) // value is a string
+ WriteOut(hFile, (LPSTR)"\"") ;
+
+ WriteOut(hFile, lpszStr) ; // output value of attribute
+ if ( ivalType != numValue ) // close the string value
+ WriteOut(hFile, (LPSTR)"\"") ;
+ WriteOut(hFile, (LPSTR)")") ;
+ }
+ }
+
+
+VOID NEAR GetVerNumber (WORD wMajorNum, WORD wMinorNum, char *szVersion)
+ {
+ char szTmp[6] ;
+
+ _ltoa((long)wMajorNum, szVersion, 10) ;
+ _ltoa((long)wMinorNum, szTmp, 10) ;
+
+ osStrCat((LPSTR)szVersion, (LPSTR)".") ; // major.
+ osStrCat((LPSTR)szVersion, (LPSTR)szTmp) ; // major.minor
+ }
+
+VOID NEAR WriteOut(FILE *hFile, LPSTR lpszData)
+ {
+ char szBuffer[fMaxBuffer];
+
+ osStrCpy((LPSTR)&szBuffer, lpszData) ;
+
+ if (fputs(szBuffer, hFile) < 0) // write the data
+ {
+ osStrCpy((LPSTR)&szBuffer, "Fail to write to file ") ;
+ osStrCat((LPSTR)&szBuffer, lpszData) ;
+ osMessage ((LPSTR)szBuffer, (LPSTR)"Tlviewer") ;
+ }
+ }
+
+/* -------------------------------------------------------------------------
+ Test: OSUTIL
+
+ Copyright (C) 1991, Microsoft Corporation
+
+ Component: OLE Programmability
+
+ Major Area: Type Information Interface
+
+ Sub Area: ITypeInfo
+
+ Test Area:
+
+ Keyword: Win16
+
+ ---------------------------------------------------------------------------
+ Purpose: Library routines for programs that run under Win16
+
+ Scenarios:
+
+ Abstract:
+
+ ---------------------------------------------------------------------------
+ Category:
+
+ Product:
+
+ Related Files: osutil.hxx
+
+ Notes:
+ ---------------------------------------------------------------------------
+ Revision History:
+
+ [ 0] 09-Mar-1993 Angelach: Created Test
+ [ 1] dd-mmm-yyyy changed made, by whom, and why
+ ---------------------------------------------------------------------------
+*/
+
+
+/*---------------------------------------------------------------------------
+ NAME : osAllocSpaces
+
+ PURPOSE : obtains some spaces from the far heap
+
+ INPUTS : nSize - no of bytes to be allocated
+
+ OUTPUT : pointer to the allocated space
+
+ NOTES : caller is responsible to free up the memory after used
+
+---------------------------------------------------------------------------*/
+
+char FAR * osAllocSpaces(WORD nSize)
+ {
+ return ( (char FAR * )_fmalloc(nSize) ) ;
+ }
+
+
+/*---------------------------------------------------------------------------
+ NAME : osDeAllocSpaces
+
+ PURPOSE : returns spaces that have been obtained from the far heap
+
+ INPUTS : lpsz - pointer to the spaces to be returned
+
+ OUTPUT : none
+
+ NOTES : caller is responsible to free up the memory after used
+
+---------------------------------------------------------------------------*/
+
+VOID FAR osDeAllocSpaces(char FAR *lpsz)
+ {
+ _ffree( lpsz ) ;
+ }
+
+
+/*---------------------------------------------------------------------------
+ NAME : osStrCmp
+
+ PURPOSE : Calls lstrcmp to perform comparsion on strings
+
+ INPUTS : lpszIn, lpszExp; strings to be compared
+
+ OUTPUT : none
+
+ NOTES :
+
+---------------------------------------------------------------------------*/
+
+int FAR osStrCmp (LPSTR lpszIn, LPSTR lpszExp)
+ {
+ return ( _fstrcmp(lpszIn, lpszExp) ) ;
+ }
+
+
+/*---------------------------------------------------------------------------
+ NAME : osStrCpy
+
+ PURPOSE : Calls lstrcpy to perform string copy
+
+ INPUTS : lpszDest - destination for string copy
+ lpszSrc - source string for string copy
+
+ OUTPUT : none
+
+ NOTES :
+
+---------------------------------------------------------------------------*/
+
+VOID FAR osStrCpy (LPSTR lpszDest, LPSTR lpszSrc)
+ {
+ _fstrcpy(lpszDest, lpszSrc) ;
+ }
+
+
+/*---------------------------------------------------------------------------
+ NAME : osStrCat
+
+ PURPOSE : Calls lstrcat to perform string concatenation
+
+ INPUTS : lpszDest - destination for string concatenation
+ lpszSrc - source string for concatenation
+
+ OUTPUT : none
+
+ NOTES :
+
+---------------------------------------------------------------------------*/
+
+VOID FAR osStrCat (LPSTR lpszDest, LPSTR lpszSrc)
+ {
+ _fstrcat(lpszDest, lpszSrc) ;
+ }
+
+/*---------------------------------------------------------------------------
+ NAME : osCreateGuid
+
+ PURPOSE : Converts a GUID value from string to GUID format
+
+ INPUTS : lpszGuid - string contains the desired GUID value
+
+ OUTPUT : pointer to the GUID structure
+
+ NOTES : caller is responsible to free up the memory after used
+
+---------------------------------------------------------------------------*/
+
+GUID FAR * osCreateGuid(LPSTR lpszGuid)
+ {
+
+ GUID FAR * lpGuid ;
+ HRESULT hRes ;
+
+ lpGuid = (GUID FAR *) osAllocSpaces(sizeof(GUID)) ;// allocate space
+ // for the Guid
+ if ( lpGuid )
+ { // convert string to GUID format
+ hRes = CLSIDFromString(lpszGuid, (LPCLSID)lpGuid);
+ if ( LOWORD (hRes) )
+ {
+ osDeAllocSpaces ((char FAR *)lpGuid) ;// release space before exit
+ return NULL ;
+ }
+ else
+ return lpGuid ; // return pointer to the
+ } // GUID structure
+ else
+ return NULL ; // no space is allocated
+
+ }
+
+
+/*---------------------------------------------------------------------------
+ NAME : osRetrieveGuid
+
+ PURPOSE : Converts a GUID structure to a readable string format
+
+ INPUTS : lpszGuid - string representation of the GUID will be returned
+ GUID - the GUID structure in concern
+
+ OUTPUT : True if conversion is succeed
+
+ NOTES :
+
+---------------------------------------------------------------------------*/
+
+BOOL FAR osRetrieveGuid (LPSTR lpszGuid, GUID inGuid)
+ {
+ char FAR * lpszTmp ;
+ HRESULT hRes ;
+
+ if ( lpszGuid )
+ { // convert GUID to it string
+ hRes = StringFromCLSID((REFCLSID) inGuid, &lpszTmp) ;
+ if ( LOWORD (hRes) ) // representation
+ {
+ return FALSE ;
+ }
+ else
+ {
+ _fstrcpy (lpszGuid, (LPSTR)lpszTmp) ;
+ // UNDONE: should free the memory with OLE's iMalloc
+ //osDeAllocSpaces (lpszTmp) ;// release space before exit
+ return TRUE ;
+ }
+ }
+ else
+ return FALSE ;
+ }
+
+/*---------------------------------------------------------------------------
+ NAME : osGetSize
+
+ PURPOSE : returns size of the input data
+
+ INPUTS : inVT - data type; WORD
+
+ OUTPUT : size of inVT; WORD
+
+ NOTES :
+
+---------------------------------------------------------------------------*/
+
+WORD FAR osGetSize (WORD inVT)
+ {
+ WORD tSize ;
+
+ switch ( inVT )
+ {
+ case VT_I2:
+ tSize = sizeof(short) ;
+ break ;
+ case VT_I4:
+ tSize = sizeof(long) ;
+ break ;
+ case VT_R4:
+ tSize = sizeof(float) ;
+ break ;
+ case VT_R8:
+ tSize = sizeof(double) ;
+ break ;
+ case VT_CY:
+ tSize = sizeof(CY) ;
+ break ;
+ case VT_DATE:
+ tSize = sizeof(DATE) ;
+ break ;
+ case VT_BSTR:
+ tSize = sizeof(BSTR) ;
+ break ;
+ case VT_ERROR:
+ tSize = sizeof(SCODE) ;
+ break ;
+ case VT_BOOL:
+ tSize = sizeof(VARIANT_BOOL) ;
+ break ;
+ case VT_VARIANT:
+ tSize = sizeof(VARIANT) ;
+ break ;
+ case VT_I1:
+ tSize = sizeof(char) ;
+ break ;
+ case VT_UI1:
+ tSize = sizeof(char) ;
+ break ;
+ case VT_UI2:
+ tSize = sizeof(short) ;
+ break ;
+ case VT_UI4:
+ tSize = sizeof(long) ;
+ break ;
+ case VT_I8:
+ tSize = sizeof(long)*2 ;
+ break ;
+ case VT_UI8:
+ tSize = sizeof(long)*2 ;
+ break ;
+ case VT_INT:
+ tSize = sizeof(int) ;
+ break ;
+ case VT_UINT:
+ tSize = sizeof(int) ;
+ break ;
+ case VT_VOID:
+ tSize = 0 ;
+ break ;
+ case VT_HRESULT:
+ tSize = sizeof(HRESULT) ;
+ break ;
+ case VT_LPSTR:
+ tSize = sizeof(LPSTR) ;
+ break ;
+ case VT_PTR:
+ tSize = 4 ;
+ break ;
+ case VT_SAFEARRAY:
+ tSize = sizeof(ARRAYDESC FAR *) ;
+ break ;
+ default:
+ tSize = 1 ;
+ break ;
+ }
+
+ return tSize ;
+}
+
+/*---------------------------------------------------------------------------
+ NAME : osGetMemberSize
+
+ PURPOSE : returns size of the member, type of which is inVT, of a struct
+
+ INPUTS : pSize - max size of the previous members; WORD
+ inVT - type of the current member; WORD
+
+ OUTPUT : size of the current member; WORD
+
+ NOTES : value is machine dependent:
+ Win16 = 1 (everything is packed -> always = 1)
+ Win32 = natural alignment (everything is on the even-byte
+ boundary; size of every member is based on the biggest
+ size of the members
+ mac = everything is on the even-byte boundary
+ see silver\cl\clutil.cxx for a table of the alignement information
+---------------------------------------------------------------------------*/
+
+WORD FAR osGetMemberSize (WORD *pSize, WORD inVT)
+ {
+ WORD aSize ;
+
+ aSize = osGetSize(inVT) ;
+
+ return aSize ;
+ }
+
+/*---------------------------------------------------------------------------
+ NAME : osGetAlignment
+
+ PURPOSE : returns value of the alignment
+
+ INPUTS : none
+
+ OUTPUT : value of the aliangment; WORD
+
+ NOTES : value is machine dependent:
+ Win16 = 1 (everything is packed -> always = 1)
+ Win32 = natural alignment (everything is on the even-byte
+ boundary)
+ mac = everything is on the even-byte boundary
+ see silver\cl\clutil.cxx for a table of the alignement information
+---------------------------------------------------------------------------*/
+
+WORD FAR osGetAlignment ()
+ {
+ return 1 ;
+ }
+
+
+
+/*---------------------------------------------------------------------------
+ NAME : osMessage
+
+ PURPOSE : Displays a MessageBox
+
+ INPUTS : Message to be displayed; a string of characters
+
+ OUTPUT : none
+
+ NOTES :
+
+---------------------------------------------------------------------------*/
+
+VOID FAR osMessage (LPSTR lpszMsg, LPSTR lpszTitle)
+ {
+#ifdef MAC
+ DisplayLine (lpszMsg) ;
+#else
+ MessageBox (NULL, lpszMsg, lpszTitle, MB_OK) ;
+#endif
+ }
+ }
diff --git a/private/oleauto/src/mktyplib/tlviewer.hxx b/private/oleauto/src/mktyplib/tlviewer.hxx
new file mode 100644
index 000000000..3bd3c6d0c
--- /dev/null
+++ b/private/oleauto/src/mktyplib/tlviewer.hxx
@@ -0,0 +1,157 @@
+/* -------------------------------------------------------------------------
+ Test: OSUTIL
+
+ Copyright (C) 1991, Microsoft Corporation
+
+ Component: OLE Programmability
+
+ Major Area: Type Information Interface
+
+ Sub Area: ITypeInfo
+
+ Test Area:
+
+ Keyword: Win16
+
+ ---------------------------------------------------------------------------
+ Purpose: constants for programs that run under Win16
+
+ Scenarios:
+
+ Abstract:
+
+ ---------------------------------------------------------------------------
+ Category:
+
+ Product:
+
+ Related Files:
+
+ Notes:
+ ---------------------------------------------------------------------------
+ Revision History:
+
+ [ 0] 09-Mar-1993 Angelach: Created Test
+ [ 1] dd-mmm-yyyy changed made, by whom, and why
+ ---------------------------------------------------------------------------
+*/
+
+
+// routines defined in osutil.cpp
+
+char FAR * osAllocSpaces (WORD) ;
+VOID FAR osDeAllocSpaces (char FAR *) ;
+GUID FAR * osCreateGuid (LPSTR) ;
+BOOL FAR osRetrieveGuid (LPSTR, GUID) ;
+WORD FAR osGetSize (WORD) ;
+WORD FAR osGetMemberSize (WORD *, WORD) ;
+WORD FAR osGetAlignment (VOID) ;
+int FAR osStrCmp (LPSTR, LPSTR) ;
+VOID FAR osStrCpy (LPSTR, LPSTR) ;
+VOID FAR osStrCat (LPSTR, LPSTR) ;
+
+HRESULT FAR osOleInit (VOID) ;
+VOID FAR osMessage (LPSTR, LPSTR) ;
+
+// external routine
+
+VOID FAR mainEntry (LPSTR lpCmd) ;
+
+#define defaultOutput (LPSTR) "tlviewer.out"
+#define cchFilenameMax 256 // max chars in a filename
+#define fMaxBuffer 256
+#define aMaxName 15
+#define MAX_NAMES 65
+
+// name of valid attributes
+#define attrAppObj (LPSTR) "appobject"
+#define attrDefault (LPSTR) "default"
+#define attrDllName (LPSTR) "dllname"
+#define attrEntry (LPSTR) "entry"
+#define attrHelpCont (LPSTR) "helpcontext"
+#define attrHelpFile (LPSTR) "helpfile"
+#define attrHelpStr (LPSTR) "helpstring"
+#define attrId (LPSTR) "id"
+#define attrIn (LPSTR) "in"
+#define attrLcid (LPSTR) "lcid"
+#define attrOption (LPSTR) "optional"
+#define attrOut (LPSTR) "out"
+#define attrPropget (LPSTR) "propget"
+#define attrPropput (LPSTR) "propput"
+#define attrProppr (LPSTR) "propputref"
+#define attrPublic (LPSTR) "public"
+#define attrRestrict (LPSTR) "restricted"
+#define attrReadonly (LPSTR) "readonly"
+#define attrString (LPSTR) "string"
+#define attrUuid (LPSTR) "uuid"
+#define attrVar (LPSTR) "vararg"
+#define attrVer (LPSTR) "version"
+
+#define noValue 0 // attribute has no value
+#define numValue 1 // attribute has numeric value
+#define strValue 2 // attribute has string value
+
+
+#define fnWrite "w" // file attribute - write only
+
+#define szFileHeader (LPSTR) "/* Textual file generated for type library: "
+#define szEndStr (LPSTR) " */\n\n\n"
+#define szInputInvalid (LPSTR) " Input file is not a valid type library\n\n"
+#define szReadFail (LPSTR) " // *** Error in reading the type library: "
+#define szBeginAttr (LPSTR) "["
+#define szEndAttr (LPSTR) "] "
+#define szEndAttrNl (LPSTR) "]\n"
+#define szRefDll (LPSTR) " // this function referring routine in a dll\n"
+#define szImpLib (LPSTR) " // defined in library: "
+
+// global variables
+char szDumpInputFile[cchFilenameMax] ; // name of input library file
+char szDumpOutputFile[cchFilenameMax] ; // name of output text file
+char szLibName[cchFilenameMax] ; // name of the type library
+
+ITypeLib FAR *ptLib ; // pointer to the type library
+ITypeInfo FAR *ptInfo ; // pointer to the type definition
+TYPEATTR FAR *lpTypeAttr ; // pointer to attribute of type def
+int strFlag = 0 ; // for string attribute
+BOOL endAttrFlag = FALSE ; // if need to end the attribute-list
+short cArrFlag = -1 ; // if it is a c array
+BOOL isInherit = FALSE ; // if the interface has a base interface
+
+// prototypes for local functions
+
+VOID NEAR ProcessInput (VOID) ;
+VOID NEAR OutToFile (HRESULT) ;
+BOOL NEAR fOutLibrary (FILE *) ;
+VOID NEAR tOutEnum (FILE *, UINT) ;
+VOID NEAR tOutRecord (FILE *, UINT) ;
+VOID NEAR tOutModule (FILE *, UINT) ;
+VOID NEAR tOutInterface(FILE *, UINT) ;
+VOID NEAR tOutDispatch (FILE *, UINT) ;
+VOID NEAR tOutCoclass (FILE *, UINT) ;
+VOID NEAR tOutAlias (FILE *, UINT) ;
+VOID NEAR tOutUnion (FILE *, UINT) ;
+VOID NEAR tOutEncunion (FILE *, UINT) ;
+VOID NEAR tOutName (FILE *, UINT) ;
+VOID NEAR tOutType (FILE *, TYPEDESC) ;
+VOID NEAR tOutCDim (FILE *, TYPEDESC) ;
+VOID NEAR tOutAliasName(FILE *, HREFTYPE) ;
+VOID NEAR tOutValue (FILE *, BSTR, VARDESC FAR *) ;
+VOID NEAR tOutMember (FILE *, LONG, BSTR, TYPEDESC) ;
+VOID NEAR tOutVar (FILE *) ;
+VOID NEAR tOutFuncAttr (FILE *, FUNCDESC FAR *, DWORD, BSTR) ;
+VOID NEAR tOutCallConv (FILE *, FUNCDESC FAR *) ;
+VOID NEAR tOutParams (FILE *, FUNCDESC FAR *, BSTR) ;
+VOID NEAR tOutFunc (FILE *) ;
+VOID NEAR tOutUUID (FILE *, GUID) ;
+VOID NEAR tOutAttr (FILE *, int) ;
+VOID NEAR tOutMoreAttr (FILE *) ;
+VOID NEAR WriteAttr (FILE *, LPSTR, LPSTR, int) ;
+VOID NEAR GetVerNumber (WORD w, WORD, char *) ;
+VOID NEAR WriteOut (FILE *, LPSTR) ;
+
+
+// prototypes for routines defined in osutil.cpp
+
+char FAR * osAllocSpaces (WORD nSize) ;
+VOID FAR osDeAllocSpaces (char FAR *lpsz) ;
+BOOL FAR osRetrieveGuid (LPSTR, GUID) ;
diff --git a/private/oleauto/src/mktyplib/tmpguid.c b/private/oleauto/src/mktyplib/tmpguid.c
new file mode 100644
index 000000000..b2477cb98
--- /dev/null
+++ b/private/oleauto/src/mktyplib/tmpguid.c
@@ -0,0 +1,23 @@
+/***
+*tmpguid.c
+*
+* Copyright (C) 1993, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Temporary definitions of GUIDs that will eventually be picked
+* up from typeinfo libs.
+*
+*****************************************************************************/
+
+#include "mktyplib.h"
+#include <ole2.h>
+
+// this redefines the DEFINE_GUID() macro to do allocation.
+//
+#include <initguid.h>
+
+DEFINE_OLEGUID(IID_ITypeInfo, 0x00020401, 0, 0);
+#ifdef MAC // UNDONE: temporary for DIMALLOC hack
+DEFINE_OLEGUID(IID_IUnknown, 0x00000000, 0, 0);
+#endif //MAC
diff --git a/private/oleauto/src/mktyplib/tokens.h b/private/oleauto/src/mktyplib/tokens.h
new file mode 100644
index 000000000..2d21f65ba
--- /dev/null
+++ b/private/oleauto/src/mktyplib/tokens.h
@@ -0,0 +1,132 @@
+// lexer-specific defines and types
+
+// reserved word and special token ID's
+typedef enum {
+ RW_NOTFOUND = 0,
+// special character RWs
+ RW_EOF,
+ RW_LBRACKET,
+ RW_RBRACKET,
+ RW_LCURLY,
+ RW_RCURLY,
+ RW_LPAREN,
+ RW_RPAREN,
+ RW_SEMI,
+ RW_COLON,
+ RW_PERIOD,
+ RW_COMMA,
+ RW_ASSIGN,
+ RW_POINTER,
+ RW_HYPHEN,
+
+// keyword RWs
+ RW_LIBRARY,
+ RW_TYPEDEF,
+ RW_ENUM,
+ RW_STRUCT,
+ RW_MODULE,
+ RW_INTERFACE,
+ RW_DISPINTERFACE,
+ RW_COCLASS,
+ RW_PROPERTIES,
+ RW_METHODS,
+ RW_IMPORTLIB,
+ RW_PASCAL,
+ RW_CDECL,
+ RW_STDCALL,
+ RW_UNSIGNED,
+ RW_UNION,
+ RW_EXTERN,
+ RW_FAR,
+ RW_SAFEARRAY,
+ RW_CONST,
+#if FV_PROPSET
+ RW_PROPERTY_SET,
+#endif //FV_PROPSET
+
+// literals
+ LIT_STRING,
+ LIT_NUMBER,
+ LIT_UUID,
+ LIT_ID,
+
+// operators
+ OP_ADD,
+ OP_SUB,
+ OP_MUL,
+ OP_DIV,
+ OP_MOD,
+ OP_EXP,
+ OP_LOG_AND,
+ OP_LOG_OR,
+ OP_LOG_NOT,
+ OP_BIT_AND,
+ OP_BIT_OR,
+ OP_BIT_NOT,
+ OP_LSHIFT,
+ OP_RSHIFT,
+ OP_EQ,
+ OP_LE,
+ OP_LT,
+ OP_GE,
+ OP_GT,
+
+ OP_MIN = OP_ADD,
+ OP_MAX = OP_GT,
+
+// attribute reserved words
+ ATTR_UUID,
+ ATTR_VERSION,
+ ATTR_DLLNAME,
+ ATTR_ENTRY,
+ ATTR_ID,
+ ATTR_HELPSTRING,
+ ATTR_HELPCONTEXT,
+ ATTR_HELPFILE,
+ ATTR_LCID,
+ ATTR_PROPGET,
+ ATTR_PROPPUT,
+ ATTR_PROPPUTREF,
+ ATTR_OPTIONAL,
+ ATTR_IN,
+ ATTR_OUT,
+ ATTR_STRING,
+ ATTR_VARARG,
+ ATTR_APPOBJECT,
+ ATTR_RESTRICTED,
+ ATTR_PUBLIC,
+ ATTR_READONLY,
+ ATTR_ODL,
+ ATTR_DEFAULT,
+ ATTR_SOURCE,
+ ATTR_BINDABLE,
+ ATTR_REQUESTEDIT,
+ ATTR_DISPLAYBIND,
+ ATTR_DEFAULTBIND,
+ ATTR_LICENSED,
+ ATTR_PREDECLID,
+ ATTR_HIDDEN,
+ ATTR_RETVAL,
+ ATTR_CONTROL,
+ ATTR_DUAL,
+ ATTR_NONEXTENSIBLE,
+ ATTR_OLEAUTOMATION,
+} TOKID;
+
+#define fACCEPT_ATTR 0x0001
+#define fACCEPT_UUID 0x0002
+#define fACCEPT_NUMBER 0x0004
+#define fACCEPT_EOF 0x0008
+#define fACCEPT_OPERATOR 0x0010
+#define fACCEPT_STRING 0x0020
+
+
+typedef struct {
+ TOKID id;
+ union {
+ LPSTR lpsz;
+ GUID FAR * lpUuid;
+ DWORD number;
+ };
+ WORD cbsz; // only if string
+} TOKEN;
diff --git a/private/oleauto/src/mktyplib/typelib.err b/private/oleauto/src/mktyplib/typelib.err
new file mode 100644
index 000000000..eac517ef0
--- /dev/null
+++ b/private/oleauto/src/mktyplib/typelib.err
@@ -0,0 +1,85 @@
+//
+// UNDONE: need to make a pass through these errors, making them more
+// UNDONE: useful/readable.
+//
+// NOTE: code in TYPEOUT.CPP assumes that TYPE_E_IOERROR is first.
+TYPELIBERR(TYPE_E_IOERROR, "I/O error"),
+TYPELIBERR(TYPE_E_OUTOFBOUNDS, "Invalid number of arguments"),
+TYPELIBERR(TYPE_E_TYPEMISMATCH, "Type mismatch"),
+TYPELIBERR(TYPE_E_CANTCREATETMPFILE, "Error creating unique tmp file"),
+TYPELIBERR(TYPE_E_BUFFERTOOSMALL, "Buffer too small"),
+TYPELIBERR(TYPE_E_INVDATAREAD, "Old format or invalid type library"),
+TYPELIBERR(TYPE_E_UNSUPFORMAT, "Old format or invalid type library"),
+TYPELIBERR(TYPE_E_REGISTRYACCESS, "Error accessing the OLE registry"),
+TYPELIBERR(TYPE_E_LIBNOTREGISTERED, "Library not registered"),
+TYPELIBERR(TYPE_E_UNDEFINEDTYPE, "Bound to unknown type"),
+TYPELIBERR(TYPE_E_QUALIFIEDNAMEDISALLOWED, "Qualified name disallowed"),
+TYPELIBERR(TYPE_E_INVALIDSTATE, "Invalid forward reference, or reference to uncompiled type"),
+TYPELIBERR(TYPE_E_WRONGTYPEKIND, "Type mismatch"),
+TYPELIBERR(TYPE_E_ELEMENTNOTFOUND, "Element not found"),
+TYPELIBERR(TYPE_E_AMBIGUOUSNAME, "Ambiguous name"),
+TYPELIBERR(TYPE_E_NAMECONFLICT, "Name already exists in the library"),
+TYPELIBERR(TYPE_E_UNKNOWNLCID, "Unknown LCID"),
+TYPELIBERR(TYPE_E_DLLFUNCTIONNOTFOUND, "Function not defined in specified DLL"),
+
+TYPELIBERR(TYPE_E_BADMODULEKIND, "Wrong module kind for the operation"),
+TYPELIBERR(TYPE_E_CIRCULARTYPE, "Circular dependency between types/modules"),
+TYPELIBERR(TYPE_E_INCONSISTENTPROPFUNCS, "Inconsistent property functions"),
+TYPELIBERR(TYPE_E_SIZETOOBIG, "Size may not exceed 64K"),
+TYPELIBERR(TYPE_E_DUPLICATEID, "Duplicate ID in inheritance heirarchy"),
+
+#if VBA2
+TYPELIBERR(TYPE_E_INVALIDID, "Incorrect inheritence depth in standard OLE hmember."),
+#endif // VBA2
+
+TYPELIBERR(TYPE_E_CANTLOADLIBRARY, "Error loading type library/DLL"),
+
+TYPELIBERR(E_NOTIMPL, "OLE error E_NOTIMPL"),
+TYPELIBERR(E_OUTOFMEMORY, "Out of memory"),
+TYPELIBERR(E_INVALIDARG, "OLE error E_INVALIDARG"),
+TYPELIBERR(E_NOINTERFACE, "OLE error E_NOINTERFACE"),
+TYPELIBERR(E_ABORT, "OLE error E_ABORT"),
+TYPELIBERR(E_UNEXPECTED, "OLE error E_UNEXPECTED"),
+TYPELIBERR(E_POINTER, "OLE error E_POINTER"),
+TYPELIBERR(E_HANDLE, "OLE error E_HANDLE"),
+TYPELIBERR(E_FAIL, "OLE error E_FAIL"),
+TYPELIBERR(E_ACCESSDENIED, "Access denied"),
+
+TYPELIBERR(STG_E_INVALIDFUNCTION, "Invalid Function"),
+TYPELIBERR(STG_E_FILENOTFOUND, "File not found"),
+TYPELIBERR(STG_E_PATHNOTFOUND, "Path not found"),
+TYPELIBERR(STG_E_TOOMANYOPENFILES, "Too many open files"),
+TYPELIBERR(STG_E_ACCESSDENIED, "Access denied"),
+TYPELIBERR(STG_E_INVALIDHANDLE, "Invalid handle"),
+TYPELIBERR(STG_E_INSUFFICIENTMEMORY, "Out of memory"),
+TYPELIBERR(STG_E_INVALIDPOINTER, "Invalid pointer"),
+TYPELIBERR(STG_E_NOMOREFILES, "No more files"),
+TYPELIBERR(STG_E_DISKISWRITEPROTECTED, "Disk is write-protected"),
+TYPELIBERR(STG_E_SEEKERROR, "Seek error"),
+TYPELIBERR(STG_E_WRITEFAULT, "Write fault"),
+TYPELIBERR(STG_E_READFAULT, "Read fault"),
+TYPELIBERR(STG_E_SHAREVIOLATION, "Share violation"),
+TYPELIBERR(STG_E_LOCKVIOLATION, "Lock violation"),
+//This error is returned by OpenTypeLib when it is given a file which is not
+//an OLE docfile.
+TYPELIBERR(STG_E_FILEALREADYEXISTS, "File is not a valid type library"),
+TYPELIBERR(STG_E_INVALIDPARAMETER, "Invalid parameter"),
+TYPELIBERR(STG_E_MEDIUMFULL, "Disk full"),
+TYPELIBERR(STG_E_ABNORMALAPIEXIT, "Abnormal API exit"),
+TYPELIBERR(STG_E_INVALIDHEADER, "Invalid header"),
+TYPELIBERR(STG_E_INVALIDNAME, "Invalid name"),
+TYPELIBERR(STG_E_UNKNOWN, "OLE error STG_E_UNKNOWN"),
+TYPELIBERR(STG_E_UNIMPLEMENTEDFUNCTION, "Unimplemented OLE function"),
+TYPELIBERR(STG_E_INVALIDFLAG, "Invalid flag"),
+TYPELIBERR(STG_E_INUSE, "OLE error STG_E_INUSE"),
+TYPELIBERR(STG_E_NOTCURRENT, "OLE error STG_E_NOTCURRENT"),
+TYPELIBERR(STG_E_REVERTED, "OLE error STG_E_REVERTED"),
+TYPELIBERR(STG_E_CANTSAVE, "Can't save"),
+TYPELIBERR(STG_E_OLDFORMAT, "Old format or invalid type library"),
+TYPELIBERR(STG_E_OLDDLL, "Old DLL"),
+TYPELIBERR(STG_E_SHAREREQUIRED, "SHARE.EXE required"),
+TYPELIBERR(STG_E_NOTFILEBASEDSTORAGE, "OLE error STG_E_NOTFILEBASEDSTORAGE"),
+TYPELIBERR(STG_E_EXTANTMARSHALLINGS, "OLE error STG_E_EXTANTMARSHALLINGS"),
+
+// CONSIDER: these are just warnings -- correct to treat them as errors?
+TYPELIBERR(STG_S_CONVERTED, "OLE warning STG_S_CONVERTED"),
diff --git a/private/oleauto/src/mktyplib/typout.cpp b/private/oleauto/src/mktyplib/typout.cpp
new file mode 100644
index 000000000..5eb13c4a7
--- /dev/null
+++ b/private/oleauto/src/mktyplib/typout.cpp
@@ -0,0 +1,1186 @@
+#include "mktyplib.h"
+
+#include <malloc.h>
+#include <stdio.h>
+
+#ifndef WIN32
+#include <ole2.h>
+#include "dispatch.h"
+#endif //!WIN32
+
+#include "errors.h"
+#include "parser.h"
+
+#include "fileinfo.h"
+#include "intlstr.h"
+
+#if !FV_UNICODE_OLE
+#define LHashValOfNameSysA LHashValOfNameSys
+#endif //FV_UNICODE_OLE
+
+
+extern "C" {
+
+// external C data
+extern TYPLIB typlib; // structure that holds all file data
+extern SYSKIND SysKind;
+extern int iAlignMax;
+extern WORD cArgsMax; // max # of args in any function
+extern SCODE scodeErrCur; // SCODE of current error
+
+
+// external C routines
+extern INT FAR FCmpCaseIns(LPSTR str1, LPSTR str2);
+extern LPTYPE FAR lpTypePublic(LPTYPE lpType);
+
+// local data
+ELEMDESC FAR* rgFuncArgs; // array of function args
+LPOLESTR FAR* rgszFuncArgNames; // array of function arg names
+
+LPSTR lpszItemCur; // current item we're working on
+
+// C prototypes
+VOID FAR OutputTyplib(CHAR * szTypeLibFile);
+VOID FAR LoadExtTypeLib(LPIMPORTLIB lpImpLib);
+LPTYPE FAR FindExeType(LPSTR lpszTypeName);
+LPTYPE FAR FindExeTypeInLib(LPSTR lpszLibName, LPSTR lpszTypeName);
+
+VOID NEAR OutputTypeInfos(ICreateTypeLib FAR * lpdtlib);
+VOID NEAR OutputFuncs(ICreateTypeInfo FAR* lpdtinfo, LPENTRY pEntry, LPFUNC pFuncList, TYPEKIND tkind);
+VOID NEAR OutputElems(ICreateTypeInfo FAR* lpdtinfo, LPELEM pPropList, TYPEKIND tkind);
+VOID NEAR OutputAlias(ICreateTypeInfo FAR* lpdtinfo, LPTYPE lpTypeAlias);
+VOID NEAR LoadElemDesc(ICreateTypeInfo FAR* lpdtinfo, ELEMDESC FAR* lpElemDesc, LPELEM pElem);
+VOID NEAR UpdateHRefType(ICreateTypeInfo FAR* lpdtinfo, LPTYPE lpTypeBase);
+VOID NEAR OutputInterface(ICreateTypeInfo FAR* lpdtinfo, LPENTRY pEntry);
+VOID NEAR OutputDispinter(ICreateTypeInfo FAR* lpdtinfo, LPENTRY pEntry);
+VOID NEAR OutputClass(ICreateTypeInfo FAR* lpdtinfo, LPENTRY pEntry);
+VOID NEAR OutputBaseInterfaces(ICreateTypeInfo FAR* lpdtinfo, LPENTRY pEntry, TYPEKIND tkind);
+VOID NEAR MethodError(HRESULT res);
+
+
+// error reporting macros
+#define CHECKRESULT(x) if (FAILED((res = (x))) != 0) MethodError(res);
+#define SETITEMCUR(x) lpszItemCur = x;
+BOOL fDoingOutput = FALSE; // set to TRUE once we start
+ // writing the type library
+
+#if FV_UNICODE_OLE
+// Unicode conversion routines
+
+#define CW_BUFFER 1024 // 1K ought to do it
+OLECHAR szBufW[CW_BUFFER]; // handy static buffer
+
+OLECHAR FAR * ToW(char FAR* lpszA)
+{
+ UINT cb;
+
+ cb = strlen(lpszA)+1;
+ Assert(cb <= CW_BUFFER);
+
+ SideAssert (MultiByteToWideChar(CP_ACP,
+ MB_PRECOMPOSED,
+ lpszA,
+ cb,
+ szBufW,
+ cb) != 0);
+
+ return szBufW;
+}
+
+OLECHAR FAR * ToNewW(char FAR* lpszA)
+{
+ OLECHAR FAR * szW;
+ UINT cb;
+
+ cb = strlen(lpszA)+1;
+ szW = (LPOLESTR)_fmalloc(cb * sizeof(OLECHAR));
+
+ SideAssert (MultiByteToWideChar(CP_ACP,
+ MB_PRECOMPOSED,
+ lpszA,
+ cb,
+ szW,
+ cb) != 0);
+
+ return szW;
+}
+
+char FAR * ToA(OLECHAR FAR* lpszW)
+{
+ SideAssert (WideCharToMultiByte(CP_ACP,
+ 0,
+ lpszW,
+ -1,
+ (char FAR *)szBufW,
+ CW_BUFFER,
+ NULL,
+ NULL) != 0);
+
+ return (CHAR *)szBufW;
+}
+#else //FV_UNICODE_OLE
+
+// Non-unicode routines are a NOP
+#define ToW(lpszA) lpszA
+#define ToNewW(lpszA) lpszA
+#define ToA(lpszW) lpszW
+
+#endif //FV_UNICODE_OLE
+
+
+VOID FAR OutputTyplib
+(
+ CHAR * szTypeLibFile
+)
+{
+ HRESULT res;
+ ICreateTypeLib FAR * lpdtlib;
+#ifndef MAC
+ CHAR szTypeLibFileTmp[128];
+#endif //!MAC
+ WORD wLibFlags;
+
+ fDoingOutput = TRUE; // signal to error reporting code
+ SETITEMCUR(typlib.szLibName);
+
+#ifndef MAC
+ // pre-pend ".\" to filename if unqualified name, to work-around OLE path
+ // searching bug.
+
+ if (!XStrChr(szTypeLibFile, '\\') && !XStrChr(szTypeLibFile, '/') &&
+ *(szTypeLibFile+1) != ':')
+ { // if unqualified name
+ strcpy(szTypeLibFileTmp, ".\\");
+ strcpy(szTypeLibFileTmp+2, szTypeLibFile);
+ // this name is used later -- don't free it
+ //free(szTypeLibFile);
+ szTypeLibFile = szTypeLibFileTmp;
+ }
+
+#endif
+
+ // 1. Get * to ICreateTypeLib interface
+ CHECKRESULT(CreateTypeLib(SysKind, ToW(szTypeLibFile), &lpdtlib));
+
+ // WARNING: SetLCID must be called before the anything in the nammgr is used
+ // it needs to be called even if the user doesn't specifiy an lcid
+ // (in which case we default to an lcid of 0).
+ CHECKRESULT(lpdtlib->SetLcid(
+ (typlib.attr.fAttr & fLCID) ? typlib.attr.lLcid : 0
+ ));
+
+ // 2. Set the library name:
+ CHECKRESULT(lpdtlib->SetName(ToW(typlib.szLibName)));
+
+ // 3. Set the library attributes, if present:
+ if (typlib.attr.fAttr & fHELPSTRING)
+ CHECKRESULT(lpdtlib->SetDocString(ToW(typlib.attr.lpszHelpString)));
+
+ if (typlib.attr.fAttr & fHELPCONTEXT)
+ CHECKRESULT(lpdtlib->SetHelpContext(typlib.attr.lHelpContext));
+
+ if (typlib.attr.fAttr & fHELPFILE)
+ CHECKRESULT(lpdtlib->SetHelpFileName(ToW(typlib.attr.lpszHelpFile)));
+
+ if (typlib.attr.fAttr & fVERSION)
+ CHECKRESULT(lpdtlib->SetVersion(typlib.attr.wVerMajor, typlib.attr.wVerMinor));
+
+ if (typlib.attr.fAttr & fUUID)
+ CHECKRESULT(lpdtlib->SetGuid(*typlib.attr.lpUuid));
+
+ wLibFlags = 0;
+ if (typlib.attr.fAttr & fRESTRICTED)
+ wLibFlags |= LIBFLAG_FRESTRICTED;
+ if (typlib.attr.fAttr2 & f2CONTROL)
+ wLibFlags |= LIBFLAG_FCONTROL;
+ if (typlib.attr.fAttr & fHIDDEN)
+ wLibFlags |= LIBFLAG_FHIDDEN;
+ CHECKRESULT(lpdtlib->SetLibFlags(wLibFlags));
+
+ // 4. Output all the typinfo's into the type library
+ if (typlib.pEntry) // if any entries
+ OutputTypeInfos(lpdtlib);
+
+ // 5. Save the typlib to the give file
+ SETITEMCUR(typlib.szLibName);
+
+ CHECKRESULT(lpdtlib->SaveAllChanges());
+
+ // 6. Cleanup. All done -- release release the ICreateTypeLib.
+ lpdtlib->Release(); // release the ICreateTypeLib
+
+}
+
+
+// WARNING: must be kept in ssync with TENTRYKIND enum in FILEINFO.H
+TYPEKIND rgtkind[] = {
+ TKIND_ALIAS, // tTYPEDEF
+ TKIND_RECORD, // tSTRUCT
+ TKIND_ENUM, // tENUM
+ TKIND_UNION, // tUNION
+ TKIND_MODULE, // tMODULE
+ TKIND_INTERFACE, // tINTERFACE
+ TKIND_DISPATCH, // tDISPINTER
+ TKIND_COCLASS, // tCOCLASS
+// TKIND_xxx, // tINTRINISIC
+// TKIND_xxx, // tREF
+// TKIND_xxx, // tANY
+};
+
+// WARNING: must be kept in ssync with TYPEKIND enum in DISPATCH.H
+TENTRYKIND rgtentrykind[] = {
+ tENUM, // TKIND_ENUM
+ tSTRUCT, // TKIND_RECORD
+ tMODULE, // TKIND_MODULE
+ tINTERFACE, // TKIND_INTERFACE
+ tDISPINTER, // TKIND_DISPATCH
+ tCOCLASS, // TKIND_COCLASS
+ tTYPEDEF, // TKIND_ALIAS
+ tUNION, // TKIND_UNION
+};
+
+// For each library entry, creates a typeinfo in the typelib,
+// and fills it in.
+VOID NEAR OutputTypeInfos
+(
+ ICreateTypeLib FAR * lpdtlib
+)
+{
+ LPENTRY pEntry;
+ TYPEKIND tkind;
+ HRESULT res;
+ ICreateTypeInfo FAR* lpdtinfo;
+ WORD wTypeFlags;
+
+ // First allocate an array of ELEMDESCs to hold the max # of
+ // args of any function we need to describe.
+ rgFuncArgs = (ELEMDESC FAR*)_fmalloc(cArgsMax * sizeof(ELEMDESC));
+ rgszFuncArgNames = (LPOLESTR FAR *)_fmalloc((cArgsMax+1) * sizeof(LPOLESTR));
+ if (rgFuncArgs == NULL || rgszFuncArgNames == NULL)
+ ParseError(ERR_OM);
+
+ // pass 1 -- create the typeinfo's
+ pEntry = (LPENTRY)ListFirst(typlib.pEntry); // point to first entry
+ for (;;)
+ {
+
+ // determine if we are going to create a typeinfo for this guy
+ switch (pEntry->type.tentrykind)
+ {
+ case tTYPEDEF:
+ if (pEntry->attr.fAttr) // create lpdtinfo only if
+ break; // this is a 'PUBLIC' typedef
+
+NoTypeInfos:
+ pEntry->lpdtinfo = NULL; // no lpdtinfo for this
+
+ case tREF: // no typeinfo's made for these
+ case tINTRINSIC:
+ goto Next_Entry1;
+
+ default:
+ // no typeinfo's made for forward declarations
+ if (pEntry->type.tentrykind & tFORWARD)
+ goto NoTypeInfos;
+ if (pEntry->type.tentrykind & tIMPORTED)
+ goto Next_Entry1; // nothing for imported types
+ break;
+ }
+
+ // 1. determine kind of typeinfo to create
+ tkind = rgtkind[pEntry->type.tentrykind];
+
+ // 2. Create type library entry (TypeInfo) of a given name/and
+ // type, getting a pointer to the ICreateTypeInfo interface
+ SETITEMCUR(pEntry->type.szName);
+ CHECKRESULT(lpdtlib->CreateTypeInfo(ToW(pEntry->type.szName), tkind, &lpdtinfo));
+ pEntry->lpdtinfo = lpdtinfo;
+
+ // 3. Set the item's attributes:
+ if (pEntry->attr.fAttr & fUUID)
+ CHECKRESULT(lpdtinfo->SetGuid(*pEntry->attr.lpUuid));
+
+ if (pEntry->attr.fAttr & fHELPSTRING)
+ CHECKRESULT(lpdtinfo->SetDocString(ToW(pEntry->attr.lpszHelpString)));
+
+ if (pEntry->attr.fAttr & fHELPCONTEXT)
+ CHECKRESULT(lpdtinfo->SetHelpContext(pEntry->attr.lHelpContext));
+
+ if (pEntry->attr.fAttr & fVERSION)
+ CHECKRESULT(lpdtinfo->SetVersion(pEntry->attr.wVerMajor, pEntry->attr.wVerMinor));
+
+ // 4. save lptinfo for this guy in case somebody references it
+ CHECKRESULT(lpdtinfo->QueryInterface(IID_ITypeInfo, (VOID FAR* FAR*)&pEntry->type.lptinfo));
+
+ // if this type has a forward declaration
+ if (pEntry->lpEntryForward)
+ {
+ // copy "real" type info over top of forward declaration,
+ // because folks have pointers to the forward declaration
+ pEntry->lpEntryForward->type.tdesc = pEntry->type.tdesc;
+ pEntry->lpEntryForward->type.lptinfo = pEntry->type.lptinfo;
+ // Only need to copy these 2 fields from the type (the
+ // others aren't referenced at type creation time.
+ }
+
+Next_Entry1:
+ // advance to next entry if not all done
+ if (pEntry == (LPENTRY)ListLast(typlib.pEntry))
+ break; // exit if all done
+ pEntry = (LPENTRY)pEntry->type.pNext;
+ }
+
+
+ // pass 2 -- process each entry
+ pEntry = (LPENTRY)ListFirst(typlib.pEntry); // point to first entry
+ for (;;)
+ {
+
+ // 1. Get our lpdtinfo again if we have one
+
+ switch (pEntry->type.tentrykind)
+ {
+ case tREF:
+ case tINTRINSIC:
+ goto Next_Entry2; // these guys don't have lpdtinfo field
+ default:
+ if (pEntry->type.tentrykind & tIMPORTED)
+ goto Next_Entry2; // no lpdtinfo field
+ break;
+ }
+
+ lpdtinfo = pEntry->lpdtinfo;
+ if (lpdtinfo == NULL) // skip if no lpdtinfo created
+ goto Next_Entry2; // (forward decl or non-public typedef)
+
+ // set up for error reporting
+ SETITEMCUR(pEntry->type.szName);
+
+ // 2. determine kind of typeinfo we're dealing with
+ tkind = rgtkind[pEntry->type.tentrykind];
+
+ // 2a. Set the typeinfo flags
+ wTypeFlags = 0;
+ if (tkind == TKIND_COCLASS) {
+ // COCLASSs always have FCANCREATE bit set
+ wTypeFlags |= TYPEFLAG_FCANCREATE;
+ // these are only valid on COCLASSs
+ if (pEntry->attr.fAttr & fAPPOBJECT)
+ wTypeFlags |= (WORD)TYPEFLAG_FAPPOBJECT;
+ if (pEntry->attr.fAttr & fLICENSED)
+ wTypeFlags |= (WORD)TYPEFLAG_FLICENSED;
+ if (pEntry->attr.fAttr & fPREDECLID)
+ wTypeFlags |= (WORD)TYPEFLAG_FPREDECLID;
+ }
+ if (pEntry->attr.fAttr & fHIDDEN)
+ wTypeFlags |= (WORD)TYPEFLAG_FHIDDEN;
+ if (pEntry->attr.fAttr2 & f2CONTROL)
+ wTypeFlags |= (WORD)TYPEFLAG_FCONTROL;
+ if (pEntry->attr.fAttr2 & f2NONEXTENSIBLE)
+ wTypeFlags |= (WORD)TYPEFLAG_FNONEXTENSIBLE;
+ if (pEntry->attr.fAttr2 & f2DUAL) // DUAL implies OLEAUTOMATION
+ wTypeFlags |= (WORD)(TYPEFLAG_FDUAL | TYPEFLAG_FOLEAUTOMATION);
+ if (pEntry->attr.fAttr2 & f2OLEAUTOMATION)
+ wTypeFlags |= (WORD)TYPEFLAG_FOLEAUTOMATION;
+ CHECKRESULT(lpdtinfo->SetTypeFlags(wTypeFlags));
+
+ // 3. now process each kind of entry
+ switch (tkind)
+ {
+ case TKIND_ALIAS:
+
+ OutputAlias(lpdtinfo, pEntry->type.td.ptypeAlias);
+ break;
+
+ case TKIND_RECORD: // struct's, enum's, and union's are
+ case TKIND_ENUM: // all very similar
+ case TKIND_UNION:
+ OutputElems(lpdtinfo, pEntry->type.structenum.elemList, tkind);
+ break;
+
+ case TKIND_MODULE:
+ OutputFuncs(lpdtinfo, pEntry, pEntry->module.funcList, tkind);
+ OutputElems(lpdtinfo, pEntry->module.constList, tkind);
+ break;
+
+ case TKIND_INTERFACE:
+ OutputInterface(lpdtinfo, pEntry);
+ break;
+
+ case TKIND_DISPATCH:
+ OutputDispinter(lpdtinfo, pEntry);
+ break;
+
+ case TKIND_COCLASS:
+ OutputClass(lpdtinfo, pEntry);
+ break;
+
+#if FV_PROPSET
+ case TKIND_PROPSET:
+ // CONSIDER: (FV_PROPSET) do something with base_propset name
+ OutputElems(lpdtinfo, pEntry->propset.propList, tkind);
+ break;
+#endif //FV_PROPSET
+ default:
+ Assert(FALSE);
+ };
+
+ // 3a. Set the alignment for this TypeInfo. Must be done before
+ // Layout().
+ CHECKRESULT(lpdtinfo->SetAlignment(iAlignMax));
+
+ // 4. Compile this typeinfo we've just created.
+ SETITEMCUR(pEntry->type.szName);
+ CHECKRESULT(lpdtinfo->LayOut());
+
+ // 5. Cleanup. All done with lpdtinfo.
+ lpdtinfo->Release();
+
+Next_Entry2:
+ // advance to next entry if not all done
+ if (pEntry == (LPENTRY)ListLast(typlib.pEntry))
+ break; // exit if all done
+ pEntry = (LPENTRY)pEntry->type.pNext;
+ }
+
+
+ // now clean up everything else
+ _ffree(rgFuncArgs); // done with function args we allocated
+ _ffree(rgszFuncArgNames);
+
+}
+
+VOID NEAR OutputFuncs
+(
+ ICreateTypeInfo FAR* lpdtinfo,
+ LPENTRY pEntry,
+ LPFUNC pFuncList,
+ TYPEKIND tkind
+)
+{
+
+ LPFUNC pFunc;
+ LPELEM pArg;
+ HRESULT res;
+ UINT iFunc = 0; // function index
+ LPOLESTR lpszDllName;
+ LPSTR lpszProcName;
+ SHORT i;
+ FUNCDESC FuncDesc;
+ LPOLESTR FAR* lplpszArgName;
+
+ if (pFuncList == NULL) // just return if no functions to output
+ return;
+
+ FuncDesc.lprgelemdescParam = rgFuncArgs; // set up array of args
+
+ pFunc = (LPFUNC)ListFirst(pFuncList); // point to first entry
+#if FV_UNICODE_OLE
+ lpszDllName = (pEntry->attr.fAttr & fDLLNAME ? ToNewW(pEntry->attr.lpszDllName) : NULL);
+#else
+ lpszDllName = pEntry->attr.lpszDllName;
+#endif
+
+ for (;;)
+ {
+ // Fill in the FUNCDESC structure with the function's info
+
+ // set up funckind
+ switch (tkind) {
+ case TKIND_MODULE:
+ FuncDesc.funckind = FUNC_STATIC;
+ break;
+ case TKIND_INTERFACE:
+ FuncDesc.funckind = FUNC_PUREVIRTUAL;
+ break;
+ case TKIND_DISPATCH:
+ FuncDesc.funckind = FUNC_DISPATCH;
+ break;
+ default:
+ Assert(FALSE);
+ }
+
+ // set up invkind
+ FuncDesc.invkind = INVOKE_FUNC; // default
+ if (pFunc->func.attr.fAttr & fPROPGET)
+ FuncDesc.invkind = INVOKE_PROPERTYGET;
+ else if (pFunc->func.attr.fAttr & fPROPPUT)
+ FuncDesc.invkind = INVOKE_PROPERTYPUT;
+ else if (pFunc->func.attr.fAttr & fPROPPUTREF)
+ FuncDesc.invkind = INVOKE_PROPERTYPUTREF;
+
+ // set up callconv
+ if (pFunc->func.attr.fAttr2 & f2PASCAL)
+ // CC_MACPASCAL if /mac specified, CC_MSCPASCAL otherwise
+ FuncDesc.callconv = (CALLCONV)(SysKind == SYS_MAC ? CC_MACPASCAL: CC_MSCPASCAL);
+ else if (pFunc->func.attr.fAttr2 & f2CDECL)
+ FuncDesc.callconv = CC_CDECL;
+ else if (pFunc->func.attr.fAttr2 & f2STDCALL)
+ FuncDesc.callconv = CC_STDCALL;
+#ifdef DEBUG
+ else Assert(FALSE);
+#endif //DEBUG
+
+ FuncDesc.wFuncFlags = 0;
+ if (pFunc->func.attr.fAttr & fRESTRICTED)
+ FuncDesc.wFuncFlags |= (WORD)FUNCFLAG_FRESTRICTED;
+ if (pFunc->func.attr.fAttr & fSOURCE)
+ FuncDesc.wFuncFlags |= (WORD)FUNCFLAG_FSOURCE;
+ if (pFunc->func.attr.fAttr & fBINDABLE)
+ FuncDesc.wFuncFlags |= (WORD)FUNCFLAG_FBINDABLE;
+ if (pFunc->func.attr.fAttr & fREQUESTEDIT)
+ FuncDesc.wFuncFlags |= (WORD)FUNCFLAG_FREQUESTEDIT;
+ if (pFunc->func.attr.fAttr & fDISPLAYBIND)
+ FuncDesc.wFuncFlags |= (WORD)FUNCFLAG_FDISPLAYBIND;
+ if (pFunc->func.attr.fAttr & fDEFAULTBIND)
+ FuncDesc.wFuncFlags |= (WORD)FUNCFLAG_FDEFAULTBIND;
+ if (pFunc->func.attr.fAttr & fHIDDEN)
+ FuncDesc.wFuncFlags |= (WORD)FUNCFLAG_FHIDDEN;
+
+ // set up cParams & cParamsOpt
+ FuncDesc.cParams = pFunc->cArgs;
+ FuncDesc.cParamsOpt = pFunc->cOptArgs;
+ //NOTE: cParamsOpt can be set to -1, to note that last parm is a
+ //NOTE: [safe] array of variant args. This corresponds to the
+ //NOTE: 'vararg' attribute in the input description. If this was
+ //NOTE: specified, the parser set pFunc->cOptArgs to -1 for us.
+
+ // set up misc unused stuff
+ FuncDesc.oVft = 0; // only used for FUNC_VIRTUAL
+ FuncDesc.cScodes = -1; // list of SCODEs unknown
+ FuncDesc.lprgscode = NULL;
+
+ // set id field if 'id' attribute specified
+ if (pFunc->func.attr.fAttr & fID)
+ FuncDesc.memid = pFunc->func.attr.lId;
+ else
+ FuncDesc.memid = DISPID_UNKNOWN;
+
+ // set up elemdescFunc
+ // Contains the ID, name, and return type of the function
+ LoadElemDesc(lpdtinfo, &(FuncDesc.elemdescFunc), &pFunc->func);
+
+ // save function name
+ lplpszArgName = rgszFuncArgNames;
+ *lplpszArgName++ = ToNewW(pFunc->func.szElemName);
+ SETITEMCUR(pFunc->func.szElemName);
+
+ // set up the lprgelemdescParam array of info for each parameter
+ pArg = pFunc->argList; // point to last arg, if any
+ for (i = 0; i < pFunc->cArgs; i++)
+ {
+ pArg = pArg->pNext; // point to next arg (first arg
+ // first time through loop)
+ LoadElemDesc(lpdtinfo, &(FuncDesc.lprgelemdescParam[i]), pArg);
+ *lplpszArgName++ = ToNewW(pArg->szElemName); // save arg name
+ }
+
+ // Define the function item:
+ CHECKRESULT(lpdtinfo->AddFuncDesc(iFunc, &FuncDesc));
+
+ // set the names of the function and the parameters
+ Assert(i == pFunc->cArgs);
+
+ // don't set the name of the last param for proput/putref functions
+ if (pFunc->func.attr.fAttr & (fPROPPUT | fPROPPUTREF)) {
+ i--;
+ }
+
+ CHECKRESULT(lpdtinfo->SetFuncAndParamNames(iFunc, rgszFuncArgNames, i+1));
+#if FV_UNICODE_OLE
+ // free the unicode function & param names
+ lplpszArgName = rgszFuncArgNames;
+ for (i = 0; i <= pFunc->cArgs; i++) {
+ _ffree(*lplpszArgName); // done with unicode name
+ lplpszArgName++;
+ }
+#endif //FV_UNICODE_OLE
+
+ // Set the function item's remaining attributes:
+ if (pFunc->func.attr.fAttr & fHELPSTRING)
+ CHECKRESULT(lpdtinfo->SetFuncDocString(iFunc, ToW(pFunc->func.attr.lpszHelpString)));
+ if (pFunc->func.attr.fAttr & fHELPCONTEXT)
+ CHECKRESULT(lpdtinfo->SetFuncHelpContext(iFunc, pFunc->func.attr.lHelpContext));
+ // Handle case of a DLL entrypoint
+ if (pFunc->func.attr.fAttr & fENTRY)
+ {
+ // If high word of name is zero, then call by ordnal
+ // If high word of name is non-zero, then call by name
+ // (same as GetProcAddress)
+
+ lpszProcName = pFunc->func.attr.lpszProcName;
+#if FV_UNICODE_OLE
+ if (HIWORD(lpszProcName)) {
+ lpszProcName = (LPSTR)ToW(lpszProcName);
+ }
+#endif //FV_UNICODE_OLE
+ CHECKRESULT(lpdtinfo->DefineFuncAsDllEntry(iFunc, lpszDllName, (LPOLESTR)lpszProcName));
+ }
+
+ // advance to next entry if not all done
+ if (pFunc == (LPFUNC)ListLast(pFuncList))
+ break; // exit if all done
+ pFunc = (LPFUNC)pFunc->func.pNext;
+ iFunc++; // advance function counter
+ }
+#if FV_UNICODE_OLE
+ if (lpszDllName)
+ _ffree(lpszDllName); // done with unicode name
+#endif //FV_UNICODE_OLE
+}
+
+VOID NEAR OutputElems
+(
+ ICreateTypeInfo FAR* lpdtinfo,
+ LPELEM pElemList,
+ TYPEKIND tkind
+)
+{
+
+ LPELEM pElem;
+ HRESULT res;
+ UINT iElem = 0; // element index
+ VARDESC VarDesc;
+
+
+ if (pElemList == NULL)
+ return;
+
+ pElem = (LPELEM)ListFirst(pElemList); // point to first entry
+
+ for (;;)
+ {
+
+ // First fill in the VARDESC structure with the element's info
+ SETITEMCUR(pElem->szElemName);
+
+ VarDesc.memid = DISPID_UNKNOWN; // assume not a dispinterface
+
+ // Set up varkind
+ switch (tkind)
+ {
+ case TKIND_ENUM: // for enum elements
+ case TKIND_MODULE: // for const's
+ VarDesc.varkind = VAR_CONST;
+ VarDesc.lpvarValue = pElem->lpElemVal; // * to value
+ if (tkind == TKIND_MODULE)
+ goto DoLoadElemDesc; // set up the tdesc
+
+ // For ENUM elements, can't call LoadElemDesc, because
+ // we have no pElem->elemType. Do the required work here.
+
+ VarDesc.elemdescVar.tdesc.vt = VT_INT; // element type
+ // is an INT
+ VarDesc.elemdescVar.idldesc.wIDLFlags = 0; // no IDL info
+#ifdef WIN16
+ VarDesc.elemdescVar.idldesc.bstrIDLInfo = NULL;
+#else //WIN16
+ VarDesc.elemdescVar.idldesc.dwReserved = 0;
+#endif //WIN16
+ break;
+
+ case TKIND_RECORD:
+ case TKIND_UNION:
+ VarDesc.varkind = VAR_PERINSTANCE;
+ goto DoLoadElemDesc;
+
+ default:
+#if FV_PROPSET
+ Assert(tkind == TKIND_DISPATCH || tkind == TKIND_PROPSET);
+#else //FV_PROPSET
+ Assert(tkind == TKIND_DISPATCH);
+#endif //FV_PROPSET
+ VarDesc.varkind = VAR_DISPATCH;
+
+ // id' attribute required
+ Assert (pElem->attr.fAttr & fID);
+ VarDesc.memid = pElem->attr.lId;
+
+DoLoadElemDesc:
+ // Set up elemdescVar. Contains name, and type of item.
+ LoadElemDesc(lpdtinfo, &(VarDesc.elemdescVar), pElem);
+ }
+
+ // VarDesc.oInst is not used when doing AddVarDesc
+ VarDesc.wVarFlags = 0;
+ if (pElem->attr.fAttr & fREADONLY)
+ VarDesc.wVarFlags |= (WORD)VARFLAG_FREADONLY;
+ if (pElem->attr.fAttr & fSOURCE)
+ VarDesc.wVarFlags |= (WORD)VARFLAG_FSOURCE;
+ if (pElem->attr.fAttr & fBINDABLE)
+ VarDesc.wVarFlags |= (WORD)VARFLAG_FBINDABLE;
+ if (pElem->attr.fAttr & fREQUESTEDIT)
+ VarDesc.wVarFlags |= (WORD)VARFLAG_FREQUESTEDIT;
+ if (pElem->attr.fAttr & fDISPLAYBIND)
+ VarDesc.wVarFlags |= (WORD)VARFLAG_FDISPLAYBIND;
+ if (pElem->attr.fAttr & fDEFAULTBIND)
+ VarDesc.wVarFlags |= (WORD)VARFLAG_FDEFAULTBIND;
+ if (pElem->attr.fAttr & fHIDDEN)
+ VarDesc.wVarFlags |= (WORD)VARFLAG_FHIDDEN;
+
+ // Now define the element
+ CHECKRESULT(lpdtinfo->AddVarDesc(iElem, &VarDesc));
+
+ // Lastly, set element's remaining attributes:
+ CHECKRESULT(lpdtinfo->SetVarName(iElem, ToW(pElem->szElemName)));
+
+ if (pElem->attr.fAttr & fHELPSTRING)
+ CHECKRESULT(lpdtinfo->SetVarDocString(iElem, ToW(pElem->attr.lpszHelpString)));
+ if (pElem->attr.fAttr & fHELPCONTEXT)
+ CHECKRESULT(lpdtinfo->SetVarHelpContext(iElem, pElem->attr.lHelpContext));
+ // advance to next entry if not all done
+ if (pElem == (LPELEM)ListLast(pElemList))
+ break; // exit if all done
+ pElem = pElem->pNext;
+ iElem++; // advance element counter
+ }
+}
+
+
+// update the tdesc.HRefType field of the base type prior to
+// using a given type.
+VOID NEAR UpdateHRefType
+(
+ ICreateTypeInfo FAR* lpdtinfo,
+ LPTYPE lpTypeBase
+)
+{
+
+ HRESULT res;
+ HREFTYPE hreftype;
+ LPSTR szTypeName;
+ LPTYPE lpTypeCArray;
+
+ // get * to real base type, ignoring non-public typedef's
+ lpTypeBase = lpTypePublic(lpTypeBase);
+ lpTypeCArray = NULL; // assume not a C array
+
+ // CONSIDER: non-pointer to a forward declare with no def yet should give an
+ // CONSIDER: error. This isn't the right check, but it's close.
+ // CONSIDER: error currently gets caught by Layout() so it's no big deal.
+ //if (lpTypeBase->tdesc.vt == VT_USERDEFINED && (lpTypeBase->tentrykind & ~tFORWARD))
+ // goto NoDef;
+
+
+ while (lpTypeBase->tentrykind == tREF) // for VT_PTR, VT_SAFEARRAY or
+ // VT_CARRAY
+ {
+ if (lpTypeBase->tdesc.vt == VT_CARRAY)
+ lpTypeCArray = lpTypeBase;
+ else
+ lpTypeCArray = NULL; // not a C array
+ lpTypeBase = lpTypeBase->ref.ptypeBase;
+
+ // get * to real base type, ignoring non-public typedef's
+ lpTypeBase = lpTypePublic(lpTypeBase);
+ }
+
+
+ // update the tdesc.hreftype of the base type if necessary
+ if (lpTypeBase->tdesc.vt == VT_USERDEFINED)
+ {
+
+ if (lpTypeBase->lptinfo == NULL)
+ { // we're trying to use a forward declaration to a
+ // type with no real definition
+//NoDef:
+ switch (lpTypeBase->tentrykind & ~tFORWARD)
+ {
+ case tSTRUCT:
+ case tENUM:
+ case tUNION:
+ szTypeName = lpTypeBase->structenum.szTag;
+ break;
+ default:
+ szTypeName = lpTypeBase->szName;
+ break;
+ }
+ ItemError(szFmtErrOutput, szTypeName, OERR_NO_DEF);
+ }
+
+ // get reference to given typeinfo
+ CHECKRESULT(lpdtinfo->AddRefTypeInfo(lpTypeBase->lptinfo, &hreftype));
+
+ // store this in the appropriate tdesc
+ if (lpTypeCArray) // C arrays have a separate tdesc
+ lpTypeCArray->tdesc.lpadesc->tdescElem.hreftype = hreftype;
+ else
+ lpTypeBase->tdesc.hreftype = hreftype;
+ }
+}
+
+
+VOID NEAR OutputAlias
+(
+ ICreateTypeInfo FAR* lpdtinfo,
+ LPTYPE lpTypeAlias
+)
+{
+ HRESULT res;
+
+ // update the tdesc.hreftype field of the base type if it's
+ // a user-defined type.
+ UpdateHRefType(lpdtinfo, lpTypeAlias);
+
+ // Define the alias:
+ CHECKRESULT(lpdtinfo->SetTypeDescAlias(&(lpTypePublic(lpTypeAlias)->tdesc)));
+}
+
+
+// Fills in a ELEMDESC (for enum's, properties, property_set properties,
+// function names, function parms)
+VOID NEAR LoadElemDesc
+(
+ ICreateTypeInfo FAR* lpdtinfo,
+ ELEMDESC FAR* lpElemDesc,
+ LPELEM pElem
+)
+{
+ WORD wFlags;
+
+ // set up the type description
+
+ // update the tdesc.hreftype field of the element type if it's
+ // a user-defined type.
+ UpdateHRefType(lpdtinfo, pElem->elemType);
+
+ lpElemDesc->tdesc = lpTypePublic(pElem->elemType)->tdesc; // copy the tdesc
+
+ // set up the idldesc field
+ wFlags = 0;
+ if (pElem->attr.fAttr & fIN)
+ wFlags |= IDLFLAG_FIN;
+ if (pElem->attr.fAttr & fOUT)
+ wFlags |= IDLFLAG_FOUT;
+ if (pElem->attr.fAttr & fLCID)
+ wFlags |= IDLFLAG_FLCID;
+ if (pElem->attr.fAttr & fRETVAL)
+ wFlags |= IDLFLAG_FRETVAL;
+ lpElemDesc->idldesc.wIDLFlags = wFlags;
+#ifdef WIN16
+ lpElemDesc->idldesc.bstrIDLInfo = NULL; // no additional info
+#else //WIN16
+ lpElemDesc->idldesc.dwReserved = 0;
+#endif //WIN16
+
+}
+
+
+
+VOID NEAR OutputInterface
+(
+ ICreateTypeInfo FAR* lpdtinfo,
+ LPENTRY pEntry
+)
+{
+
+ if (pEntry->type.inter.interList)
+ { // handle inheritance if any base interface(s)
+ OutputBaseInterfaces(lpdtinfo, pEntry, TKIND_INTERFACE);
+ }
+
+ OutputFuncs(lpdtinfo, pEntry, pEntry->inter.funcList, TKIND_INTERFACE);
+}
+
+
+VOID NEAR OutputDispinter
+(
+ ICreateTypeInfo FAR* lpdtinfo,
+ LPENTRY pEntry
+)
+{
+ // handle inheritance from IDispatch or some other interface
+ OutputBaseInterfaces(lpdtinfo, pEntry, TKIND_DISPATCH);
+
+ OutputFuncs(lpdtinfo, pEntry, pEntry->dispinter.methList, TKIND_DISPATCH);
+
+ OutputElems(lpdtinfo, pEntry->dispinter.propList, TKIND_DISPATCH);
+}
+
+
+VOID NEAR OutputClass
+(
+ ICreateTypeInfo FAR* lpdtinfo,
+ LPENTRY pEntry
+)
+{
+ // tell typelib.dll about the list of implemented interface(s)
+ OutputBaseInterfaces(lpdtinfo, pEntry, TKIND_COCLASS);
+}
+
+
+VOID NEAR OutputBaseInterfaces
+(
+ ICreateTypeInfo FAR* lpdtinfo,
+ LPENTRY pEntry,
+ TYPEKIND tkind
+)
+{
+ HREFTYPE hreftype;
+ HRESULT res;
+ LPINTER lpinterList = pEntry->type.inter.interList;
+ LPINTER lpinter;
+ SHORT i;
+ INT implTypeFlags;
+
+ Assert (lpinterList); // caller should have checked this for use
+ // point to first base interface
+ lpinter = (LPINTER)ListFirst(lpinterList);
+ for (i=0;;i++)
+ {
+ // get index of typeinfo of base interface/dispinterface
+ if (lpinter->ptypeInter->lptinfo == NULL)
+ ItemError(szFmtErrOutput, lpinter->ptypeInter->szName, OERR_NO_DEF);
+
+ CHECKRESULT(lpdtinfo->AddRefTypeInfo(lpinter->ptypeInter->lptinfo, &hreftype));
+
+ CHECKRESULT(lpdtinfo->AddImplType(i, hreftype));
+
+ //
+ if (tkind == TKIND_COCLASS) {
+ // need to always set the flags for items in a coclass
+ implTypeFlags = 0;
+ if (lpinter->fAttr & fDEFAULT)
+ implTypeFlags |= IMPLTYPEFLAG_FDEFAULT;
+ if (lpinter->fAttr & fRESTRICTED)
+ implTypeFlags |= IMPLTYPEFLAG_FRESTRICTED;
+ if (lpinter->fAttr & fSOURCE)
+ implTypeFlags |= IMPLTYPEFLAG_FSOURCE;
+ CHECKRESULT(lpdtinfo->SetImplTypeFlags(i, implTypeFlags));
+ }
+
+ // advance to next entry if not all done
+ if (lpinter == (LPINTER)ListLast(lpinterList))
+ break; // exit if all done
+ lpinter = (LPINTER)lpinter->pNext;
+ } // WHILE
+}
+
+
+// ************************************************************************
+// Functions for looking up external types
+// ************************************************************************
+
+// load an external type library
+VOID FAR LoadExtTypeLib
+(
+ LPIMPORTLIB lpImpLib
+)
+{
+ ITypeLib FAR* lptlib;
+ HRESULT res;
+ BSTR bstrName;
+
+ SETITEMCUR(lpImpLib->lpszFileName);
+
+ // get * to ITypeLib interface
+ CHECKRESULT(LoadTypeLib(ToW(lpImpLib->lpszFileName), &lptlib));
+ lpImpLib->lptlib = lptlib;
+
+ // get name of this library
+ CHECKRESULT(lptlib->GetDocumentation(-1, &bstrName, NULL, NULL, NULL));
+ // copy library name from the BSTR
+ lpImpLib->lpszLibName = _fstrdup(ToA(bstrName));
+
+ SysFreeString(bstrName); // free the BSTR
+
+ // get * to ITypeComp interface
+ CHECKRESULT(lptlib->GetTypeComp(&(lpImpLib->lptcomp)));
+
+ // get library attributes
+ CHECKRESULT(lptlib->GetLibAttr(&(lpImpLib->lptlibattr)));
+
+}
+
+
+VOID FAR CleanupImportedTypeLibs()
+{
+ LPIMPORTLIB lpImpLib;
+ LPENTRY pEntry;
+
+ // free up each of the referenced lptinfo's
+ if (typlib.pEntry) {
+ pEntry = (LPENTRY)ListFirst(typlib.pEntry); // point to first entry
+ for (;;)
+ {
+ // release the ITypeInfo
+ if (pEntry->type.lptinfo != NULL &&
+ (pEntry->type.tentrykind & tFORWARD) == 0)
+ pEntry->type.lptinfo->Release();
+
+ // advance to next entry if not all done
+ if (pEntry == ListLast(typlib.pEntry))
+ break; // exit if all done
+ pEntry = (LPENTRY)pEntry->type.pNext;
+ }
+ }
+
+ if (typlib.pImpLib)
+ { // only if any imported type libraries
+
+ // point to first imported library entry
+ lpImpLib = (LPIMPORTLIB)ListFirst(typlib.pImpLib);
+ for (;;)
+ {
+ if (lpImpLib->lptcomp) {
+ lpImpLib->lptcomp->Release();
+ }
+
+ if (lpImpLib->lptlibattr) {
+ Assert (lpImpLib->lptlib);
+ lpImpLib->lptlib->ReleaseTLibAttr(lpImpLib->lptlibattr);
+ }
+
+ if (lpImpLib->lptlib) {
+ lpImpLib->lptlib->Release();
+ }
+
+ // advance to next entry if not all done
+ if (lpImpLib == (LPIMPORTLIB)ListLast(typlib.pImpLib))
+ break; // exit if all done
+ lpImpLib = lpImpLib->pNext;
+ } // WHILE
+ }
+}
+
+
+// find type defined in an external type library,
+// and add it to the type table if found.
+// lpszLibName is NULL if we're to look in ALL external type libraries.
+LPTYPE FAR FindExtType
+(
+ LPSTR lpszLibName,
+ LPSTR lpszTypeName
+)
+{
+ LPIMPORTLIB lpImpLib;
+ HRESULT res;
+ ULONG lHashVal;
+ ITypeInfo FAR* lptinfo;
+ ITypeComp FAR* lptcomp;
+
+ Assert (lpszTypeName != NULL);
+
+ if (typlib.pImpLib != NULL) // if any imported type libraries
+ {
+ // point to first imported library entry
+ lpImpLib = (LPIMPORTLIB)ListFirst(typlib.pImpLib);
+
+ for (;;)
+ {
+
+ // if we're to look in all libraries, or this specific lib
+ if (lpszLibName == NULL || !FCmpCaseIns(lpszLibName, lpImpLib->lpszLibName))
+ {
+
+ SETITEMCUR(lpImpLib->lpszFileName);
+ lHashVal = LHashValOfNameSysA(lpImpLib->lptlibattr->syskind,
+ lpImpLib->lptlibattr->lcid,
+ lpszTypeName);
+
+ CHECKRESULT(lpImpLib->lptcomp->BindType(ToW(lpszTypeName), lHashVal, &lptinfo, &lptcomp));
+ if (lptinfo) // if found
+ {
+ // create a type table entry for this guy
+ ListInsert(&typlib.pEntry, sizeof(TYPE));
+
+ // lpszTypeName will get freed by caller.
+ // We must allocate new memory for it.
+ typlib.pEntry->type.szName = _fstrdup(lpszTypeName);
+
+ // CONSIDER: do a GetTypeAttr on this guy,
+ // to ensure it's not a 'module' type
+
+ typlib.pEntry->type.tdesc.vt = VT_USERDEFINED;
+ // init this now in case of error, since
+ // error cleanup code looks at this.
+ typlib.pEntry->type.lptinfo = NULL;
+
+ LPTYPEATTR ptypeattr;
+ TENTRYKIND tentrykind;
+
+ CHECKRESULT(lptinfo->GetTypeAttr(&ptypeattr));
+ // Get the interface typeinfo instead of
+ // the Dispinteface version.
+ if (ptypeattr->wTypeFlags & TYPEFLAG_FDUAL){
+ ITypeInfo FAR* lptinfo2;
+ HREFTYPE hreftype;
+ CHECKRESULT(lptinfo->GetRefTypeOfImplType((unsigned int)-1, &hreftype));
+ CHECKRESULT(lptinfo->GetRefTypeInfo(hreftype, &lptinfo2));
+ lptinfo->Release();
+ lptinfo->ReleaseTypeAttr(ptypeattr);
+ lptinfo = lptinfo2;
+ CHECKRESULT(lptinfo->GetTypeAttr(&ptypeattr));
+ }
+ typlib.pEntry->type.lptinfo = lptinfo;
+
+ // assume generic imported type
+ tentrykind = (TENTRYKIND)(rgtentrykind[ptypeattr->typekind] | tIMPORTED);
+ if (lpszLibName) {
+ tentrykind = (TENTRYKIND)(tentrykind | tQUAL);
+ }
+ typlib.pEntry->type.tentrykind = tentrykind;
+ typlib.pEntry->type.import.wTypeFlags = ptypeattr->wTypeFlags;
+
+ lptinfo->ReleaseTypeAttr(ptypeattr);
+ return &(typlib.pEntry->type); // all done
+ }
+ }
+
+ // advance to next entry if not all done
+ if (lpImpLib == (LPIMPORTLIB)ListLast(typlib.pImpLib))
+ break; // exit if all done
+ lpImpLib = lpImpLib->pNext;
+ } // WHILE
+ }
+ return (LPTYPE)NULL; //type not found
+}
+
+#define TYPELIBERR(name,string) name
+static SCODE rgTypelibScodes[] = {
+ #include "typelib.err" // TYPELIB.DLL scodes
+ S_FALSE // end of table
+};
+#undef TYPELIBERR
+
+void NEAR MethodError
+(
+ HRESULT res
+)
+{
+ ERR err;
+ int i;
+ CHAR * szFormat;
+
+ Assert(FAILED(res)); // should only be called if error
+
+ scodeErrCur = GetScode(res); // get scode from the hresult
+
+ // pick appripriate error format string, depending on whether we are
+ // reading an imported type library, or writing one.
+ if (fDoingOutput)
+ szFormat = szFmtErrOutput;
+ else
+ szFormat = szFmtErrImportlib;
+
+ // find err constant that matches this scode, if any
+ for (i = 0; ;i++)
+ {
+ if (rgTypelibScodes[i] == scodeErrCur)
+ { // found error in mapping table. Add table index to
+ // first TYPELIB.DLL error to get error constant.
+ err = (ERR)(i + OERR_TYPE_E_IOERROR);
+ break;
+ }
+ else if (rgTypelibScodes[i] == S_FALSE)
+ { // not in our mapping table -- use general error
+ err = OERR_TYPEINFO;
+ szFormat = szFmtErrUnknown;
+ break;
+ }
+ }
+
+ ItemError(szFormat, lpszItemCur, err);
+}
+
+}; // end of C data
diff --git a/private/oleauto/src/typelib/blkdsc32.hxx b/private/oleauto/src/typelib/blkdsc32.hxx
new file mode 100644
index 000000000..5843c792c
--- /dev/null
+++ b/private/oleauto/src/typelib/blkdsc32.hxx
@@ -0,0 +1,232 @@
+/***
+*sheapmgr.hxx - Silver Heap Manager
+*
+* Copyright (C) 1993, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Manages a huge array of bytes. Supports alloc/realloc/free.
+*
+*Implementation Notes:
+* OE_WIN16: use GlobalAlloc and family
+* else: Defers to host implementation of IMalloc.
+*
+*Revision History:
+*
+* 02-Nov-93 ilanc: Created.
+*
+*****************************************************************************/
+
+#ifndef BLKDESC32_HXX_INCLUDED
+#define BLKDESC32_HXX_INCLUDED
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szBLKDSC32_HXX)
+#define SZ_FILE_NAME g_szBLKDSC32_HXX
+#endif
+
+// forward declarations
+class STREAM;
+
+
+// **********************************
+// *** class BLKDESC32 starts here ***
+// **********************************
+//
+
+
+/***
+*class BLKDESC32 - 'blkdesc': block descriptor
+*Purpose:
+* The class implements block descriptors.
+* Describes a block allocated the heap manager.
+*
+*Implementation Notes:
+*
+***********************************************************************/
+
+class BLKDESC32
+{
+ friend class BLKMGR32;
+ friend class DYNBLKMGR32;
+
+public:
+ BLKDESC32();
+ ~BLKDESC32();
+
+ nonvirt TIPERROR Init(ULONG cbSize);
+
+ nonvirt BYTE *QtrOfBlock() const;
+ nonvirt ULONG CbSize() const;
+ nonvirt VOID Free();
+ nonvirt TIPERROR Realloc(ULONG cbSizeNew);
+ nonvirt BOOL IsValid() const;
+ nonvirt TIPERROR Read(STREAM *pstrm);
+ nonvirt TIPERROR Write(STREAM *pstrm);
+ nonvirt ULONG GetSize() const;
+
+ // Locking methods
+ nonvirt VOID Lock();
+ nonvirt VOID Unlock();
+ nonvirt BOOL IsLocked() const;
+
+ // Debug/test methods
+#if ID_DEBUG
+ nonvirt VOID DebShowState(UINT uLevel) const;
+#else
+ nonvirt VOID DebShowState(UINT uLevel) const {}
+#endif
+
+private:
+ // 32bit pointer to managed huge memblock.
+ BYTE *m_qbMemBlock;
+ ULONG m_cbSize;
+
+ // Since blocks are managed separately in we lock them at
+ // block level (unlike the 16bit implementation).
+ //
+ UINT m_cLocks;
+
+ // Sheapshaking now means: copy memblock to new block and
+ // placing old memblock on queue waiting to be freed.
+ //
+};
+
+// *******************************
+// *** BLKDESC32 inline methods ***
+// *******************************
+//
+
+/***
+*PUBLIC BLKDESC32::Lock
+*Purpose:
+* Lock the block.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID BLKDESC32::Lock()
+{
+ DebAssert(IsValid(), "BLKDESC32::Lock: Block invalid.");
+
+ m_cLocks++;
+}
+
+
+/***
+*PUBLIC BLKDESC32::Unlock
+*Purpose:
+* Unlock the block.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID BLKDESC32::Unlock()
+{
+ DebAssert(IsValid(), "BLKDESC32::Unlock: Block invalid.");
+
+ DebAssert(m_cLocks > 0, "BLKDESC32::Unlock: underflow.");
+ m_cLocks--;
+}
+
+
+/***
+*PUBLIC BLKDESC32::IsLocked
+*Purpose:
+* Tests if block is locked.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* TRUE if block is locked -- i.e. at least one lock.
+***********************************************************************/
+
+inline BOOL BLKDESC32::IsLocked() const
+{
+ DebAssert(IsValid(), "BLKDESC32::IsLocked: Block invalid.");
+
+ return (BOOL)(m_cLocks > 0);
+}
+
+
+/***
+*PUBLIC BLKDESC32::IsValid - Tests if block is valid.
+*Purpose:
+* Tests if block is valid. Note that a 0-size block is valid,
+* however its m_qbMemBlock must be non-NULL to be valid (i.e. a
+* 0-size block does have an entry in the heap -- it just happens
+* to be of length 0).
+*
+*Entry:
+* None.
+*
+*Exit:
+* Returns TRUE if block valid (i.e. m_qbMemBlock != NULL), else FALSE.
+*
+***********************************************************************/
+
+inline BOOL BLKDESC32::IsValid() const
+{
+ return (m_qbMemBlock != NULL);
+}
+
+
+/***
+*PUBLIC BLKDESC32::CbSize - size of block accessor (get).
+*Purpose:
+* Returns size of block.
+*
+*Implementation Notes:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+inline ULONG BLKDESC32::CbSize() const
+{
+ DebAssert(IsValid(), "BLKDESC32::cbSize: Block invalid.");
+ return m_cbSize;
+}
+
+
+/***
+*PUBLIC BLKDESC32::QtrOfBlock - returns block address.
+*Purpose:
+* Returns pointer to logical memblock.
+*
+*Implementation Notes:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+inline BYTE *BLKDESC32::QtrOfBlock() const
+{
+ DebAssert(IsValid(), "BLKDESC32::QtrOfBlock: Block invalid.");
+
+ return m_qbMemBlock;
+}
+
+
+#endif // ! BLKDESC32_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/blkmgr.cxx b/private/oleauto/src/typelib/blkmgr.cxx
new file mode 100644
index 000000000..2c7927296
--- /dev/null
+++ b/private/oleauto/src/typelib/blkmgr.cxx
@@ -0,0 +1,1385 @@
+/***
+*blkmgr.cxx - Block Manager
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* The block manager provides memory management services for a
+* a contiguous block of memory allocated from the compile-time
+* heap. It manages sub-blocks ("chunks") and supports compaction.
+* See \silver\doc\ic\blkmgr.doc for more information.
+*
+*Revision History:
+*
+* 30-Jan-90 ilanc: Created.
+* 14-Feb-91 ilanc: Private member m_hblock becomes m_blkdesc.
+* hheap_mgr --> sheapmgr
+* 07-Mar-91 ilanc: Added IsValid() method.
+* 19-Mar-91 ilanc: Fixed AllocChunk() and FreeChunk().
+* Chunk size is always at least sizeof(FREE_CHUNK).
+* 21-Mar-91 ilanc: Made some stuff inline.
+* 27-Mar-91 ilanc: Read and write blocks.
+* 26-Jul-91 t-toddw: added Trim() method.
+* 07-Aug-91 t-toddw: compaction routines now use the actual chunk size
+* and m_hfreechunk handling is much cleaner.
+* 09-Aug-91 t-toddw: USHORT Trim() becomes UINT Trim().
+* Updated to use CbSizeChunkTrue() member function.
+* 16-Aug-91 t-toddw: Moved con/destructor to blkmgr.hxx.
+* Cleaned up various things as per alanc's review.
+* 21-Aug-91 ilanc: No more m_psheapmgr. On 16-bit assume SHEAP_MGR
+* at ofs 0 in segment. On 32-bit no need for
+* SHEAP_MGR. Need diff version for 32-bit. This
+* is 16-bit version.
+* 07-Oct-91 stevenl: StartCompact() now calls MEMFREE on m_pbBlkCopy
+* if it can't allocate m_pbBitmap.
+*
+* 25-Mar-92 ilanc: Rm'ed static Create (no need).
+* 30-Mar-92 ilanc: Added freelist coalescing.
+* 13-Apr-92 ilanc: Round up chunk alloc size to 4-byte multiple,
+* this makes freechunk easier (nothing
+* need leak).
+* 07-Sep-93 w-jeffc: MapChunk now correctly leaves pointer to new
+* chunk after copy
+*
+*Implementation Notes:
+* Block manager can manage no more than 64K memory blocks.
+* Handles to chunks are 16-bit values.
+* This means that blocks can't grow beyond 64K.
+*
+* Each block manager has a BLK_DESC which owns a memory block
+* which in turn is managed by the SHEAP_MGR.
+* Each block is managed inside the memory block of a BLK_DESC.
+*
+* On segmented architectures (os2 1.x, Win16):
+* The BLK_MGR object is itself also allocated
+* in the "reserved" section of a SHEAP_MGR,
+* thus the SHEAP_MGR/BLK_DESC/BLK_MGR must all fit inside a single
+* segment.
+*
+* On win32: the block manager is allocated in a single 4Mb
+* region of virtual memory. All the BLK_MGRs of a single SHEAP_MGR
+* must fit in that region. Note in addition that block realloc
+* might cause *much* movement -- since all other blocks might
+* be affected.
+*
+* On Mac: as in segmented, each bklmgr obj is alloced in the
+* "reserved" section fo a SHEAP_MGR which maintains a handle
+* to a relocatable mac memblock within which each managed
+* blkdesc/blkmgr is suballocated.
+*
+* Chunks may be allocated and deallocated by the block manager.
+* A handle is returned (HCHUNK) that is guaranteed never to
+* change as long as the block isn't compacted. Note that
+* the handle is actually just an offset into the block (this
+* allows handle dereference to be fast).
+*
+* The block manager maintains a freechunk list from which it
+* attempts to allocate chunks. When a chunk is freed it is
+* returned to the freelist -- freechunks are of a minimum
+* size of 4 bytes (they contains their size and a next link).
+* No memory leaks occur cos chunk allocs are always multiples
+* of FREE_CHUNK size.
+*
+* Free chunks are coalesced in the following manner:
+* the freelist is maintained in ascending order by position.
+* When a freechunk is added to the list it is placed in the
+* appropriate position -- however, if it transpires that the
+* previous freechunk (if there is one) ends exactly before
+* the new freechunk, the new chunk is coalesced to the previous
+* by modifying the previous's header. Likewise if there is
+* a next freechunk. So in the best case, the newfreechunk
+* can coalesce two old freechunks. In the worst case, no
+* coalescing is done at all.
+*
+*****************************************************************************/
+
+#define BLKMGR_VTABLE // export blk mgr vtable
+
+#include "silver.hxx"
+#include "typelib.hxx"
+#include <stddef.h>
+#include <stdlib.h>
+#include <string.h>
+#include <limits.h>
+
+#include "mem.hxx"
+#include "sheapmgr.hxx"
+#include "blkmgr.hxx"
+#include "stream.hxx"
+#include "xstring.h"
+
+#pragma hdrstop(RTPCHNAME)
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+char szOleBlkmgrCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleBlkmgrCxx
+#else
+static char szBlkmgrCxx[] = __FILE__;
+#define SZ_FILE_NAME szBlkmgrCxx
+#endif
+#endif //ID_DEBUG
+
+
+
+
+// This constant is used for the initial size of an allocated block.
+//
+// const UINT BM_cbSizeInitial = 0x100;
+const UINT BM_cbSizeInitial = 0x020;
+// const UINT BM_cbSizeInitial = 0x080;
+
+/*******************
+*
+* static, public
+* TIPERROR BLK_MGR::CreateStandalone(BLK_MGR **ppbm)
+*
+* Purpose:
+* This may be called by clients who need a single block manager,
+* and don't care what segment it is allocated in.
+*
+* NOTE: Clients who use this function must be sure to release
+* the block manager by calling BLK_MGR::FreeStandalone(pbm)
+*
+* A BLK_MGR must be intialized by a SHEAPMGR, and both of these
+* objects must be located in the same segment.
+*
+* Exit:
+* *ppbm points to a newly constructed and initialized block manager.
+*
+*************************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR BLK_MGR::CreateStandalone(BLK_MGR **ppbm, BOOL fRoundUp)
+{
+ TIPERROR err = TIPERR_None;
+ SHEAP_MGR *psheapmgr = NULL;
+ BLK_MGR *pbm = NULL;
+
+ IfErrGo( SHEAP_MGR::Create(&psheapmgr,
+ sizeof(SHEAP_MGR) + sizeof(BLK_MGR) ));
+ pbm = (BLK_MGR *) (psheapmgr +1);
+
+ pbm = new(pbm) BLK_MGR;
+
+ IfErrGo( pbm->Init(psheapmgr, TRUE, fRoundUp));
+ *ppbm = pbm;
+ return TIPERR_None;
+
+Error:
+ if (psheapmgr) {
+ delete psheapmgr;
+ }
+ return err;
+}
+#pragma code_seg()
+
+/***
+* void BLK_MGR::FreeStandalone(BLK_MGR *pbm)
+*
+* Purpose:
+* This frees both the dyn block manager itself and the sheapmgr
+* associated with it.
+*
+*********************************************************************/
+#pragma code_seg(CS_INIT)
+void BLK_MGR::FreeStandalone(BLK_MGR *pbm)
+{
+ SHEAP_MGR *psheapmgr;
+
+ if (!pbm) {
+ return;
+ }
+
+ psheapmgr = ((SHEAP_MGR *) pbm) -1;
+
+ pbm->Free();
+ delete psheapmgr;
+}
+#pragma code_seg()
+
+
+
+// Class methods
+//
+
+/***
+*PUBLIC BLK_MGR::BLK_MGR - constructor
+*Purpose:
+* Note that Init() must still be called before
+* this block manager can be used.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#if OE_MAC
+#pragma code_seg(CS_INIT)
+#endif
+BLK_MGR::BLK_MGR()
+{
+ m_pbBitmap = m_pbBlkCopy = NULL;
+ m_fCoalesce = TRUE;
+ m_fRoundUp = TRUE;
+}
+#if OE_MAC
+#pragma code_seg()
+#endif
+
+/***
+*PUBLIC BLK_MGR::ConsChunkToFreeList - Cons a chunk to free list.
+*Purpose:
+* Cons a chunk to the free list. This is fast and is useful
+* for non-coalescing BLK_MGRs.
+*
+*Entry:
+* hchunk handle to chunk to cons to list.
+* cbSize its size.
+*
+*Exit:
+* No errors. Side effects freelisthead.
+*
+***********************************************************************/
+#if OE_MAC
+#pragma code_seg(CS_INIT)
+#endif
+VOID BLK_MGR::ConsChunkToFreeList(HCHUNK hchunk, UINT cbSize)
+{
+ FREE_CHUNK *qfreechunk;
+
+ DebAssert(cbSize >= sizeof(FREE_CHUNK), "bad chunk size.");
+
+ qfreechunk = (FREE_CHUNK *)QtrOfHandle(hchunk);
+ qfreechunk->m_cbSize = (USHORT)cbSize;
+ qfreechunk->m_hfreechunkNext = m_hfreechunk;
+ m_hfreechunk = (sHFREE_CHUNK)hchunk;
+}
+#if OE_MAC
+#pragma code_seg()
+#endif
+
+
+
+/***
+*PUBLIC BLK_MGR::Init - initialize the block manager
+*Purpose:
+* Initializes the block manager. Assigns a heap manager.
+* Gets a block from the heap manager and initializes it.
+*
+* CONSIDER: having a discrete bit to indicate compaction phase
+* as opposed to testing the bitmap and block copy pointers.
+*
+* NOTE: Can't be called during compaction.
+*
+*Implementation Notes:
+* Calls ReInit() to initialize private members to consistent state.
+* (Which in particular inits m_hfreechunk to HCHUNK_Nil).
+*
+*Entry:
+* psheapmgr - pointer to a heap manager object.
+*
+*Exit:
+* TIPERROR (OOM)
+*
+***********************************************************************/
+#if OE_MAC
+#pragma code_seg(CS_INIT)
+#endif
+TIPERROR BLK_MGR::Init(SHEAP_MGR *psheapmgr, BOOL fCoalesce, BOOL fRoundUp)
+{
+ TIPERROR err;
+
+ DebAssert(IsValid() == FALSE,
+ "BLK_MGR::Init: whoops! block manager should be invalid.");
+
+ // Do they want to coalesce?
+ m_fCoalesce = fCoalesce;
+ m_fRoundUp = FALSE;
+
+ // Initialize block descriptor with initial size.
+ if (!(err = m_blkdesc.Init(psheapmgr, BM_cbSizeInitial))) {
+ ReInit();
+
+ DebAssert(m_hfreechunk == HCHUNK_Nil,
+ "BLK_MGR::Init: m_hfreechunk not initialized.");
+
+ DebAssert((m_pbBlkCopy == NULL) && (m_pbBitmap == NULL),
+ "BLK_MGR::Init: m_pbBlkCopy/m_pbBitmap not initialized.");
+
+ DebAssert(IsValid(), "BLK_MGR::Init: invalid block.");
+
+ // init freechunk list.
+ ConsChunkToFreeList((HCHUNK)0, BM_cbSizeInitial);
+ return TIPERR_None;
+ }
+ else
+ return err;
+}
+#if OE_MAC
+#pragma code_seg()
+#endif
+
+/***
+*PRIVATE BLK_MGR::AddChunkToFreeList - Adds a chunk to the freelist.
+*Purpose:
+* Add a chunk to the free list.
+*
+*Implementation Notes:
+* Calculates how many bytes will be left after cbSizeChunk
+* bytes have been allocated from the freechunk. Attempts
+* to create a freechunk from those leftover bytes and add
+* then to the freelist.
+*
+* Can only creates freechunks of min size 4. Otherwise they
+* leak.
+*
+* If they want to coalesce then:
+* Coalesces freelist by maintaining list in ascending order
+* by position and then on insertion checks to see if
+* adjacent freechunks are contiguous. If so, coalesces.
+* else
+* just cons chunk to front of list.
+*
+*Entry:
+* hchunk - chunk handle to add to free list (IN).
+* cbSizeChunk - chunk size (IN).
+*
+*Exit:
+* Modifies free chunk list to reflect allocated chunk.
+*
+*Errors:
+* No errors.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+VOID BLK_MGR::AddChunkToFreeList(HCHUNK hchunkNew, UINT cbSizeChunk)
+{
+ FREE_CHUNK *qfreechunkCur;
+ FREE_CHUNK *qfreechunkNew;
+ FREE_CHUNK *qfreechunkPrev;
+ HFREE_CHUNK hfreechunkCur, hfreechunkPrev;
+ BOOL fAdded = FALSE;
+
+ DebAssert(cbSizeChunk >= sizeof(FREE_CHUNK), "bad chunksize.");
+
+ if (!m_fCoalesce) {
+ ConsChunkToFreeList(hchunkNew, cbSizeChunk);
+ DebCheckState(0);
+ return;
+ }
+
+ qfreechunkNew = (FREE_CHUNK *)QtrOfHandle(hchunkNew);
+
+ // We can and must set the size field immediately here
+ // since we are assured that the new freechunk is at least two bytes.
+ //
+ qfreechunkNew->m_cbSize = (USHORT)cbSizeChunk;
+
+ // listhead
+ hfreechunkCur = m_hfreechunk;
+ hfreechunkPrev = (HFREE_CHUNK)HCHUNK_Nil;
+
+ // Insert chunk into ordered freelist.
+ while (hfreechunkCur != (HFREE_CHUNK)HCHUNK_Nil) {
+
+ DebAssert((UINT)hchunkNew != (UINT)hfreechunkCur, "bad free list.");
+
+ // NOTE TO SELF: cast handles and compare values.
+ // Have we found the right place?
+ //
+ if ((UINT)hchunkNew < (UINT)hfreechunkCur) {
+
+ // Now let's see if we can coalesce with previous free chunk.
+ if (hfreechunkPrev != HCHUNK_Nil) {
+ qfreechunkPrev = (FREE_CHUNK *)QtrOfHandle((HCHUNK)hfreechunkPrev);
+ if (hfreechunkPrev + (UINT)qfreechunkPrev->m_cbSize == hchunkNew) {
+ // yes we can...
+ qfreechunkPrev->m_cbSize += (USHORT)cbSizeChunk;
+ qfreechunkNew = qfreechunkPrev;
+ }
+ else {
+ // no, we can't coalesce with prev freechunk,
+ // so we attempt to create a new separate freechunk.
+ // We know chunk is of sufficient size to be a freechunk,
+ // so no need to leak.
+ // Init and link in new freechunk to free list.
+ // it might end up getting coalesced with hchunkCur
+ //
+ qfreechunkPrev->m_hfreechunkNext = (sHFREE_CHUNK)hchunkNew;
+ qfreechunkNew->m_hfreechunkNext = (sHFREE_CHUNK)hfreechunkCur;
+
+ } // of else
+ } // of if
+ else {
+ // We're before every other chunk in the free list, so add in
+ // at the head.
+ DebAssert(hchunkNew < m_hfreechunk, "free list not sorted");
+
+ m_hfreechunk = hchunkNew;
+ qfreechunkNew->m_hfreechunkNext = (sHFREE_CHUNK)hfreechunkCur;
+ }
+
+ // Now let's see if we can coalesce qfreechunkNew
+ // with next free chunk (referenced by hfreechunkCur).
+ // Note: that qfreechunkNew either references the new
+ // freechunk which wasn't coalesced or the prev freechunk
+ // which has been coalesced with the new freechunk.
+ //
+ qfreechunkCur = (FREE_CHUNK *)QtrOfHandle((HCHUNK)hfreechunkCur);
+ if (((BYTE *)qfreechunkNew + qfreechunkNew->m_cbSize) ==
+ (BYTE *)qfreechunkCur) {
+ // increment size field;
+ qfreechunkNew->m_cbSize += qfreechunkCur->m_cbSize;
+
+ DebAssert(qfreechunkNew->m_cbSize >= sizeof(FREE_CHUNK),
+ "whoops! bad freechunk.");
+
+ // and link.
+ qfreechunkNew->m_hfreechunkNext = qfreechunkCur->m_hfreechunkNext;
+ }
+ else {
+ // can't coalesce, so link to next.
+ // we know chunk is big enough to be a FREE_CHUNK.
+ //
+ qfreechunkNew->m_hfreechunkNext = (sHFREE_CHUNK)hfreechunkCur;
+ }
+
+ fAdded = TRUE;
+ break; // break out of while iteration.
+ } // of if
+
+ DebAssert(fAdded == FALSE, "should have broken out.");
+
+
+ // save previous.
+ hfreechunkPrev = hfreechunkCur;
+
+ // get next.
+ hfreechunkCur =
+ ((FREE_CHUNK *)QtrOfHandle(hfreechunkCur))->m_hfreechunkNext;
+
+ // Need to special-case coalescing this new freechunk with
+ // the *last* freechunk on the list.
+ //
+ if (hfreechunkCur == HCHUNK_Nil) {
+ qfreechunkPrev = (FREE_CHUNK *)QtrOfHandle((HCHUNK)hfreechunkPrev);
+ if (hfreechunkPrev + (UINT)qfreechunkPrev->m_cbSize == hchunkNew) {
+ // yes we can...
+ qfreechunkPrev->m_cbSize += (USHORT)cbSizeChunk;
+ fAdded = TRUE;
+ }
+ // we should break out of the loop since hfreechunkCur == Nil
+ }
+ } // of while
+
+ // We either got here cos we broke out of the while loop
+ // after having added the chunk to the free list...
+ // or we need to append to the end of the possibly empty freelist.
+ //
+ if (fAdded == FALSE) {
+
+ DebAssert(((m_hfreechunk == HCHUNK_Nil) &&
+ (hfreechunkPrev == HCHUNK_Nil)) ||
+ (hchunkNew > hfreechunkPrev), "bad freelist.");
+
+ // We know chunk is big enough to be a FREE_CHUNK,
+ // so append to freelist.
+ //
+ qfreechunkNew->m_cbSize = (USHORT)cbSizeChunk;
+ qfreechunkNew->m_hfreechunkNext = (sHFREE_CHUNK)HCHUNK_Nil;
+
+ if (hfreechunkPrev != HCHUNK_Nil) {
+ qfreechunkPrev = (FREE_CHUNK *)QtrOfHandle((HCHUNK)hfreechunkPrev);
+ qfreechunkPrev->m_hfreechunkNext = hchunkNew;
+ }
+ else {
+ m_hfreechunk = (sHFREE_CHUNK)hchunkNew;
+ }
+ } // end of if fAdded
+ DebCheckState(0);
+ return;
+}
+#pragma code_seg()
+
+/***
+*PRIVATE BLK_MGR::HfreechunkOfCbSize - Get a freechunk of sufficient size.
+*Purpose:
+* Get freechunk of sufficient size.
+*
+*Implementation Notes:
+* Searches list for freechunk of sufficient size, removes it
+* from freelist if found and returns the leftover to freelist
+* by splicing the leftover in place.
+*
+*Entry:
+* cbSizeChunk size they want (IN)
+*
+*Exit:
+* HFREE_CHUNK of sufficiently large chunk. No errors.
+* HCHUNK_Nil if no such.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+HFREE_CHUNK BLK_MGR::HfreechunkOfCbSize(UINT cbSizeChunk)
+{
+ HFREE_CHUNK hfreechunk, hfreechunkPrev, hfreechunkLeftover;
+ FREE_CHUNK *qfreechunk, *qfreechunkPrev, *qfreechunkLeftover;
+ sHFREE_CHUNK *qhfreechunk;
+ UINT cbSizeLeftover;
+
+ cbSizeChunk = CbSizeChunkTrue(cbSizeChunk);
+
+ hfreechunk = m_hfreechunk;
+ hfreechunkPrev = (HFREE_CHUNK)HCHUNK_Nil;
+
+ // Iterate over free chunk list for a sufficiently large chunk.
+ while ((hfreechunk != HCHUNK_Nil) &&
+ ((qfreechunk =
+ (FREE_CHUNK *)QtrOfHandle(hfreechunk))->m_cbSize <
+ (USHORT)cbSizeChunk)) {
+
+ // Save previous
+ hfreechunkPrev = hfreechunk;
+
+ // Get next
+ hfreechunk = qfreechunk->m_hfreechunkNext;
+ }
+
+ // If a freechunk found then remove it from list
+ // and if OB then splice in leftover
+ // else splice in leftover if large enough.
+ //
+ if (hfreechunk != HCHUNK_Nil) {
+
+ DebAssert(QtrOfHandle(hfreechunk) == (BYTE *)qfreechunk,
+ "bad list.");
+
+ // Since we are allocating the first part of a freechunk
+ // (and possibly all of it), we can't possibly be
+ // coalescing -- so we can just splice the leftover directly into
+ // the list.
+ //
+ cbSizeLeftover = qfreechunk->m_cbSize - (USHORT)cbSizeChunk;
+
+#if ID_DEBUG
+ // We assert that there is either no leftover at all or
+ // that it's enough to be a FREE_CHUNK -- since we always
+ // allocate in multiples of sizeof(FREE_CHUNK) this must be the case.
+ //
+ if (m_fRoundUp) {
+ DebAssert((cbSizeLeftover % sizeof(FREE_CHUNK)) == 0,
+ "should be no leftover or at least FREE_CHUNK big.");
+ }
+ // If not fRoundUp we can leak leftovers of size < sizeof(FREE_CHUNK)
+ // Note: nothing to test here since we test below anyway...
+
+#endif // ID_DEBUG
+
+ // *possible* new freechunk of size cbSizeLeftover.
+ hfreechunkLeftover = (HFREE_CHUNK)((UINT)hfreechunk+cbSizeChunk);
+
+ // Set up leftover if big enough.
+ if (cbSizeLeftover >= sizeof(FREE_CHUNK)) {
+ qfreechunkLeftover =
+ (FREE_CHUNK *)QtrOfHandle((HCHUNK)hfreechunkLeftover);
+ qfreechunkLeftover->m_hfreechunkNext = qfreechunk->m_hfreechunkNext;
+ qfreechunkLeftover->m_cbSize = (USHORT)cbSizeLeftover;
+ }
+
+ // Set up freechunk handle to modify... either list head
+ // or previous list elem.
+ //
+ if (hfreechunkPrev != HCHUNK_Nil) {
+ qfreechunkPrev = (FREE_CHUNK *)QtrOfHandle((HCHUNK)hfreechunkPrev);
+
+ qhfreechunk = &qfreechunkPrev->m_hfreechunkNext;
+
+ }
+ else {
+ // We're removing the first freechunk in list.
+ DebAssert(m_hfreechunk == hfreechunk, "bad list.");
+
+ qhfreechunk = &m_hfreechunk;
+ }
+
+ // Link in the leftover if large enough.
+ *qhfreechunk = (sHFREE_CHUNK)(cbSizeLeftover < sizeof(FREE_CHUNK) ?
+ qfreechunk->m_hfreechunkNext :
+ hfreechunkLeftover);
+ } // if (hfreechunk != HCHUNK_Nil)
+
+ return hfreechunk;
+}
+#pragma code_seg()
+
+/***
+*PRIVATE BLK_MGR::AllocChunk2 - allocates a chunk in block.
+*Purpose:
+* Allocates a contiguous chunk in block of cbSize bytes.
+* Chunk is allocated from free list with a first fit strategy.
+* (DAK says best fit not worth it).
+*
+* If no chunk is sufficiently large then the block is grown
+* by deferring to the heap manager.
+* Note that an even number of bytes is always returned.
+*
+* NOTE: Can't be called during compaction.
+* CONSIDER: adding non-virtual methods to FREE_CHUNK
+* to do free chunk list manipulation.
+*
+*
+*Implementation Notes:
+* Attempts to find a large-enough chunk on the free chunk list,
+* if none, asks heap mgr to realloc the block. Asserts that
+* the realloced block is large enough to accomodate this chunk
+* request. Simply calls itself recursively to complete the
+* request. Hence asserts that only *one* recursive call can
+* be made.
+* If there is a large-enough free chunk we just use it directly.
+*
+* NOTE: return OOM if no chunk large enough on free list and
+* block is locked.
+*
+* How much to grow block by? Right now: max of initial block
+* and requested chunk size
+*
+*Entry:
+* phchunk - pointer to chunk handle (OUT).
+* cbSizeChunk - count of bytes to allocate (IN).
+* cDepth - recursive call depth (IN).
+*
+*Exit:
+* Returns handle to allocated chunk in block. Reallocs block
+* if not large enough to accomodate request. Modifies free chunk
+* list to reflect allocated chunk.
+*
+*Errors:
+* TIPERROR (OOM)
+* Returns OOM if cbSizeChunk > USHRT_MAX.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR BLK_MGR::AllocChunk2(HCHUNK *phchunk, UINT cbSizeChunk, UINT cDepth)
+{
+ HFREE_CHUNK hfreechunk;
+ UINT cbSizeBlk; // Current block size.
+ ULONG cbSizeBlkNew2; // Size of new block.
+ UINT cbSizeBlkNew; // Size of new block.
+ UINT cbSizeFreeChunkNew; // Size of new free chunk.
+ TIPERROR err;
+
+ DebCheckState(0);
+
+ DebAssert(phchunk != NULL, "BLK_MGR::AllocChunk2: bad ptr.");
+
+ DebAssert((m_pbBlkCopy == NULL) && (m_pbBitmap == NULL),
+ "BLK_MGR::AllocChunk2: Compaction underway.");
+
+
+ cbSizeChunk = CbSizeChunkTrue(cbSizeChunk); // get physical chunk size
+
+ if (cbSizeChunk > USHRT_MAX) {
+ return TIPERR_OutOfMemory;
+ }
+
+ // Iterate over free chunk list for a sufficiently large chunk.
+ hfreechunk = HfreechunkOfCbSize(cbSizeChunk);
+
+ if (hfreechunk == HCHUNK_Nil) {
+
+ DebAssert(cDepth == 0, "BLK_MGR::AllocChunk2: reentered twice.");
+
+ // Couldn't find big enough chunk.
+ // If we're locked return an OOM
+ // else ask the heap manager to realloc the block.
+ //
+ if (IsLocked()) {
+ return TIPERR_OutOfMemory;
+ }
+
+ cbSizeBlk = CbSize();
+ cbSizeBlkNew2 = (ULONG)cbSizeBlk +
+ max(max(cbSizeChunk, BM_cbSizeInitial), sizeof(FREE_CHUNK));
+
+ if (cbSizeBlkNew2 > USHRT_MAX || cbSizeBlkNew2 == 0) {
+ return TIPERR_OutOfMemory;
+ }
+
+ // Alloc some more memory.
+ IfErrRet(m_blkdesc.Realloc((UINT)cbSizeBlkNew2));
+
+ // Now need to link in the new memory to the free list
+ // and call myself recursively. The recursive call
+ // is a tail-call and as such could be converted
+ // to iteration automatically.
+ // The new free chunk will be of size (newsize-oldsize) and
+ // its location in the new block is simply at offset oldsize
+ // in the new block.
+ // Add it onto the free list and make the recursive call.
+ // Since we've added a sufficiently large chunk, this
+ // recursive call *must* succeed.
+ //
+ cbSizeBlkNew = CbSize();
+ cbSizeFreeChunkNew = cbSizeBlkNew-cbSizeBlk;
+
+ // New chunk must be big enough to be a FREE_CHUNK.
+ DebAssert(cbSizeFreeChunkNew >= sizeof(FREE_CHUNK),
+ "BLK_MGR::AllocChunk2: new block not large enough after Realloc.");
+
+ // New chunk must be big enough to fulfill this request.
+ DebAssert(cbSizeFreeChunkNew >= cbSizeChunk,
+ "BLK_MGR::AllocChunk2: new block not large enough after Realloc.");
+
+ // Add it to freelist.
+ AddChunkToFreeList((HCHUNK)cbSizeBlk, cbSizeFreeChunkNew);
+
+ // Now return the result of the recursive call.
+ return AllocChunk2(phchunk, cbSizeChunk, cDepth+1);
+ }
+ else {
+#if ID_DEBUG
+ // If we didn't have to allocate any memory for this block, realloc
+ // it to its current size to guarentee that it gets moved.
+ //
+ if (cDepth == 0) {
+ IfErrRet(m_blkdesc.Realloc(CbSize()));
+ }
+#endif // ID_DEBUG
+
+ // hfreechunk is guaranteed to be large enough, so we just
+ // use it.
+ //
+ DebAssert(
+ ((FREE_CHUNK *)QtrOfHandle(hfreechunk))->m_cbSize >= (USHORT)cbSizeChunk,
+ "bad free chunk.");
+
+ *phchunk = (HCHUNK)hfreechunk;
+ DebCheckHandle(*phchunk);
+ return TIPERR_None;
+ }
+}
+#pragma code_seg()
+
+
+
+
+
+
+
+
+
+/***
+*PUBLIC BLK_MGR::FreeChunk - Frees a chunk in block.
+*Purpose:
+* Frees a chunk of a given size in a block. Returns block to
+* to free chunk list by consing onto front of list.
+*
+*Implementation Notes:
+* Note that the block manager doesn't remember the size of its chunks
+* -- this is the client's responsibility. No checking is done here to
+* ensure that chunks are freed with an accurate size; the size specified
+* by the client is rounded up appropriately to obtain the actual size
+* reserved by the chunk allocator, however. This does not prevent all
+* memory leaks -- freed chunks are not merged into adjacent free chunks.
+* This can produce "creeping fragmentation" that can only be cleaned out
+* by compacting the block.
+* NOTE: that when freechunk coalescing is done this problem will
+* be alleviated.
+*
+* NOTE: Can't be called during compaction.
+* NOTE: it's a bug if client attempts to free a locked chunk,
+* so assert HOWEVER since locking a chunk locks its block
+* this would mean we couldn't let them free "unlocked"
+* chunks. So only enable this assertion if and when
+* we implement true chunk-level locking.
+*
+*Entry:
+* hchunk - handle to chunk to free.
+* cbSizeChunk - size of chunk to free.
+*
+*Exit:
+* m_hfreechunk is updated. No errors.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+VOID BLK_MGR::FreeChunk(HCHUNK hchunk, UINT cbSizeChunk)
+{
+ DebAssert(hchunk != HCHUNK_Nil, "BLK_MGR::FreeChunk: Nil handle.");
+
+ DebAssert(IsValid(), "BLK_MGR::FreeChunk: invalid block.");
+
+ DebAssert((m_pbBlkCopy == NULL) && (m_pbBitmap == NULL),
+ "BLK_MGR::FreeChunk: Compaction underway.");
+
+ // get actual chunk size
+ cbSizeChunk = CbSizeChunkTrue(cbSizeChunk);
+
+ // Add chunk to free list.
+ AddChunkToFreeList(hchunk, cbSizeChunk);
+}
+#pragma code_seg()
+
+/***
+*PUBLIC BLK_MGR::Trim - Shrinks a block to purge trailing free areas.
+*Purpose:
+* Attempts to shrink the block to reclaim free memory at the end of it.
+* A Trim immediately after an EndCompact will reclaim all free memory
+* in the block, as the current implementation leaves all free memory at
+* the end of the block.
+*
+*Implementation Notes:
+* Calls Trim/1 until nothing more trimmed.
+*
+*Entry:
+* None
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR BLK_MGR::Trim()
+{
+ UINT cbReclaimed = 0;
+ TIPERROR err;
+
+ // Trim the block
+ do {
+ IfErrRet(Trim(&cbReclaimed));
+ } while (cbReclaimed != 0);
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+/***
+*PRIVATE BLK_MGR::Trim - Shrinks a block to purge trailing free areas.
+*Purpose:
+* Attempts to shrink the block to reclaim free memory at the end of it.
+* A Trim immediately after an EndCompact will reclaim all free memory
+* in the block, as the current implementation leaves all free memory at
+* the end of the block.
+*
+*Implementation Notes:
+* NOTE: Can't be called during compaction.
+* WARNING: Trim will only reclaim one free list item! Since the free list
+* is not optimized, Trim will usually have to be called more than
+* once. When Trim has exhausted its possibilities it will return zero
+* bytes freed.
+* NOTE: Trim is intended as a client-directed exception handler for heap
+* allocation, and should only be needed for very large heaps. Because
+* block shrinking can cause other blocks in the heap to be moved,
+* Trim should not be relied on as a fast routine.
+* NOTE: returns OOM if block locked.
+*
+*Entry:
+* puCbReclaimed - Produces the number of bytes
+* that were reclaimed, or zero if the block
+* could not be shrunk (OUT).
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR BLK_MGR::Trim(UINT *puCbReclaimed)
+{
+ USHORT cb, cbBytesFreed = 0;
+ FREE_CHUNK freechunkDummy; // dummy chunk to simplify list code
+ FREE_CHUNK *qfreechunk;
+ FREE_CHUNK *qfreechunk2; // scratch pointers for list walking
+ TIPERROR err = TIPERR_None;
+
+ // If this segment is locked then do not trim (return TIPERROR_None)
+ if (IsLocked()) {
+ return TIPERR_None;
+ }
+
+#if ID_DEBUG
+ // For win16 we do not put a real lock on the run-time segment. But we
+ // put a debug lock, to prevent memory movement. To be able to save
+ // the blockmgr while the module is in runnable state we check for the
+ // debug lock. If the there is a debug lock we do not trim this block.
+
+#if OE_SEGMENTED
+ DebAssert(!((SHEAP_MGR *)OOB_MAKEP2(this, 0))->DebIsLocked(),
+ " Cannot trim ");
+#endif
+
+#endif
+
+ freechunkDummy.m_hfreechunkNext = m_hfreechunk; // cons a dummy chunk onto list
+ qfreechunk = &freechunkDummy;
+ while (qfreechunk->m_hfreechunkNext != HCHUNK_Nil) {
+ qfreechunk2 = (FREE_CHUNK *)QtrOfHandle(qfreechunk->m_hfreechunkNext);
+
+ // see if this chunk is at the end of the block, and snip it if so
+ cb = CbSizeChunkTrue(qfreechunk2->m_cbSize);
+ if (CbSize() == (UINT)cb + (UINT)qfreechunk->m_hfreechunkNext) {
+ qfreechunk->m_hfreechunkNext = qfreechunk2->m_hfreechunkNext;
+ // Could argue that shrinking a block can't
+ // generate an error -- don't believe this???
+ // No - don't! Realloc-when-shrinking semantics are NOT
+ // defined thus... some implementations might try to
+ // move block elsewhere... or perhaps block is locked
+ // in a multi-threaded system by another thread.
+ //
+
+ // shrink block
+ IfErrRet(m_blkdesc.Realloc(CbSize() - cb));
+ cbBytesFreed = cb;
+ break; // and stop looking
+ }
+ else {
+ qfreechunk = qfreechunk2; // keep looking
+ }
+ }
+ // cdr off dummy to get list
+ m_hfreechunk = freechunkDummy.m_hfreechunkNext;
+
+ *puCbReclaimed = cbBytesFreed; // return # of bytes freed
+ return err;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC BLK_MGR::HszLen - Returns length of the specified string.
+*Purpose:
+* This computes and returns the length of the zero-terminated string
+* specified by hsz. This is almost equivalent to strlen(QtrOfHandle(hsz)),
+* except that the call to strlen could invalidate the result of
+* QtrOfHandle.
+*
+*Implementation Notes:
+* This function does NOT call strlen to do its work.
+*
+*Entry:
+* hsz - The handle to the string.
+*
+*Exit:
+* Total free size.
+*
+***********************************************************************/
+#if !OE_WIN32 //Dead code on Win32
+#pragma code_seg(CS_INIT)
+UINT BLK_MGR::HszLen(HCHUNK hsz) const
+{
+ XSZ qch;
+ UINT cb;
+
+ qch = (XSZ)QtrOfHandle(hsz);
+ for (cb = 0; *qch != '\0'; qch++, cb++);
+ return cb;
+}
+#pragma code_seg()
+#endif //!OE_WIN32
+
+
+
+/***
+*PUBLIC BLK_MGR::Free - Frees the managed block.
+*Purpose:
+* Frees the block managed by this block manager.
+* NOTE: Can't be called during compaction.
+* NOTE: assert that block not locked --
+* in the sheap-level-only-locking implementation this
+* implies that can't have any locks on the sheap at all
+* in order to free a block.
+*
+*Implementation Notes:
+* Defers to blkdesc member.
+* And then reinitializes private state.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None. No errors.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+VOID BLK_MGR::Free()
+{
+ DebAssert(IsValid(), "BLK_MGR::Free: invalid block.");
+
+ DebAssert((m_pbBlkCopy == NULL) && (m_pbBitmap == NULL),
+ "BLK_MGR::Free: Compaction underway.");
+
+ DebAssert(IsLocked() == FALSE, "whoops! block locked.");
+
+ m_blkdesc.Free();
+ ReInit();
+
+ DebAssert(IsValid() == FALSE,
+ "BLK_MGR::Free: whoops! block manager should be invalid.");
+}
+#pragma code_seg()
+
+
+
+
+/***
+*PUBLIC BLK_MGR::Read - Read in instance from stream
+*Purpose:
+* Load previously serialized BLK_MGR into this BLK_MGR.
+* First read in block "meta"-info. In this case, just the
+* free chunk list head (handle).
+* then defer to BLK_DESC for the block contents itself.
+*
+*Entry:
+* pstrm - stream to read data from
+*
+*Exit:
+* TIPERROR
+*
+*Errors:
+* Returns errors generated by STREAM::Read.
+*
+***********************************************************************/
+
+TIPERROR BLK_MGR::Read(STREAM *pstrm)
+{
+ BYTE fCoalesce;
+ TIPERROR err;
+
+ DebAssert((m_pbBlkCopy == NULL) && (m_pbBitmap == NULL),
+ "BLK_MGR::Read: Compaction underway.");
+
+ DebAssert(IsValid(), "BLK_MGR::Read: Block invalid.");
+
+ // Read freechunk list head from serialized rep.
+ IfErrRet(pstrm->ReadUShort(&m_hfreechunk));
+
+ // Read in coalescse freelist state
+ IfErrRet(pstrm->ReadByte(&fCoalesce));
+ m_fCoalesce = (USHORT) fCoalesce;
+
+
+ // Read actual block contents
+ err = m_blkdesc.Read(pstrm);
+
+#if HP_BIGENDIAN
+ if (!err)
+ SwapFreeList(TRUE); // swap back bytes in the free list
+#endif //HP_BIGENDIAN
+
+ return err;
+}
+
+
+/***
+*PUBLIC BLK_MGR::Write - Write out instance to stream
+*Purpose:
+* Serialize the BLK_MGR to a stream.
+*
+*Implementation Notes:
+* First Trim the block.
+* Then write out block "meta"-info. In this case, just the
+* free chunk list head (handle).
+* then defer to BLK_DESC for the block contents itself.
+*
+*Entry:
+* pstrm - stream to write data to
+*
+*Exit:
+* TIPERROR
+*
+*Exceptions:
+* errors returned by STREAM::Write()
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR BLK_MGR::Write(STREAM *pstrm)
+{
+ BYTE fCoalesce;
+ TIPERROR err;
+
+ DebAssert((m_pbBlkCopy == NULL) && (m_pbBitmap == NULL),
+ "BLK_MGR::Write: Compaction underway.");
+
+ DebAssert(IsValid(), "BLK_MGR::Write: Block invalid.");
+
+ // Trim the block
+ IfErrRet(Trim());
+
+ // Write out freechunk list head to stream.
+ IfErrRet(pstrm->WriteUShort(m_hfreechunk));
+
+ // Write out coalescse freelist state.
+ fCoalesce = (BYTE)m_fCoalesce;
+ IfErrRet(pstrm->WriteByte(fCoalesce));
+
+
+#if HP_BIGENDIAN
+ SwapFreeList(FALSE); // swap bytes in the free list
+#endif //HP_BIGENDIAN
+
+ // Write actual block contents
+ err = m_blkdesc.Write(pstrm);
+#if HP_BIGENDIAN
+ SwapFreeList(TRUE); // swap back bytes in the free list
+#endif //HP_BIGENDIAN
+ return err;
+}
+
+
+#pragma code_seg()
+
+
+/***
+*PUBLIC BLK_MGR::GetSize
+*Purpose:
+* Returns size of block + extra debug shift bytes.
+*
+
+*Entry:
+* None.
+*
+*Exit:
+* UINT : size of block desc.
+*
+***********************************************************************/
+
+UINT BLK_MGR::GetSize() const
+{
+ if (IsValid())
+ return CbSize();
+ else
+ return 0;
+}
+
+
+#if HP_BIGENDIAN
+/***
+*PRIVATE BLK_MGR::SwapFreeList
+*Purpose:
+* Swaps/unswaps the bytes in the free list in a blkmgr
+*
+*Implementation Notes:
+* Iterates down freechunk list, swapping/unswapping all bytes
+*
+*Entry:
+* fSwapFirst == TRUE if we're to swap bytes before looking at them
+* (ie we're un-swapping)
+*
+*Exit:
+* None
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE )
+VOID BLK_MGR::SwapFreeList(BOOL fSwapFirst)
+{
+ FREE_CHUNK *qfreechunk; // Iterates over free chunks.
+ HFREE_CHUNK hfreechunk;
+
+ // Iterate over free chunk list.
+ hfreechunk = m_hfreechunk;
+ while (hfreechunk != HCHUNK_Nil) {
+ qfreechunk = (FREE_CHUNK *)QtrOfHandle(hfreechunk);
+
+ hfreechunk = qfreechunk->m_hfreechunkNext; // Get next handle
+ // (assuming we're swapping)
+
+ // swap the FREE_CHUNK structure
+ SwapStruct(qfreechunk, FREE_CHUNK_LAYOUT);
+
+ if (fSwapFirst) // if un-swapping, get next unswapped handle
+ hfreechunk = qfreechunk->m_hfreechunkNext;
+
+ }
+}
+#pragma code_seg( )
+#endif //HP_BIGENDIAN
+
+
+#if ID_DEBUG
+/***
+*PUBLIC BLK_MGR::DebShowState - BLK_MGR state
+*Purpose:
+* Show BLK_MGR state
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+*Exceptions:
+* None.
+*
+***********************************************************************/
+
+VOID BLK_MGR::DebShowState(UINT uLevel) const
+{
+ BYTE *pb;
+ UINT i;
+
+ DebPrintf("free chunk handle: %u\n", m_hfreechunk);
+ DebPrintf("block size: %u\n", CbSize());
+
+ if (uLevel == 0) {
+ for (pb = m_blkdesc.QtrOfBlock(), i=0 ; i < CbSize(); i++, pb++) {
+ DebPrintf("%d: %u\n", i, (CHAR)*pb);
+ }
+ }
+
+ if (uLevel == 1) {
+ HFREE_CHUNK hfreechunk = m_hfreechunk;
+ FREE_CHUNK *qfreechunk;
+
+ while (hfreechunk != HCHUNK_Nil) {
+ qfreechunk = (FREE_CHUNK *)QtrOfHandle(hfreechunk);
+ DebPrintf("free chunk: handle=%u, size=%u\n", hfreechunk,
+ qfreechunk->m_cbSize);
+ hfreechunk = qfreechunk->m_hfreechunkNext; // Get next.
+ }
+ }
+}
+
+/***
+*PUBLIC BLK_MGR::DebCheckState - BLK_MGR state
+*Purpose:
+* Check BLK_MGR state
+*
+*Implementation Notes:
+* Walks the free chunk list verifying that the following is true:
+* (1) the free list is not circular; this is determined by counting
+* number of free chunks and if it exceeds cMaxFreeChunkLimit then
+* we assert with "circular free chunk list".
+* (2) all free chunks are trivially valid; that is, their handles are
+* even and they are contained within the block.
+* (3) none of the free chunks overlap.
+* (4) if this is a coalescing BLK_MGR, that
+* handles are monotonically increasing
+*
+* NOTE: assumes (chunk handle == offset into block) implementation.
+* NOTE: assumes a limit of cMaxFreeChunkLimit free chunks per block --
+* this is used as a guard against list circularity. The current
+* 64K limit on blocks means that this should be at least 16384.
+*
+*Entry:
+* uLevel level of checking: 0 - means NOP (unless g_fHeapChk on).
+* 1 - means do it regardless of g_fHeapChk.
+*
+*
+*Exit:
+* Either asserts or returns.
+*
+***********************************************************************/
+
+#if OE_WIN16
+// NOTE: C7 compiler asserts with -Ox
+#pragma optimize("g", off)
+#endif //OE_WIN16
+VOID BLK_MGR::DebCheckState(UINT uLevel) const
+{
+ const UINT cMaxFreeChunkLimit = 20000; // limit on # of free chunks
+ UINT cFree = 0; // count of # of free chunks
+ HFREE_CHUNK hfreechunk, hchunk; // handles for walking free list
+ FREE_CHUNK *qfreechunk, *qfreechunk2; // pointers for walking free list
+
+ // Do they want us to really do something?
+ if (uLevel == 0) {
+ if (g_fHeapChk == FALSE) {
+ return;
+ }
+ }
+
+ DebAssert(IsValid(), "BLK_MGR::DebCheckState: invalid block.");
+
+ // (1) FREE LIST NOT CIRCULAR
+ // (2) FREE CHUNKS TRIVIALLY VALID
+ for (hfreechunk = m_hfreechunk;
+ hfreechunk != HCHUNK_Nil;
+ hfreechunk = qfreechunk->m_hfreechunkNext) // walk the free list
+ {
+ DebAssert(cFree++ < cMaxFreeChunkLimit,
+ "BLK_MGR::DebCheckState: circular free chunk list.");
+
+ DebAssert(0 == (1 & (UINT)hfreechunk),
+ "BLK_MGR::DebCheckState: odd chunk handle.");
+
+ qfreechunk = (FREE_CHUNK *)QtrOfHandle(hfreechunk);
+
+ DebAssert((UINT)hfreechunk+qfreechunk->m_cbSize <= CbSize(),
+ "BLK_MGR::DebCheckState: free chunk outside the block.");
+
+ if (m_fCoalesce) {
+ // ensure monotonically increasing handles.
+ if (qfreechunk->m_hfreechunkNext != HCHUNK_Nil) {
+ DebAssert(qfreechunk->m_hfreechunkNext > hfreechunk,
+ "freelist not sorted.");
+ }
+ }
+ }
+
+ // (3) NO FREE CHUNKS OVERLAP
+ for (hfreechunk = m_hfreechunk;
+ hfreechunk != HCHUNK_Nil;
+ hfreechunk = qfreechunk->m_hfreechunkNext) // walk the free list
+ {
+ qfreechunk = (FREE_CHUNK *)QtrOfHandle(hfreechunk);
+ for (hchunk = qfreechunk->m_hfreechunkNext;
+ hchunk != HCHUNK_Nil;
+ hchunk = qfreechunk2->m_hfreechunkNext) // walk rest of free list
+ {
+ qfreechunk2 = (FREE_CHUNK *)QtrOfHandle(hchunk);
+ DebAssert((ULONG)qfreechunk+qfreechunk->m_cbSize <= (ULONG) qfreechunk2 ||
+ (ULONG)qfreechunk2+qfreechunk2->m_cbSize <= (ULONG) qfreechunk,
+ "BLK_MGR::DebCheckState: two free chunks overlap.");
+ }
+ }
+
+ // CONSIDER: (Ilanc) Be nice t check that the free list is indeed
+ // coalesced at this point.
+}
+#if OE_WIN16
+#pragma optimize("", on)
+#endif //OE_WIN16
+
+// Checks if chunk handle is valid:
+// even and within bounds,
+// and not on free list.
+//
+VOID BLK_MGR::DebCheckHandle(HCHUNK hchunk) const
+{
+ HFREE_CHUNK hfreechunk;
+ FREE_CHUNK *qfreechunk;
+
+ if (m_fRoundUp) {
+ DebAssert(((hchunk & (sizeof(FREE_CHUNK)-1)) == 0) &&
+ (hchunk < CbSize()), "bad handle.");
+ }
+ else {
+ DebAssert(((hchunk & 1) == 0) && (hchunk < CbSize()), "bad handle.");
+ }
+
+ // walk the free list.
+ // Don't bother with free list during compaction... no point.
+ //
+ if ((m_pbBlkCopy == NULL) && (m_pbBitmap == NULL)) {
+ for (hfreechunk = m_hfreechunk;
+ hfreechunk != HCHUNK_Nil;
+ hfreechunk = qfreechunk->m_hfreechunkNext) {
+
+ DebAssert(hchunk != (HCHUNK)hfreechunk,
+ "BLK_MGR::DebCheckHandle: hchunk in freelist.");
+
+ qfreechunk = (FREE_CHUNK *)QtrOfHandle(hfreechunk);
+ }
+ }
+}
+
+
+
+#endif // ID_DEBUG
diff --git a/private/oleauto/src/typelib/blkmgr.hxx b/private/oleauto/src/typelib/blkmgr.hxx
new file mode 100644
index 000000000..7c343bf9a
--- /dev/null
+++ b/private/oleauto/src/typelib/blkmgr.hxx
@@ -0,0 +1,752 @@
+/***
+*blkmgr.hxx - Block Manager
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* The block manager provides memory management services for a
+* a contiguous block of memory allocated from the compile-time
+* heap. It manages sub-blocks ("chunks") and supports compaction.
+* See \silver\doc\ic\blkmgr.doc for more information.
+*
+*Revision History:
+*
+* 30-Jan-91 ilanc: Created.
+* 14-Feb-91 ilanc: Private member HBLOCK becomes BLK_DESC
+* 07-Mar-91 ilanc: Added IsValid() method.
+* 07-Mar-91 ilanc: Moved HCHUNK typedef to inc\types.h
+* 21-Mar-91 ilanc: Made some stuff inline and added
+* PtrOfHandle/2 (with addtl offset param).
+* 27-Mar-91 ilanc: Read and Write blocks.
+* 07-Jun-91 ilanc: Ripped exceptions... return TIPERRORs.
+* 29-Jul-91 t-toddw: added Trim() method, fixed a PtrOfHandle comment.
+* 30-Jul-91 ilanc: Fixed Trim() decl syntax error.
+* 09-Aug-91 t-toddw: Trim now returns UINT, Added CbSizeChunkTrue().
+* 21-Aug-91 ilanc: Added MAKESHEAPMGRP macro. Removed m_psheapmgr
+* member.
+* 25-Mar-92 ilanc: Rm'ed static Create (no need).
+* 26-Mar-92 ilanc: Added CbSizeFree().
+* 01-Apr-92 ilanc: Added *optional* coalescing. Default is yes.
+* Init() takes optional 2nd fCoalesce param.
+* 17-Dec-92 w-peterh: reordered data members
+*
+*Implementation Notes:
+*
+*
+*****************************************************************************/
+
+#ifndef BLKMGR_HXX_INCLUDED
+#define BLKMGR_HXX_INCLUDED
+
+#include <limits.h>
+#include "sheapmgr.hxx"
+
+class STREAM; // #include "stream.hxx"
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szBLKMGR_HXX)
+#define SZ_FILE_NAME g_szBLKMGR_HXX
+#endif
+
+
+// Macro to convert a segment pointer to a SHEAP_MGR*
+#define MAKESHEAPMGRP \
+ ((SHEAP_MGR *) OOB_MAKEP(OOB_SELECTOROF(this), 0))
+
+
+// Handle to a free chunk in a block. Implemented just as an offset
+// from beginning of block.
+//
+typedef UINT HFREE_CHUNK;
+
+// Packed handle to a free chunk in a block. Implemented just as an offset
+// from beginning of block.
+//
+typedef USHORT sHFREE_CHUNK;
+
+
+// This constant is the size of the bitmap used during compaction.
+//
+extern const UINT BM_cbSizeBitmap ;
+
+// This constant is used for the initial size of an allocated block.
+//
+extern const UINT BM_cbSizeInitial;
+
+//
+// struct: FREE_CHUNK
+// The following struct simply maps the header of a free chunk
+// into two fields: size and next. Each free chunk on the free
+// list is immediately followed by size number of (free) bytes.
+// NOTE: Assumes that sizeof(USHORT)==sizeof(HCHUNK)
+//
+struct FREE_CHUNK {
+ union {
+ USHORT m_cbSize; // Size of free chunk w/o this header.
+ sHCHUNK m_hchunkNew; // Forwarding handle.
+ };
+ sHFREE_CHUNK m_hfreechunkNext; // Handle of next free chunk in list.
+ // HCHUNK_Nil indicates end of list.
+};
+
+#if HP_BIGENDIAN
+#define FREE_CHUNK_LAYOUT "ss" // layout for byte swapping
+#endif //HP_BIGENDIAN
+
+
+#if OE_MAC68K
+#if ID_SWAPPABLE
+#define CS_BLKMGR "Oblkmgr","swappable"
+#else
+#if !OE_WIN32
+#define CS_BLKMGR "Oblkmgr"
+#else //!OE_WIN32
+#define CS_BLKMGR
+#endif //!OE_WIN32
+#endif
+
+#else
+#define CS_BLKMGR
+#endif
+
+/***
+*class BLK_MGR - 'blkmgr': Block manager
+*Purpose:
+* The class implements the block manager. TYPE_DATA and NAM_MGR
+* use the block manager to manage their idnodes and names respectively.
+*
+***********************************************************************/
+
+class BLK_MGR
+{
+ friend class DYN_BLK_MGR;
+public:
+ BLK_MGR();
+ ~BLK_MGR();
+
+ static void FreeStandalone(BLK_MGR *pbm);
+ // non-OB blkmgr clients, e.g. OLE, do not round up by default.
+ static TIPERROR CreateStandalone(BLK_MGR **ppbm, BOOL fRoundUp = FALSE);
+ nonvirt TIPERROR Init(SHEAP_MGR *psheapmgr,
+ BOOL fCoalesce = TRUE,
+ BOOL fRoundUp = FALSE);
+
+
+ nonvirt TIPERROR AllocChunk(HCHUNK *phchunk, UINT cbSizeChunk);
+ nonvirt TIPERROR AllocXSZ(HCHUNK *phchunk, XSZ xsz);
+ nonvirt TIPERROR Read(STREAM *pstrm);
+ nonvirt TIPERROR Write(STREAM *pstrm);
+ nonvirt BYTE *QtrOfHandle(HCHUNK hchunk) const;
+ nonvirt BYTE *QtrOfHandle(HCHUNK hchunk, UINT oChunk) const;
+ nonvirt BYTE *QtrOfOldHandle(HCHUNK hchunkOld) const;
+ nonvirt TIPERROR StartCompact();
+ nonvirt HCHUNK MapChunk(HCHUNK hchunkOld, UINT cbSize);
+ nonvirt HCHUNK MapXSZ(HCHUNK hchunkOld);
+ nonvirt BOOL IsForwarded(HCHUNK hchunk) const;
+ nonvirt VOID EndCompact();
+ nonvirt VOID FreeChunk(HCHUNK hchunk, UINT cbSize);
+ nonvirt VOID FreeXSZ(HCHUNK);
+ nonvirt VOID Free();
+ nonvirt BOOL IsValid() const;
+ nonvirt UINT CbSizeFree() const;
+ nonvirt TIPERROR Trim();
+ #if !OE_WIN32
+ nonvirt UINT HszLen(HCHUNK hsz) const;
+ #endif
+
+ // Locking methods
+ nonvirt VOID Lock();
+ nonvirt VOID Unlock();
+ nonvirt BOOL IsLocked() const;
+
+ nonvirt VOID Lock(HCHUNK hchunk);
+ nonvirt VOID Unlock(HCHUNK hchunk);
+ nonvirt BOOL IsLocked(HCHUNK hchunk) const;
+ nonvirt UINT GetSize() const;
+ nonvirt UINT GetRemainingSize() const;
+
+ // Is empty method
+ nonvirt BOOL IsEmpty() const;
+
+ nonvirt SHEAP_MGR *Psheapmgr() const;
+
+ // Debug/test methods
+#if ID_DEBUG
+ nonvirt VOID DebShowState(UINT uLevel) const;
+ nonvirt VOID DebCheckState(UINT uLevel) const;
+ nonvirt VOID DebCheckHandle(HCHUNK hchunk) const;
+#else
+ nonvirt VOID DebShowState(UINT uLevel) const {}
+ nonvirt VOID DebCheckState(UINT uLevel) const {}
+ nonvirt VOID DebCheckHandle(HCHUNK hchunk) const {}
+#endif
+
+
+
+private:
+ nonvirt TIPERROR Trim(UINT *puCbReclaimed);
+ nonvirt TIPERROR AllocChunk2(HCHUNK *phchunk, UINT cbSizeChunk, UINT cDepth);
+ nonvirt BYTE *PtrOfCopy();
+ nonvirt VOID SetBit(UINT uBit) const;
+ nonvirt BOOL GetBit(UINT uBit) const;
+ nonvirt VOID ReInit();
+ nonvirt UINT CbSizeChunkTrue(UINT cbSize) const;
+ nonvirt HFREE_CHUNK HfreechunkOfCbSize(UINT cbSizeChunk);
+ nonvirt VOID AddChunkToFreeList(HCHUNK hchunk, UINT cbSizeChunk);
+ nonvirt VOID ConsChunkToFreeList(HCHUNK hchunk, UINT cbSize);
+ nonvirt UINT CbSize() const;
+#if HP_BIGENDIAN
+ nonvirt VOID SwapFreeList(BOOL fSwapFirst);
+#endif //HP_BIGENDIAN
+
+ BLK_DESC m_blkdesc;
+ sHFREE_CHUNK m_hfreechunk; // serialized
+ BYTE *m_pbBlkCopy;
+ BYTE *m_pbBitmap;
+
+ USHORT m_fCoalesce:1; // serialized
+ USHORT m_fRoundUp:1; // serialized: allocs should be rounded
+ // up to sizeof(FREE_CHUNK) boundaries.
+ USHORT undone:14;
+
+#ifdef BLKMGR_VTABLE
+#pragma VTABLE_EXPORT
+#endif
+};
+
+
+// inline methods
+//
+
+/***
+*PUBLIC BLK_MGR::~BLK_MGR - destructor
+*Purpose:
+* Destroys a block manager.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_BLKMGR)
+inline BLK_MGR::~BLK_MGR()
+{
+ // Do nothing, block will vanish when the heap is destructed.
+ // Note that has an embedded BLK_DESC member which is
+ // automagically destructed when this dtor is called.
+ // The BLK_DESC dtor frees the block (by deferring to the
+ // SHEAP_MGR).
+ DebAssert((m_pbBlkCopy == NULL) && (m_pbBitmap == NULL),
+ "BLK_MGR::~BLKMGR: whoops! compaction didn't complete.");
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC BLK_MGR::Psheapmgr
+*Purpose:
+* Gets containing sheapmgr
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_BLKMGR)
+inline SHEAP_MGR *BLK_MGR::Psheapmgr() const
+{
+ return m_blkdesc.Psheapmgr();
+}
+
+
+/***
+*PUBLIC BLK_MGR::IsValid - Tests if block manager in valid state.
+*Purpose:
+* Tests if block manager is valid -- i.e. has been allocated
+* a block. Defers to blkdesc member.
+*
+*Entry:
+* None.
+*
+*Exit:
+* Returns TRUE if valid, else FALSE.
+*
+***********************************************************************/
+#pragma code_seg(CS_BLKMGR)
+inline BOOL BLK_MGR::IsValid() const
+{
+ return m_blkdesc.IsValid();
+}
+#pragma code_seg()
+
+
+/***
+*PRIVATE BLK_MGR::CbSize - Size of block.
+*Purpose:
+* Returns size of block. Simply defers to allocating
+* heap manager.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+#pragma code_seg(CS_CORE)
+inline UINT BLK_MGR::CbSize() const
+{
+ DebAssert(IsValid(), "BLK_MGR::cbSize: invalid block.");
+
+ return m_blkdesc.CbSize();
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC BLK_MGR::QtrOfHandle - Converts handle to pointer.
+*Purpose:
+* Converts a chunk handle into a pointer. A Nil handle is
+* *NOT* converted to a NULL pointer (asserts).
+*
+*Entry:
+* hchunk - Handle to a chunk.
+*
+*Exit:
+* Returns a pointer to that chunk.
+*
+***********************************************************************/
+#pragma code_seg(CS_CORE)
+// CONSIDER: andrewso 30-Jun-93
+// QtrOfBlockActual is merged with QtrOfBlock, which in turn has
+// been merged with BLK_MGR::QtrOfHandle to avoid a problem
+// with inlining QtrOfBlockActual when QtrOfHandle is called. When we
+// upgrade our compiler with one that does inlining better, put this
+// stuff back.
+//
+// NOTE: This is legal because we are a friend to
+// BLK_DESC.
+//
+inline BYTE *BLK_MGR::QtrOfHandle(HCHUNK hchunk) const
+{
+ DebAssert(hchunk != HCHUNK_Nil, "BLK_MGR::QtrOfHandle: Nil handle.");
+
+ DebAssert(IsValid(), "BLK_MGR::QtrOfHandle: invalid block.");
+
+ DebAssert((UINT)hchunk < CbSize(),
+ "BLK_MGR::QtrOfHandle: handle out of bounds.");
+
+ return
+
+#if OE_MACNATIVE
+ OOB_MAKEP2(m_blkdesc.m_psheapmgr->m_hMemHeap,
+ m_blkdesc.m_qbMemBlock)
+#else
+ OOB_MAKEP2(&m_blkdesc, m_blkdesc.m_qbMemBlock)
+#endif
+
+#if ID_DEBUG
+ + ((m_blkdesc.m_fShiftUp == TRUE) ? 0 : SHM_cbShift)
+#endif
+ + (UINT)hchunk;
+
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC BLK_MGR::QtrOfHandle - Converts handle and offset to pointer.
+*Purpose:
+* Converts a chunk handle and an offset into chunk to a pointer.
+* A Nil handle is *NOT* converted to a NULL pointer
+* (QtrOfHandle asserts).
+*
+*Entry:
+* hchunk - Handle to a chunk.
+* oChunk - Offset into chunk.
+*
+*Exit:
+* Returns a pointer to offset within chunk.
+*
+***********************************************************************/
+#pragma code_seg(CS_CORE)
+inline BYTE *BLK_MGR::QtrOfHandle(HCHUNK hchunk, UINT oChunk) const
+{
+ DebAssert(IsValid(), "BLK_MGR::QtrOfHandle: invalid block.");
+ DebAssert(((UINT)hchunk + oChunk) < CbSize(),
+ "BLK_MGR::QtrOfHandle: handle out of bounds.");
+
+ return QtrOfHandle(hchunk) + oChunk;
+}
+#pragma code_seg()
+
+
+/***
+*PRIVATE BLK_MGR::GetBit - Gets bit in bitmap.
+*Purpose:
+* Indicates whether bit is set in bitmap.
+*
+* CONSIDER: make inline
+*
+*Entry:
+* uBit - Bit to test.
+*
+*Exit:
+* Returns TRUE if bit set otherwise FALSE.
+*
+***********************************************************************/
+#pragma code_seg(CS_CORE)
+inline BOOL BLK_MGR::GetBit(UINT uBit) const
+{
+ DebAssert(IsValid(), "BLK_MGR::GetBit: invalid block.");
+
+ UINT uBitsElem=sizeof(m_pbBitmap[0]) * CHAR_BIT;
+ return m_pbBitmap[uBit/uBitsElem] & (1 << (uBit % uBitsElem));
+}
+#pragma code_seg()
+
+/***
+*PRIVATE BLK_MGR::SetBit - Sets bit in bitmap.
+*Purpose:
+* Sets bit in bitmap.
+*
+* CONSIDER: make inline
+*
+*Entry:
+* uBit - Bit to set.
+*
+*Exit:
+*
+***********************************************************************/
+#pragma code_seg(CS_BLKMGR)
+inline VOID BLK_MGR::SetBit(UINT uBit) const
+{
+ DebAssert(IsValid(), "BLK_MGR::SetBit: invalid block.");
+
+ UINT uBitsElem=sizeof(m_pbBitmap[0]) * CHAR_BIT;
+ m_pbBitmap[uBit/uBitsElem] |= (1 << (uBit % uBitsElem));
+}
+#pragma code_seg()
+
+
+/***
+*PRIVATE BLK_MGR::ReInit - Reinitializes a block manager.
+*Purpose:
+* Reinitializes the private members of a block manager. Called
+* by Init() and by Free(). Note that can't assert IsValid()
+* here since Free() invalidates a block.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_BLKMGR)
+inline VOID BLK_MGR::ReInit()
+{
+ // Init private members.
+ m_pbBlkCopy=NULL;
+ m_pbBitmap=NULL;
+ m_hfreechunk=HCHUNK_Nil; // Initialize first free chunk
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC BLK_MGR::IsForwarded - has chunk been forwarded during compaction.
+*Purpose:
+* Indicates whether chunk addressed by handle has been forwarded
+* during compaction phase. Simply tests bitmap offset. Since
+* even-sized chunks are always allocated, each bit in the bitmap
+* represents one short, hence hchunk is divided by two before
+* bitmap is tested.
+*
+*Entry:
+* hchunk - handle of chunk.
+*
+*Exit:
+* Returns TRUE if chunk already forwarded else FALSE.
+*
+***********************************************************************/
+#pragma code_seg(CS_BLKMGR)
+inline BOOL BLK_MGR::IsForwarded(HCHUNK hchunk) const
+{
+ DebAssert(IsValid(), "BLK_MGR::IsForwarded: invalid block.");
+
+ DebAssert((m_pbBlkCopy != NULL) && (m_pbBitmap != NULL),
+ "BLK_MGR::MapChunk: not in midst of compaction.");
+
+ DebAssert(((UINT)hchunk & (sizeof(FREE_CHUNK)-1)) == 0,
+ "BLK_MGR::IsForwarded: hchunk not even.");
+
+ return GetBit(((UINT)hchunk) >> 2);
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC BLK_MGR::AllocChunk - allocates a chunk in block.
+*Purpose:
+* Allocates a contiguous chunk in block of cbSize bytes.
+*
+*Implementation Notes:
+* Note: simply defers to AllocChunk2 (private recursive method).
+*
+*Entry:
+* phchunk - pointer to chunk handle (OUT).
+* cbSizeChunk - count of bytes to allocate (IN).
+*
+*Exit:
+* Returns pointer to handle to allocated chunk in block.
+*
+***********************************************************************/
+#pragma code_seg(CS_CORE)
+inline TIPERROR BLK_MGR::AllocChunk(HCHUNK *phchunk, UINT cbSizeChunk)
+{
+ return AllocChunk2(phchunk, cbSizeChunk, 0);
+}
+
+
+/***
+*PUBLIC BLK_MGR::CbSizeChunkTrue - how much physical memory does a chunk occupy.
+*Purpose:
+* Utility routine to obtain the physical size of a chunk
+* from the client specified size of a chunk.
+* For OB:
+* This enforces the always multiple of sizeof(FREE_CHUNK), big enough
+* to hold a FREE_CHUNK and if this chunk if freed and it's allocated
+* so that some part of it remains, the remnant is be enough to
+* be returned to the freelist.
+*
+* For OLE:
+* Minimum freechunk must be 4 (sizeof(FREE_CHUNK)), but above that
+* we only enforce even size chunks. Possible then 2b remnants
+* can leak, but this is worth it because in OLE we rarely realloc.
+*
+*Entry:
+* cbSize - size client requested (in bytes)
+*
+*Exit:
+* UINT - actual number of bytes that should be allocated
+*
+***********************************************************************/
+
+inline UINT BLK_MGR::CbSizeChunkTrue(UINT cbSize) const
+{
+#if OE_RISC
+
+ return (cbSize < sizeof(FREE_CHUNK)) ?
+ (sizeof(FREE_CHUNK) + SHM_cbAlign-1) & ~(SHM_cbAlign-1) :
+ (cbSize + SHM_cbAlign-1) & ~(SHM_cbAlign-1);
+
+#else
+
+ if (m_fRoundUp) {
+ // round up to multiple of sizeof(FREE_CHUNK)
+ return (cbSize < sizeof(FREE_CHUNK)) ?
+ sizeof(FREE_CHUNK) :
+ (cbSize + sizeof(FREE_CHUNK)-1) & ~(sizeof(FREE_CHUNK)-1);
+ }
+ else {
+ // round up only to even size
+ return (cbSize < sizeof(FREE_CHUNK)) ?
+ sizeof(FREE_CHUNK) :
+ (cbSize + 1 & ~1);
+ }
+
+#endif // OE_RISC
+
+}
+
+
+/***
+*PUBLIC BLK_MGR::Lock
+*Purpose:
+* Lock the block.
+*
+*Implementation Notes:
+* Defers to blkdesc.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+inline VOID BLK_MGR::Lock()
+{
+ DebAssert(IsValid(), "BLK_MGR::Lock: Block invalid.");
+
+ m_blkdesc.Lock();
+}
+
+
+/***
+*PUBLIC BLK_MGR::Unlock
+*Purpose:
+* Unlock the block.
+*
+*Implementation Notes:
+* Defers to blkdesc.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID BLK_MGR::Unlock()
+{
+ DebAssert(IsValid(), "BLK_MGR::Unlock: Block invalid.");
+
+ m_blkdesc.Unlock();
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC BLK_MGR::IsLocked
+*Purpose:
+* Tests if block is locked.
+*
+*Implementation Notes:
+* Defers to blkdesc.
+*
+*Entry:
+*
+*Exit:
+* TRUE if block is locked -- i.e. at least one lock.
+***********************************************************************/
+#pragma code_seg(CS_BLKMGR)
+inline BOOL BLK_MGR::IsLocked() const
+{
+ DebAssert(IsValid(), "BLK_MGR::IsLocked: Block invalid.");
+
+ return m_blkdesc.IsLocked();
+}
+
+
+/***
+*PUBLIC BLK_MGR::Lock
+*Purpose:
+* Lock a chunk.
+*
+*Implementation Notes:
+* Defers to Lock/0. Locking a chunk locks its block.
+*
+*Entry:
+* hchunk Handle of chunk to lock.
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID BLK_MGR::Lock(HCHUNK hchunk)
+{
+ DebAssert(IsValid(), "BLK_MGR::Lock: Block invalid.");
+ DebCheckHandle(hchunk);
+
+ Lock();
+}
+
+
+/***
+*PUBLIC BLK_MGR::Unlock
+*Purpose:
+* Unlock the block.
+*
+*Implementation Notes:
+* Defers to Unlock()/0. Unlocking a chunk, unlocks its block.
+*
+*Entry:
+* hchunk Handle of chunk to lock.
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID BLK_MGR::Unlock(HCHUNK hchunk)
+{
+ DebAssert(IsValid(), "BLK_MGR::Unlock: Block invalid.");
+ DebCheckHandle(hchunk);
+
+ Unlock();
+}
+
+
+/***
+*PUBLIC BLK_MGR::IsLocked
+*Purpose:
+* Tests if chunk is locked.
+*
+*Implementation Notes:
+* Defers to IsLocked()/0
+*
+*Entry:
+* hchunk Handle of chunk to lock.
+*
+*Exit:
+* TRUE if chunk is locked -- i.e. at least one lock.
+***********************************************************************/
+inline BOOL BLK_MGR::IsLocked(HCHUNK hchunk) const
+{
+ DebAssert(IsValid(), "BLK_MGR::IsLocked: Block invalid.");
+ DebCheckHandle(hchunk);
+
+ return IsLocked();
+}
+
+
+/***
+*PUBLIC BLK_MGR::IsEmpty
+*Purpose:
+* Tests if blk is empty.
+*
+*Implementation Notes:
+* Simply compares CbSize with CbSizeFree, since no chunks
+* can leak the block is empty iff CbSize == CbSizeFree.
+*
+*Entry:
+*
+*Exit:
+* TRUE if block is empty -- i.e. no allocated chunks.
+*
+***********************************************************************/
+
+inline BOOL BLK_MGR::IsEmpty() const
+{
+ // In typelib we cannot determine if the block manager is empty or not
+ // as we round up to 2 bytes always.
+ DebAssert(0, " Cannot call this function ");
+ return FALSE;
+}
+
+
+/***
+*PUBLIC BLK_MGR::GetRemainingSize
+*Purpose:
+* Returns remaining size but deferring to blkdesc.
+*
+
+*Entry:
+* None.
+*
+*Exit:
+* UINT - remaining size.
+*
+***********************************************************************/
+
+inline UINT BLK_MGR::GetRemainingSize() const
+{
+ return m_blkdesc.GetRemainingSize();
+}
+
+
+#pragma code_seg()
+
+#endif // ! BLKMGR_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/bstr.h b/private/oleauto/src/typelib/bstr.h
new file mode 100644
index 000000000..a79c59cd1
--- /dev/null
+++ b/private/oleauto/src/typelib/bstr.h
@@ -0,0 +1,109 @@
+// BSTR.H - public BSTR stucture and prototypes
+//
+//
+// Revision History:
+// 11-Aug-92 w-peterh: added CopyBstr()
+//
+
+
+#ifndef BSTR_H_INCLUDED
+#define BSTR_H_INCLUDED
+
+#include "types.h"
+
+#if __cplusplus
+extern "C" {
+#endif
+
+#ifndef ID_INT_IS_LONG
+typedef unsigned int UINT;
+#endif
+
+#define AllocBstr SysAllocString
+#define ReallocBstr SysReAllocString
+#define AllocBstrLen SysAllocStringLen
+#define ReallocBstrLen SysReAllocStringLen
+#define FreeBstr SysFreeString
+
+#if OE_WIN32
+#define AllocBstrA SysAllocStringA
+#define ReallocBstrA SysReAllocStringA
+#define AllocBstrLenA SysAllocStringLenA
+#define ReallocBstrLenA SysReAllocStringLenA
+#define FreeBstrA SysFreeStringA
+#else
+#define AllocBstrA AllocBstr
+#define ReallocBstrA ReallocBstr
+#define AllocBstrLenA AllocBstrLen
+#define ReallocBstrLenA ReallocBstrLen
+#define FreeBstrA FreeBstr
+#define BstrLenA BstrLen
+#define CopyBstrA CopyBstr
+#endif // OE_WIN16
+
+
+#include "tiperr.h"
+
+// define some functions that are simple enough to do inline
+//
+
+__inline UINT BstrLen(BSTR bstr)
+{
+ if(bstr == NULL)
+ return 0;
+#if OE_WIN32
+ return (unsigned int)((((DWORD FAR*)bstr)[-1]) / 2);
+#else
+ return (unsigned int)(((DWORD FAR*)bstr)[-1]);
+#endif
+}
+
+#if OE_WIN32
+__inline UINT BstrLenA(BSTRA bstr)
+{
+ if(bstr == NULL)
+ return 0;
+ return (unsigned int)(((DWORD FAR*)bstr)[-1]);
+}
+#endif //OE_WIN32
+
+
+__inline TIPERROR CopyBstr (LPBSTR lpbstrDest, BSTR bstrSrc)
+{
+ if (bstrSrc) {
+
+ *lpbstrDest = AllocBstrLen(bstrSrc, BstrLen(bstrSrc));
+ if (*lpbstrDest == NULL)
+ return TIPERR_OutOfMemory;
+ }
+ else
+ *lpbstrDest = NULL;
+
+ return TIPERR_None;
+}
+#if OE_WIN32
+__inline TIPERROR CopyBstrA (LPBSTRA lpbstrDest, BSTRA bstrSrc)
+{
+ if (bstrSrc) {
+
+ *lpbstrDest = AllocBstrLenA(bstrSrc, BstrLenA(bstrSrc));
+ if (*lpbstrDest == NULL)
+ return TIPERR_OutOfMemory;
+ }
+ else
+ *lpbstrDest = NULL;
+
+ return TIPERR_None;
+}
+#endif
+
+__inline int PASCAL ReallocBstrBstr(BSTR FAR *pbstrDest, BSTR bstrSrc)
+{
+ return ReallocBstrLen(pbstrDest, bstrSrc, BstrLen(bstrSrc));
+}
+
+#if __cplusplus
+} /* extern C */
+#endif
+
+#endif /* BSTR_H_INCLUDED */
diff --git a/private/oleauto/src/typelib/cltypes.hxx b/private/oleauto/src/typelib/cltypes.hxx
new file mode 100644
index 000000000..5b34156bc
--- /dev/null
+++ b/private/oleauto/src/typelib/cltypes.hxx
@@ -0,0 +1,687 @@
+/***
+*cltypes.hxx - Class Lib component-wide header file.
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Component-wide stuff. See \silver\doc\client\tmembers.doc for
+* more info on these definitions.
+*
+* This file defines the following:
+* enum TYPEKIND
+* enum PERSISTENCEKIND
+* typedef HMEMBER
+* typedef HIMPTYPE
+* enum ACCESS
+* enum VAR_KIND
+* enum DECLKIND
+* enum TYPEDESCKIND
+* enum PTRKIND
+* enum FUNC_KIND
+* enum CALLINGCONVENTION
+* enum PARAMKIND
+* enum SPECIALKIND
+* enum INFOKIND
+* enum VARDESCKIND
+* enum DEFNKIND
+* struct VAROFS
+* struct VMETHOFS
+* struct VBASEPOS
+* struct VARPOS
+* struct VMETHPOS
+* struct EDITKIND
+*
+*
+*Revision History:
+* 25-Feb-91 ilanc: Created
+* [01] 25-Feb-91 petergo: Added HIMPTYPE
+* [02] 27-Feb-91 ilanc: Added DECLKIND
+* [03] 28-Feb-91 ilanc: Moved to ..\cl
+* [04] 07-Mar-91 petergo: Add HLNAM_Nil
+* [05] 10-Mar-91 ilanc: Added VKIND_Formal, VKIND_Local, ACCESS_Ignore
+* [06] 21-May-91 ilanc: Added PARAMKIND enum
+* [07] 06-Jun-91 ilanc: Windowsian typedefs...
+* [08] 31-Oct-91 ilanc: Added TKIND_Alias
+* [09] 15-Nov-91 ilanc: Added SPECIALKIND enum.
+* [10] 02-Mar-91 petergo: Added HGNAM_Nil.
+* [11] 16-Mar-92 ilanc: Added EDITKIND
+* [12] 02-Apr-92 ilanc: Added VARDESCKIND.
+* [13] 20-Apr-92 stevenl: Added DEFNKIND.
+* [14] 03-Jun-92 w-peterh: Added HMEMBER Accessor functions
+* [15] 16-Jun-92 w-peterh: Added DEFNKIND DK_RecTypeDefn
+* [16] 02-Jul-92 w-peterh: Added INFOKIND INFOKIND_NestedType
+* [17] 30-Jul-92 w-peterh: Added IsMatchOfVisibility()
+* [18] 18-Aug-92 w-peterh: Added IMPADDR(from impmgr.hxx)
+* [19] 22-Oct-92 w-peterh: Added HRESDESCTBL
+* [20] 14-Nov-92 ilanc: Added INVOKEKIND
+* [21] 21-Nov-92 Rajiv: Updated Edit Kind.
+* [22] 25-Nov-92 ilanc: Made HMEMBER/sHMEMBER 32 bits.
+* [23] 14-Dec-92 w-peterh: Moved INVOKEKIND to clhost.h
+* [24] 12-Feb-93 w-peterh: added VDK_Base*, PARAMKIND_Ignore
+* [25] 30-Apr-93 w-jeffc: added sACCESS, sDEFNKIND and layout strings
+* for virtual function structures
+*
+*Implementation Notes:
+* Note: we assume (for now) large-model compilation on 16-bit.
+* I.e. all pointers are far. If and when we distribute
+* header files we probably need to make sure that pointer
+* types are explicitly far.
+*
+*****************************************************************************/
+
+#ifndef CLTYPES_HXX_INCLUDED
+#define CLTYPES_HXX_INCLUDED
+
+// enum TYPEDESCKIND - tdesckind
+//
+// defined in tdesck.hxx
+//
+// WARNING:
+// There is an array in dumptlib.cxx that is indexed by this enum.
+
+#include "silver.hxx"
+#include "tdesck.hxx"
+#include <limits.h>
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szCLTYPES_HXX)
+#define SZ_FILE_NAME g_szCLTYPES_HXX
+#endif
+
+
+typedef CALLCONV CALLINGCONVENTION;
+
+// Error codes generated by methods of the CLASSLIB protocols are
+// of type TIPERROR. The error code are defined in cliberrs.hxx.
+// NOTE: tiperrs.hxx is defined in types.h
+// typedef USHORT TIPERROR;
+
+class TYPEMGR;
+typedef TYPEMGR *LPTYPEMGR;
+typedef LPTYPEMGR *LPLPTYPEMGR;
+
+typedef ITypeLibA *LPITypeLib;
+typedef LPITypeLib *LPLPITypeLib;
+
+class TYPEINFO;
+typedef TYPEINFO* LPTYPE_INFO;
+typedef LPTYPE_INFO* LPLPTYPEINFO;
+
+class DYN_TYPEMEMBERS;
+typedef DYN_TYPEMEMBERS* LPDYNTYPEMEMBERS;
+typedef LPDYNTYPEMEMBERS* LPLPDYNTYPEMEMBERS;
+
+class TYPEFIXUPS;
+typedef TYPEFIXUPS* LPTYPEFIXUPS;
+typedef LPTYPEFIXUPS* LPLPTYPEFIXUPS;
+
+class DEFN_TYPEBIND;
+typedef DEFN_TYPEBIND* LPDEFNTBIND;
+typedef LPDEFNTBIND* LPLPDEFNTBIND;
+
+typedef LPOLESTR TYPEID;
+typedef TYPEID* LPTYPEID;
+typedef LPTYPEID* LPLPTYPEID;
+
+
+// PERSISTENCEKIND enum - pkind
+//
+// WARNING:
+// There is an array in dumptlib.cxx that is indexed by this enum.
+enum PERSISTENCEKIND
+{
+ PKIND_None,
+ PKIND_Serializable,
+ PKIND_Persistent
+};
+
+
+// HMEMBER - hmember: entry import handle
+// HIMPTYPE - himptype: type imp
+// HLNAM - hlnam: local name handle
+// HGNAM - hgnam: global name handle
+typedef ULONG HMEMBER; // 25-Nov-92: now 32bit
+typedef HMEMBER sHMEMBER;
+typedef UINT HIMPTYPE;
+typedef USHORT sHIMPTYPE;
+typedef UINT HIMPADDR;
+typedef USHORT sHIMPADDR;
+typedef HCHUNK HLNAM;
+typedef sHCHUNK sHLNAM;
+typedef HCHUNK HNAMSTR;
+typedef sHCHUNK sHNAMSTR;
+typedef ULONG HGNAM;
+typedef ULONG sHGNAM;
+typedef LPVOID IMPADDR;
+
+
+// Constants that go with these types
+const HLNAM HLNAM_Nil = HCHUNK_Nil;
+const HGNAM HGNAM_Nil = 0x00000000;
+const HIMPTYPE HIMPTYPE_Nil = 0xFFFF;
+const HIMPADDR HIMPADDR_Nil = 0xFFFF;
+
+/* HMEMBERs The Full story (part II):
+*
+* HMEMBERs are handles to a modules data or function members and
+* are unique (except property fn.) within a TypeInfo's scope.
+*
+* HMEMBERs have the following form:
+*
+* 01<user bits:4><unused:4><nesting level:6><offset:16>
+*
+* Where the user bits can have any value, the unused bits are always
+* zero (reserved for future use) and the nesting level is equal to
+* the number of inhertence levels below the current TypeInfo.
+*
+****************************************************************************/
+
+const HMEMBER HMEMBER_Nil = (HMEMBER)DISPID_UNKNOWN;
+
+#define HMEMBER_ReservedBits (0x80000000) // Reserved
+#define HMEMBER_StdOleId (0x40000000) // Standard OLE Hmember
+
+#define HMEMBER_UserBits (0x3C000000)
+#define HMEMBER_BrkModeBit (0x04000000)
+#define HMEMBER_UserBitsShift 26
+
+#define HMEMBER_Unused (0x03C00000)
+#define HMEMBER_UnusedShift 22
+
+#define HMEMBER_NestDepth (0x003F0000)
+#define HMEMBER_NestDepthShift 16
+#define HMEMBER_NestDepthSize 6
+
+#define HMEMBER_Offset (0x0000FFFF)
+
+// Hmember helpers.
+
+inline UINT UserBits(HMEMBER hmember)
+{
+ return (UINT)((hmember & HMEMBER_UserBits) >> HMEMBER_UserBitsShift);
+}
+
+inline UINT NestDepth(HMEMBER hmember)
+{
+ return (UINT)((hmember & HMEMBER_NestDepth) >> HMEMBER_NestDepthShift);
+}
+
+inline UINT Offset(HMEMBER hmember)
+{
+ return (UINT)(hmember & HMEMBER_Offset);
+}
+
+inline BOOL IsStdOleHmember(HMEMBER hmember)
+{
+ return !(hmember & HMEMBER_ReservedBits)
+ && (hmember & HMEMBER_StdOleId);
+}
+
+inline HMEMBER SetUserBits(UINT bits)
+{
+ DebAssert(!(((LONG)bits << HMEMBER_UserBitsShift) & ~HMEMBER_UserBits),
+ "Invalid field.");
+
+ return (LONG)bits << HMEMBER_UserBitsShift;
+}
+
+inline HMEMBER SetNestDepth(UINT bits)
+{
+ DebAssert(!(((LONG)bits << HMEMBER_NestDepthShift) & ~HMEMBER_NestDepth),
+ "Invalid field.");
+
+ return (LONG)bits << HMEMBER_NestDepthShift;
+}
+
+
+/* OLE HMEMBERS -- the full story (part II)
+*
+* The hmember is set as above with the first set of user bits is
+* formatted as follows:
+*
+* <is FuncDesc>0000
+*
+* The offset is the index of the Desc.
+*
+****************************************************************************/
+
+#define HMEMBER_Func (0x8) // offset is for FuncDesc
+
+const UINT HMEMBER_PredeclId = (UINT)ID_DEFAULTINST;
+
+inline BOOL AddedInBrkMode(HMEMBER hmember)
+{
+ DebAssert(hmember != HMEMBER_Nil, "Bad hmember");
+
+ return (BOOL) ((hmember & HMEMBER_BrkModeBit) == 0);
+}
+
+
+
+inline BOOL IsFunction(HMEMBER hmember)
+{
+ DebAssert(hmember != HMEMBER_Nil, "Bad hmember");
+
+ return (BOOL) UserBits(hmember) & HMEMBER_Func;
+}
+
+inline HMEMBER FunctionHmemberOfOffset(UINT offset, UINT nestDepth)
+{
+ return HMEMBER_StdOleId
+ | SetUserBits(HMEMBER_Func)
+ | SetNestDepth(nestDepth)
+ | (HMEMBER)(offset);
+}
+
+inline HMEMBER DataHmemberOfOffset(UINT offset, UINT nestDepth)
+{
+ return HMEMBER_StdOleId
+ | SetNestDepth(nestDepth)
+ | (HMEMBER)(offset);
+}
+
+
+// enum ACCESS - access
+//
+// WARNING:
+// There is an array in dumptlib.cxx that is indexed by this enum.
+enum ACCESS
+{
+ ACCESS_Private,
+ ACCESS_Public
+};
+
+typedef USHORT sACCESS;
+
+
+/***
+*PROTECTED IsMatchOfVisibility - Filter on visibility.
+*Purpose:
+* Filter on visibility.
+*
+*Implementation Notes:
+* // *** WRITE SOME MORE HERE ****
+*Entry:
+*
+*Exit:
+* None.
+*
+*Errors:
+* BOOL
+*
+***********************************************************************/
+
+inline BOOL IsMatchOfVisibility(ACCESS accessMbr, ACCESS accessClient)
+{
+ return (accessMbr >= accessClient);
+}
+
+
+// enum VAR_KIND - vkind
+//
+// WARNING:
+// There is an array in dumptlib.cxx that is indexed by this enum.
+enum VAR_KIND
+{
+ VKIND_DataMember
+ ,VKIND_Base
+ ,VKIND_Enumerator
+ ,VKIND_Formal
+};
+
+
+// enum DECLKIND - declkind
+//
+enum DECLKIND
+{
+ DECLKIND_Implicit,
+ DECLKIND_Typechar,
+ DECLKIND_Explicit
+};
+
+
+
+// enum PTRKIND - ptrkind
+//
+// WARNING:
+// There is an array in dumptlib.cxx that is indexed by this enum.
+enum PTRKIND
+{
+ PTRKIND_Ignore,
+ PTRKIND_Near,
+ PTRKIND_Far,
+ PTRKIND_Near32,
+ PTRKIND_Far32,
+ PTRKIND_Based,
+ PTRKIND_Huge,
+ PTRKIND_Basic,
+};
+
+
+// enum FUNC_KIND - fkind
+//
+enum FUNC_KIND
+{
+ FKIND_NonVirtual,
+ FKIND_Virtual,
+ FKIND_Static,
+ FKIND_Dispatch
+};
+
+
+// enum PARAMKIND - paramkind
+//
+enum PARAMKIND
+{
+ PARAMKIND_In,
+ PARAMKIND_Out,
+ PARAMKIND_InOut,
+ PARAMKIND_Ignore
+};
+
+
+// enum SPECIALKIND - specialkind
+// Purpose:
+// Enumerates different kinds of special functions.
+//
+enum SPECIALKIND
+{
+ SPECIALKIND_Normal,
+ SPECIALKIND_Ctor,
+ SPECIALKIND_Dtor
+};
+
+
+// enum INFOKIND - infokind
+// Purpose:
+// Enumerates different kinds of INFOs.
+//
+enum INFOKIND
+{
+ INFOKIND_Var,
+ INFOKIND_Func,
+ INFOKIND_Param,
+ INFOKIND_NestedType
+};
+
+
+// enum VARDESCKIND - vdesckind
+// Purpose:
+// Enumerates different kinds Basic variables.
+//
+enum VARDESCKIND
+{
+ VDK_Unknown,
+ VDK_LocalIntrinsic,
+ VDK_LocalRecord,
+ VDK_LocalObject,
+ VDK_ByvalIntrinsic,
+ VDK_ByvalRecord,
+ VDK_ByvalObject, // illegal
+ VDK_ByrefIntrinsic,
+ VDK_ByrefRecord,
+ VDK_ByrefObject,
+ VDK_ByptrIntrinsic, // illegal
+ VDK_ByptrRecord, // illegal
+ VDK_ByptrObject,
+ VDK_DataMemberIntrinsic,
+ VDK_DataMemberRecord,
+ VDK_DataMemberObject,
+ VDK_BaseIntrinsic, // Illegal
+ VDK_BaseRecord, // Illegal
+ VDK_BaseObject
+};
+
+
+// enum DEFNKIND - dk
+// Purpose:
+// Enumerates different kinds of defns.
+// Includes some defns that don't derive
+// from DEFN, like DLLENTRY_DEFN.
+// Specifically excludes MEMBER_DEFN, since
+// it only exists to be included in MBR_VAR_DEFN, etc.
+//
+enum DEFNKIND
+{
+ DK_VarDefn,
+ DK_ParamDefn,
+ DK_MbrVarDefn,
+ DK_FuncDefn,
+ DK_VirtualFuncDefn,
+ DK_DllEntryDefn,
+ DK_RecTypeDefn
+};
+
+typedef USHORT sDEFNKIND;
+
+
+// enum BASICVARKIND - basicvkind
+// Purpose:
+// enumerates different "classes" of basic Variable kinds
+//
+enum BASICVARKIND
+{
+ BVKIND_Intrinsic,
+ BVKIND_Record,
+ BVKIND_Object
+};
+
+
+// enum COMPSTATE
+// enumeration specifying the various possible compilation states
+//
+enum COMPSTATE {
+ CS_UNDECLARED,
+ CS_SEMIDECLARED,
+ CS_DECLARED,
+ CS_REGENERATE,
+ CS_COMPILED,
+ CS_ADDRESSABLE,
+ CS_QUASIDECLARED,
+ CS_QUASIUNDECLARED,
+ CS_RUNNABLE
+};
+
+
+#pragma pack(2) // want all these guys to word-align
+
+// struct VAROFS - vo
+// Purpose:
+// Structure for describing the offset within an instance to
+// a data member, non-virtual base member or virtual function
+// table pointer.
+//
+// *** if you modify this structure, also update the layout string below
+// (see SwapStruct() for more info)
+//
+// CONSIDER: vba2
+// struct VAROFS
+// {
+// LONG oVar;
+// inline VAROFS() { oVar = -1; }
+// };
+//
+// // layout string for TYPE_DATA byte swapping
+// #define VAROFS_LAYOUT "l"
+
+
+// struct VMETHOFS - vmo
+// Purpose:
+// Extends VAROFS to describe the offset w/in the vft indicated
+// by VAROFS::oVar of the slot of a virtual function.
+//
+// *** if you modify this structure, also update the layout string below
+// (see SwapStruct() for more info)
+//
+// CONSIDER: vba2
+// struct VMETHOFS: public VAROFS
+struct VMETHOFS
+{
+ SHORT ovft;
+ inline VMETHOFS() { ovft = -1; }
+};
+
+// layout string for TYPE_DATA byte swapping
+// CONSIDER: vba2
+// #define VMETHOFS_LAYOUT VAROFS_LAYOUT "s"
+#define VMETHOFS_LAYOUT "s"
+
+// struct VBASEPOS - vbp
+// Purpose:
+// Structure for describing the position of a virtual base member.
+// This entails determining (1) where the appropriate vbt is and
+// (2) what the offset with that table is (that offset itself
+// contains the offset from THIS where the virtual base may be
+// found.
+//
+// *** if you modify this structure, also update the layout string below
+// (see SwapStruct() for more info)
+//
+// CONSIDER: vba2
+// struct VBASEPOS
+// {
+// LONG oPvbt;
+// LONG oFixup;
+// SHORT ovbt;
+// inline VBASEPOS() { oPvbt = -1; ovbt = -1; oFixup = -1; }
+// };
+//
+// // layout string for TYPE_DATA byte swapping
+// #define VBASEPOS_LAYOUT "lls"
+
+
+// struct VARPOS - vp
+// Purpose:
+// Combines VBASEPOS and VAROFS to describe the position of
+// a data member, non-virtual base member or Pvft.
+//
+// CONSIDER: vba2
+// struct VARPOS : public VBASEPOS, public VAROFS
+// {
+// // NOTE: no introduced members.
+// };
+
+
+// struct VMETHPOS - vmp
+// Purpose:
+// Combines VMETHOFS and VBASEPOS to describe a
+// virtual method slot. Used to describe overridden methods in
+// base classes to subclassing clients. The VBASEPOS part
+// describes how to access a virtual base member that is or
+// contains the introducing class of the method. The VMETHOFS
+// part completes the description with the accessor to the
+// virtual method slot itself. For instance, the VAROFS part
+// might indicate how to access the pvft in the embedded
+// introducing class given a virtual base member.
+//
+// *** if you modify this structure, also update the layout string below
+// (see SwapStruct() for more info)
+//
+// CONSIDER: vba2
+// struct VMETHPOS : public VMETHOFS, public VBASEPOS
+struct VMETHPOS : public VMETHOFS
+{
+ // NOTE: no introduced members
+};
+
+// layout string for TYPE_DATA byte swapping
+// CONSIDER: vba2
+// #define VMETHPOS_LAYOUT VMETHOFS_LAYOUT VBASEPOS_LAYOUT
+#define VMETHPOS_LAYOUT VMETHOFS_LAYOUT
+
+#pragma pack() // reset to default
+
+// struct VBASECPOS - vbcp
+// Purpose:
+// Structure for "canonically" describing the position of a
+// virtual base member.
+// A "canonic" description is simply encoded as the TYPEID to
+// the TYPEINFO of the virtual base class.
+//
+// CONSIDER: vba2
+// struct VBASECPOS
+// {
+// LPSTR szTypeIdVbase;
+// inline VBASECPOS() { szTypeIdVbase = NULL; }
+// };
+
+
+// struct VARCPOS - vcp
+// Purpose:
+// Combines VBASECPOS and VAROFS to describe the "canonical" position of
+// a data member, non-virtual base member or Pvft.
+// Canonical since it is possibly in terms of the TYPEID to
+// the virtual base "owner" of the table.
+//
+// CONSIDER: vba2
+// struct VARCPOS : public VBASECPOS, public VAROFS
+// {
+// // NOTE: no introduced members.
+// };
+
+
+// struct VMETHCPOS - vmcp
+// Purpose:
+// Combines VMETHOFS and VBASECPOS to describe a "canonic"
+// virtual method slot. Used to describe overridden methods in
+// base classes to subclassing clients. If virtual method is
+// defined by a virtual base then VBASECPOS::szTypeIdVbase
+// attribute is the TYPEID ot the TYPEINFO of that base.
+// Otherwise (i.e. not defined by a virtual base) this is NULL.
+//
+// CONSIDER: vba2
+// struct VMETHCPOS : public VMETHOFS, public VBASECPOS
+// {
+// // NOTE: no introduced members
+// };
+
+// struct VMETHCPOSLIST;
+// typedef VMETHCPOSLIST* LPVMETHCPOSLIST;
+// typedef LPVMETHCPOSLIST* LPLPVMETHCPOSLIST;
+
+// These are stub declarations...
+//
+struct VBTDEFN;
+typedef VBTDEFN* LPVBTDEFN;
+typedef LPVBTDEFN* LPLPVBTDEFN;
+
+struct VBTDEFNLIST;
+typedef VBTDEFNLIST* LPVBTDEFNLIST;
+typedef LPVBTDEFNLIST* LPLPVBTDEFNLIST;
+
+struct VBASEDEFN;
+typedef VBASEDEFN* LPVBASEDEFN;
+typedef LPVBASEDEFN* LPLPVBASEDEFN;
+
+struct VBASEDEFNLIST;
+typedef VBASEDEFNLIST* LPVBASEDEFNLIST;
+typedef LPVBASEDEFNLIST* LPLPVBASEDEFNLIST;
+
+
+#if OE_MACPPC
+/***
+*struct DLLTEMPLATECALLBLOCK
+*Purpose:
+* Structure that holds Mac/PPC Dll Template Calling information.
+* This structure is used by entrymgr.cxx and instmgr.cxx when
+* resolving Dll entry points.
+*
+* [Note: The structure itself resides inside the Declare template and,
+* thus, this MUST match asm description in template.s.]
+*
+***********************************************************************/
+
+struct DLLTEMPLATECALLBLOCK {
+ void * pvTargetAddr; // target address for Dll template
+ void * pv68KAddr; // target 68k address (if applicable)
+ ProcInfoType theProcInfo; // Apple OS ProcInfoType value
+ UniversalProcPtr theProcPtr; // Apple OS Universal Proc Ptr
+ unsigned short usTargetRefnum; // target refnum
+ unsigned short usSavedRefnum; // saved refnum
+};
+#endif // OE_MACPPC
+
+
+#endif // ! CLTYPES_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/clutil.cxx b/private/oleauto/src/typelib/clutil.cxx
new file mode 100644
index 000000000..8561e8d58
--- /dev/null
+++ b/private/oleauto/src/typelib/clutil.cxx
@@ -0,0 +1,3210 @@
+/***
+*clutil.cxx - Class Lib component-wide utility functions.
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Component-wide utility function.
+*
+*Revision History:
+* [00] 20-Jun-91 ilanc: Created
+* [01] 02-Dec-91 ilanc: Added IsSimpleType
+* [02] 12-Dec-91 ilanc: Return uDllOrdinal == ~0 if no dll entry pt
+* in GetDllEntryOfDataInfo.
+* [03] 12-Apr-92 ilanc: Changed Count() signature.
+* [04] 12-May-92 stevenl: Added TDESCKIND_Object to the IsSimpleType fn.
+* [05] 15-Nov-92 RajivK: Added GetTimeStamp()
+* [06] 17-Nov-92 RajivK: Added GetTypelibOfLibId()
+* [07] 25-Dec-92 RajivK: Added GetExecutingProject()
+* [08] 18-Jan-93 w-peterh: use new TYPEDESCKIND values
+* [09] 10-Feb-93 RajivK: Added IsModuleFrameOnStack() && IsBasicFrameOnStack()
+* [10] 12-Feb-93 w-peterh: added itdesc utils,
+* changed IsSimpleType to accept Int/Uint
+* 16-Feb-93 w-jeffc: added HinstOfOLB
+* [11] 23-Feb-93 RajivK: Changed AppDataInit() to use IMalloc Interface
+* [12] 23-Feb-93 RajivK: Added ReleaseStackResources()
+* [13] 02-Mar-93 w-peterh: added VtValidInVariant() and VtValidInVariantArg()
+* added SizeEnumOfSysKind()
+* [14] 24-Mar-93 dougf: Added TDESCKIND_LPSTR to the IsSimpleType fn.
+* [15] 04-Apr-93 RajivK: Support for Typelib on MAC
+* [16] 30-Apr-93 w-jeffc: made DEFN data members private
+* [17] 22-May-93 w-barryb: Rename OB to VBA
+* [18] 20-Jul-93 Suresh: Undid the '-' to '\' hack we had for pre 4.2 ole
+* [19] 30-Jul-93 JeffRob: Use PEXFRAME and PEXFRAME_NULL (OOB bug #756)
+* [20] 22-Sep-93 RajivK: Support for accent and case insensitive comparision/Tables.
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "typelib.hxx"
+#include "silver.hxx"
+
+#include "xstring.h"
+#include <time.h>
+#include <ctype.h> // for isspace() et al.
+#include "cltypes.hxx"
+#include "clutil.hxx"
+#include "stdlib.h"
+#include "tdata.hxx" // for TYPE_DATA
+#include "exbind.hxx" // for EXBIND
+#include "tls.h"
+#include "stream.hxx"
+#include "gdtinfo.hxx"
+#include "impmgr.hxx"
+#include "bstr.h"
+
+#include "oletmgr.hxx"
+
+#if OE_WIN32
+#include "oautil.h"
+#endif // OE_WIN32
+
+#pragma hdrstop(RTPCHNAME)
+
+#if OE_WIN32
+STDAPI CoSetState(IUnknown FAR* punk); // from OLE32.DLL
+STDAPI_(void) ReleaseBstrCache(APP_DATA *); // from BSTR.CPP
+#endif //OE_WIN32
+
+#if OE_MAC
+#include <ctype.h>
+#include "macos\resource.h"
+#include "macos\files.h"
+#include "macos\errors.h"
+#include "macos\folders.h"
+#include "macos\textutil.h"
+#include "macos\osutils.h"
+#include "sysutils.h"
+#endif
+
+#if OE_WIN16
+#include "dos.h"
+#endif // OE_WIN16
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+static char szOleClutilCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleClutilCxx
+#else
+static char szClutilCxx[] = __FILE__;
+#define SZ_FILE_NAME szClutilCxx
+#endif
+#endif //ID_DEBUG
+
+#if OE_MAC
+#define g_rgbExcepTblNew Og_rgbExcepTblNew
+#define g_rgbPartialBaseTblMEngIreland Og_rgbPartialBaseTblMEngIreland
+#define g_rgbPartialBaseTblMNorwegian Og_rgbPartialBaseTblMNorwegian
+#define g_rgbPartialBaseTblMGreek Og_rgbPartialBaseTblMGreek
+#define g_rgbPartialBaseTblWEngIreland Og_rgbPartialBaseTblWEngIreland
+#define g_rgbPartialBaseTblWNorwegian Og_rgbPartialBaseTblWNorwegian
+#define g_rgbPartialBaseTblWTurkish Og_rgbPartialBaseTblWTurkish
+#define g_rgbPartialBaseTblWIceland Og_rgbPartialBaseTblWIceland
+#define g_rgbPartialBaseTblWGreek Og_rgbPartialBaseTblWGreek
+#endif // OE_MAC
+
+
+
+
+#if OE_MAC
+OLECHAR FAR* szPlatSubkey1 = "mac";
+#elif OE_WIN16
+OLECHAR FAR* szPlatSubkey1 = "win16";
+OLECHAR FAR* szPlatSubkey2 = "win32";
+#elif OE_WIN32
+OLECHAR FAR* szPlatSubkey1 = L"win32";
+OLECHAR FAR* szPlatSubkey2 = L"win16";
+#else
+#error "unexpected OE"
+#endif // OE_WIN32
+
+#if OE_MAC
+
+EBERR GetPathFromFSSpec(const FSSpec *pfsspec, char *pchPathname, UINT cbPathname)
+{
+ long parID;
+ char * pchPathnameLim = pchPathname+cbPathname;
+ XCHAR rgchFileString[_MAX_PATH+1];
+ CInfoPBRec dirParmblk;
+ ParamBlockRec volParmblk;
+
+ // determine name from FSSpec volume reference number
+
+ volParmblk.volumeParam.ioNamePtr = (unsigned char *)pchPathname;
+ volParmblk.volumeParam.ioVRefNum = pfsspec->vRefNum;
+ volParmblk.volumeParam.ioVolIndex = 0;
+
+ if (PBGetVInfoSync(&volParmblk) != noErr)
+ return TIPERR_PathNotFound;
+
+ // convert PSTR volume name to C string, add a null
+ // and point to it
+
+ p2cstr((unsigned char *)pchPathname);
+ pchPathname += strlen(pchPathname);
+ DebAssert(pchPathname < pchPathnameLim, "rtGetPathFromFSSpec");
+ *pchPathname = '\0';
+
+ // start with parent ID of resulting file
+
+ parID = pfsspec->parID;
+
+ // while directory is not root of volume, process it
+
+ if (parID != fsRtParID) {
+ while (parID != fsRtDirID) {
+
+ // determine name from FSSpec parent directory index
+
+ dirParmblk.hFileInfo.ioNamePtr = (unsigned char *)&rgchFileString;
+ dirParmblk.hFileInfo.ioVRefNum = pfsspec->vRefNum;
+ dirParmblk.hFileInfo.ioDirID = parID;
+ dirParmblk.hFileInfo.ioFDirIndex = -1;
+
+ if (PBGetCatInfoSync(&dirParmblk) != noErr)
+ return TIPERR_PathNotFound;
+
+ // convert PSTR directory name to C string,
+ // and insert it preceded by a colon into result
+
+ if (pchPathname+(unsigned char)rgchFileString[0]+1 >= pchPathnameLim)
+ return TIPERR_PathNotFound;
+
+ p2cstr((unsigned char *)rgchFileString);
+ memmove(pchPathname + strlen(rgchFileString) + 1, pchPathname,
+ strlen(pchPathname) + 1);
+ *pchPathname = ':';
+ strncpy(pchPathname + 1, rgchFileString, strlen(rgchFileString));
+
+ // get parent directory next level up
+
+ parID = dirParmblk.hFileInfo.ioFlParID;
+ }
+
+ // copy the FSSpec filename to the path with
+ // its terminating null
+
+ if (pchPathname + pfsspec->name[0] + 1 >= pchPathnameLim)
+ return TIPERR_PathNotFound;
+
+ p2cstr((unsigned char *)pfsspec->name);
+ pchPathname += strlen(pchPathname);
+ *pchPathname++ = ':';
+ strcpy(pchPathname, (char *)&(pfsspec->name));
+ }
+
+
+ // restore *pfsspec.
+ c2pstr((char *)pfsspec->name);
+
+ return TIPERR_None;
+}
+
+#pragma code_seg(CS_INIT)
+EBERR GetFSSpecOfAliasPath(char *pchPathname, FSSpec *pfsspec,
+ BOOL *pbAliasSeen, char **ppchEnd,
+ BOOL fResolveFile)
+{
+ TIPERROR eberr = TIPERR_None;
+ OSErr err = noErr;
+ Boolean bIsFolder;
+ Boolean bWasAlias;
+ Boolean bAliasSeen = FALSE;
+
+ char chFileString[_MAX_PATH+1];
+
+ char * pchStart;
+ char * pchEnd;
+ char * pchTemp = chFileString;
+
+ // get the substring of the device
+
+ pchStart = pchPathname;
+ pchEnd = xstrchr(pchStart, ':');
+
+ //UNDONE MAC: need to resolve aliases to volumes here
+
+ // if no folder, then return immediately
+
+ if (!pchEnd || *(pchEnd + 1) == '\0')
+ return TIPERR_None;
+
+ // copy device to temp string
+
+ strncpy(pchTemp, pchStart, pchEnd - pchStart);
+ pchTemp += pchEnd - pchStart;
+
+ // get substring of the first folder
+
+ pchStart = pchEnd;
+ pchEnd = xstrchr(pchStart + 1, ':');
+ if (!pchEnd)
+ pchEnd = xstrchr(pchStart + 1, '\0');
+ strncpy(pchTemp, pchStart, pchEnd - pchStart);
+ pchTemp += pchEnd - pchStart;
+
+ // terminate the device and first folder substring
+
+ *pchTemp = '\0';
+
+ // convert "device:folder1" to a PSTR for FSSpec processing
+
+ c2pstr(chFileString);
+
+ // from full pathname in pchPathname make a file specification
+
+ err = FSMakeFSSpec(0, 0, (unsigned char *)chFileString, pfsspec);
+
+ // resolve any alias chains from "device:folder1"
+
+ if (err == noErr && MacEnvHasAliasMgr()) {
+
+ err = ResolveAliasFile(pfsspec, TRUE, &bIsFolder, &bWasAlias);
+ bAliasSeen |= bWasAlias;
+ }
+
+ // update *pfsspec with the next folder string if it exists
+
+ while (err == noErr && *pchEnd == ':' && *(pchEnd + 1) != '\0') {
+
+ // move :<pfsspec->name>:<next folder> string to array
+
+ pchTemp = chFileString;
+ *pchTemp++ = ':';
+ p2cstr(pfsspec->name);
+ strcpy(pchTemp, (char *)&(pfsspec->name));
+ pchTemp += strlen(pchTemp);
+
+ // get the next folder string and copy it to the array
+
+ pchStart = pchEnd;
+
+ pchEnd = xstrchr(pchStart + 1, ':');
+ if (!pchEnd)
+ pchEnd = xstrchr(pchStart + 1, '\0');
+
+ strncpy(pchTemp, pchStart, pchEnd - pchStart);
+ pchTemp += pchEnd - pchStart;
+ *pchTemp = '\0';
+
+ // convert "device:folder1" to a PSTR for FSSpec processing
+
+ c2pstr(chFileString);
+
+ err = FSMakeFSSpec(pfsspec->vRefNum, pfsspec->parID,
+ (unsigned char *)chFileString, pfsspec);
+
+ if (*pchEnd == 0 && !fResolveFile)
+ // Only file part is left, don't resolve the alias.
+ break;
+
+ if (err == noErr && MacEnvHasAliasMgr()) {
+
+ err = ResolveAliasFile(pfsspec, TRUE, &bIsFolder, &bWasAlias);
+ bAliasSeen |= bWasAlias;
+ }
+ }
+
+ // finished scan or error was found, if error was fnfErr and scan
+ // was finished, treat as no error and FSSpec is valid
+
+ if (err == fnfErr && (*pchEnd == '\0' ||
+ (*pchEnd == ':' && *(pchEnd + 1) == '\0')))
+ err = noErr;
+
+ *pbAliasSeen = bAliasSeen;
+ *ppchEnd = pchEnd;
+
+ if (err != noErr) {
+ eberr = TIPERR_PathNotFound;
+ }
+
+ return eberr;
+}
+#pragma code_seg()
+
+/***
+*EBERR GetPathFromAlias - Converts alias record to a fullpath.
+*Inputs:
+* halias - The alias record's handle.
+*
+*Outputs:
+* If the file represented by the alias is found, its fullpath
+* is copied into the output buffer pchPathname. If the resolution
+* of halias involved modifying the alias record, *pwasChanged is
+* set to a non-zero value. Otherwise, it is set to 0.
+*
+* If unsuccessful, the appropriate error code is returned.
+***************************************************************/
+EBERR GetPathFromAlias(AliasHandle halias, char *pchPathname, UINT cbPathname, BOOL *pwasChanged)
+{
+ FSSpec fsspec;
+
+ DebAssert(MacEnvHasAliasMgr(), "GetPathFromAlias");
+
+ // Resolve the alias.
+ if (ResolveAlias(NULL, halias, &fsspec, (unsigned char *)pwasChanged))
+ return TIPERR_PathNotFound;
+
+ // Convert the returned fsspec into a fullpath.
+ if (GetPathFromFSSpec(&fsspec, pchPathname, cbPathname))
+ return TIPERR_PathNotFound;
+
+ return TIPERR_None;
+}
+
+/***
+*EBERR GetAliasFromPath - Converts fullpath to an alias record.
+*Inputs:
+* szPathname - The fullpath.
+*
+*Outputs:
+* If successful, a new alias record is created that can be used
+* (by GetPathFromAlias) to robustly find the specified file later.
+* *phalias is set to point at this new alias record.
+*
+* If unsuccessful, the appropriate error code is returned (most
+* likely out of memory).
+*********************************************************************/
+#pragma code_seg(CS_INIT)
+EBERR GetAliasFromPath(LPSTR szPathname, AliasHandle *phalias)
+{
+ FSSpec fsspec;
+ char *pchEnd;
+ BOOL wasAliased;
+ TIPERROR err;
+ OSErr oserr;
+
+ DebAssert(MacEnvHasAliasMgr(), "GetPathFromAlias");
+
+ // Convert the path to an fsspec, accounting for alias files.
+ IfErrRet(GetFSSpecOfAliasPath(szPathname, &fsspec, &wasAliased, &pchEnd, TRUE));
+
+ // Create an alias record from the fsspec.
+ oserr = NewAlias(NULL, &fsspec, phalias);
+ if (oserr != noErr){
+ // This is not very good. For example, NewAlias will return
+ // (-120) dirNFErr - directory not found, if the given path only
+ // contains the volume name.
+ //
+ // The caller of this routine needs to be careful not to take
+ // the errors it gets back from the routine too seriously.
+ //
+ return TIPERR_OutOfMemory;
+ }
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+/***
+*TIPERROR MacFileSearch - Searches for a filename on the mac.
+*
+*Inputs:
+* szFile - The name (no path portion) of the file to find.
+*
+*Outputs:
+* If the file is found, the full path is returned in *pbstr.
+* Otherwise, TIPERR_FileNotFound is returned.
+*
+*Implementation:
+* The TypelibFolder key in the registry entry is used to obtain the
+* "standard" typelib location, both as a path and as an alias (system7).
+* If the file is not in the standard typelib folder (or if one isn't
+* registered), try the mac's <0,0,name> search (current folder, then
+* system folder).
+**************************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR MacFileSearch(LPSTR szFile, BSTRA *pbstr)
+{
+ BSTRA bstrFolder, bstr;
+ struct _stat statBuf;
+ TIPERROR err;
+ FSSpec fsspec;
+ XCHAR rgchPathName[256];
+ OSErr oserr;
+
+ // Get the registered typelib folder's path.
+ if ((err = TiperrOfHresult(QueryTypeLibFolder(&bstrFolder))) == TIPERR_None) {
+
+ // Combine the filename with that folder's path.
+ err = MakeAbsolutePath(bstrFolder, szFile, &bstr);
+ FreeBstr(bstrFolder);
+ if (err)
+ return err;
+
+ // If the resulting file exists, return success.
+ if (_stat(bstr, &statBuf) != -1) {
+ *pbstr = bstr;
+ return TIPERR_None;
+ }
+
+ // Otherwise, free the guess and try the <0,0,name>.
+ FreeBstr(bstr);
+ }
+
+ // Mac "Poor Man's Search Path"
+ // 1. Look in Current Drive, Current Directory.
+ // 2. Look in System Folder of Boot Drive.
+ //
+ c2pstr(szFile);
+ oserr = FSMakeFSSpec(0, 0, (unsigned char*)szFile, &fsspec);
+ if (oserr) {
+ // Locate the System Folder.
+ oserr = FindFolder( ((short)kOnSystemDisk),
+ kSystemFolderType,
+ kDontCreateFolder,
+ &fsspec.vRefNum,
+ &fsspec.parID );
+ if (oserr) {
+ err = TIPERR_FileNotFound;
+ goto Error;
+ }
+
+ oserr = FSMakeFSSpec(fsspec.vRefNum, fsspec.parID,
+ (unsigned char *)szFile, &fsspec);
+ if (oserr) {
+ err = TIPERR_FileNotFound;
+ goto Error;
+ }
+ }
+
+ // At this point, we should have a valid FSSpec to a file or have exited.
+ IfErrRet(GetPathFromFSSpec(&fsspec, rgchPathName, sizeof(rgchPathName)));
+ if ((bstr = AllocBstr(rgchPathName)) == NULL) {
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+
+ *pbstr = bstr;
+ err = TIPERR_None;
+
+Error:
+ p2cstr((unsigned char*)szFile);
+ return err;
+}
+#pragma code_seg()
+#endif // OE_MAC
+
+
+/***
+*TIPERROR IsUnqualifiable - Can this modules be bound to?
+*
+*Purpose:
+* To determine whether a given ITypeInfo can be bound to
+* in an unqualified way.
+*
+*Inputs:
+* ptinfo - The ITypeInfo to look for
+*
+*Outputs:
+* returns TRUE if bindable
+*
+* NOTE: This can fail, and if so, the results are FALSE
+*
+******************************************************************************/
+#pragma code_seg( CS_CORE2 )
+BOOL IsUnqualifiable(GEN_DTINFO *pgdtinfo)
+{
+ BOOL fUnqual = FALSE;
+ TIPERROR err = TIPERR_None;
+
+ DebAssert(pgdtinfo, "Bad typeinfo");
+
+ // Check the typekind
+ switch (pgdtinfo->GetTypeKind()) {
+ case TKIND_ENUM:
+ case TKIND_MODULE:
+ fUnqual = TRUE;
+ break;
+
+ case TKIND_COCLASS:
+ // In the COCLASS case, we must check to see
+ // if this is an appobj.
+ //
+ if (pgdtinfo->Pdtroot()->GetTypeFlags() & TYPEFLAG_FAPPOBJECT) {
+ fUnqual = TRUE;
+ break;
+ }
+ }
+
+ return fUnqual;
+}
+#pragma code_seg()
+
+
+
+
+
+
+
+#if ID_TEST
+/***
+*PUBLIC DebGetNameCacheStats
+*Purpose:
+* Gets the name cache stats for a non-OB type library. Used
+* in tclcmds.
+*
+*Entry:
+* pgtlibole - the typelib to get the stats from
+*
+*Exit:
+* cProjTrys, cProjHits, cModTrys, cModHits, cGlobHits - the stats
+*
+***********************************************************************/
+STDAPI DebGetNameCacheStats(ITypeLibA FAR* ptlib, UINT FAR* cProjTrys,
+ UINT FAR* cProjHits, UINT FAR* cModTrys,
+ UINT FAR* cModHits, UINT FAR* cGlobHits)
+{
+ GenericTypeLibOLE *pgtlibole = (GenericTypeLibOLE *)ptlib;
+
+ *cModTrys = pgtlibole->DebGetNameCacheModTrys();
+ *cModHits = pgtlibole->DebGetNameCacheModHits();
+ *cGlobHits = pgtlibole->DebGetNameCacheGlobHits();
+
+ return NOERROR;
+}
+#endif //ID_TEST
+
+// Static data members needed for fast comparision of strings.
+//
+static LCID Rby_lcidCur;
+static BOOL Rby_fEuroLcid;
+
+#define UNKNOWN -1
+// Define static array of intrinsic type sizes
+//
+// NOTE: there are three different tables - one each for SYS_WIN32,
+// SYS_MAC and SYS_WIN16. It is assumed that the sizes of things
+// in the table (ie DATE) will NOT CHANGE BETWEEN PLATFORMS RUNNING
+// THE SAME OS. (ie an int on win32 intel is the same size as
+// an int on win32 alpha) If this is not the case, these table
+// must be extended.
+//
+char NEARDATA g_rgrgcbSizeType[SYS_MAX][TDESCKIND_MAX] = {
+
+// SYS_WIN16 sizes
+{
+/* 0 */ UNKNOWN, // "Empty"
+/* 1 */ UNKNOWN, // "Null"
+/* 2 */ 2, // "I2"
+/* 3 */ 4, // "I4"
+/* 4 */ 4, // "R4"
+/* 5 */ 8, // "R8"
+/* 6 */ 8, // "Currency"
+/* 7 */ sizeof(DATE), // "Date"
+/* 8 */ 4, // "String"
+/* 9 */ 4, // "Object"
+/* 10 */ sizeof(SCODE), // "Error"
+/* 11 */ 2, // "Bool"
+/* 12 */ sizeof(VARIANT), // "Value"
+/* 13 */ 4, // "IUnknown"
+/* 14 */ 4, // "WideString"
+/* 15 */ UNKNOWN, // no vartype
+/* 16 */ 1, // "I1"
+/* 17 */ 1, // "UI1"
+/* 18 */ 2, // "UI2"
+/* 19 */ 4, // "UI4"
+/* 20 */ 8, // "I8"
+/* 21 */ 8, // "UI8"
+/* 22 */ 2, // *** "Int"
+/* 23 */ 2, // *** "Uint"
+/* 24 */ 0, // "Void" (note: only one that's 0)
+/* 25 */ sizeof(HRESULT), // "Hresult"
+/* 26 */ 4, // "Ptr"
+/* 27 */ sizeof(ARRAYDESC FAR *), // "BasicArray" -- resizeable is default
+/* 28 */ UNKNOWN, // "Carray"
+/* 29 */ UNKNOWN, // "UserDefined"
+/* 30 */ 4, // "LPSTR"
+/* 31 */ 4, // "LPWSTR"
+}
+,
+
+// SYS_WIN32 sizes
+{
+/* 0 */ UNKNOWN, // "Empty"
+/* 1 */ UNKNOWN, // "Null"
+/* 2 */ 2, // "I2"
+/* 3 */ 4, // "I4"
+/* 4 */ 4, // "R4"
+/* 5 */ 8, // "R8"
+/* 6 */ 8, // "Currency"
+/* 7 */ sizeof(DATE), // "Date"
+/* 8 */ 4, // "String"
+/* 9 */ 4, // "Object"
+/* 10 */ sizeof(SCODE), // "Error"
+/* 11 */ 2, // "Bool"
+/* 12 */ sizeof(VARIANT), // "Value"
+/* 13 */ 4, // "IUnknown"
+/* 14 */ 4, // "WideString"
+/* 15 */ UNKNOWN, // no vartype
+/* 16 */ 1, // "I1"
+/* 17 */ 1, // "UI1"
+/* 18 */ 2, // "UI2"
+/* 19 */ 4, // "UI4"
+/* 20 */ 8, // "I8"
+/* 21 */ 8, // "UI8"
+/* 22 */ 4, // *** "Int"
+/* 23 */ 4, // *** "Uint"
+/* 24 */ 0, // "Void" (note: only one that's 0)
+/* 25 */ sizeof(HRESULT), // "Hresult"
+/* 26 */ 4, // "Ptr"
+/* 27 */ sizeof(ARRAYDESC FAR *), // "BasicArray" -- resizeable is default
+/* 28 */ UNKNOWN, // "Carray"
+/* 29 */ UNKNOWN, // "UserDefined"
+/* 30 */ 4, // "LPSTR"
+/* 31 */ 4, // "LPWSTR"
+}
+,
+
+// SYS_MAC sizes
+{
+/* 0 */ UNKNOWN, // "Empty"
+/* 1 */ UNKNOWN, // "Null"
+/* 2 */ 2, // "I2"
+/* 3 */ 4, // "I4"
+/* 4 */ 4, // "R4"
+/* 5 */ 8, // "R8"
+/* 6 */ 8, // "Currency"
+/* 7 */ sizeof(DATE), // "Date"
+/* 8 */ 4, // "String"
+/* 9 */ 4, // "Object"
+/* 10 */ sizeof(SCODE), // "Error"
+/* 11 */ 2, // "Bool"
+/* 12 */ sizeof(VARIANT), // "Value"
+/* 13 */ 4, // "IUnknown"
+/* 14 */ 4, // "WideString"
+/* 15 */ UNKNOWN, // no vartype
+/* 16 */ 1, // "I1"
+/* 17 */ 1, // "UI1"
+/* 18 */ 2, // "UI2"
+/* 19 */ 4, // "UI4"
+/* 20 */ 8, // "I8"
+/* 21 */ 8, // "UI8"
+/* 22 */ 4, // *** "Int"
+/* 23 */ 4, // *** "Uint"
+/* 24 */ 0, // "Void" (note: only one that's 0)
+/* 25 */ sizeof(HRESULT), // "Hresult"
+/* 26 */ 4, // "Ptr"
+/* 27 */ sizeof(ARRAYDESC FAR *), // "BasicArray" -- resizeable is default
+/* 28 */ UNKNOWN, // "Carray"
+/* 29 */ UNKNOWN, // "UserDefined"
+/* 30 */ 4, // "LPSTR"
+/* 31 */ 4, // "LPWSTR"
+}
+
+}; // end of g_rgrgcbSizeType
+
+
+// Define static array of intrinsic type alignments
+// UNKNOWN indicates unknown -- needs to be computed on the fly.
+//
+// These alignment values are the largest necessary - they are scaled down
+// using the ICreateTypeInfo::SetAlignment function.
+//
+char NEARDATA g_rgcbAlignment[TDESCKIND_MAX] =
+{
+/* 0 */ UNKNOWN, // "Empty",
+/* 1 */ UNKNOWN, // "Null",
+/* 2 */ 2, // "I2",
+/* 3 */ 4, // "I4",
+/* 4 */ 4, // "R4",
+/* 5 */ 8, // "R8",
+/* 6 */ 8, // "Currency",
+/* 7 */ 8, // "Date",
+/* 8 */ 4, // "String",
+/* 9 */ 4, // "Object",
+/* 10 */ 4, // "Error",
+/* 11 */ 2, // "Bool",
+/* 12 */ 8, // "Value",
+/* 13 */ 4, // "IUnknown",
+/* 14 */ 4, // "WideString",
+/* 15 */ UNKNOWN, // no vartype
+/* 16 */ 1, // "I1",
+/* 17 */ 1, // "UI1",
+/* 18 */ 2, // "UI2",
+/* 19 */ 4, // "UI4",
+/* 20 */ 8, // "I8",
+/* 21 */ 8, // "UI8",
+/* 22 */ 4, // "Int",
+/* 23 */ 4, // "Uint",
+/* 24 */ 0, // "Void", (NOTE: only one that's 0)
+/* 25 */ 4, // "Hresult",
+/* 26 */ 4, // "Ptr",
+/* 27 */ 4, // "BasicArray", -- resizeable is default.
+/* 28 */ UNKNOWN, // "Carray"
+/* 29 */ UNKNOWN, // "UserDefined",
+/* 30 */ 4, // "LPSTR",
+/* 31 */ 4, // "LPWSTR",
+};
+
+
+
+
+// ************************************
+// mapping and sizeof VARTYPE functions
+// ************************************
+
+
+#if ID_DEBUG
+// These datamembers are defined here to ensure that all the objects
+// required for typelib.dll are linked into mebapp.exe
+#if OE_MAC
+
+// WARNING : WARNING : WARNING : WARNING : WARNING : WARNING :
+// Do not remove any symbol from this list. Other wise on MAC the linker
+// will screw up and link to the wrong definition and cause more GRIEF then
+// you can imagine.
+
+extern char szOleBlkmgrCxx[];
+extern char szOleDfntbindCxx [];
+extern char szOleDfntcompCxx[];
+extern char szOleDfstreamCxx[];
+extern char szOleDtbindCxx[];
+extern char szOleDtmbrs[];
+extern char szOleGDTInfoCxx[];
+extern char szOleEntryMgrCxx[];
+extern char szOleGptbindCxx[];
+extern char szOleImpmgrCxx[];
+extern char szOleMemCxx[];
+extern char szOleSheapmgrCxx[];
+extern char szOleNammgrCxx[];
+extern char szOleTdataCxx[];
+extern char szOleTdata2Cxx[];
+extern char szOleDebugCxx[];
+extern char szOleRtsheapCxx[];
+extern char szOleFstreamCxx[];
+
+
+
+XCHAR *g_rgMapFileNameType[] = {
+ szOleBlkmgrCxx, szOleClutilCxx, szOleDfntbindCxx ,
+ szOleDfntcompCxx, szOleDfstreamCxx , szOleDtbindCxx,
+ szOleDtmbrs, szOleGDTInfoCxx, szOleEntryMgrCxx, szOleGptbindCxx,
+ szOleImpmgrCxx, szOleMemCxx, szOleDebugCxx, szOleSheapmgrCxx,
+ szOleNammgrCxx, szOleTdataCxx, szOleTdata2Cxx,
+ szOleFstreamCxx, szOleRtsheapCxx
+};
+
+#endif // OE_MAC
+
+#endif // ID_DEBUG
+
+/***
+*void GetTimeStamp() - Returns an ascii time stamp to the specified buffer.
+*
+*Purpose:
+* Constructs an ascii timestamp and puts it into the specified buffer.
+*
+*Inputs:
+* None
+*
+*Outputs:
+* pchTimeStamp - The buffer in which the timestamp is placed. The
+* length of the string placed in the buffer will always
+* be CCH_TIMESTAMP_LENGTH. The string is terminated with
+* '\0', so pbTimeStamp must point to at least
+* CCH_TIMESTAMP_LENGTH+1 characters.
+******************************************************************************/
+#if OE_WIN16
+// Windows call to execute Int 21 - not defined in WINDOWS.H
+extern "C" {void PASCAL DOS3CALL(void);}
+#endif
+
+#pragma code_seg(CS_CORE)
+void GetTimeStamp(OLECHAR *pchTimeStamp)
+{
+ static BYTE bUnique;
+#if OE_WIN32
+ SYSTEMTIME st;
+ ULONG ul;
+
+ GetLocalTime(&st);
+ pchTimeStamp[0] = '0' + (bUnique>>4);
+ pchTimeStamp[1] = '0' + (bUnique&0x0f);
+ bUnique++;
+ ul = st.wSecond+st.wMinute*60+st.wHour*3600+st.wDay*86400+st.wMonth*2678400+(st.wYear-1970)*32140800;
+ oultoa(ul, pchTimeStamp+2, 16);
+#elif OE_WIN16
+ ULONG ul;
+ int iYear;
+ char chMonth, chDay, chHour, chMinute, chSecond;
+
+ __asm {
+ mov ah, 0x2a ; GetDate
+ call DOS3CALL
+ mov iYear, cx
+ mov chMonth, dh
+ mov chDay, dl
+
+ mov ah, 0x2c ; GetTime
+ call DOS3CALL
+ mov chHour, ch
+ mov chMinute, cl
+ mov chSecond, dh
+ }
+ pchTimeStamp[0] = '0' + (bUnique>>4);
+ pchTimeStamp[1] = '0' + (bUnique&0x0f);
+ bUnique++;
+ ul = chSecond+chMinute*60+chHour*3600+chDay*86400+chMonth*2678400+(iYear-1970)*32140800;
+ oultoa(ul, pchTimeStamp+2, 16);
+#else
+ time_t timestamp;
+
+ time(&timestamp);
+ oultoa((ULONG)bUnique++, pchTimeStamp, 16);
+ oultoa((ULONG)timestamp, pchTimeStamp+ostrblen(pchTimeStamp), 16);
+#endif //OE_WIN32
+}
+#pragma code_seg()
+
+
+
+/***
+*TIPERROR SzLibIdLocalTypeIdOfTypeId() - Parses TypeId.
+*
+* Purpose:
+* Parses a TypeId into constituent LibId and Local TypeId.
+*
+* Inputs:
+* szTypeId - The TypeId to dismember (IN).
+*
+* Outputs:
+* If successful:
+* *pbstrLibId is set to a BSTR copy of the LibId (OUT).
+* *pszLocalTypeId is set to point at the Local TypeId (points into
+* szTypeId).
+* Return TIPERR_None.
+*
+* If invalid TypeId, returns TIPERR_BadTypeId.
+* If fails for some other reason (e.g. OutOfMemory), return appropriate
+* TIPERROR value. If fails, *pbstrLibId and *pszLocalTypeId remain
+* unchanged.
+******************************************************************************/
+
+TIPERROR SzLibIdLocalTypeIdOfTypeId(LPOLESTR szTypeId, BSTR *pbstrLibId, LPOLESTR *pszLocalTypeId)
+{
+ LPOLESTR pch;
+ BSTR bstr;
+
+ // If the first character of the TypeId is not an asterisk, then it
+ // refers to a registered TypeId and contains no LibId component.
+ if (szTypeId[0] != WIDE('*')) {
+ *pszLocalTypeId = szTypeId;
+ if (pbstrLibId != NULL)
+ *pbstrLibId = NULL;
+ return TIPERR_None;
+ }
+
+ // Otherwise, locate the last asterisk in the string.
+ pch = ostrrchr(szTypeId, WIDE('*'));
+
+ // It had better not be the initial asterisk.
+ if (pch == szTypeId)
+ return TIPERR_BadTypeId;
+
+ // It is the delimiter between the libid and the local typeid,
+ // so make a copy of the libid and point at the local typeid.
+ // Only copy the libId if the caller requested the libId portion.
+
+ if (pbstrLibId != NULL) {
+ if ((bstr = AllocBstrLen(szTypeId, pch-szTypeId)) == NULL)
+ return TIPERR_OutOfMemory;
+
+ *pbstrLibId = bstr;
+ }
+
+ *pszLocalTypeId = pch+1;
+ return TIPERR_None;
+}
+
+
+
+
+BOOL IsSimpleType(TYPEDESCKIND tdesckind)
+{
+ switch (tdesckind) {
+ case TDESCKIND_Ptr:
+ case TDESCKIND_UserDefined:
+ case TDESCKIND_BasicArray:
+ case TDESCKIND_Carray:
+ return FALSE;
+ case TDESCKIND_UI1:
+ case TDESCKIND_I1:
+ case TDESCKIND_UI2:
+ case TDESCKIND_I2:
+ case TDESCKIND_UI4:
+ case TDESCKIND_I4:
+ case TDESCKIND_UI8:
+ case TDESCKIND_I8:
+ case TDESCKIND_R4:
+ case TDESCKIND_R8:
+ case TDESCKIND_Void:
+ // Beyond this point, not necessarily supported by all impls.
+ case TDESCKIND_String:
+ case TDESCKIND_Currency:
+ case TDESCKIND_Date:
+ case TDESCKIND_Value:
+ case TDESCKIND_Object:
+ case TDESCKIND_IUnknown:
+ case TDESCKIND_Int:
+ case TDESCKIND_Uint:
+ case TDESCKIND_HResult:
+ case TDESCKIND_Bool:
+ case TDESCKIND_Error:
+ case TDESCKIND_LPSTR:
+ case TDESCKIND_LPWSTR:
+ return TRUE;
+ case TDESCKIND_Empty:
+ case TDESCKIND_Null:
+ default:
+ DebHalt("bad tdesckind.");
+ return FALSE;
+ }
+}
+
+
+
+
+/***
+*HashSz
+*Purpose:
+* Compute random value based on sz
+* ANY MODIFICATIONS TO THIS FUNCTION SHOULD ALSO BE DONE FOR HashSzTerm
+*
+*Entry:
+* sz
+*
+*Exit:
+* UINT containing hash value
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+UINT HashSz(LPOLESTR szW)
+
+//UNDONE OA95: use _rotr to compute hash once it can be inlined
+// Pragma below causes following error from compiler:
+// error C2164: '_rotr' : intrinsic function not declared
+//
+// #pragma intrinsic(_rotr) //ensure _rotr is inlined
+//
+{
+#if FV_UNICODE
+#if HP_16BIT
+#error UINT not big enough to hold two characters
+#endif
+#endif
+ UINT Sum = 0;
+ XCHAR *pch;
+
+ DebAssert(szW != 0, "HashSz zero length sz");
+
+#if OE_WIN32
+ LPSTR sz;
+
+ if (ConvertStringToA(szW, &sz))
+ return 0; // UNDONE OA95: out of memory
+#else
+ #define sz szW
+#endif
+
+ pch = sz;
+
+// Process the string two characters at a time
+// If FV_UNICODE this means two words at a time otherwise one word at a time
+
+ for (;;) {
+
+#if FV_UNICODE
+ Sum += *(DWORD *)pch;
+// Sum = _rotr(Sum,3) ^ *(DWORD *)pch;
+#else
+ Sum += *(WORD *)pch;
+// Sum = _rotr(Sum,3) ^ *(WORD *)pch;
+#endif
+
+ // Exit if second char of two chars just used was zero
+ // Note that we don't care about DBCS character boundaries,
+ // so ++ is ok.
+ pch++;
+ if (*pch == 0)
+ break;
+
+ // Exit if first char of next two chars is zero
+ pch++;
+ if (*pch == 0)
+ break;
+ }
+
+#if OE_WIN32
+ ConvertStringFree(sz);
+#else
+ #undef sz
+#endif
+
+ Sum ^= Sum >> 8;
+ return Sum;
+}
+#pragma code_seg()
+
+/***
+*HashSzTerm
+*Purpose:
+* Exactly the same as HashSz above except checks for a specific
+* terminating character in addition to the null character
+* ANY MODIFICATIONS TO THIS FUNCTION SHOULD ALSO BE DONE FOR HashSz
+*
+*Entry:
+* sz
+*
+*Exit:
+* UINT containing hash value
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CORE2)
+UINT HashSzTerm(LPOLESTR szW, XCHAR xchTerm)
+
+//UNDONE OA95: use _rotr to compute hash once it can be inlined
+// Pragma below causes following error from compiler:
+// error C2164: '_rotr' : intrinsic function not declared
+//
+// #pragma intrinsic(_rotr) //ensure _rotr is inlined
+//
+{
+#if FV_UNICODE
+#if HP_16BIT
+#error UINT not big enough to hold two characters
+#endif
+#endif
+ UINT Sum = 0;
+ XCHAR *pch;
+
+ DebAssert(szW != 0, "HashSz zero length sz");
+
+#if OE_WIN32
+ LPSTR sz;
+
+ if (ConvertStringToA(szW, &sz))
+ return 0; // UNDONE OA95: out of memory
+#else
+ #define sz szW
+#endif
+
+ pch = sz;
+
+// Process the string two characters at a time
+// If FV_UNICODE this means two words at a time otherwise one word at a time
+
+ for (;;) {
+
+#if FV_UNICODE
+ // UNONDE : this needs to be fixed to work across different platform.
+ Sum += *(DWORD *)pch;
+ // Sum = _rotr(Sum,3) ^ *(DWORD *)pch;
+#else
+ // Make the hash function platform independent. On BIGENDIAN machine
+ // we byte swap and then interpret is as WORD.
+#if HP_BIGENDIAN
+ Sum += (WORD) *(BYTE *)pch + ((WORD)(*(BYTE *)(pch +1)) << 8);
+#else
+ Sum += *(WORD *)pch;
+#endif
+ // Sum = _rotr(Sum,3) ^ *(WORD *)pch;
+#endif
+
+ // Exit if second char of two chars just used was zero
+ // Note that we don't care about DBCS character boundaries,
+ // so ++ is ok.
+ pch++;
+ if (*pch == xchTerm || *pch == 0)
+ break;
+
+ // Exit if first char of next two chars is zero
+ pch++;
+ if (*pch == xchTerm || *pch == 0)
+ break;
+ }
+
+#if OE_WIN32
+ ConvertStringFree(sz);
+#else
+ #undef sz
+#endif
+
+ Sum ^= Sum >> 8;
+ return Sum;
+}
+#pragma code_seg()
+
+
+// enable stack checking on these suckers -- they're potentially
+// massivly recursive
+#pragma check_stack(on)
+
+#pragma code_seg(CS_CREATE) // only used by dstrmgr code
+/***
+*PUBLIC SwapElementIndex(ULONG *rgulToSort, UINT *rguIndex, UINT iLow, UINT iHigh)
+*Purpose: Swap the element in iLow and iHigh for both
+* the array rgulToSort and rguIndex.
+*
+*Entry
+* rgulToSort, rguIndex : array's whose elements needs to be swapped
+* iLow, iHigh : index to interchange the elements.
+*
+*Exit:
+* None.
+***********************************************************************/
+VOID NEAR SwapElementIndex(ULONG *rgulToSort, UINT *rguIndex, UINT iLow, UINT iHigh)
+{
+ ULONG ulTmp=0;
+ UINT uTmp=0;
+
+ ulTmp = *(rgulToSort+iLow);
+ *(rgulToSort+iLow) = *(rgulToSort+iHigh);
+ *(rgulToSort+iHigh) = ulTmp;
+
+ // if the index array is passed then swap the index array also.
+ if (rguIndex) {
+ uTmp = *(rguIndex+iLow);
+ *(rguIndex+iLow) = *(rguIndex+iHigh);
+ *(rguIndex+iHigh) = uTmp;
+ } //if
+
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC QuickSortIndex(ULONG *rgulToSort, UINT *rguIndex, UINT uCount)
+*Purpose: QuickSort.
+*
+*
+*Entry
+*
+*
+*Exit:
+* None.
+***********************************************************************/
+VOID QuickSortIndex(ULONG *rgulToSort, UINT *rguIndex, UINT uCount)
+{
+ ULONG ulMid=0;
+ UINT iLow=0, iHigh=uCount-1;
+
+ if (uCount <= 1)
+ return;
+
+ // Get the middle element as the value for partition.
+ ulMid = *(rgulToSort + uCount/2);
+
+
+
+ while (iLow < iHigh) {
+ while((*(rgulToSort+iLow) <= ulMid) && (iLow < iHigh)) iLow++;
+
+ while((*(rgulToSort+iHigh) >= ulMid) && (iLow < iHigh)) iHigh--;
+
+ if (iLow < iHigh) {
+ // swap the numbers
+ SwapElementIndex(rgulToSort, rguIndex, iLow, iHigh);
+ } // if
+ } // while
+
+
+ DebAssert(iLow == iHigh, "Terminating condition");
+
+ // Take care of all the termination conditions. iLow and iHigh are
+ // pointing to the same location. Adjust these so that it points to the
+ // end of the subarrays.
+ if (iHigh == uCount-1) {
+ // all elements were < or = to ulMid.
+ //
+ // if the last element is ulMid then dec. iLow
+ // i.e. reduce the array size if possible.
+ if (*(rgulToSort+iHigh) < ulMid) {
+ // swap the middle element with the last element.
+ SwapElementIndex(rgulToSort, rguIndex, uCount/2, iHigh);
+ }
+ iLow--;
+
+ }
+ else {
+ if (iLow == 0) {
+ // all elements were > or = to ulMid
+ //
+ // if the last element is ulMid then inc. iHigh
+ // i.e. reduce the array size if possible.
+ if (*(rgulToSort+iHigh) > ulMid) {
+ // swap the middle element with the first element.
+ SwapElementIndex(rgulToSort, rguIndex, 0, uCount/2);
+ }
+ iHigh++;
+ }
+ else {
+ // Adjust iLow and iHigh so that these points to the right place
+ if (*(rgulToSort+iHigh) > ulMid)
+ iLow--;
+ else
+ iHigh++;
+ }
+ }
+
+ // Sort the lower sub array
+ QuickSortIndex(rgulToSort, rguIndex, (UINT)iLow+1);
+ // Sort the upper sub array
+ QuickSortIndex(rgulToSort+iLow+1, rguIndex+iLow+1, (UINT)(uCount-iLow-1));
+
+
+}
+#pragma code_seg()
+#pragma check_stack() // return to the default
+
+
+
+
+/***
+* Functions for manipulating LISTs implemented with DEFNs (managed
+* by TYPE_DATA).
+*
+*Purpose:
+* The following are functions that implement the "list" protocol.
+* These macros are used specifically by the DYN_TYPEMEMBERS
+* impl that defers to the contained TYPE_DATA.
+*
+*Implementation Notes:
+* POSITION is implemented as a DEFN handle.
+* Some functions are MEMBERINFO specific, some are general
+* to be used by INFOs.
+*
+*****************************************************************************/
+#if ID_DEBUG
+/***
+* Count - List cardinality.
+*
+*Purpose:
+* Returns size of list.
+*
+*Implementation Notes:
+* Cheapo and slow implementation -- enumerates from listhead.
+* CONSIDER: actually "wasting" an int for a m_count data member.
+*****************************************************************************/
+
+UINT Count(TYPE_DATA *ptdata, HDEFN hdefnFirst)
+{
+ /* Cheapo and slow implementation -- enumerates from listhead. */
+ // Note: we ensure no circularity by asserting that list length
+ // is < 64K.
+ //
+ UINT cElements = 0;
+ HDEFN hdefn = hdefnFirst;
+
+ while (hdefn != HDEFN_Nil) {
+ cElements++;
+ DebAssert(cElements < USHRT_MAX, "circular list.");
+ hdefn = ptdata->QdefnOfHdefn(hdefn)->HdefnNext();
+ }
+ return cElements;
+}
+#endif //ID_DEBUG
+
+
+
+
+
+
+/***
+*TIPERROR GetBStrOfHsz
+*
+*Purpose:
+* Allocate a local string containing the string in the passed in XSZ
+*
+*Entry:
+* pbm - The block manager that can dereference hsz.
+* hsz - The hsz refering to the string data to be used for initializing
+* the new BSTRA.
+*
+*Exit:
+* *plstr is set to the new lstr.
+* TIPERROR
+****************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR GetBStrOfHsz(BLK_MGR *pbm, HCHUNK hsz, BSTR *pbstr)
+{
+ BSTR bstr;
+
+ // If hsz is a nil handle, return NULL.
+ if (hsz == HCHUNK_Nil) {
+ *pbstr = NULL;
+ return TIPERR_None;
+ }
+
+#if OE_WIN32
+ // Allocate and copy all at once - the Win32 sheap
+ // will not move during the alloc or copy
+ // pbm->HszLen() asumes Ansi strings so isn't valid
+ bstr = AllocBstr((LPOLESTR)pbm->QtrOfHandle(hsz));
+ if (bstr == NULL)
+ return TIPERR_OutOfMemory;
+
+ *pbstr = bstr;
+#else
+ LPOLESTR qchSrc;
+
+ // Allocate enough space for the string.
+ bstr = AllocBstrLen(NULL, pbm->HszLen(hsz));
+ if (bstr == NULL)
+ return TIPERR_OutOfMemory;
+
+ *pbstr = bstr;
+
+ // Now copy the string into the new lstr. Don't use
+ // strcpy, because that far call might invalidate qchSrc.
+ // Note that we don't care about DBCS character boundaries,
+ // so ++ is ok.
+ qchSrc = (LPOLESTR)pbm->QtrOfHandle(hsz);
+ do {
+ *bstr++ = *qchSrc;
+ } while (*qchSrc++ != '\0');
+
+#endif
+
+ return TIPERR_None;
+}
+
+
+#pragma code_seg()
+
+
+
+#if OE_WIN16
+#pragma optimize("q",off)
+#endif
+// UNDONE: do we really need to turn off optimizations for 700 lines???
+
+
+
+
+/**********
+*CompareHimptypes
+*
+*Purpose:
+* Compare two user-defined types for equality given two himptypes
+* Loads their respective typeinfos by extracting
+* their himptypes and compares
+* the addresses of the typeinfos for identity.
+* NOTE: this depends on the typemgr only ever loading
+* a single typeinfo per module w/in a process.
+*
+*Entry:
+* ptdata1 TYPE_DATA of first type (IN)
+* himptype1 Handle of first type (IN) must be != HIMPTYPE_Nil
+* ptdata2 TYPE_DATA of second type (IN)
+* himptype2 Handle of second type (IN) must be != HIMPTYPE_Nil
+* fEqual TRUE if same type (OUT)
+*
+*Errors:
+* TIPERROR
+***********/
+
+TIPERROR CompareHimptypes(TYPE_DATA * const ptdata1,
+ HIMPTYPE himptype1,
+ TYPE_DATA * const ptdata2,
+ HIMPTYPE himptype2,
+ BOOL *pfEqual)
+{
+ ITypeInfoA *ptinfo1;
+ ITypeInfoA *ptinfo2;
+ TIPERROR err;
+
+ DebAssert(himptype1 != HIMPTYPE_Nil && himptype2 != HIMPTYPE_Nil,
+ "caller's job to test for HIMPTYPE_Nil");
+
+ // Get respective typeinfos
+ IfErrRet(ptdata1->Pimpmgr()->GetTypeInfo(himptype1, DEP_None, &ptinfo1));
+ IfErrGo(ptdata2->Pimpmgr()->GetTypeInfo(himptype2, DEP_None, &ptinfo2));
+ // Compare pointer identity.
+ *pfEqual = (ptinfo1 == ptinfo2);
+ RELEASE(ptinfo2);
+
+ // fall through...
+Error:
+ RELEASE(ptinfo1);
+ return err;
+} // CompareHimptypes
+
+
+
+
+/***
+* BOOL VerifyLcid(LCID lcid)
+*
+* Purpose: Checks if the passed in lcid is valid.
+*
+* Inputs:
+* lcid : LCID that needs to be verified.
+*
+* Outputs: BOOL : return TRUE if the passed in lcid is a valid LCID
+* else return FALSE
+*
+*****************************************************************************/
+#pragma code_seg(CS_INIT)
+extern "C" BOOL VerifyLcid(LCID lcid)
+{
+#if 0
+ return IsValidLocale(lcid, LCID_SUPPORTED);
+#else
+ // Call the nlsapi function to compare string. If the compare
+ // succeeds then the LCID is valid or else the passed in lcid is
+ // invalid. This is because the only reason the comparision will
+ // fail is if the lcid is invalid.
+ char rgTest[] = "Test\0";
+
+ if (!lcid)
+ return FALSE;
+ return (BOOL)(CompareStringA(lcid,
+ NORM_IGNORECASE | NORM_IGNORENONSPACE,
+ rgTest, -1,
+ rgTest, -1) == 2);
+#endif
+}
+#pragma code_seg()
+
+
+#if !OE_WIN32
+/***
+* OLE_TYPEMGR Poletmgr() - Returns the current task's OLE_TYPEMGR.
+*
+* Purpose:
+* This function returns a pointer to the current task's OLE_TYPEMGR.
+* Note : OLE_TYPEMGR is not reference counted
+* Inputs:
+* None
+*
+* Outputs:
+*
+*
+*****************************************************************************/
+#pragma code_seg(CS_INIT)
+OLE_TYPEMGR *Poletmgr()
+{
+ return Pappdata()->m_poletmgr;
+}
+#pragma code_seg()
+
+#endif // !OE_WIN32
+
+
+/***
+*TIPERROR SplitGuidLibId - Parses a LIBIDKIND_Registered-format libid.
+*
+*Inputs:
+* szLibId - The LIBIDKIND_Registered-format libid to be parsed.
+*
+*Outputs:
+* *pszGuid points at the beginning of the guid portion.
+* *pszGuidEnd points at the '#' terminating the guid portion.
+* *pwMaj is set to the major version number in the libid.
+* *pwMin is set to the minor version number in the libid.
+* *plcid is set to the lcid in the libid.
+* If pszPath is not NULL, the *pszPath is set to the start of the path
+* portion and *pszPathEnd is set to the terminating '#'.
+* TIPERR_BadLibId is returned if the libid is not in proper format.
+* Otherwise returns TIPERR_None.
+****************************************************************************/
+#pragma code_seg(CS_CORE2)
+TIPERROR SplitGuidLibId(LPOLESTR szLibId, LPOLESTR *pszGuid, LPOLESTR *pszGuidEnd, WORD *pwMaj, WORD *pwMin, LCID *plcid, LPOLESTR *pszPath, LPOLESTR *pszPathEnd)
+{
+ LPOLESTR pchEnd;
+
+ // The LibId must be of the form:
+ // *\<kind><szGuid>#maj.min#lcid#<path>#<regname>
+
+ if (GetLibIdKind(szLibId) != LIBIDKIND_Registered &&
+ GetLibIdKind(szLibId) != LIBIDKIND_ForeignRegistered)
+ return TIPERR_BadLibId;
+
+ // Get the GUID out of the LibId.
+ *pszGuid = szLibId+3;
+ if ((*pszGuidEnd = ostrchr(*pszGuid, WIDE('#'))) == NULL)
+ return TIPERR_BadLibId;
+
+ // Get the version number out.
+ pchEnd = *pszGuidEnd+1;
+ *pwMaj = (WORD)ostrtoul(pchEnd, &pchEnd, 16);
+ if (*pchEnd++ != WIDE('.'))
+ return TIPERR_BadLibId;
+ *pwMin = (WORD)ostrtoul(pchEnd, &pchEnd, 16);
+ if (*pchEnd++ != WIDE('#'))
+ return TIPERR_BadLibId;
+
+ // Get the lcid out.
+ *plcid = (LCID)ostrtoul(pchEnd, &pchEnd, 16);
+ if (*pchEnd++ != WIDE('#'))
+ return TIPERR_BadLibId;
+
+ // Get the path out.
+ if (pszPath != NULL) {
+ *pszPath = pchEnd;
+ if ((*pszPathEnd = ostrchr(*pszPath, WIDE('#'))) == NULL)
+ return TIPERR_BadLibId;
+ }
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+#if 0 //Dead Code
+/***
+*PUBLIC BOOL FIsLibId
+*Purpose:
+* Answers if the given string is a LibId.
+*
+*Entry:
+* szMaybeLibId = the string that might be a LibId.
+*
+*Exit:
+* return value = BOOL
+*
+***********************************************************************/
+BOOL FIsLibId(LPOLESTR szMaybeLibId)
+{
+ return(ostrlen(szMaybeLibId) >= 3
+ && GetLibIdKind(szMaybeLibId) != LIBIDKIND_Unknown);
+}
+#endif //0
+
+/***
+*GetLibIdKind - Returns the kind of libid szLibId is.
+*******************************************************************/
+LIBIDKIND GetLibIdKind(LPOLESTR szLibId)
+{
+ if (szLibId[0] == WIDE('*') && szLibId[1] == WIDE('\\')) {
+ switch (szLibId[2]) {
+
+
+ case 'G':
+ return OE_MAC?LIBIDKIND_ForeignRegistered:LIBIDKIND_Registered;
+ case 'H':
+ return OE_MAC?LIBIDKIND_Registered:LIBIDKIND_ForeignRegistered;
+ case 'R':
+ return LIBIDKIND_Compressed;
+ }
+ }
+
+ return LIBIDKIND_Unknown;
+}
+
+
+
+/***
+*TIPERROR GetPathOfLibId - Returns the path of the specified typelib.
+*
+*Purpose:
+* This function determines the full path of the typelib specified by
+* szLibId and returns a BSTR copy of that path.
+*
+*Inputs:
+* szLibId - The libid.
+*
+*Outputs:
+* *pbstrPath is set to a BSTR copy of the path corresponding to szLibId.
+* TIPERROR
+************************************************************************/
+TIPERROR GetPathOfLibId(LPOLESTR szLibId, BSTR *pbstrPath)
+{
+ TIPERROR err;
+ BSTR bstrPath;
+ LPOLESTR szGuid, szGuidEnd;
+ WORD wMaj, wMin;
+ LCID lcid;
+ OLECHAR *sz=NULL, szPath[_MAX_PATH];
+
+ switch (GetLibIdKind(szLibId)) {
+
+ case LIBIDKIND_Registered:
+ IfErrRet(SplitGuidLibId(szLibId, &szGuid, &szGuidEnd, &wMaj, &wMin, &lcid, NULL, NULL));
+ *szGuidEnd = '\0';
+ err = GetRegInfoForTypeLibOfSzGuid(szGuid, wMaj, wMin, lcid, szPath, TRUE);
+ *szGuidEnd = '#';
+ sz = szPath;
+ break;
+ }
+
+ if (sz != NULL) {
+ if ((bstrPath = AllocBstr(sz)) == NULL)
+ return TIPERR_OutOfMemory;
+ *pbstrPath = bstrPath;
+ return TIPERR_None;
+ }
+
+ return TIPERR_BadLibId;
+}
+
+
+/***
+* TIPERROR GetRegLibOfLibId() - Opens a registered typelib, given a libId.
+*
+* Purpose:
+* This function finds and loads a GenericTypeLibOLE (probably created
+* by MkTypLib), given its LibId. This is used both by the implementation
+* of the OLE version of the import manager (indirectly through
+* GetTypeInfoOfCompressedTypeId) and by the TYPEMGR in OB.
+*
+* Inputs:
+* szLibId - The Typelib's LibId.
+*
+* Outputs:
+* TIPERR_None is returned and *pptlib is set to the loaded
+* typelib if successful.
+*
+* Otherwise, *pptlib remains unchanged.
+*
+*****************************************************************************/
+#pragma code_seg( CS_CORE2 )
+TIPERROR GetRegLibOfLibId(LPOLESTR szLibId, ITypeLibA **pptlib)
+{
+ // The LibId must be of the form:
+ // *\<kind><szGuid>#maj.min#lcid#<path>#<regname>
+ TIPERROR err;
+ WORD wMaj, wMin;
+ LPOLESTR szPath, pchEnd, szGuid, pchGuidEnd;
+ LCID lcid;
+ LPOLESTR szFile;
+
+ IfErrRet(SplitGuidLibId(szLibId, &szGuid, &pchGuidEnd, &wMaj, &wMin, &lcid, &szPath, &pchEnd));
+
+ // Load the Typelib.
+ *pchGuidEnd = '\0';
+ err = TiperrOfHresult(LoadRegTypeLibOfSzGuid(szGuid, wMaj, wMin, lcid,
+ pptlib));
+ *pchGuidEnd = '#';
+
+ // If the registry lookup failed for some reason, then try using the
+ // path encoded in the libid if we have one.
+ if (err != TIPERR_None) {
+
+ // CONSIDER: (dougf) 5/26/93 probably don't want to bother doing this if
+ // the imbedded pathname doesn't correspond to the current
+ // system (e.g. if we're OE_MAC and we're trying to load a MAC
+ // typelib created on Windows, the pathname will be in DOS format)
+
+ // Try loading the typelib.
+ *pchEnd = '\0';
+ if (*szPath != '\0') { // Don't try to load unless we've got a path.
+ // A "library not registered" error (what
+ // we probably have now) is probably better
+ // for the user than a "file not found" error.
+
+ // Strip off any path portion to force LoadTypeLib to search for
+ // the typelib.
+ szFile = IsolateFilename(szPath);
+
+ err = TiperrOfHresult(LoadTypeLib(szFile, pptlib));
+ }
+ *pchEnd = '#';
+ }
+
+ return err;
+}
+#pragma code_seg( )
+
+
+/***
+* TIPERROR GetRegInfoForTypeLibOfSzGuid().
+*
+* Purpose:
+* This function produces the fully qualified path name based on the
+* guid, wMajorNum, wMajorNum, and lcid. It returns
+* a string containing the fully qualified path name.
+*
+* Inputs:
+* szGuid : string representation of GUID
+* wMaj : Mojor version number of the Typelib to be loaded
+* wMin : Minor version number of the Typelib to be loaded
+* lcid : Lcid of the lib to be loaded.
+* fMustExist : TRUE if we're to ensure the existence of the file
+*
+* Outputs:
+* rgFileName : Fully qualified path name (size is _MAX_PATH).
+*
+*
+* TIPERR_None is returned if successful.
+**
+*****************************************************************************/
+#pragma code_seg(CS_QUERY)
+TIPERROR
+GetRegInfoForTypeLibOfSzGuid(LPOLESTR szGuid,
+ WORD wMaj,
+ WORD wMin,
+ LCID lcid,
+ LPOLESTR rgFileName,
+ BOOL fMustExist)
+{
+ TIPERROR err = TIPERR_None;
+ TLIBKEY tlibkey;
+ HKEY hkeyLcid;
+ OLECHAR szPath[_MAX_PATH];
+ OLECHAR szLcid[9];
+ LCID lcidBest;
+ OLECHAR * szPlatform;
+ long cb;
+
+ // Open the registry key for the typelib. Fail if there is no entry
+ // for this typelib.
+ IfErrRet(OpenTypeLibKey(szGuid, wMaj, wMin, &tlibkey));
+
+ // Get the Lcid that we can use to path of the TypeLib.
+ IfErrGo(GetBestLcidMatch(tlibkey.hkeyVers, lcid, &lcidBest, &szPlatform));
+ lcid = lcidBest;
+
+ // point szLcid at a zero-terminated ascii hex
+ // representation of the lcid.
+ oultoa(lcid, szLcid, 16);
+
+ if (oRegOpenKey(tlibkey.hkeyVers, szLcid, &hkeyLcid) != ERROR_SUCCESS) {
+ err = TIPERR_LibNotRegistered;
+ goto Error;
+ }
+
+ // Try to open that file. If that succeeds, then return that
+ // typelib. Otherwise, return the error.
+ cb = sizeof(szPath)/sizeof(szPath[0]);
+
+ if (!(err = GetRegisteredPath(hkeyLcid,
+ szPlatform,
+ szPath,
+ &cb,
+ fMustExist))) {
+ ostrcpy(rgFileName, szPath);
+ }
+
+ RegCloseKey(hkeyLcid);
+
+Error:
+ CloseTypeLibKey(&tlibkey);
+ return err;
+}
+#pragma code_seg()
+
+
+
+
+/***
+* TIPERROR LoadRegTypeLibOfSzGuid().
+*
+* Purpose:
+* This function finds and loads a GenericTypeLibOLE (probably created
+* by MkTypLib), given its guid, wMajorNum, wMajorNum, and lcid. It returns
+* a pointer to the typelib specified by the above parameters.
+*
+* Inputs:
+* szGuid : string representation of the GUID of the lib to be loaded.
+* wMaj : Mojor version number of the Typelib to be loaded
+* wMin : Minor version number of the Typelib to be loaded
+* lcid : Lcid of the lib to be loaded.
+*
+* Outputs:
+* *pptlib : is set to point to the typelib loaded if successful or else
+* pptlib remains unchanged.
+*
+* TIPERR_None is returned if successful.
+**
+*****************************************************************************/
+STDAPI
+LoadRegTypeLibOfSzGuid(LPOLESTR szGuid,
+ WORD wMaj,
+ WORD wMin,
+ LCID lcid,
+ ITypeLibA **pptlib)
+
+{
+
+ OLECHAR szPath[_MAX_PATH];
+ HRESULT hresult;
+ TIPERROR err;
+ BOOL fLoadingStdole;
+
+ // cache the typelib if it is the current stdole[32].tlb
+ fLoadingStdole = ( (wMaj == STDOLE_MAJORVERNUM)
+ && (wMin == STDOLE_MINORVERNUM)
+ && (ostrcmp(szGuid, g_szGuidStdole) == 0));
+
+ if (fLoadingStdole) {
+ APP_DATA *pappdata;
+ pappdata = Pappdata(); // DON'T rely on this after LoadTypeLib
+ if (pappdata != NULL && pappdata->m_ptlibStdole) {
+ // stdole is already cached, so use it and save registry hits, etc.
+ *pptlib = pappdata->m_ptlibStdole;
+ (*pptlib)->AddRef();
+ return NOERROR;
+ }
+ }
+
+ // Get the path name of the file
+ // (don't check that this file/path exists)
+ IfErrRetHresult(GetRegInfoForTypeLibOfSzGuid(szGuid,
+ wMaj,
+ wMin,
+ lcid,
+ szPath,
+ FALSE));
+
+ // Load the lib.
+ hresult = LoadTypeLib(szPath, pptlib);
+
+ // If the load failed due to file not found, then strip off the
+ // path and try the load again to search for the typelib by name.
+ //
+ LPOLESTR szFile;
+
+ if (hresult != NOERROR) {
+ err = TiperrOfHresult(hresult);
+ if (err == TIPERR_PathNotFound || TIPERR_FileNotFound) {
+ // Strip off any path portion to force LoadTypeLib to search for
+ // the typelib.
+ szFile = IsolateFilename(szPath);
+ hresult = LoadTypeLib(szFile, pptlib);
+ }
+ }
+
+ if (hresult == NOERROR && fLoadingStdole) {
+ // cache the stdole pointer for future calls, but don't AddRef(). If
+ // stdole's reference count goes to 0, it will set m_ptlibStdole to
+ // NULL on its own. This is because the APP_DATA structure is freed
+ // when the last typelib is released, and the APP_DATA structure has
+ // a typelib pointer in it. We don't want a circular dependency.
+ // can't use pappdata above, since it might not have been allocated
+ // until LoadTypeLib().
+ Pappdata()->m_ptlibStdole = *pptlib;
+ }
+ return hresult;
+}
+
+
+/***
+* TIPERROR LoadRegTypeLib().
+*
+* Purpose:
+* This function finds and loads a GenericTypeLibOLE (probably created
+* by MkTypLib), given its guid, wMajorNum, wMajorNum, and lcid. It returns
+* a pointer to the typelib specified by the above parameters.
+*
+* Inputs:
+* guid : CLSIID/GUID of the lib to be loaded.
+* wMaj : Mojor version number of the Typelib to be loaded
+* wMin : Minor version number of the Typelib to be loaded
+* lcid : Lcid of the lib to be loaded.
+*
+* Outputs:
+* *pptlib : is set to point to the typelib loaded if successful or else
+* pptlib remains unchanged.
+*
+* TIPERR_None is returned if successful.
+**
+*****************************************************************************/
+STDAPI LoadRegTypeLib(REFGUID guid,
+ WORD wMaj,
+ WORD wMin,
+ LCID lcid,
+ ITypeLibA **pptlib)
+
+{
+
+ HRESULT hresult = NOERROR;
+ TIPERROR err = TIPERR_None;
+ OLECHAR szGuid[CCH_SZGUID0];
+ TLIBATTR *ptlibattr;
+
+#if !OE_WIN32
+ // since this can be the first call into typelib.dll
+ TlsCleanupDeadTasks();
+#endif //!OE_WIN32
+
+ if (pptlib == NULL) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+ StringFromGUID2(guid, szGuid, CCH_SZGUID0);
+
+ // Free the szGuid before the call to LoadRegTypeLibOfszGuid as that call
+ // can release the APP_DATA
+ //
+ IfOleErrRet(LoadRegTypeLibOfSzGuid(
+ szGuid,
+ wMaj,
+ wMin,
+ lcid,
+ pptlib));
+
+ IfOleErrGo((*pptlib)->GetLibAttr(&ptlibattr));
+
+ // Verify that the loaded typelib has the requested guid and major
+ // version number and the minor version number and the lcid are
+ // compatible with that requested.
+ if (ptlibattr->guid != guid || ptlibattr->wMajorVerNum != wMaj ||
+ ptlibattr->wMinorVerNum < wMin ||
+ (ptlibattr->lcid != lcid && ptlibattr->lcid != (LCID)(PRIMARYLANGID(lcid)) &&
+ ptlibattr->lcid != 0)) {
+ (*pptlib)->ReleaseTLibAttr(ptlibattr);
+ (*pptlib)->Release();
+ return ReportResult(0, TYPE_E_LIBNOTREGISTERED, 0, 0);
+ }
+
+ (*pptlib)->ReleaseTLibAttr(ptlibattr);
+ return NOERROR;
+
+Error:
+ (*pptlib)->Release();
+ return hresult;
+}
+
+
+#pragma code_seg(CS_QUERY)
+/***
+* HRESULT QueryPathOfRegTypeLib().
+*
+* Purpose:
+* This function produces the fully qualified path name based on the
+* guid, wMajorNum, wMajorNum, and lcid. It returns
+* a string containing the fully qualified path name.
+*
+*IMPLEMENTATION NOTES: Defers to GetRegInfoForTypeLibOfSzGuid
+*
+* Inputs:
+* guid : CLSIID/GUID of the lib to be loaded.
+* wMaj : Mojor version number of the Typelib to be loaded
+* wMin : Minor version number of the Typelib to be loaded
+* lcid : Lcid of the lib to be loaded.
+*
+* Outputs:
+* lplpPathName : *lplpPathName points to the string containing the
+* path registered in the typelib.
+*
+*
+* NOERROR is returned if successful. In Case of Error *lplpPathName is not
+* modified.
+*
+*****************************************************************************/
+STDAPI QueryPathOfRegTypeLib(REFGUID guid,
+ WORD wMaj,
+ WORD wMin,
+ LCID lcid,
+ LPBSTR lpbstrPathName)
+{
+
+ OLECHAR szGuid[CCH_SZGUID0];
+ OLECHAR szPath[_MAX_PATH];
+ TIPERROR err;
+
+#if !OE_WIN32
+ // since this can be the first call into typelib.dll
+ TlsCleanupDeadTasks();
+#endif //!OE_WIN32
+
+ if (lpbstrPathName == NULL) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+ StringFromGUID2(guid, szGuid, CCH_SZGUID0);
+
+ IfErrGo(GetRegInfoForTypeLibOfSzGuid(szGuid,
+ wMaj,
+ wMin,
+ lcid,
+ szPath,
+ FALSE));
+
+ // Allocate Space for return value, and copy pathname to it
+ if ((*lpbstrPathName = AllocBstrLen(szPath, ostrblen0(szPath))) == NULL)
+ err = TIPERR_OutOfMemory;
+
+
+Error:
+ return HresultOfTiperr(err);
+
+}
+#pragma code_seg()
+
+
+
+#if ID_DEBUG
+
+// NAME_CACHE debug methods
+// Note: they are here since there is no ncache.cxx file,
+// the rest of the implementation is inline only however these
+// methods can't be inlined since they contain strings and thus
+// might overflow dgroup.
+//
+
+/***
+*PUBLIC NAME_CACHE::DebShowState - NAME_CACHE state
+*Purpose:
+* Show NAME_CACHE state
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+*Exceptions:
+* None.
+*
+***********************************************************************/
+
+VOID NAME_CACHE::DebShowState(UINT uLevel) const
+{
+ BYTE bNamcache;
+ UINT i, j;
+
+ DebPrintf("*** NAME_CACHE ***\n");
+ if (IsValid()) {
+ for (i=0; i < NAMCACHE_cbSize; i++) {
+ bNamcache = m_rgBitmap[i];
+ for (j=0; j < sizeof(bNamcache) * CHAR_BIT; j++) {
+ DebPrintf("%s", bNamcache & (1 << j));
+ }
+ DebPrintf("\n");
+ }
+ }
+ else {
+ DebPrintf("Invalid\n");
+ }
+
+ DebPrintf("\n");
+
+}
+
+#endif
+
+#if OE_WIN16
+#pragma optimize("q",on)
+#endif
+
+
+/******************** Init Functions *************/
+
+VOID InitTypeDesc(TYPEDESC *ptdesc)
+{
+ DebAssert(ptdesc != NULL, "Invalid Arg.");
+ ptdesc->vt = VT_EMPTY;
+}
+
+
+VOID InitIdlDesc(IDLDESC *pidldesc)
+{
+ DebAssert(pidldesc != NULL, "Invalid Arg.");
+#if OE_WIN16
+ pidldesc->bstrIDLInfo = NULL;
+#else //OE_WIN16
+ pidldesc->dwReserved = 0;
+#endif //OE_WIN16
+}
+
+
+VOID InitElemDesc(ELEMDESC *pelemdesc)
+{
+ DebAssert(pelemdesc != NULL, "Invalid Arg.");
+ InitTypeDesc(&(pelemdesc->tdesc));
+ InitIdlDesc(&(pelemdesc->idldesc));
+}
+
+
+VOID InitVarDesc(VARDESCA *pvardesc)
+{
+ DebAssert(pvardesc != NULL, "Invalid Arg.");
+ pvardesc->varkind = VAR_PERINSTANCE;
+ InitElemDesc(&(pvardesc->elemdescVar));
+}
+
+
+VOID InitFuncDesc(FUNCDESC *pfuncdesc)
+{
+ DebAssert(pfuncdesc != NULL, "Invalid Arg.");
+ pfuncdesc->cParams = 0;
+ pfuncdesc->cParamsOpt = 0;
+ InitElemDesc(&(pfuncdesc->elemdescFunc));
+ pfuncdesc->lprgelemdescParam = NULL;
+}
+
+
+/*************** Clear Functions ******************/
+
+
+VOID ClearTypeDesc(TYPEDESC *ptypedesc)
+{
+ DebAssert(ptypedesc != NULL, "Invalid Arg.");
+
+ switch (ptypedesc->vt) {
+ case VT_PTR :
+ case VT_SAFEARRAY :
+ FreeTypeDesc(ptypedesc->lptdesc);
+ break;
+ case VT_CARRAY :
+ FreeArrayDesc(ptypedesc->lpadesc);
+ break;
+ }
+}
+
+
+VOID ClearIdlDesc(IDLDESC *pidldesc)
+{
+ DebAssert(pidldesc != NULL, "Invalid Arg.");
+
+#if OE_WIN16
+ FreeBstr(pidldesc->bstrIDLInfo);
+#endif //OE_WIN16
+}
+
+
+VOID ClearArrayDesc(ARRAYDESC *parraydesc)
+{
+ DebAssert(parraydesc != NULL, "Invalid Arg.");
+ ClearTypeDesc(&(parraydesc->tdescElem));
+}
+
+
+VOID ClearElemDesc(ELEMDESC *pelemdesc)
+{
+ DebAssert(pelemdesc != NULL, "Invalid Arg.");
+ ClearTypeDesc(&(pelemdesc->tdesc));
+ ClearIdlDesc(&(pelemdesc->idldesc));
+}
+
+
+/*************** Free Functions ********************/
+
+
+VOID FreeVarDesc(VARDESCA *pvardesc)
+{
+ if (pvardesc) {
+ ClearElemDesc(&(pvardesc->elemdescVar));
+ if (pvardesc->varkind == VAR_CONST) {
+ VariantClearA(pvardesc->lpvarValue);
+ MemFree(pvardesc->lpvarValue);
+ }
+ MemFree(pvardesc);
+ }
+}
+
+
+VOID FreeFuncDesc(FUNCDESC *pfuncdesc)
+{
+ UINT cParams;
+ ELEMDESC *pelemdesc;
+
+ if (pfuncdesc) {
+ ClearElemDesc(&(pfuncdesc->elemdescFunc));
+
+ // these limits are defined in defn.hxx
+ DebAssert(pfuncdesc->cParams <= MAX_CARGS, "Too Many Params.");
+
+ if (pfuncdesc->lprgelemdescParam != NULL) {
+ cParams = pfuncdesc->cParams;
+ pelemdesc = pfuncdesc->lprgelemdescParam;
+ while (cParams > 0) {
+ ClearElemDesc(pelemdesc);
+ pelemdesc += 1;
+ cParams -= 1;
+ }
+ MemFree(pfuncdesc->lprgelemdescParam);
+ }
+ // we use new to create FUNCDESC.
+ MemFree(pfuncdesc);
+ }
+}
+
+
+VOID FreeTypeDesc(TYPEDESC *ptypedesc)
+{
+ if (ptypedesc != NULL) {
+ ClearTypeDesc(ptypedesc);
+ MemFree(ptypedesc);
+ }
+}
+
+
+VOID FreeArrayDesc(ARRAYDESC *parraydesc)
+{
+ if (parraydesc) {
+ ClearArrayDesc(parraydesc);
+ MemFree(parraydesc);
+ }
+}
+
+
+TIPERROR CopyArrayDesc(ARRAYDESC **pparraydescDest, ARRAYDESC *parraydescSrc)
+{
+ UINT cb;
+
+ DebAssert(pparraydescDest && parraydescSrc, "Invalid Arguments");
+ cb = offsetof(ARRAYDESC, rgbounds) + parraydescSrc->cDims * sizeof(SAFEARRAYBOUND);
+
+ *pparraydescDest = (ARRAYDESC*) MemAlloc(cb);
+
+ if (! *pparraydescDest) {
+ return TIPERR_OutOfMemory;
+ }
+ memcpy(*pparraydescDest, parraydescSrc, cb);
+
+ return TIPERR_None;
+}
+
+
+TIPERROR CopyTypeDesc(TYPEDESC *ptdescDest, TYPEDESC *ptdescSrc)
+{
+ TIPERROR err;
+
+ DebAssert(ptdescDest && ptdescSrc, "Invalid Arguments");
+
+ ptdescDest->vt = VT_EMPTY;
+
+ switch (ptdescSrc->vt) {
+ case VT_PTR :
+ case VT_SAFEARRAY :
+ DebAssert(ptdescSrc->lptdesc, "Invalid Src ptr");
+ ptdescDest->lptdesc = (TYPEDESC *)MemAlloc(sizeof(TYPEDESC));
+ if (!(ptdescDest->lptdesc)) {
+ return TIPERR_OutOfMemory;
+ }
+ if ((err = CopyTypeDesc(ptdescDest->lptdesc, ptdescSrc->lptdesc))
+ != TIPERR_None) {
+ MemFree(ptdescDest->lptdesc);
+ return err;
+ }
+ break;
+ case VT_USERDEFINED :
+ ptdescDest->hreftype = ptdescSrc->hreftype;
+ break;
+ case VT_CARRAY :
+ IfErrRet(CopyArrayDesc(&(ptdescDest->lpadesc), ptdescSrc->lpadesc));
+ break;
+
+
+ } // switch
+ ptdescDest->vt = ptdescSrc->vt;
+
+ return TIPERR_None;
+}
+
+/***
+*TIPERROR GetLibIdOfRegLib - Constructs the libId of a registered typelib.
+*
+*Purpose:
+* This method creates a registered typelib's LibId, given all of the
+* information that goes into that LibId.
+*
+*Inputs:
+* szGuid - The registry string form of the guid under which the
+* typelib is registered.
+* wMajor - The major version number of the typelib.
+* wMinor - The minor version number of the typelib.
+* lcid - The typelib's lcid.
+* szRegName - The registered name of the typelib.
+*
+*Outputs:
+* If successful, the function returns TIPERR_None and sets *pbstrLibId
+* to a BSTRA copy of the LibId. Otherwise, the appropriate error code
+* is returned.
+***************************************************************************/
+TIPERROR GetLibIdOfRegLib(LPOLESTR szGuid, WORD wMajor, WORD wMinor, LCID lcid, LPOLESTR szPath, LPOLESTR szRegName, BSTR *pbstrLibId)
+{
+ // Note that the chars in rgchLibId will always be single-byte chars in DBCS.
+ // #maj.min#lcid# (*\<kind>, szGuid, path, and regname will not appear in this array).
+ OLECHAR rgchLibId[1+9+1+4+1+1];
+ OLECHAR *pchEnd;
+ BSTR bstr;
+ int cbGuid = ostrblen(szGuid);
+ int cbPath = ostrblen(szPath);
+
+ // Construct (in rgchLibId) all of the libId except for the guid and
+ // the registered name, between which the contents of rgchLibId will
+ // be sandwiched.
+ pchEnd = rgchLibId;
+ *pchEnd++ = '#';
+ oultoa(wMajor, pchEnd, 16);
+ pchEnd = ostrchr(pchEnd, '\0');
+ *pchEnd++ = '.';
+ oultoa(wMinor, pchEnd, 16);
+ pchEnd = ostrchr(pchEnd, '\0');
+ *pchEnd++ = '#';
+ oultoa(lcid, pchEnd, 16);
+ pchEnd = ostrchr(pchEnd, '\0');
+ *pchEnd++ = '#';
+ *pchEnd = '\0';
+
+ // Now that we know the correct length for the bstr, allocate it.
+ bstr = AllocBstrLen(NULL, 3+cbGuid+(pchEnd-rgchLibId)+cbPath+1+ostrblen(szRegName));
+ if (bstr == NULL)
+ return TIPERR_OutOfMemory;
+
+ // Copy the concatenation of "*\<kind>", szGuid, rgchLibId, szPath, '#', and szRegName
+ // (i.e. the whole libId) into the bstr.
+ ostrcpy(bstr, OE_MAC?WIDE("*\\H"):WIDE("*\\G"));
+ ostrcpy(bstr+3, szGuid);
+ ostrcpy(bstr+3+cbGuid, rgchLibId);
+ ostrcpy(bstr+3+cbGuid+(pchEnd-rgchLibId), szPath);
+ bstr[3+cbGuid+(pchEnd-rgchLibId)+cbPath] = '#';
+ ostrcpy(bstr+3+cbGuid+(pchEnd-rgchLibId)+cbPath+1, szRegName);
+ *pbstrLibId = bstr;
+ return TIPERR_None;
+}
+
+
+/***
+*TIPERROR GetLibIdOfTypeLib - Obtains the full LibId from a TypeLib.
+*
+*Purpose:
+* This method can be used to get the libId of a typelib, even if that
+* typelib doesn't support LibIds to external clients. If the typelib
+* is really an OB project, we directly use the GetTypeLib method.
+* Otherwise, we construct a "registered guid" libId, using the guid
+* obtained through the ITypeLib interface.
+*
+*Inputs:
+* ptlib - The typelib whose libId is desired.
+*
+*Outputs:
+* If successful, the function returns TIPERR_None and sets *pbstrLibId
+* to a BSTR copy of the LibId. Otherwise, the appropriate error code
+* is returned.
+***************************************************************************/
+TIPERROR GetLibIdOfTypeLib(ITypeLibA *ptlib, LPOLESTR szPath, BSTR *pbstrLibId)
+{
+ TIPERROR err;
+ HRESULT hresult;
+ TLIBATTR *ptlibattr;
+ BSTR bstrDoc = NULL;
+ OLECHAR szGuid[CCH_SZGUID0];
+
+
+ // Otherwise, get the typelib's guid, version number, lcid, and
+ // docstring, and construct a LibId from that.
+ IfOleErrRetTiperr(ptlib->GetLibAttr(&ptlibattr));
+ IfOleErrGoTo(ptlib->GetDocumentation(-1, NULL, &bstrDoc, NULL, NULL), OleErr);
+
+ // Convert the guid into the registry string format.
+ StringFromGUID2(ptlibattr->guid, szGuid, CCH_SZGUID0);
+
+ // Now construct the LibId from the guid, version number, lcid, and
+ // registered name.
+ err = GetLibIdOfRegLib(
+ szGuid,
+ ptlibattr->wMajorVerNum,
+ ptlibattr->wMinorVerNum,
+ ptlibattr->lcid,
+ szPath,
+ (bstrDoc?bstrDoc:WIDE("")),
+ pbstrLibId);
+
+ // FALL THROUGH!!!
+
+Error:
+ FreeBstr(bstrDoc);
+ ptlib->ReleaseTLibAttr(ptlibattr);
+ return err;
+
+OleErr:
+ err = TiperrOfHresult(hresult);
+ goto Error;
+}
+
+
+
+
+
+/***
+* TIPERROR GetTypeInfoOfTypeId - Gets a typeinfo from an uncompressed typeId.
+* Purpose:
+* Returns a pointer to a TYPEINFO object that describes a class.
+* This TYPEINFO must eventually be released by calling:
+* TYPEINFO::Release()
+*
+* Entry:
+* szTypeId TypeId of TypeInfo to be loaded
+* pptinfo returns pointer to the referenced ITypeInfo.
+*
+* Exit:
+* TIPERROR
+*
+***********************************************************************/
+TIPERROR GetTypeInfoOfTypeId(LPOLESTR szTypeId, ITypeInfoA **pptinfo)
+{
+ ITypeLibA *ptlib;
+ TIPERROR err;
+ BSTR bstrLibId;
+ LPOLESTR szTmp;
+ UINT itype;
+
+ // Split the TypeId into its LibId/LocalTypeId components.
+ // Sets szTypeId to the local typeId component.
+ IfErrRet(SzLibIdLocalTypeIdOfTypeId(szTypeId, &bstrLibId, &szTypeId));
+
+ // Get the typelib.
+ err = GetRegLibOfLibId(bstrLibId, &ptlib);
+ FreeBstr(bstrLibId);
+
+ if (err != TIPERR_None)
+ return err;
+
+
+ // If this is the OLE implementation or the typelib is not a
+ // GEN_PROJECT, interpret the local typeid portion of the typeId
+ // as an index into the typelib and use the ITypeLib::GetTypeInfo
+ // method.
+
+ DebAssert(*szTypeId == '#', "GetTypeInfoOfTypeId");
+ itype = (UINT)ostrtoul(szTypeId+1, &szTmp, 16);
+ DebAssert(*szTmp == '\0', "GetTypeInfoOfTypeId");
+
+ err = TiperrOfHresult(ptlib->GetTypeInfo(itype, pptinfo));
+
+ ptlib->Release();
+ return err;
+}
+
+
+/***
+*TIPERROR OpenTypeLibKey - Opens the registry key for a typelib
+*
+*Purpose:
+* This function opens the system registry key for the specified typelib.
+* From this key, the typelib's registered name, its directory, filespec,
+* and the specific filenames of various localized versions of the typelib
+* may be obtained.
+*
+*Inputs:
+* szGuid - The registry string form of the guid under which the
+* typelib is registered.
+* wMajor - The major version number of the typelib.
+* wMinor - The minor version number of the typelib.
+*
+*Outputs:
+* If successful, the function returns TIPERR_None and fills *ptlibkey
+* with the opened HKEY and all parent HKEYs. In this case, the caller
+* is responsible for eventually using CloseTypeLibKey to close all of
+* these HKEYs.
+*
+* Otherwise, the appropriate error code is returned.
+***************************************************************************/
+#pragma code_seg(CS_QUERY)
+TIPERROR OpenTypeLibKey(LPOLESTR szGuid, WORD wMajor, WORD wMinor, TLIBKEY *ptlibkey)
+{
+ // maj.min\0
+ OLECHAR rgchVer[4+1+4+1];
+ CHAR rgchVerA[4+1+4+1], *pchA;
+ OLECHAR rgchVerBestMatch[4+1+4+1];
+ OLECHAR *pchEnd;
+ HKEY hkeyTLib, hkeyGuid;
+ DWORD iVer;
+ WORD wMaj, wMin;
+ WORD wMinorMax = wMinor;
+ TIPERROR err = TIPERR_None;
+
+ // Open up the typelib section of the registry.
+ if (RegOpenKey(HKEY_CLASSES_ROOT, "TypeLib", &hkeyTLib) != ERROR_SUCCESS)
+ return TIPERR_RegistryAccess;
+
+ // Now open up the guid, if it is registered.
+ if (oRegOpenKey(hkeyTLib, szGuid, &hkeyGuid) != ERROR_SUCCESS) {
+ err = TIPERR_LibNotRegistered;
+ goto Error;
+ }
+
+ // assume the first guess is the best (it usually is)
+ itoa(wMajor, rgchVerA, 10);
+ for (pchA = rgchVerA; *pchA; ++pchA);
+ ;
+ *pchA = '.';
+ pchA++;
+ itoa(wMinor, pchA, 10);
+ if (RegOpenKey(hkeyGuid, rgchVerA, &ptlibkey->hkeyVers) == ERROR_SUCCESS)
+ goto Success;
+
+ // Initialize the best match to nothing.
+ rgchVerBestMatch[0] = '\0';
+
+ for (iVer = 0;
+ oRegEnumKey(hkeyGuid, iVer, rgchVer, sizeof(rgchVer)/sizeof(OLECHAR)) == ERROR_SUCCESS;
+ iVer++) {
+
+ // Get the major version number from rgchVer.
+ wMaj = (WORD)ostrtoul(rgchVer, &pchEnd, 16);
+
+ // If the format of this key isn't #.#, ignore it.
+ if (*pchEnd != '.')
+ continue;
+
+ // Get the minor version number from rgchVer.
+ wMin = (WORD)ostrtoul(pchEnd+1, NULL, 16);
+
+ // If we have an exact version number match, use this key.
+ // Copy the key to the best match string buffer and exit the loop.
+ if (wMaj == wMajor && wMin == wMinor) {
+ ostrcpy(rgchVerBestMatch, rgchVer);
+ break;
+ }
+
+ // Otherwise, check to see if this is a more reasonable match than
+ // any key we've yet encountered in this loop.
+
+ // In OLE code, the best non-exact match is the one with the highest
+ // minor version number, and which matches the major version number
+ // exactly. If no matching major version number is found, the search
+ // will fail.
+ if (wMaj == wMajor && wMin > wMinorMax) {
+ wMinorMax = wMin;
+ ostrcpy(rgchVerBestMatch, rgchVer);
+ }
+ }
+
+ // We have now either found an exact match on the version number,
+ // a usable best match on the version number, or nothing usable.
+ // In the first two cases, rgchVerBestMatch holds the key to be opened.
+ // In the last case, rgchVerBestMatch is zero-length and we fail.
+ if (rgchVerBestMatch[0] != '\0') {
+ if (oRegOpenKey(hkeyGuid, rgchVerBestMatch, &ptlibkey->hkeyVers) != ERROR_SUCCESS)
+ {
+ DebAssert(0, "OpenTypeLibKey");
+ }
+ }
+ else {
+ err = TIPERR_LibNotRegistered;
+ RegCloseKey(hkeyGuid);
+ goto Error;
+ }
+
+Success:
+ ptlibkey->hkeyTLib = hkeyTLib;
+ ptlibkey->hkeyGuid = hkeyGuid;
+ return TIPERR_None;
+
+Error:
+ RegCloseKey(hkeyTLib);
+ return err;
+}
+#pragma code_seg()
+
+
+/***
+*VOID CloseTypeLibKey - Closes a TLIBKEY opened by OpenTypeLibKey.
+***************************************************************************/
+#pragma code_seg(CS_QUERY)
+VOID CloseTypeLibKey(TLIBKEY *ptlibkey)
+{
+ RegCloseKey(ptlibkey->hkeyVers);
+ RegCloseKey(ptlibkey->hkeyGuid);
+ RegCloseKey(ptlibkey->hkeyTLib);
+}
+
+
+#pragma code_seg()
+
+
+/***
+*LPOLESTR SkipVolumeName - Skips over the volume name in the specified path.
+*
+*Purpose:
+* Returns a pointer to the next character beyond the volume name (e.g.
+* drive letter or net share name) at the beginning of szPath. If there
+* is no such volume name at the beginning of szPath, then *pszOut is set
+* to szPath.
+************************************************************************/
+static LPOLESTR SkipVolumeName(LPOLESTR szPath)
+{
+ LPOLESTR sz;
+
+#if OE_MAC
+
+ // If the first character is a ':', then szPath does not start with
+ // a volume name.
+ if (szPath[0] == ':')
+ return szPath;
+
+ sz = xstrchr(szPath, ':');
+ if (sz == NULL)
+ return xstrchr(szPath, '\0');
+ else
+ return sz;
+
+#else // OE_MAC
+
+ // If szPath begins with a drive letter, return the char beyond the
+ // colon.
+ if (szPath[0] != '\0' && *ostrinc(szPath) == ':')
+ return ostrinc(ostrinc(szPath));
+
+ // If szPath begins with "\\", then the format should be "\\str\str\path".
+ // In this case, return a pointer to the backslash before <path>.
+ if (szPath[0] == '\\' && szPath[1] == '\\' &&
+ (sz = ostrchr(szPath+2, '\\')) != NULL &&
+ (sz = ostrchr(sz+1, '\\')) != NULL) {
+ return sz;
+ }
+
+ return szPath;
+#endif // OE_MAC
+}
+
+#if OE_MAC
+#define DirectoryDelimiter ':'
+#else
+#define DirectoryDelimiter WIDE('\\')
+#endif
+
+/***
+*LPOLESTR SkipNextDir - Skips over the next directory in the specified path.
+*
+*Purpose:
+* If szPath begins with a directory delimiter, return a pointer just
+* beyond it.
+*
+* Otherwise, return a pointer to the next directory delimiter (or to
+* the terminating zero if there isn't one).
+************************************************************************/
+static LPOLESTR SkipNextDir(LPOLESTR szPath)
+{
+ LPOLESTR sz;
+
+ if (*szPath == DirectoryDelimiter)
+ return szPath+1;
+
+ sz = ostrchr(szPath, DirectoryDelimiter);
+
+ if (sz == NULL)
+ return ostrchr(szPath, '\0');
+ else
+ return sz;
+}
+
+
+/***
+*LPOLESTR StripDirsFromEnd - Strips directory portions from the end of a path.
+*
+*Purpose:
+* This function strips the specified number of directory portions from
+* the end of the specified path.
+*
+*Inputs:
+* szPath - The path.
+* cDirs - The number directories to strip from the end of the path.
+*
+*Outputs:
+* Returns a pointer to the first character of the stripped path.
+* Returns NULL if there aren't cDirs directories in szPath to strip.
+*
+*CONSIDER:
+* This is an n^2/2 algorithm on the number of chars in szPath in the
+* case of multi-byte character set. We need to evaluate how critical
+* this is and do something better in this case if necessary.
+************************************************************************/
+static LPOLESTR StripDirsFromEnd(LPOLESTR szPath, UINT cDirs)
+{
+ LPOLESTR szLim;
+
+ // Find the end of the string.
+ szLim = ostrchr(szPath, '\0');
+
+ // If the last character of the string is a directory delimiter,
+ // back up one to avoid hitting the terminating delimiter when
+ // searching for the last directory.
+ if (szLim > szPath) {
+ szLim = ostrdec(szPath, szLim);
+ if (*szLim != DirectoryDelimiter)
+ szLim = ostrinc(szLim);
+ }
+
+ // Specially handle the boundary case of there being no directories
+ // to strip from szPath.
+ if (szLim == szPath) {
+ if (cDirs == 0)
+ return szLim;
+ else
+ return NULL;
+ }
+
+ // Strip off the correct number of directories.
+ while (cDirs-- > 0) {
+ do {
+ szLim = ostrdec(szPath, szLim);
+ } while (szLim > szPath && *szLim != DirectoryDelimiter);
+
+ // If we ran out of path to strip and we're not done stripping
+ // yet, return NULL to indicate the failure.
+ if (szLim == szPath &&
+ (cDirs != 0 || *szLim != DirectoryDelimiter)) {
+ return NULL;
+ }
+ }
+
+ return szLim;
+}
+
+
+
+
+/***
+*TIPERROR MakeAbsolutePath - Recreates an absolute path from a relative one.
+*
+*Inputs:
+* szFrom - The absolute path from which the relative path goes.
+* This must not contain a filename at the end.
+* szRel - A relative path created by MakeRelativePath. If this is not
+* a relative path, then a BSTR copy of it is returned and szFrom
+* is ignored.
+*
+*Outputs:
+* *pbstrAbs is allocated and set to an absolute path formed by applying
+* szRel to szFrom.
+*
+* Returns TIPERR_PathNotFound if szRel specifies too many "..\"s for
+* szFrom.
+*
+*************************************************************************/
+TIPERROR MakeAbsolutePath(LPOLESTR szFrom, LPOLESTR szRel, BSTR *pbstrAbs)
+{
+ UINT cDotDot;
+ BSTR bstrAbs;
+ LPOLESTR szFromLim;
+
+ // Determine if there's a volume name or if the first character
+ // is a backslash (non-mac only). If so, then szRel is not a
+ // relative path and just return a BSTRA copy of it. Just return
+ // a copy of szRel also if szFrom is empty.
+ if (szFrom[0] == '\0'
+#if OE_MAC
+ // As a special case for this function, treat a stand-alone
+ // filename (no colons) as a relative path, even though
+ // SkipVolumeName treats it as a volume name.
+ || (szRel != SkipVolumeName(szRel) && xstrchr(szRel, ':') != NULL)
+#else
+ || szRel != SkipVolumeName(szRel)
+ || szRel[0] == '\\'
+#endif // OE_MAC
+ ) {
+ bstrAbs = AllocBstr(szRel);
+ if (bstrAbs == NULL)
+ return TIPERR_OutOfMemory;
+ *pbstrAbs = bstrAbs;
+ return TIPERR_None;
+ }
+
+ // szRel begins with 0 or more "..\"s. Count them and skip over
+ // them.
+ for (cDotDot = 0; ostrncmp(szRel, WIDE("..\\"),3) == 0; cDotDot++, szRel = ostrinc(ostrinc(ostrinc(szRel))));
+
+ // Now strip off cDotDot directories from the end of szFrom.
+ szFromLim = StripDirsFromEnd(szFrom, cDotDot);
+
+ //
+ if (szFromLim == NULL)
+ return TIPERR_PathNotFound;
+
+ // The result will be the remaining szFrom appended to the remaining
+ // szTo, with a directory delimiter between them. Calculate the size
+ // of the BSTR to allocate to hold this and allocate it.
+
+#if OE_MAC
+ if (*szRel == ':')
+ szRel++;
+#endif // OE_MAC
+
+ bstrAbs = AllocBstrLen(NULL, (szFromLim+1-szFrom) + ostrblen0(szRel));
+ if (bstrAbs == NULL)
+ return TIPERR_OutOfMemory;
+
+ // Fill the bstr.
+ ostrncpy(bstrAbs, szFrom, szFromLim-szFrom);
+ bstrAbs[szFromLim-szFrom] = DirectoryDelimiter;
+ ostrcpy(bstrAbs+(szFromLim-szFrom)+1, szRel);
+
+ // Set the output parameter and return success.
+ *pbstrAbs = bstrAbs;
+ return TIPERR_None;
+}
+
+/***
+*TIPERROR GetBestLcidMatch - Get best registered lcid.
+*
+*Purpose:
+* Given the hkey of a particular registered typelib and the ideal LCID
+* of the typelib we'd like to reference, get the closest matching LCID
+* that is actually registered for that typelib. We first check for an
+* exact match. Then we check for <primary language/default sublang>.
+* If both of those fail, we just return the default lcid (0).
+*
+*Inputs:
+* hkey - The open registry key (probably opened via OpenTypeLibKey) for
+* a particular version of a particular typelib.
+* lcidIdeal - The lcid we'd ideally like to find.
+*
+*Outputs:
+* *plcidBest is set to the best matching lcid available, if one exists.
+* Returns TIPERR_None if a reasonable match is found.
+*
+* Note that the only possible failures here are due either to hkey being
+* invalid, or to it pointing at a corrupted registry entry.
+*************************************************************************/
+#pragma code_seg(CS_QUERY)
+
+BOOL FExistsRegisteredTypelib(HKEY hkey, char * rgchLcid, OLECHAR ** pszPlatform)
+{
+ HKEY hkeyLcid;
+ HKEY hkeyPlatform;
+ BOOL fExists = FALSE;
+
+ if (RegOpenKey(hkey, rgchLcid, &hkeyLcid) == ERROR_SUCCESS) {
+ if (oRegOpenKey(hkeyLcid, szPlatSubkey1, &hkeyPlatform) == ERROR_SUCCESS){
+ *pszPlatform = szPlatSubkey1;
+ RegCloseKey(hkeyPlatform);
+ fExists = TRUE; // got it
+ }
+#if OE_WIN
+ else if (oRegOpenKey(hkeyLcid, szPlatSubkey2, &hkeyPlatform) == ERROR_SUCCESS){
+ *pszPlatform = szPlatSubkey2;
+ RegCloseKey(hkeyPlatform);
+ fExists = TRUE; // got it
+ }
+#endif //OE_WIN
+ RegCloseKey(hkeyLcid);
+ }
+ return fExists;
+}
+
+TIPERROR GetBestLcidMatch(HKEY hkey, LCID lcidIdeal, LCID *plcidBest, OLECHAR ** pszPlatform)
+{
+ char rgchLcid[10];
+
+ // Create a string form of lcidIdeal.
+ ultoa(lcidIdeal, rgchLcid, 16);
+
+ // Is that LCID available?
+ if (FExistsRegisteredTypelib(hkey, rgchLcid, pszPlatform))
+ goto Found;
+
+ // If we didn't find an exact match to lcidIdeal, try getting the
+ // path corresponding to the same primary language but 0 sublang.
+ lcidIdeal = PRIMARYLANGID(lcidIdeal);
+ ultoa(lcidIdeal, rgchLcid, 16);
+ if (FExistsRegisteredTypelib(hkey, rgchLcid, pszPlatform))
+ goto Found;
+
+ // If we didn't find that, get the path corresponding to lcid 0.
+ lcidIdeal = 0;
+ rgchLcid[0] = '0';
+ rgchLcid[1] = '\0';
+ if (FExistsRegisteredTypelib(hkey, rgchLcid, pszPlatform))
+ goto Found;
+
+ return TIPERR_LibNotRegistered;
+
+Found:
+ // Finally, return the best matching lcid.
+ *plcidBest = lcidIdeal;
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+
+#if !OE_MAC
+
+/***
+*TIPERROR ConvertPathToUNC - Converts driveletter:path to \\server\share\path
+*Inputs:
+* szPath - A full path which may start with a drive letter.
+*Outputs:
+* If szPath doesn't start with a drive letter or if the drive letter refers
+* to a local device and not to a net share, then TIPERR_None is returned
+* and *pbstrOut is set to NULL.
+*
+* If szPath does start with a drive letter that refers to a net share,
+* then *plpstrOut is set to a copy of szPath, with the UNC \\server\share
+* replacing the drive letter.
+****************************************************************************/
+TIPERROR ConvertPathToUNC(LPOLESTR szPath, LPOLESTR *plpstrOut)
+{
+ OLECHAR szLocalDevice[4];
+ OLECHAR szUNCName[40];
+ LPOLESTR sz;
+ UINT wnErr;
+#if OE_WIN32
+ DWORD cbUNC; //defined differently on NT than Win
+#else
+ UINT cbUNC;
+#endif
+
+ LPOLESTR lpstr;
+
+ if (szPath[0] == '\0' || szPath[1] != ':') {
+ goto NoConversion;
+ }
+
+ szLocalDevice[0] = szPath[0];
+ szLocalDevice[1] = ':';
+ szLocalDevice[2] = '\0';
+
+ cbUNC = sizeof(szUNCName)/sizeof(szUNCName[0]);
+ wnErr = oWNetGetConnection(szLocalDevice, szUNCName, &cbUNC);
+
+ switch (wnErr) {
+ case WN_SUCCESS:
+ // cbUNC is *SUPPOSED* to hold the length of the name + the terminating
+ // zero, but the WIN16 version doesn't work under Windows NT v1.0, so
+ // we ignore it, and re-compute the length ourselves.
+ cbUNC = ostrblen(szUNCName); // length without null
+
+ // If this is not a UNC netname, convert it to a UNC name if possible.
+ if (szUNCName[0] != '\\' || szUNCName[1] != '\\') {
+
+ // If the name is a novell net name, convert it to UNC.
+ // UNDONE: DBCS: szUNCName[cbUNC-1] is incorrect for DBCS strings.
+ // It should probably be a fast-enough equivalent of:
+ // *xstrdec(szUNCName+cbUNC)
+ // The above line of code may, in fact, be fast enough.
+ if ((sz = ostrchr(szUNCName, '/')) != NULL &&
+ szUNCName[cbUNC-1] == ':') {
+ memmove(szUNCName+2, szUNCName, cbUNC*sizeof(OLECHAR));
+ szUNCName[0] = '\\';
+ szUNCName[1] = '\\';
+ DebAssert(sz[2] == '/', "ConvertPathToUNC");
+ sz[2] = '\\';
+ DebAssert(szUNCName[cbUNC+1] == ':', "ConvertPathToUNC");
+ szUNCName[cbUNC+1] = '\0';
+
+ // We added two backslashes and removed a colon.
+ // Update cbUNC appropriately.
+ cbUNC++;
+ }
+
+ // Otherwise, we have no clue what it is so don't convert the
+ // original filename.
+ else {
+ goto NoConversion;
+ }
+ }
+
+ // allocate string of length: UNCnameLen + (PathLen - 2) + 1 (for null)
+ lpstr = (LPOLESTR)MemAlloc(
+ (cbUNC+ostrblen(szPath)-2+1)*sizeof(OLECHAR));
+ if (lpstr == NULL)
+ return TIPERR_OutOfMemory;
+ ostrcpy(lpstr, szUNCName);
+ ostrcpy(lpstr+cbUNC, szPath+2);
+ *plpstrOut = lpstr;
+ return TIPERR_None;
+
+ case WN_BAD_POINTER:
+ case WN_MORE_DATA:
+ DebHalt("ConvertPathToUNC made a bad call to WNetGetConnection");
+ case WN_NET_ERROR:
+ return TIPERR_PathNotFound;
+
+ case WN_OUT_OF_MEMORY:
+ return TIPERR_OutOfMemory;
+
+ case WN_BAD_VALUE:
+ case WN_NOT_CONNECTED:
+ case WN_NOT_SUPPORTED:
+NoConversion:
+ *plpstrOut = NULL;
+ return TIPERR_None;
+ }
+
+ return TIPERR_None;
+}
+
+#endif // !OE_MAC
+
+
+/***
+* XSZ GetPathEnd - Returns the final path delimiter in the fullpath.
+* Returns NULL if there is no path delimiter in the fullpath.
+**************************************************************/
+#pragma code_seg(CS_INIT)
+LPOLESTR GetPathEnd(LPOLESTR szPath)
+{
+ LPOLESTR sz1, sz2;
+ sz1 = ostrrchr(szPath, WIDE('\\'));
+ sz2 = ostrrchr(szPath, WIDE(':'));
+ if (sz2 != NULL && sz1 <= sz2)
+ return sz2;
+ else
+ return sz1;
+}
+#pragma code_seg()
+
+/***
+* LPOLESTR IsolateFilename - Returns the filename in the fullpath.
+**************************************************************/
+LPOLESTR IsolateFilename(LPOLESTR szPath)
+{
+ LPOLESTR sz = GetPathEnd(szPath);
+ if (sz == NULL)
+ return szPath;
+ else
+ return sz+1;
+}
+
+#if OE_MAC
+#pragma code_seg( CS_CORE2 )
+#pragma PCODE_OFF
+#define EqualStringDiacNoCase(str1, str2) EqualString((str1), (str2), false, true)
+BOOL IsFilenameEqual(LPSTR szFile1, LPSTR szFile2)
+{
+ BOOL f;
+ c2pstr(szFile1);
+ c2pstr(szFile2);
+ f = EqualStringDiacNoCase((unsigned char *)szFile1,
+ (unsigned char *)szFile2);
+ p2cstr((unsigned char *)szFile1);
+ p2cstr((unsigned char *)szFile2);
+ return f;
+}
+#pragma PCODE_ON
+#pragma code_seg( )
+#endif // OE_MAC
+
+
+
+
+/***
+*ParseConstValString - parses a string of constant values for conditional compilation
+*
+*Inputs:
+* szDecl - a string with the following syntax :
+* [identifier = [+|-]value[: identifier = [+|-]value]*]
+* where each identifier has to be unique
+*
+*Output:
+* bstrdatarr - filled with the identifier strings and their corresponding values
+*
+* Exit:
+* Returns EBERR_InvalidCanstValSyntax if syntax of szDecl not correct,
+* else TIPERR_None or TIPERR_OutOfMemory.
+***********************************************************************/
+
+
+#if 0 //Dead Code
+/****************
+*TIPERROR IsDispatchType - Does a derive from IDispatch?
+*************************************************************/
+TIPERROR IsDispatchType(ITypeInfoA *ptinfo, BOOL *pisDispatch)
+{
+ TIPERROR err = TIPERR_None;
+ HREFTYPE hreftype;
+ TYPEATTR *ptattr;
+ ITypeInfoA *ptinfoNext;
+
+ ptinfo->AddRef();
+
+ // Loop until we find end of base list or find IDispatch.
+ while (1) {
+ IfErrGo(TiperrOfHresult(ptinfo->GetTypeAttr(&ptattr)));
+
+ // If ptinfo's typekind or guid tells us it's IDispatch, return TRUE.
+ if (ptattr->typekind == TKIND_DISPATCH ||
+ ptattr->guid == IID_IDispatch) {
+ *pisDispatch = TRUE;
+ break;
+ }
+
+ // This interface is not IDispatch and, if it has no base type,
+ // it can't derive from IDispatch. So return FALSE.
+ if (ptattr->cImplTypes == 0) {
+ *pisDispatch = FALSE;
+ break;
+ }
+
+ DebAssert(ptattr->typekind == TKIND_INTERFACE || ptattr->typekind == TKIND_COCLASS, "what else is there?");
+ DebAssert(ptattr->typekind != TKIND_INTERFACE || ptattr->cImplTypes == 1, "interface with multiple inheritance?!");
+
+ // Done with the typeattr.
+ ptinfo->ReleaseTypeAttr(ptattr);
+
+ // Get the base type of this interface
+ // or the default interface of this coclass.
+ IfErrGo(TiperrOfHresult(ptinfo->GetRefTypeOfImplType(0, &hreftype)));
+ IfErrGo(TiperrOfHresult(ptinfo->GetRefTypeInfo(hreftype, &ptinfoNext)));
+
+ ptinfo->Release();
+ ptinfo = ptinfoNext;
+ }
+
+ ptinfo->ReleaseTypeAttr(ptattr);
+
+Error:
+ ptinfo->Release();
+ return err;
+}
+#endif //0
+
+/***
+*oWNetGetConnection() - Faster version of WNetGetConnection for 16-bits
+*
+*Purpose:
+* WNetGetConnection is needlessly slow if the drive letter happens to
+* correspond to a local drive. GetDriveType() is much faster, so call it
+* to see if the drive is local or not. If it isn't, use WNetGetConnection
+* to get the UNC path name
+*
+****************************************************************************/
+#if OE_WIN16 // defined in ntstring.cxx for OE_WIN32
+UINT WINAPI oWNetGetConnection(LPSTR lpLocalName, LPSTR lpRemoteName, UINT FAR* lpnLength)
+{
+ UINT drivetype;
+ INT driveno;
+
+ DebAssert(*lpnLength == 40, "All callers pass a fixed-length string");
+ DebAssert(xstrlen(lpLocalName) == 2, "All callers pass a fixed-length string");
+ DebAssert(lpLocalName[1] == ':', "All callers pass a drive letter only");
+
+ // Win16 GetDriveType() must be passed a drive number (0=A, 1=B, etc.)
+ if (lpLocalName[0] >= 'A' && lpLocalName[0] <= 'Z')
+ driveno=lpLocalName[0]-'A';
+ else if (lpLocalName[0] >= 'a' && lpLocalName[0] <= 'z')
+ driveno=lpLocalName[0]-'a';
+ else
+ goto BadDriveLetter; // let WNetGetConnection choose the return value
+
+ drivetype = GetDriveType(driveno);
+ if ( DRIVE_FIXED == drivetype ||
+ DRIVE_REMOVABLE == drivetype) {
+ return WN_NOT_CONNECTED;
+ }
+BadDriveLetter:
+ return WNetGetConnection(lpLocalName, lpRemoteName, lpnLength);
+}
+#endif //!OE_WIN16
+
+
+
+
+#pragma code_seg(CS_QUERY)
+
+#ifndef OLEMINORVERS
+#if OE_WIN32
+#define OLEMINORVERS 10 // assume OLE 2.10
+#else //OE_WIN32
+// win16 typelib.dll for Daytona will require a special build. Oh well.
+#define OLEMINORVERS 02 // assume OLE 2.02
+#endif //OE_WIN32
+#endif //!OLEMINORVERS
+
+//Typelib version support
+#include "verstamp.h"
+#undef rmm // Use a fixed number for rmm
+#define rmm OLEMINORVERS
+// keep 'rup' the same as OB's version number for simplicity
+
+STDAPI_(DWORD) OaBuildVersion(void)
+{
+ // return rmm in the the high word, rup in the low word
+ return MAKELONG(rup, rmm);
+}
+#pragma code_seg()
diff --git a/private/oleauto/src/typelib/clutil.hxx b/private/oleauto/src/typelib/clutil.hxx
new file mode 100644
index 000000000..0d8fc3f30
--- /dev/null
+++ b/private/oleauto/src/typelib/clutil.hxx
@@ -0,0 +1,417 @@
+/***
+*clutil.hxx - Class Lib component-wide utility functions.
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Component-wide utility function headers.
+*
+*Revision History:
+* 20-Jun-91 ilanc: Create
+* 03-Apr-92 martinc: placed the extern declarations outside of inline-fctns
+* 18-Jan-93 w-peterh: moved TypeDescKind <-> VarType functions from icutil.hxx
+* 12-Feb-93 w-peterh: added itdesc util functions
+* 16-Feb-93 w-jeffc: added HinstOfOLB
+* 28-Jun-93 stevenl: HinstOfCurOLB, ReleaseCurOLB
+* 24-Feb-94 RajivK: Added Make Exe support.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#ifndef CLUTIL_HXX_INCLUDED
+#define CLUTIL_HXX_INCLUDED
+
+#if OE_MAC
+#include "macos/aliases.h" // for AliasHandle
+#endif // OE_MAC
+
+#include "silver.hxx"
+#include "defn.hxx"
+#include "bstr.h"
+#include "blkmgr.hxx"
+#include "tdesck.hxx"
+
+
+#if OE_WIN32
+#include "winnls.h"
+#endif
+
+
+class EXBIND;
+class DYN_TYPEROOT;
+class NAMMGR;
+class GEN_PROJECT;
+class BSTRDATA_ARRAY;
+class GEN_PROJECT;
+
+ class OLE_TYPEMGR;
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szCLUTIL_HXX)
+#define SZ_FILE_NAME g_szCLUTIL_HXX
+#endif
+
+
+#if OE_WIN16
+#define SYSKIND_CURRENT SYS_WIN16
+#endif // OE_WIN16
+#if OE_WIN32
+#define SYSKIND_CURRENT SYS_WIN32
+#endif // OE_WIN32
+#if OE_MAC
+#define SYSKIND_CURRENT SYS_MAC
+#endif // OE_MAC
+
+
+// utility functions
+// Defines the GUID Layout structure
+#define GUID_Layout "lssbbbbbbbb"
+
+#if OE_MAC
+TIPERROR MacFileSearch(LPSTR szFile, BSTRA *pbstr);
+EBERR GetPathFromAlias(AliasHandle halias, char *pchPathname, UINT cbPathname, BOOL *pwasChanged);
+EBERR GetAliasFromPath(LPSTR szPathname, AliasHandle *phalias);
+#endif // OE_MAC
+
+VOID QuickSortIndex(ULONG *rgulToSort, UINT *rguIndex, UINT uCount);
+
+// Define min instance size for std module, min alignment
+#define CB_MIN_INSTANCE 2
+#define CB_MIN_ALIGNMENT 1
+
+
+#define HIMPTYPE_BASECLASS 0 // Note the himptype of the base class
+ // is always 0
+
+
+#if !OE_MAC
+TIPERROR ConvertPathToUNC(LPOLESTR szPath, LPOLESTR *pbstrOut);
+#endif // !OE_MAC
+
+VOID ReleaseAllRefdTypeLib();
+VOID ReleaseAllAppObject();
+
+class BASIC_TYPEINFO;
+
+#pragma code_seg()
+
+TIPERROR GetRegInfoForTypeLib(REFGUID guid,
+ WORD wMajorNum,
+ WORD wMinorNum,
+ LCID lcid,
+ LPOLESTR rgFileName);
+
+// Free functions free the structure and its contents
+VOID FreeFuncDesc(FUNCDESC FAR *pfdesc);
+VOID FreeVarDesc(VARDESCA FAR *pvardesc);
+VOID FreeTypeDesc(TYPEDESC FAR *ptypedesc);
+VOID FreeArrayDesc(ARRAYDESC FAR *parraydesc);
+
+// Init functions do not free or allocate, they only set a structures values
+// to some default values so Clear or Free functions can operate ok
+VOID InitTypeDesc(TYPEDESC FAR *ptdesc);
+VOID InitIdlDesc(IDLDESC FAR *pidldesc);
+VOID InitElemDesc(ELEMDESC FAR *pelemdesc);
+VOID InitVarDesc(VARDESCA FAR *pvardesc);
+VOID InitFuncDesc(FUNCDESC FAR *pfdesc);
+
+// Clear functions free the structures contents only
+VOID ClearArrayDesc(ARRAYDESC FAR *parraydesc);
+VOID ClearTypeDesc(TYPEDESC FAR *ptypedesc);
+VOID ClearIdlDesc(IDLDESC FAR *pidldesc);
+VOID ClearElemDesc(ELEMDESC FAR *pelemdesc);
+
+// Copy functions
+TIPERROR CopyArrayDesc(ARRAYDESC **pparraydescDest, ARRAYDESC *parraydescSrc);
+TIPERROR CopyTypeDesc(TYPEDESC *ptdescDest, TYPEDESC *ptdescSrc);
+
+#if !OE_WIN32
+// Defined in tip.cxx
+ OLE_TYPEMGR *Poletmgr();
+#endif // !OE_WIN32
+
+
+// some conversion functions
+extern BOOL VtValidInVariant(VARTYPE vt);
+extern BOOL VtValidInVariantArg(VARTYPE vt);
+
+
+// We define here some Tip API functions that are not yet
+// ready for prime time, i.e. they are not to be exposed
+// to object-phobic clients -- thus their decls do not appear
+// in exposed .h files. In principle, they will
+// eventually migrate to cl\clhost.h.
+// These functions are needed for our implemention of other Tip functions
+// that *are* exposed.
+// Like other Tip functions, the actual implementation is in tip.cxx.
+//
+
+
+
+
+TIPERROR ReadTextLine(STREAM *pstrm, XSZ rgchLine, UINT cchMax, BOOL shouldSkipBlankLines);
+TIPERROR WriteTextString(STREAM *pstrm, XSZ sz);
+TIPERROR WriteTextULong(STREAM *pstrm, ULONG ul);
+TIPERROR WriteTextSpaces(STREAM *pstrm, UINT cch);
+
+TIPERROR GetBestLcidMatch(HKEY hkey, LCID lcidIdeal, LCID *plcidBest, OLECHAR ** pszPlatform);
+ VOID SetOleTypemgr(OLE_TYPEMGR *poletmgr);
+
+#if !OE_WIN32
+
+#define Pmalloc() (Pappdata()->m_pimalloc)
+
+// Per-app data structure
+struct APP_DATA
+{
+ OLE_TYPEMGR FAR *m_poletmgr;
+ IMalloc FAR *m_pimalloc; // cache a pointer to the IMalloc
+ USHORT m_cTypeLib;
+ ITypeLib *m_ptlibStdole; // cache a pointer to the stdole typelib
+
+ // UNDONE: the following needs to go away when this functionality
+ // UNDONE: is moved into core OLE.
+ IErrorInfo FAR* m_perrinfo;
+
+ APP_DATA() {
+ m_pimalloc = NULL;
+ m_poletmgr = NULL;
+ m_cTypeLib = 0;
+ m_ptlibStdole = NULL;
+
+ // UNDONE: the following needs to go away when this functionality
+ // UNDONE: is moved into core OLE.
+ m_perrinfo = NULL;
+ }
+};
+
+TIPERROR InitAppData();
+VOID ReleaseAppData();
+APP_DATA *Pappdata();
+
+#endif // !OE_WIN32
+
+#if ID_DEBUG
+#define HeapChecker() Pmalloc()->IMallocHeapChecker();
+#endif
+
+
+#define CCH_TIMESTAMP_LENGTH 10
+void GetTimeStamp(OLECHAR *pchTimeStamp);
+TIPERROR CompareHimptypes(TYPE_DATA * const ptdata1,
+ HIMPTYPE himptype1,
+ TYPE_DATA * const ptdata2,
+ HIMPTYPE himptype2, BOOL *pfEqual);
+TIPERROR EquivHimptypes(TYPE_DATA * const ptdata1,
+ HIMPTYPE himptype1,
+ TYPE_DATA * const ptdata2,
+ HIMPTYPE himptype2,
+ BOOL *pfEqual);
+
+UINT HashOfHgnam(HGNAM hgnam);
+
+class GEN_DTINFO;
+BOOL IsUnqualifiable(GEN_DTINFO *pgdtinfo);
+
+// LibId handling functions
+enum LIBIDKIND {
+ LIBIDKIND_Unknown, // Error value.
+ LIBIDKIND_Registered, // *\G<guid>#maj.min#lcid#<path>#<regname>
+ // *\H on mac
+ LIBIDKIND_ForeignRegistered,// Registered libid created on foreign platform.
+ LIBIDKIND_Compressed, // *\R<hlib>, compressed libid reference.
+};
+
+#if 0
+BOOL FIsLibId(LPOLESTR szMaybeLibId);
+#endif
+LIBIDKIND GetLibIdKind(LPOLESTR szLibId);
+
+
+#if OE_MAC
+extern "C" EBERR GetPathFromFSSpec(const FSSpec *pfsspec, char *pchPathname, UINT cbPathname);
+extern "C" EBERR GetFSSpecOfAliasPath(char *pchPathname, FSSpec *pfsspec, BOOL *pbAliasSeen, char **ppchEnd, BOOL fResolveFile);
+#endif // OE_MAC
+
+TIPERROR MakeRelativePath(LPOLESTR szFrom, LPOLESTR szTo, LPOLESTR mszRel);
+TIPERROR MakeAbsolutePath(LPOLESTR szFrom, LPOLESTR szRel, BSTR *pbstrAbs);
+TIPERROR MakeAbsoluteLibId(LPOLESTR szDir, LPOLESTR szLibId, BSTR *pbstrLibIdAbs);
+TIPERROR SplitGuidLibId(LPOLESTR szLibId, LPOLESTR *pszGuid, LPOLESTR *pszGuidEnd, WORD *pwMaj, WORD *pwMin, LCID *plcid, LPOLESTR *pszPath, LPOLESTR *pszPathEnd);
+TIPERROR GetPathOfLibId(LPOLESTR szLibId, BSTR *pbstrPath);
+TIPERROR GetTypeInfoOfTypeId(LPOLESTR szTypeId, ITypeInfoA **pptinfo);
+TIPERROR GetLibIdOfRegLib(LPOLESTR szGuid, WORD wMajor, WORD wMinor, LCID lcid, LPOLESTR szPath, LPOLESTR szRegName, BSTR *pbstrLibId);
+TIPERROR GetLibIdOfTypeLib(ITypeLibA *ptlib, LPOLESTR szPath, BSTR *pbstrLibId);
+TIPERROR GetRegLibOfLibId(LPOLESTR szLibId, ITypeLibA **pptypelib);
+TIPERROR GetRegInfoForTypeLib(REFGUID guid,
+ WORD wMaj,
+ WORD wMin,
+ LCID lcid,
+ LPOLESTR rgFileName);
+STDAPI LoadRegTypeLibOfSzGuid(LPOLESTR szGuid,
+ WORD wMaj,
+ WORD wMin,
+ LCID lcid,
+ ITypeLibA **pptypelib);
+TIPERROR GetRegInfoForTypeLibOfSzGuid(LPOLESTR szGuid,
+ WORD wMaj,
+ WORD wMin,
+ LCID lcid,
+ LPOLESTR rgFileName,
+ BOOL fMustExist);
+
+struct TLIBKEY {
+ HKEY hkeyTLib, hkeyGuid, hkeyVers;
+};
+TIPERROR OpenTypeLibKey(LPOLESTR szGuid, WORD wMajor, WORD wMinor, TLIBKEY *ptlibkey);
+VOID CloseTypeLibKey(TLIBKEY *ptlibkey);
+
+
+void LibIdFromDocItem(LPOLESTR szDocItem, LPOLESTR szLibIdOut);
+void LibIdFromPath(LPOLESTR szPath, LPOLESTR szLibIdOut);
+TIPERROR SzLibIdLocalTypeIdOfTypeId(LPOLESTR szTypeId, BSTR *pbstrTypeId, LPOLESTR *pszLocalTypeId);
+TIPERROR SplitLocalTypeId(LPOLESTR szLocalTypeId, BSTR *pbstrLocalTypeId, LPOLESTR *pszEmbeddedLocalTypeId);
+TIPERROR MakeEmbeddedTypeId(LPOLESTR szTypeIdContainer, LPOLESTR szEmbeddedLocalTypeId, BSTR *pbstrTypeId);
+LPOLESTR SzTypeIdHmemberOfFunctionId(LPOLESTR szFunctionId, HMEMBER *phmember);
+
+
+TIPERROR IsTypeMembersEqual(LPDYNTYPEMEMBERS ptmbrs, LPDYNTYPEMEMBERS ptmbrs2, BOOL *pfIsEqual);
+BOOL IsSimpleType(TYPEDESCKIND tdesckind);
+
+
+BOOL IsIntegerType(TYPEDESCKIND tdesckind);
+TIPERROR GetDllEntryOfDynInfo(BSTRA *plstrDllFilename,
+ ULONG *puDllOrdinal,
+ LPOLESTR szDllFilename,
+ ULONG uDllOrdinal);
+TIPERROR GetDllEntryOfDataInfo(BSTRA *plstrDllFilename,
+ ULONG *puDllOrdinal,
+ HDLLENTRY_DEFN hdllentrydefn,
+ TYPE_DATA *ptdata);
+TIPERROR RegisterErrorOfHdefn(DYN_TYPEROOT *pdtroot,
+ TIPERROR errBind,
+ HDEFN hdefn);
+TIPERROR AddTypeLibToList(GEN_PROJECT *pgenproj);
+TIPERROR ResetTypeLibList();
+
+UINT Count(TYPE_DATA *ptdata, HDEFN hdefnFirst);
+
+VOID GetExecutingProject(GEN_PROJECT **ppgenproj);
+
+BOOL IsBasicFrameOnStack();
+BOOL IsModuleFrameOnStack(DYN_TYPEROOT *pdtroot);
+
+// Functions related to localization support
+extern "C" BOOL VerifyLcid(LCID lcid);
+BOOL LcStrEqi(LCID lcid, XSZ_CONST szStr1, XSZ_CONST szStr2);
+void StrGetNewLcid(void);
+BOOL IsEuroLang(LANGID langid);
+
+TIPERROR ParseConstValString(LPOLESTR szValues, BSTRDATA_ARRAY *pbstrdatarr);
+
+/***
+*BOOL IsDBCS()
+*Purpose:
+* Determines if a given lcid represents a DBCS locale
+*
+*Inputs:
+* lcid : locale id
+*
+*Outputs:
+* returns TRUE iff a DBCS is used with this locale
+*
+****************************************************************************/
+
+inline BOOL IsDBCS(LCID lcid)
+{
+ switch(PRIMARYLANGID(lcid)) {
+ case LANG_CHINESE:
+ case LANG_JAPANESE:
+ case LANG_KOREAN:
+ return TRUE;
+ default:
+ return FALSE;
+ }
+}
+
+
+// HCHUNK to BSTR copy/conversions.
+TIPERROR GetBStrOfHChunk(BLK_MGR *pbm, HCHUNK hchunk, int cb, BSTR *plstr);
+TIPERROR GetBStrOfHsz(BLK_MGR *pbm, HCHUNK hsz, BSTR *plstr);
+
+
+extern UINT RoundDownPower2(UINT u);
+
+// inline functions
+
+// had to move the following declerations out of the inline functions
+// SizeofTdesckind and AlignmentTdesckind (for cfront)
+
+extern char NEARDATA g_rgrgcbSizeType[SYS_MAX][TDESCKIND_MAX];
+
+inline USHORT SizeofTdesckind(TYPEDESCKIND tdesckind, SYSKIND syskind)
+{
+ return (USHORT)(SHORT)g_rgrgcbSizeType[syskind][tdesckind];
+}
+
+
+/***
+*HashOfHgnam() - Extracts hash value from hgnam
+*Purpose:
+* Extracts hash value from hgnam.
+* It can relied upon that hgnam & 0xFFFF == HashOfHlnam(hlnam).
+*
+*Entry:
+* None.
+*
+*Exit:
+*
+***********************************************************************/
+
+inline UINT HashOfHgnam(HGNAM hgnam)
+{
+ return (UINT) (hgnam & (unsigned short) 0x0000FFFF);
+}
+
+
+//////////////////////////////////////////////////////////////////
+//
+// OB Specify declarations
+//
+
+
+UINT HashSz(LPOLESTR sz);
+UINT HashSzTerm(LPOLESTR sz, XCHAR xchSeparator);
+
+
+#define _IsValidHdefn_(pos) \
+ HDEFN hdefn = (HDEFN)(ULONG)(void *)pos; \
+ return ((hdefn != HCHUNK_Nil) && (hdefn != (HCHUNK)1));
+
+#define _IsEqualHdefn_(pos, pos2) \
+ HDEFN hdefn = (HDEFN)(ULONG)(void *)pos; \
+ HDEFN hdefn2 = (HDEFN)(ULONG)(void *)pos2; \
+ return hdefn == hdefn2;
+
+
+
+LPOLESTR GetPathEnd(LPOLESTR szPath);
+LPOLESTR IsolateFilename(LPOLESTR szPath);
+
+#if OE_MAC
+BOOL IsFilenameEqual(LPSTR szFile1, LPSTR szFile2);
+#else
+#define IsFilenameEqual(s1, s2) (!ostricmp(s1, s2))
+#endif // OE_MAC
+
+
+
+
+#if 0
+TIPERROR IsDispatchType(ITypeInfoA *ptinfo, BOOL *pisDispatch);
+#endif
+
+#endif // ! CLUTIL_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/convert.cxx b/private/oleauto/src/typelib/convert.cxx
new file mode 100644
index 000000000..1984d4969
--- /dev/null
+++ b/private/oleauto/src/typelib/convert.cxx
@@ -0,0 +1,356 @@
+#include "silver.hxx"
+
+#pragma hdrstop(RTPCHNAME)
+
+#if ID_DEBUG
+# undef SZ_FILE_NAME
+static char szConvertCxx[] = __FILE__;
+# define SZ_FILE_NAME szConvertCxx
+#endif
+
+/*---------------------------------------------------------------------*/
+/* ANSI BSTR API */
+/*---------------------------------------------------------------------*/
+
+
+STDAPI_(BSTRA)
+SysAllocStringA(const char * psz)
+{
+ if(psz == NULL)
+ return NULL;
+
+ return((BSTRA) SysAllocStringByteLen(psz, xstrlen(psz)));
+}
+
+
+STDAPI_(BSTRA)
+SysAllocStringLenA(const char * psz, unsigned int len)
+{
+ return ((BSTRA) SysAllocStringByteLen(psz, len));
+}
+
+
+STDAPI_(void)
+SysFreeStringA(BSTRA bstr)
+{
+ SysFreeString((BSTR) bstr);
+}
+
+
+//+--------------------------------------------------------------------------
+//
+// Routine: StringFromGUID2A
+//
+// Synopsis: Creates an ANSI wrapper of an Unicode OLE2 routine.
+//
+// Returns: See OLE2 docs for details on this API.
+//
+//---------------------------------------------------------------------------
+STDAPI_(int) StringFromGUID2A(REFGUID rguid, LPSTR szGuid, int cbMax)
+{
+ int cchRet;
+
+#ifndef CCH_SZGUID0
+// char count of a guid in ansi/unicode form (including trailing null)
+#define CCH_SZGUID0 39
+#endif
+
+ OLECHAR szGuidW[CCH_SZGUID0];
+
+ cchRet = StringFromGUID2(rguid, szGuidW, CCH_SZGUID0);
+
+ // convert szGuidW from unicode to Ansi. Can't just convert in place.
+ WideCharToMultiByte(CP_ACP,
+ 0,
+ szGuidW,
+ CCH_SZGUID0,
+ szGuid,
+ cbMax,
+ NULL,
+ NULL);
+ return cchRet;
+}
+
+
+
+//+--------------------------------------------------------------------------
+//
+// Routine: ConvertStringToW
+//
+// Synopsis:
+//
+// Returns: HRESULT Error code.
+//
+//---------------------------------------------------------------------------
+HRESULT __fastcall ConvertStringToW(LPCSTR pStrA, LPOLESTR * ppStrW)
+{
+ ULONG Count;
+ HRESULT hResult;
+
+
+ // If input is null then just return the same.
+ if (pStrA == NULL)
+ {
+ *ppStrW = NULL;
+ return ResultFromScode(S_OK);
+ }
+
+ Count = xstrlen(pStrA) + 1;
+
+ hResult = ConvertStringAlloc(Count * sizeof(WCHAR), (LPVOID *)ppStrW);
+ if (FAILED(hResult))
+ return (hResult);
+
+ MultiByteToWideChar(CP_ACP, 0, pStrA, Count, *ppStrW, Count);
+
+ return ResultFromScode(S_OK);
+}
+
+
+//+--------------------------------------------------------------------------
+//
+// Routine: ConvertStringToA
+//
+// Synopsis:
+//
+// Returns: HRESULT Error code.
+//
+//---------------------------------------------------------------------------
+HRESULT __fastcall ConvertStringToA(LPCOLESTR pStrW, LPSTR * ppStrA)
+{
+ ULONG Count, cbAnsi;
+ HRESULT hResult;
+
+
+ // If input is null then just return the same.
+ if (pStrW == NULL)
+ {
+ *ppStrA = NULL;
+ return ResultFromScode(S_OK);
+ }
+
+ Count = wcslen(pStrW)+1;
+ cbAnsi = WideCharToMultiByte(CP_ACP, 0, pStrW, Count, NULL, 0, NULL, NULL);
+
+ hResult = ConvertStringAlloc(cbAnsi, (LPVOID *)ppStrA);
+ if (FAILED(hResult))
+ return (hResult);
+
+ WideCharToMultiByte(CP_ACP, 0, pStrW, Count, *ppStrA, cbAnsi, NULL, NULL);
+
+ return ResultFromScode(S_OK);
+}
+
+
+
+//+--------------------------------------------------------------------------
+//
+// Routine: ConvertStringAlloc
+//
+// Synopsis:
+//
+// Returns: HRESULT Error code.
+//
+//---------------------------------------------------------------------------
+HRESULT __fastcall ConvertStringAlloc(ULONG ulSize, LPVOID * pptr)
+{
+ IMalloc * pIMalloc;
+
+ // CONSIDER: use IMalloc cached in the pappdata structure
+ if (CoGetMalloc(MEMCTX_TASK, &pIMalloc) != 0)
+ return ResultFromScode(E_OUTOFMEMORY);
+
+ *pptr = pIMalloc->Alloc(ulSize);
+
+ pIMalloc->Release();
+
+ if (*pptr == NULL)
+ return ResultFromScode(E_OUTOFMEMORY);
+
+ return ResultFromScode(S_OK);
+}
+
+
+//+--------------------------------------------------------------------------
+//
+// Routine: ConvertStringFree
+//
+// Synopsis:
+//
+// Returns: HRESULT Error code.
+//
+//---------------------------------------------------------------------------
+VOID __fastcall ConvertStringFree(LPSTR ptr)
+{
+ IMalloc * pIMalloc;
+
+
+ if (ptr == NULL)
+ return;
+
+ // CONSIDER: use IMalloc cached in the pappdata structure
+ if (CoGetMalloc(MEMCTX_TASK, &pIMalloc) != 0)
+ return;
+
+ pIMalloc->Free(ptr);
+ pIMalloc->Release();
+}
+
+
+
+
+//+--------------------------------------------------------------------------
+//
+// Routine: ConvertBstrToWInPlace
+//
+// Synopsis:
+//
+// Returns: HRESULT Error code.
+//
+//---------------------------------------------------------------------------
+HRESULT __fastcall ConvertBstrToWInPlace(LPBSTR ppStrW)
+{
+ ULONG Count;
+ HRESULT hResult;
+
+
+ // If input is null then just return.
+ if (*ppStrW == NULL)
+ return ResultFromScode(S_OK);
+
+ BSTRA pStrA = (BSTRA)*ppStrW;
+
+ Count = MultiByteToWideChar(CP_ACP, 0, pStrA, SysStringByteLen((BSTR) pStrA),
+ NULL, NULL);
+
+ hResult = ConvertBstrAlloc(Count * sizeof(WCHAR), ppStrW);
+ if (FAILED(hResult))
+ return (hResult);
+
+ MultiByteToWideChar(CP_ACP, 0, pStrA, SysStringByteLen((BSTR) pStrA)+1,
+ *ppStrW, Count+1);
+
+ SysFreeStringA(pStrA);
+
+ return ResultFromScode(NOERROR);
+}
+
+
+//+--------------------------------------------------------------------------
+//
+// Routine: ConvertBstrToW
+//
+// Synopsis:
+//
+// Returns: HRESULT Error code.
+//
+//---------------------------------------------------------------------------
+HRESULT __fastcall ConvertBstrToW(LPCSTR pStrA, BSTR * ppStrW)
+{
+ ULONG Count;
+ HRESULT hResult;
+
+
+ // If input is null then just return the same.
+ if (pStrA == NULL)
+ {
+ *ppStrW = NULL;
+ return ResultFromScode(S_OK);
+ }
+
+ Count = MultiByteToWideChar(CP_ACP, 0, pStrA, SysStringByteLen((BSTR) pStrA),
+ NULL, NULL);
+
+ hResult = ConvertBstrAlloc(Count * sizeof(WCHAR), ppStrW);
+ if (FAILED(hResult))
+ return (hResult);
+
+ MultiByteToWideChar(CP_ACP, 0, pStrA, SysStringByteLen((BSTR) pStrA)+1,
+ *ppStrW, Count+1);
+
+ return ResultFromScode(NOERROR);
+}
+
+
+
+//+--------------------------------------------------------------------------
+//
+// Routine: ConvertBstrToA
+//
+// Synopsis:
+//
+// Returns: HRESULT Error code.
+//
+//---------------------------------------------------------------------------
+HRESULT __fastcall ConvertBstrToAInPlace(LPBSTRA ppStrA)
+{
+ // If input is null then just return.
+ if (*ppStrA == NULL)
+ return ResultFromScode(S_OK);
+
+ BSTR pStrW = (BSTR)*ppStrA;
+
+ HRESULT hResult = ConvertBstrToA(pStrW, ppStrA);
+ if (FAILED(hResult))
+ return (hResult);
+
+ SysFreeString(pStrW);
+
+ return (NOERROR);
+}
+
+
+//+--------------------------------------------------------------------------
+//
+// Routine: ConvertBstrToA
+//
+// Synopsis:
+//
+// Returns: HRESULT Error code.
+//
+//---------------------------------------------------------------------------
+HRESULT __fastcall ConvertBstrToA(BSTR pStrW, LPBSTRA ppStrA)
+{
+ ULONG Count;
+ HRESULT hResult;
+
+
+ // If input is null then just return the same.
+ if (pStrW == NULL)
+ {
+ *ppStrA = NULL;
+ return ResultFromScode(S_OK);
+ }
+
+ Count = WideCharToMultiByte(CP_ACP, 0, pStrW, SysStringLen(pStrW),
+ NULL, NULL, NULL, NULL);
+
+ hResult = ConvertBstrAlloc(Count, (LPBSTR)ppStrA);
+ if (FAILED(hResult))
+ return (hResult);
+
+ WideCharToMultiByte(CP_ACP, 0, pStrW, SysStringLen(pStrW)+1, *ppStrA, Count+1, NULL, NULL);
+
+ return ResultFromScode(NOERROR);
+}
+
+
+
+
+//+--------------------------------------------------------------------------
+//
+// Routine: ConvertBstrAlloc
+//
+// Synopsis:
+//
+// Returns: HRESULT Error code.
+//
+//---------------------------------------------------------------------------
+HRESULT __fastcall ConvertBstrAlloc(ULONG ulSize, LPBSTR pptr)
+{
+ *pptr = SysAllocStringByteLen(NULL, ulSize);
+ if (*pptr == NULL)
+ return ResultFromScode(E_OUTOFMEMORY);
+
+ return ResultFromScode(NOERROR);
+}
diff --git a/private/oleauto/src/typelib/convert.hxx b/private/oleauto/src/typelib/convert.hxx
new file mode 100644
index 000000000..4bbad27cc
--- /dev/null
+++ b/private/oleauto/src/typelib/convert.hxx
@@ -0,0 +1,37 @@
+#ifndef CONVERT_HXX_INCLUDED
+#define CONVERT_HXX_INCLUDED
+
+#if OE_WIN32
+
+#if 0
+STDAPI_(int) SysReAllocStringA(BSTRA FAR*, const char FAR*);
+STDAPI_(unsigned int) SysStringLenA(BSTRA);
+HRESULT __fastcall ConvertStringToWInPlace(LPOLESTR * ppStrW);
+HRESULT __fastcall ConvertStringToBstrW(LPCSTR pStrA, LPBSTR pbstrW);
+HRESULT __fastcall ConvertStringToAInPlace(LPSTR * ppStrA);
+#endif
+STDAPI_(BSTRA) SysAllocStringA(const char FAR*);
+STDAPI_(BSTRA) SysAllocStringLenA(const char FAR*, unsigned int);
+STDAPI_(int) SysReAllocStringLenA(BSTRA FAR*, const char FAR*, unsigned int);
+STDAPI_(void) SysFreeStringA(BSTRA);
+
+STDAPI_(int) StringFromGUID2A(REFGUID rguid, LPSTR lpsz, int cbMax);
+
+HRESULT __fastcall ConvertStringToW(LPCSTR pStrA, LPOLESTR * ppStrW);
+
+HRESULT __fastcall ConvertStringToA(LPCOLESTR pStrW, LPSTR * ppStrA);
+
+HRESULT __fastcall ConvertStringAlloc(ULONG ulSize, LPVOID * pptr);
+VOID __fastcall ConvertStringFree(LPSTR ptr);
+
+HRESULT __fastcall ConvertBstrToWInPlace(LPBSTR ppStrW);
+HRESULT __fastcall ConvertBstrToW(LPCSTR pStrA, BSTR * ppStrW);
+
+HRESULT __fastcall ConvertBstrToAInPlace(LPBSTRA ppStrA);
+HRESULT __fastcall ConvertBstrToA(BSTR pStrW, LPBSTRA ppStrA);
+
+HRESULT __fastcall ConvertBstrAlloc(ULONG ulSize, LPBSTR pptr);
+
+#endif //OE_WIN32 (whole file)
+
+#endif //CONVERT_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/ctseg.hxx b/private/oleauto/src/typelib/ctseg.hxx
new file mode 100644
index 000000000..86ca764bc
--- /dev/null
+++ b/private/oleauto/src/typelib/ctseg.hxx
@@ -0,0 +1,84 @@
+/***
+*ctseg.hxx - COMPILETIME_SEG header file
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* COMPILETIME_SEG maps a SHEAP_MGR managed heap for use by
+* compile-time clients (e.g. DYN_TYPEMEMBERS).
+*
+*Revision History:
+*
+* 20-Mar-91 ilanc: Created.
+*
+*****************************************************************************/
+
+#ifndef CTSEG_HXX_INCLUDED
+#define CTSEG_HXX_INCLUDED
+
+#include "sheapmgr.hxx"
+
+#include "impmgr.hxx"
+#include "dtmbrs.hxx"
+#include "entrymgr.hxx"
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szCTSEG_HXX)
+#define SZ_FILE_NAME g_szCTSEG_HXX
+#endif
+
+
+/***
+*class COMPILETIME_SEG : - ctseg
+*Purpose:
+* The COMPILETIME_SEG structure is used by DYN_TYPEROOT to specify
+* where the objects contained within the compile time segment are
+* to be constructed. No COMPILETIME_SEG instance is constructed.
+***********************************************************************/
+
+class COMPILETIME_SEG
+{
+ friend TIPERROR DYN_TYPEROOT::GetImpMgr(IMPMGR **ppimpmgr);
+ friend TIPERROR DYN_TYPEROOT::GetDtmbrs(DYN_TYPEMEMBERS **pdtmbrs);
+ friend TIPERROR DYN_TYPEROOT::GetEntMgr(ENTRYMGR **pentmgr);
+
+public:
+ SHEAP_MGR m_sheapmgr;
+
+ nonvirt UINT GetSize();
+
+#if ID_DEBUG
+ nonvirt UINT DebShowSize();
+#else
+ nonvirt VOID DebShowSize() {}
+#endif
+
+protected:
+ COMPILETIME_SEG(DYN_TYPEROOT *pdtroot);
+ nonvirt ~COMPILETIME_SEG() {}
+ COMPILETIME_SEG();
+
+ IMPMGR m_impmgr;
+ DYN_TYPEMEMBERS m_dtmbrs;
+ ENTRYMGR m_entmgr;
+};
+
+// inline methods
+//
+
+inline COMPILETIME_SEG::COMPILETIME_SEG(DYN_TYPEROOT *pdtroot)
+// : m_dtmbrs(&m_sheapmgr, pdtroot)
+{
+}
+
+inline COMPILETIME_SEG::COMPILETIME_SEG()
+{
+
+ DebHalt("COMPILETIME_SEG::COMPILETIME_SEG: can't call.");
+}
+
+
+#endif // ! CTSEG_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/dassert.c b/private/oleauto/src/typelib/dassert.c
new file mode 100644
index 000000000..3c6618788
--- /dev/null
+++ b/private/oleauto/src/typelib/dassert.c
@@ -0,0 +1,35 @@
+// WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING
+//
+// This file was automatically generated by MKASSERT on 08/04/94 01:46:55
+//
+// WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING
+
+#include "types.h"
+
+#if ID_DEBUG
+
+char FAR g_szBLKMGR_HXX[] = "BLKMGR.HXX";
+char FAR g_szDBLKMGR_HXX[] = "DBLKMGR.HXX";
+char FAR g_szCLTYPES_HXX[] = "CLTYPES.HXX";
+char FAR g_szDBINDTBL_HXX[] = "DBINDTBL.HXX";
+char FAR g_szDEFN_HXX[] = "DEFN.HXX";
+char FAR g_szENTRYMGR_HXX[] = "ENTRYMGR.HXX";
+char FAR g_szEXBIND_HXX[] = "EXBIND.HXX";
+char FAR g_szGBINDTBL_HXX[] = "GBINDTBL.HXX";
+char FAR g_szGDTINFO_HXX[] = "GDTINFO.HXX";
+char FAR g_szGPTBIND_HXX[] = "GPTBIND.HXX";
+char FAR g_szGTLIBOLE_HXX[] = "GTLIBOLE.HXX";
+char FAR g_szNAMMGR_HXX[] = "NAMMGR.HXX";
+char FAR g_szSHEAPMGR_HXX[] = "SHEAPMGR.HXX";
+char FAR g_szSTLTINFO_HXX[] = "STLTINFO.HXX";
+char FAR g_szTDATA_HXX[] = "TDATA.HXX";
+char FAR g_szTLIBUTIL_HXX[] = "TLIBUTIL.HXX";
+char FAR g_szTLS_C[] = "TLS.C";
+char FAR g_szCTSEG_HXX[] = "CTSEG.HXX";
+char FAR g_szBLKDSC32_HXX[] = "BLKDSC32.HXX";
+char FAR g_szMACHINE_HXX[] = "MACHINE.HXX";
+char FAR g_szMACROS_HXX[] = "MACROS.HXX";
+char FAR g_szBLKMGR32_HXX[] = "BLKMGR32.HXX";
+char FAR g_szDBM1632_HXX[] = "DBM1632.HXX";
+
+#endif // ID_DEBUG
diff --git a/private/oleauto/src/typelib/dbindtbl.cxx b/private/oleauto/src/typelib/dbindtbl.cxx
new file mode 100644
index 000000000..71bef3033
--- /dev/null
+++ b/private/oleauto/src/typelib/dbindtbl.cxx
@@ -0,0 +1,811 @@
+/***
+*dbindtbl.cxx - DYN_BINDNAME_TABLE class implementation
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Class for name binding table.
+*
+*Revision History:
+*
+* 17-Jun-92 ilanc: Created (from bindtbl.cxx)
+* 02-Jul-92 w-peterh: added rectypedefn support
+* 10-Jul-92 w-peterh: set ptbind member of BindDescs for Nested Types
+* 30-Jul-92 w-peterh: removed overloading of functions on arity
+* 30-Apr-93 w-jeffc: made DEFN data members private
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "silver.hxx"
+
+#define DYN_BINDNAME_TABLE_VTABLE
+#include "dbindtbl.hxx"
+#include "dtbind.hxx"
+#include "gdtinfo.hxx"
+#include "dtmbrs.hxx"
+#include "nammgr.hxx"
+#include "clutil.hxx" // for HashOfHgnam()
+#include <limits.h> // for INT_MAX
+#include "xstring.h" // for memset
+
+
+#pragma hdrstop(RTPCHNAME)
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+static char szDbindtblCxx[] = __FILE__;
+#define SZ_FILE_NAME szDbindtblCxx
+#endif
+
+
+/***
+*PUBLIC DYN_BINDNAME_TABLE::Constructor - Construct an instance.
+*Purpose:
+* Constructs a DYN_BINDNAME_TABLE instance.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+DYN_BINDNAME_TABLE::DYN_BINDNAME_TABLE()
+{
+ m_pblkmgr = NULL;
+ m_hchunkBucketTbl = HCHUNK_Nil;
+
+ m_cBuckets = BIND_INVALID_INDEX;
+
+ m_ptdata = NULL;
+ m_pnammgr = NULL;
+}
+#pragma code_seg( )
+
+
+// Dtor: no need to release m_ptdata since refcount
+// wasn't bumped.
+//
+#pragma code_seg( CS_CORE )
+DYN_BINDNAME_TABLE::~DYN_BINDNAME_TABLE()
+{
+}
+#pragma code_seg( )
+
+
+/***
+*PROTECTED DYN_BINDNAME_TBL::Pdtbind
+*Purpose:
+* Gets pointer to containing module-level typebind.
+*
+*Implementation Notes:
+* NOTE: defined inline here and not in the header becuase
+* of mutual dependency between stlib and gptbind.
+*
+* Subtracts from this pointer the offset of this
+* embedded instance in container. Offset is obtained
+* from a DYN_TYPEBIND static member const.
+*
+*Entry:
+*
+*Exit:
+* DYN_TYPEBIND *
+*
+***********************************************************************/
+
+inline DYN_TYPEBIND *DYN_BINDNAME_TABLE::Pdtbind() const
+{
+ return (DYN_TYPEBIND *)((BYTE *)this - DYN_TYPEBIND::oDbindnametbl);
+}
+
+
+/***
+*PUBLIC DYN_BINDNAME_TABLE::Initializer - initialize an instance.
+*Purpose:
+* initializes a DYN_BINDNAME_TABLE instance.
+*
+*Implementation Notes:
+*
+*Entry:
+* pblkmgr
+* pdtroot DYN_TYPEROOT of containing TYPEINFO.
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+#pragma code_seg( CS_CORE2 )
+TIPERROR DYN_BINDNAME_TABLE::Init(BLK_MGR *pblkmgr,
+ DYN_TYPEROOT *pdtroot)
+{
+ TIPERROR err;
+
+ DebAssert(pblkmgr != NULL, "DYN_BINDNAME_TABLE: pblkmgr uninitialized.");
+ DebAssert(pdtroot != NULL, "bad DYN_TYPEROOT.");
+
+ // cache NAMMGR
+ IfErrRet(pdtroot->GetNamMgr(&m_pnammgr));
+
+ // get and cache TYPE_DATA from synthesized DYN_TYPEBIND etc.
+ // Don't bump refcount -- since lifetime is no longer
+ // that TYPE_DATA.
+ //
+ m_ptdata = Pdtbind()->Pdtmbrs()->Ptdata();
+ m_pblkmgr = pblkmgr;
+
+ return TIPERR_None;
+}
+#pragma code_seg( )
+
+
+/***
+*PROTECTED DYN_BINDNAME_TABLE::GetBucketOfHlnam
+*Purpose:
+* Gets the bucket of an hlnam, based on its hash value.
+*
+*Implementation Notes:
+*
+*Entry:
+* hlnam - name to get the bucket of.
+*
+*Exit:
+* Returns a pointer to the DEFN.
+*
+***********************************************************************/
+
+UINT DYN_BINDNAME_TABLE::GetBucketOfHlnam(HLNAM hlnam) const
+{
+ DebAssert(hlnam != HCHUNK_Nil, "Invalid hlnam.");
+
+ if (m_cBuckets == 0) {
+ return (UINT)BIND_INVALID_INDEX;
+ }
+
+ return (UINT)(((USHORT)m_pnammgr->HashOfHlnam(hlnam)) % m_cBuckets);
+}
+
+
+/***
+*PUBLIC DYN_BINDNAME_TABLE::BuildTable
+*Purpose:
+* Builds hashtable.
+*
+*Implementation Notes:
+* NOTE: there is a table per derived class, i.e. the list
+* is not flattened. Must recurse on base class bindtables.
+*
+* Hashtable (HLNAM -> HDEFN) is allocated if containing
+* TYPEBIND invalid.
+* Note that only this function need knowledge of the
+* module's TYPE_DATA -- which was cached at Init time.
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR DYN_BINDNAME_TABLE::BuildTable()
+{
+ UINT cMeth, cDataMember, cNestedType;
+ TIPERROR err;
+
+ DebAssert(m_ptdata != NULL, "null TYPE_DATA.");
+
+ // release the existing table (if any).
+ ReleaseTable();
+
+ // allocate hashtable
+ // (1) determine size of hashtable:
+
+ cMeth = m_ptdata->CMeth();
+ cDataMember = m_ptdata->CDataMember();
+ cNestedType = m_ptdata->CNestedType();
+
+ // allocate the table
+ IfErrRet(SetTableSize(cMeth + cDataMember + cNestedType));
+
+ // (2) Now iterate over member lists and build BIND_DESCs
+ // and enter them into hashtable.
+ // - data members, bases, functions
+ //
+ IfErrGo(TraverseDefnList(m_ptdata->HfdefnFirstMeth()));
+ IfErrGo(TraverseDefnList(m_ptdata->HdefnFirstDataMbrNestedType()));
+
+ return TIPERR_None;
+
+Error:
+ ReleaseTable();
+ return err;
+}
+
+
+/***
+*PUBLIC DYN_BINDNAME_TABLE::ReleaseTable()
+*Purpose:
+* Invalidates the binding table.
+*
+*Entry:
+* None.
+*
+*Exit:
+* BOOL
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+VOID DYN_BINDNAME_TABLE::ReleaseTable()
+{
+ UINT cbSizeTable;
+
+ DebAssert(m_pblkmgr != NULL, "Invalid BLK_MGR.");
+
+ if (IsValid()) {
+ DebAssert(m_cBuckets != ~0, "bad bindtable.");
+
+ // free the table
+ cbSizeTable = m_cBuckets * sizeof(sHDEFN);
+ m_pblkmgr->FreeChunk(m_hchunkBucketTbl, cbSizeTable);
+ m_hchunkBucketTbl = HCHUNK_Nil;
+ }
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC DYN_BINDNAME_TABLE::AddHdefn
+*Purpose:
+* Add the given Hdefn to the table.
+*
+*Implementation Notes:
+* Note: Because we allocate the table twice the number of
+* entries in it, it should never be full. Thus we assert.
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+void DYN_BINDNAME_TABLE::AddHdefn(HDEFN hdefn)
+{
+ DEFN *qdefn;
+ sHDEFN *rqhdefn;
+ UINT iBucket, iFirstBucket;
+
+ DebAssert(IsValid(), "Table should be valid.");
+
+ // Dereference the hdefn so we can get the hlnam
+ qdefn = QdefnOfHdefn(hdefn);
+ rqhdefn = Rqhdefn();
+ iFirstBucket = GetBucketOfHlnam(qdefn->Hlnam());
+
+ BOOL fDone = FALSE;
+ for (iBucket = iFirstBucket;
+ !fDone;
+ fDone = (iBucket = (iBucket + 1) % m_cBuckets) == iFirstBucket) {
+
+ if (rqhdefn[iBucket] == (sHDEFN)HDEFN_Nil) {
+ rqhdefn[iBucket] = (sHDEFN)hdefn;
+ return;
+ }
+ }
+
+ DebHalt("Table full.");
+}
+
+
+/***
+*PUBLIC DYN_BINDNAME_TABLE::Read
+*Purpose:
+* Read serialized image of BINDNAME_TABLE.
+*
+*Implementation Notes:
+* Serialized format:
+*
+*Entry:
+* pstrm - STREAM to read image from (IN).
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR DYN_BINDNAME_TABLE::Read(STREAM *pstrm)
+{
+ USHORT ushort;
+ TIPERROR err;
+
+ DebAssert(pstrm != NULL, "bad param.");
+
+ // BLK_MGR was already deseralized by TYPE_DATA.
+
+ // Deserialize BINDNAME_TABLE meta-info.
+ IfErrRet(pstrm->ReadUShort(&ushort));
+ m_cBuckets = ushort;
+
+ IfErrRet(pstrm->ReadUShort(&ushort));
+
+ m_hchunkBucketTbl = ushort;
+
+#if HP_BIGENDIAN
+ // now that the above data members are read, we can swap the BIND_DESCs
+ SwapBindDescs();
+#endif //HP_BIGENDIAN
+
+ return TIPERR_None;
+}
+
+
+/***
+*PUBLIC DYN_BINDNAME_TABLE::Write
+*Purpose:
+* Write image of BINDNAME_TABLE.
+*
+*Implementation Notes:
+* Serialized format:
+* cBuckets
+* hchunkBucketTbl
+*
+*Entry:
+* pstrm - STREAM to write image to (IN).
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR DYN_BINDNAME_TABLE::Write(STREAM *pstrm)
+{
+ TIPERROR err;
+
+ DebAssert(pstrm != NULL, "bad param.");
+
+ // BLK_MGR was already serialized by TYPE_DATA.
+
+ // Then serialize BINDNAME_TABLE meta-info.
+ IfErrRet(pstrm->WriteUShort((USHORT)m_cBuckets));
+ IfErrRet(pstrm->WriteUShort((USHORT)m_hchunkBucketTbl));
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+#if HP_BIGENDIAN
+/***
+*PUBLIC DYN_BINDNAME_TABLE::SwapBindDescs
+*Purpose:
+* Swap the bytes in the binding tables
+*
+*Implementation Notes:
+* sHDEFNs are just USHORTs, so treat the table as one short array.
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+void DYN_BINDNAME_TABLE::SwapBindDescs() const
+{
+ if (IsValid()) {
+ SwapShortArray((VOID *)Rqhdefn(), m_cBuckets);
+ }
+}
+#endif // HP_BIGENDIAN
+
+
+/***
+*PROTECTED DYN_BINDNAME_TABLE::FindIndexOfHlnam
+*Purpose:
+* Find the instance of the hlnam.
+*
+*Implementation Notes:
+*
+*Entry:
+* hlnam - The name to find.
+* iStartBucket - Where to start looking from.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+UINT DYN_BINDNAME_TABLE::FindIndexOfHlnam(HLNAM hlnam,
+ UINT iStartBucket) const
+{
+ sHDEFN *rqhdefn;
+ UINT iBucket;
+
+ // If the table is empty, won't find it
+ DebAssert(IsValid(), "Table should be valid.");
+
+ // If the starting bucket isn't valid, then the name
+ // can't be in this table...
+ //
+ if ((USHORT)iStartBucket == BIND_INVALID_INDEX) {
+ return BIND_INVALID_INDEX;
+ }
+
+ // Dereference the hdefn so we can get the hlnam
+ rqhdefn = Rqhdefn();
+
+ // Loop through the table, starting at the given
+ // index.
+ //
+ BOOL fDone = FALSE;
+ for (iBucket = iStartBucket;
+ !fDone;
+ fDone = (iBucket = (iBucket + 1) % m_cBuckets) == iStartBucket) {
+
+ // If the bucket is empty, our linear probe failed
+ // Note: this should be the ONLY way to fail to find a given name.
+ //
+ if (rqhdefn[iBucket] == (sHDEFN)HDEFN_Nil) {
+ return (UINT)BIND_INVALID_INDEX;
+ }
+
+ // Check to see if the names are the same
+ if (QdefnOfHdefn((HDEFN)rqhdefn[iBucket])->Hlnam() == hlnam) {
+ return iBucket;
+ }
+ }
+
+ DebHalt("should never reach here since table should never be full.");
+
+ // We should never reach this, but the compiler will
+ // complain if it isn't there.
+ //
+ return (UINT)BIND_INVALID_INDEX;
+}
+
+
+/***
+*PROTECTED DYN_BINDNAME_TABLE::TraverseDefnList - Traverse vars.
+*Purpose:
+* Builds hashtable by traversing over members.
+* Called to traverse both data members and functions.
+*
+*Implementation Notes:
+* Incrementally adds each member to list ensuring that for
+* each member:
+* - can't have vars and funcs of same name.
+* - can't have funcs of same arity.
+*
+*Entry:
+* hdefn Listhead of defnlist.
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR DYN_BINDNAME_TABLE::TraverseDefnList(HDEFN hdefn)
+{
+ DEFN *qdefn, *qdefnMatch;
+ HLNAM hlnam;
+ HVAR_DEFN hvdefn;
+ VAR_DEFN *qvdefn, *qvdefnInner;
+ FUNC_DEFN *qfdefnMatch;
+ HDEFN hdefnNext;
+ INVOKEKIND invokekind, invokekindMatch;
+ UINT cRecTypeDefn = 0;
+ UINT indexMatch;
+
+ // iterate over entire list of defns
+ while (hdefn != HDEFN_Nil) {
+ qdefn = QdefnOfHdefn(hdefn);
+
+ // cache next
+ hdefnNext = qdefn->HdefnNext();
+
+ // If this is a function which has been removed with
+ // conditional compilation, don't add it to the
+ // binding tables.
+ //
+
+ // Get the hlnam to search for
+ hlnam = qdefn->Hlnam();
+
+ // Phase 1 of verification.
+ // Search table for entries of the same name.
+ // Ensure that if there is a match check that
+ // there isn't an ambiguity error.
+ // The only things that can be overloaded are properties.
+ // So...
+ //
+ indexMatch = IndexFirstOfHlnam(hlnam);
+ while (indexMatch != BIND_INVALID_INDEX) {
+ qdefnMatch = QdefnOfHdefn(HdefnOfIndex(indexMatch));
+
+ if (qdefnMatch->IsRecTypeDefn()) {
+ if (qdefn->IsRecTypeDefn()) {
+ // error: can't overload types.
+ goto Error;
+ }
+ }
+ else if (qdefnMatch->IsVarDefn()) {
+ if (!qdefn->IsRecTypeDefn()) {
+ // error: can't overload variables at all
+ // except with records.
+ //
+ goto Error;
+ }
+ }
+ else if (qdefnMatch->IsFuncDefn()) {
+ if (!qdefn->IsRecTypeDefn()) {
+ if (!qdefn->IsFuncDefn()) {
+ // error: can't overload functions except with
+ // suitable properties.
+ //
+ goto Error;
+ }
+ // So we've found a function, which means we
+ // can downcast the qdefn we're examining...
+ // Can overload functions iff safe propertyhood is observed.
+ //
+ qfdefnMatch = (FUNC_DEFN *)qdefnMatch;
+ invokekindMatch = qfdefnMatch->InvokeKind();
+ invokekind = ((FUNC_DEFN *)qdefn)->InvokeKind();
+ if ((invokekind == invokekindMatch) ||
+ (invokekind == INVOKE_FUNC) ||
+ (invokekindMatch == INVOKE_FUNC)) {
+ // error: can't have a func and func/prop of same name
+ // nor two props of same kind.
+ //
+ goto Error;
+ }
+ } // if !isrectypedefn
+ }
+ else {
+ DebHalt("bad match.");
+ } // if
+
+ // Get next
+ indexMatch = IndexNextOfHlnam(hlnam, indexMatch);
+ } // while same name
+
+ // Phase 2 of verification.
+ if (qdefn->IsRecTypeDefn()) {
+ // Check nested types for validity.
+ DebAssert(m_ptdata->Pdtroot()->IsBasic(),
+ "Embedded types in Basic modules only");
+
+ // ensure that members of this nested type
+ // all have unique names
+ // CONSIDER: this is an n-squared search, should improve speed
+ //
+ hvdefn = ((RECTYPE_DEFN *) qdefn)->HvdefnFirstMember();
+ while (hvdefn != HVARDEFN_Nil) {
+ qvdefn = m_ptdata->QvdefnOfHvdefn(hvdefn);
+ hlnam = qvdefn->Hlnam();
+ qvdefnInner = qvdefn;
+ while (qvdefnInner->HdefnNext() != HDEFN_Nil) {
+ qvdefnInner =
+ m_ptdata->QvdefnOfHvdefn((HVAR_DEFN)qvdefnInner->HdefnNext());
+ if (qvdefnInner->Hlnam() == hlnam) {
+ return TIPERR_AmbiguousName;
+ } /* if */
+ } /* while */
+ hvdefn = (HVAR_DEFN) qvdefn->HdefnNext();
+ } /* while */
+
+ cRecTypeDefn++;
+ }
+ else {
+ DebAssert(qdefn->IsVarDefn() || qdefn->IsFuncDefn(),
+ "Unexpected Defnkind");
+ } /* if rectypedefen */
+
+ // Add the defn we found to the table.
+ AddHdefn(hdefn);
+
+ // get next from cached handle.
+ hdefn = hdefnNext;
+ } // end of while
+ return TIPERR_None;
+
+Error:
+ return TIPERR_AmbiguousName;
+}
+
+
+/***
+*DYN_BINDNAME_TABLE::SetTableSize
+*Purpose:
+* Set and allocate the bindname table
+*
+*Implementation Notes:
+* Free any existing table, alloc a new table and set
+* all of its entries to HCHUNK_Nil.
+* Note we set the table size to double (DYN_BIND_SIZE_FACTOR cEntries
+* since we
+* want to improve linear probing performance and also
+* to ensure that the table can never be completely full.
+*
+*Entry:
+* cEntries - The number of entries into this table.
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR DYN_BINDNAME_TABLE::SetTableSize(UINT cEntries)
+{
+ UINT iBucket;
+ sHDEFN *rgTable;
+ HCHUNK hchunk = HCHUNK_Nil;
+
+ TIPERROR err = TIPERR_None;
+
+ // Free the current table, if any
+ if (IsValid()) {
+ m_pblkmgr->FreeChunk(m_hchunkBucketTbl, m_cBuckets * sizeof(sHDEFN));
+ m_hchunkBucketTbl = HCHUNK_Nil;
+ }
+
+ // Set the new table size
+ // CONSIDER: 27-Aug-93 andrewso
+ // Set the # of buckets to the nearest power of two. Would
+ // require saving cEntries for AddHbindescIncTable and
+ // RemoveHlnam, but should considerable speed up the mods.
+ //
+ // The +1 ensures that we always round up.
+ //
+ // NOTE: we really want to multiply by 1.5 (DYN_BIND_SIZE_FACTOR), but
+ // that drags in the floating point package, which we don't want. So do
+ // the equivelent integer multiply instead.
+ //
+ // #define DYN_BIND_SIZE_FACTOR 1.5
+ m_cBuckets = (cEntries * 3) / 2 + 1;
+
+ // Allocate a new table.
+ IfErrRet(m_pblkmgr->AllocChunk(&hchunk,
+ m_cBuckets * sizeof(sHDEFN)));
+ m_hchunkBucketTbl = hchunk;
+
+ // Initialize all entries with HDEFN_Nil
+ rgTable = Rqhdefn();
+
+ for (iBucket = 0; iBucket < m_cBuckets; iBucket++) {
+ rgTable[iBucket] = (sHDEFN)HDEFN_Nil;
+ }
+
+ return TIPERR_None;
+}
+
+#if ID_DEBUG
+
+// Helper function to determine if given hdefn is in
+// TYPE_DATA list.
+//
+BOOL DebIsHdefnInList(TYPE_DATA *ptdata, HDEFN hdefn, HDEFN hdefnFirst)
+{
+ HDEFN hdefnCur = hdefnFirst;
+
+ while (hdefnCur != HDEFN_Nil) {
+ if (hdefnCur == hdefn) {
+ // found it...
+ return TRUE;
+ }
+ hdefnCur = ptdata->QdefnOfHdefn(hdefnCur)->HdefnNext();
+ }
+ // didn't find it...
+ return FALSE;
+}
+
+
+
+VOID DYN_BINDNAME_TABLE::DebCheckState(UINT uLevel) const
+{
+ sHDEFN *rqhdefn;
+ DEFN *qdefn;
+ UINT iBucket, cDataMember = 0, cNestedType = 0, cMeth = 0;
+
+ // check blkmgr
+ m_pblkmgr->DebCheckState(uLevel);
+
+
+
+ // Walk table and ensure that each entry is in appropriate
+ // TYPE_DATA list.
+ //
+ if (m_cBuckets != 0 && m_cBuckets != BIND_INVALID_INDEX) {
+ rqhdefn = Rqhdefn();
+
+ for (iBucket = 0; iBucket < m_cBuckets; iBucket++) {
+ if (rqhdefn[iBucket] != (sHDEFN)HDEFN_Nil) {
+ qdefn = m_ptdata->QdefnOfHdefn(rqhdefn[iBucket]);
+ switch (qdefn->Defnkind()) {
+ case DK_VarDefn:
+ case DK_MbrVarDefn:
+ // Note: base members should not be in binding table.
+ DebAssert(!m_ptdata->QvdefnOfHvdefn(rqhdefn[iBucket])->IsBase(),
+ "whoops! base members shouldn't be in list.");
+ cDataMember++;
+ DebAssert(DebIsHdefnInList(
+ m_ptdata,
+ rqhdefn[iBucket],
+ m_ptdata->HdefnFirstDataMbrNestedType()),
+ "should be in list.");
+ break;
+ case DK_RecTypeDefn:
+ cNestedType++;
+ DebAssert(DebIsHdefnInList(
+ m_ptdata,
+ rqhdefn[iBucket],
+ m_ptdata->HdefnFirstDataMbrNestedType()),
+ "should be in list.");
+ break;
+ case DK_FuncDefn:
+ case DK_VirtualFuncDefn:
+ cMeth++;
+ DebAssert(DebIsHdefnInList(
+ m_ptdata,
+ rqhdefn[iBucket],
+ m_ptdata->HfdefnFirstMeth()),
+ "should be in list.");
+ break;
+ default:
+ DebHalt("DebCheckState: bad defnkind.");
+ } // switch
+ } // if
+ } // for
+ DebAssert(cMeth == m_ptdata->CAvailMeth()
+ || cMeth == m_ptdata->CMeth(), "bad func count.");
+ DebAssert(cNestedType == m_ptdata->CNestedType(), "bad nested count.");
+ DebAssert(cDataMember == m_ptdata->CDataMember(), "bad var count.");
+ }
+}
+
+
+VOID DYN_BINDNAME_TABLE::DebShowState(UINT uLevel) const
+{
+ UINT iBucket;
+ sHDEFN *rqhdefn;
+ HLNAM hlnam;
+ XCHAR xsz[256];
+
+ DebPrintf("*** DYN_BINDNAME_TABLE ***\n");
+ DebPrintf("buckets: %u\n", m_cBuckets);
+
+ if (uLevel > 0 && m_cBuckets != 0) {
+ rqhdefn = Rqhdefn();
+
+ for (iBucket = 0; iBucket < m_cBuckets; iBucket++) {
+ if (rqhdefn[iBucket] != (sHDEFN)HDEFN_Nil) {
+ hlnam = QdefnOfHdefn(rqhdefn[iBucket])->Hlnam();
+ if (m_pnammgr->StrOfHlnam(hlnam, xsz, 256) == TIPERR_None) {
+ DebPrintf(" hlnam: %s (%X)\n", xsz, hlnam);
+ }
+ else {
+ DebPrintf(" hlnam: <too long> (%X)\n", hlnam);
+ }
+ }
+ else {
+ DebPrintf(" hlnam: 0xFFFF\n");
+ }
+ }
+ }
+}
+
+#endif // ID_DEBUG
diff --git a/private/oleauto/src/typelib/dbindtbl.hxx b/private/oleauto/src/typelib/dbindtbl.hxx
new file mode 100644
index 000000000..160cc5625
--- /dev/null
+++ b/private/oleauto/src/typelib/dbindtbl.hxx
@@ -0,0 +1,249 @@
+/***
+*dbindtbl.hxx - DYN_BINDNAME_TABLE header file
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Manages module-level hashtable of names for binding.
+* Reuses BINDNAME_TABLE fucntionalkty for hashtable
+* management and provides definition of BuildTable().
+*
+*Revision History:
+*
+* 17-Jun-92 ilanc: created.
+* 02-Jul-92 w-peterh: rectypebind support
+* 30-Jul-92 w-peterh: removed function overloading
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#ifndef DYN_BINDNAME_TABLE_HXX_INCLUDED
+#define DYN_BINDNAME_TABLE_HXX_INCLUDED
+
+#include "stream.hxx"
+#include "defn.hxx" // for DEFN binding structs.
+#include "tdata.hxx"
+
+
+class DYN_TYPEBIND;
+class DYN_TYPEROOT;
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szDBINDTBL_HXX)
+#define SZ_FILE_NAME g_szDBINDTBL_HXX
+#endif
+
+
+#define BIND_INVALID_INDEX ((USHORT)~0)
+#define DYN_BIND_SIZE_FACTOR 1.5
+
+/***
+*class DYN_BINDNAME_TABLE - 'dbindtbl': BindNameTable implementation.
+*Purpose:
+* BindNameTable impl.
+*
+***********************************************************************/
+
+class DYN_BINDNAME_TABLE
+{
+public:
+ DYN_BINDNAME_TABLE();
+ virtual ~DYN_BINDNAME_TABLE();
+
+ nonvirt TIPERROR Init(BLK_MGR *pblkmgr, DYN_TYPEROOT *pdtroot);
+
+ nonvirt TIPERROR BuildTable();
+ nonvirt BOOL IsValid() const;
+ nonvirt VOID ReleaseTable();
+
+ nonvirt void AddHdefn(HDEFN hdefn);
+ nonvirt UINT IndexFirstOfHlnam(HLNAM hlnam) const;
+ nonvirt UINT IndexNextOfHlnam(HLNAM hlnam, UINT iPrevBucket) const;
+
+ nonvirt HDEFN HdefnOfIndex(UINT index) const;
+ nonvirt DEFN *QdefnOfHdefn(HDEFN hdefn, UINT oChunk = 0) const;
+
+ nonvirt TIPERROR Read(STREAM *pstrm);
+ nonvirt TIPERROR Write(STREAM *pstrm);
+#if HP_BIGENDIAN
+ VOID SwapBindDescs() const;
+#endif
+
+#if ID_DEBUG
+ nonvirt VOID DebCheckState(UINT uLevel) const;
+ nonvirt VOID DebShowState(UINT uLevel) const;
+#else //!ID_DEBUG
+ nonvirt VOID DebCheckState(UINT uLevel) const {}
+ nonvirt VOID DebShowState(UINT uLevel) const {}
+#endif //!ID_DEBUG
+
+protected:
+
+ UINT GetBucketOfHlnam(HLNAM hlnam) const;
+ UINT FindIndexOfHlnam(HLNAM hlnam, UINT iStartBucket) const;
+
+ TIPERROR TraverseDefnList(HDEFN hdefnCur);
+ TIPERROR SetTableSize(UINT cEntries);
+
+ DYN_TYPEBIND *Pdtbind() const;
+ sHDEFN *Rqhdefn() const;
+
+ // protected data members
+ BLK_MGR *m_pblkmgr; // block manager that holds the table
+ HCHUNK m_hchunkBucketTbl; // hchunk of the bucket table:
+
+
+ UINT m_cBuckets; // The number of "entries" that are
+ // currently in this table.
+
+ TYPE_DATA *m_ptdata; // cached TYPE_DATA
+ NAMMGR *m_pnammgr; // cached NAMMGR
+
+#ifdef DYN_BINDNAME_TABLE_VTABLE
+#pragma VTABLE_EXPORT
+#endif
+};
+
+
+/***
+*PUBLIC DYN_BINDNAME_TABLE::IsValid() - Is table valid?
+*Purpose:
+* Reports if table valid.
+*
+*Entry:
+* None.
+*
+*Exit:
+* BOOL
+***********************************************************************/
+
+inline BOOL DYN_BINDNAME_TABLE::IsValid() const
+{
+ return (BOOL)(m_hchunkBucketTbl != HCHUNK_Nil);
+}
+
+
+/***
+*PUBLIC DYN_BINDNAME_TABLE::IndexFirstOfHlnam
+*Purpose:
+* Get the first HDEFN of this HLNAM
+*
+*Implementation Notes:
+*
+*Entry:
+* hlnam - the name to look for
+*
+*Exit:
+* Returns the index to the HDEFN
+*
+***********************************************************************/
+
+inline UINT DYN_BINDNAME_TABLE::IndexFirstOfHlnam(HLNAM hlnam) const
+{
+ return FindIndexOfHlnam(hlnam, GetBucketOfHlnam(hlnam));
+}
+
+
+/***
+*PUBLIC DYN_BINDNAME_TABLE::IndexNextOfHlnam
+*Purpose:
+* Get the next HDEFN of this HLNAM
+*
+*Implementation Notes:
+*
+*Entry:
+* hlnam - the name to look for
+* iPrevBucket - the bucket we want to start searching from
+*
+*Exit:
+* Returns the index to the HDEFN
+*
+***********************************************************************/
+inline UINT DYN_BINDNAME_TABLE::IndexNextOfHlnam(HLNAM hlnam,
+ UINT iPrevBucket) const
+{
+ UINT iStartBucket;
+
+ if (iPrevBucket == BIND_INVALID_INDEX) {
+ return BIND_INVALID_INDEX;
+ }
+
+ iStartBucket = (iPrevBucket + 1) % m_cBuckets;
+ return FindIndexOfHlnam(hlnam, iStartBucket);
+}
+
+
+/***
+*PUBLIC DYN_BINDNAME_TABLE::HdefnOfIndex
+*Purpose:
+* Return the Hdefn of a given index
+*
+*Implementation Notes:
+*
+*Entry:
+* index - the index to get the hdefn of.
+*
+*Exit:
+* Returns a pointer to the DEFN.
+*
+***********************************************************************/
+
+inline HDEFN DYN_BINDNAME_TABLE::HdefnOfIndex(UINT index) const
+{
+ if ((USHORT)index == BIND_INVALID_INDEX) {
+ return HDEFN_Nil;
+ }
+
+ DebAssert(index < m_cBuckets, "Invalid index");
+
+ return Rqhdefn()[index];
+}
+
+/***
+*PUBLIC DYN_BINDNAME_TABLE::QdefnOfHdefn - Address of a DEFN
+*Purpose:
+* Converts a handle to a DEFN to a pointer.
+*
+*Implementation Notes:
+*
+*Entry:
+* hdefn - Handle to a DEFN.
+* oChunk - Optional offset within chunk.
+*
+*Exit:
+* Returns a pointer to the DEFN.
+*
+***********************************************************************/
+
+inline DEFN* DYN_BINDNAME_TABLE::QdefnOfHdefn(HDEFN hdefn, UINT oChunk) const
+{
+ return (DEFN *)m_pblkmgr->QtrOfHandle(hdefn, oChunk);
+}
+
+
+/***
+*PROTECTED DYN_BINDNAME_TABLE::Rqhdefn()
+*Purpose:
+* Returns a pointer to the hdefn table.
+*
+*Entry:
+* None.
+*
+*Exit:
+* Returns a pointer to the hdefn table. The pointer is only valid
+* for a short time.
+*
+***********************************************************************/
+
+inline sHDEFN *DYN_BINDNAME_TABLE::Rqhdefn() const
+{
+ DebAssert(IsValid(), "Bad table.");
+
+ return (sHDEFN *)m_pblkmgr->QtrOfHandle(m_hchunkBucketTbl);
+}
+
+
+#endif // ! DYN_BINDNAME_TABLE_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/dblkmgr.hxx b/private/oleauto/src/typelib/dblkmgr.hxx
new file mode 100644
index 000000000..46bddac67
--- /dev/null
+++ b/private/oleauto/src/typelib/dblkmgr.hxx
@@ -0,0 +1,690 @@
+/***
+*dblkmgr.hxx - Dynamic Block Manager
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* The dynamic block manager provides memory management services for a
+* a contiguous block of memory allocated from the compile-time
+* heap. It manages moveable and reallocatable sub-blocks ("chunks")
+* and supports compaction.
+*
+*Revision History:
+*
+* 24-Mar-92 ilanc: Created.
+* 07-Apr-92 ilanc: Cleaned up order of inline funcs for cfront.
+* 17-Dec-92 w-peterh: reordered data members
+*
+*****************************************************************************/
+
+#ifndef DBLKMGR_HXX_INCLUDED
+#define DBLKMGR_HXX_INCLUDED
+
+#include <limits.h>
+#include "sheapmgr.hxx"
+#include "blkmgr.hxx"
+
+class STREAM; // #include "stream.hxx"
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szDBLKMGR_HXX)
+#define SZ_FILE_NAME g_szDBLKMGR_HXX
+#endif
+
+
+// This constant is used for the initial size of a handle table.
+//
+extern const UINT DBM_cbSizeHandleTableInitial;
+
+// HANDLETABLE_ENTRY - te
+// these describe the entries in the handle table.
+// Guess what? they are just HCHUNKs.
+// For internal use only.
+//
+typedef HCHUNK TE;
+typedef sHCHUNK sTE;
+
+// Handle to a HANDLE_TABLE_ENTRY - hte
+// For external use.
+//
+typedef UINT HTE;
+typedef USHORT sHTE;
+
+#if OE_RISC & !HP_I386
+#define DBLKMGR_HEADER_SIZE 8
+// MIPS and ALPHA must be 8 byte aligned
+#else
+#define DBLKMGR_HEADER_SIZE sizeof(USHORT)
+// Present value of DBLKMGE_HEADER_SIZE
+#endif
+
+/***
+*class DYN_BLK_MGR - 'dblkmgr': Dynamic Block manager
+*Purpose:
+* The class implements the dynamic block manager.
+*
+***********************************************************************/
+
+class DYN_BLK_MGR
+{
+ friend VOID ValidateChunks(DYN_BLK_MGR *pdblkmgr);
+
+public:
+ DYN_BLK_MGR();
+ ~DYN_BLK_MGR();
+
+ static TIPERROR CreateStandalone(DYN_BLK_MGR **ppdbm);
+ static void FreeStandalone(DYN_BLK_MGR *pdbm);
+
+ nonvirt TIPERROR Init(SHEAP_MGR *psheapmgr, BOOL fCoalesce = TRUE);
+
+ nonvirt TIPERROR AllocChunk(HTE *phte, UINT cbSizeChunk);
+ nonvirt TIPERROR Read(STREAM *pstrm);
+ nonvirt TIPERROR Write(STREAM *pstrm);
+ nonvirt BYTE *QtrOfHandle(HTE hte) const;
+ nonvirt VOID FreeChunk(HTE hte);
+ nonvirt VOID Free();
+ nonvirt BOOL IsValid() const;
+
+ // Locking methods
+ nonvirt VOID Lock();
+ nonvirt VOID Unlock();
+ nonvirt BOOL IsLocked() const;
+
+ nonvirt VOID Lock(HTE hte);
+ nonvirt VOID Unlock(HTE hte);
+ nonvirt BOOL IsLocked(HTE hte) const;
+
+ // Is empty method
+ nonvirt BOOL IsEmpty() const;
+
+ // *** NEW ***
+ nonvirt UINT CbSize(HTE hte);
+ nonvirt TIPERROR Compact();
+ nonvirt TIPERROR ReallocChunk(HTE hte, UINT cbSizeChunkNew);
+ nonvirt UINT CteTable() const;
+ nonvirt UINT GetSize() const;
+
+ // Debug/test methods
+#if ID_DEBUG
+ nonvirt VOID DebShowState(UINT uLevel) const;
+ nonvirt VOID DebCheckState(UINT uLevel) const;
+ nonvirt VOID DebCheckHandle(HTE hte) const;
+#else
+ nonvirt VOID DebShowState(UINT uLevel) const {}
+ nonvirt VOID DebCheckState(UINT uLevel) const {}
+ nonvirt VOID DebCheckHandle(HTE hte) const {}
+#endif
+
+#if ID_TEST
+ nonvirt BOOL IsValidHte(HTE hte) const;
+#endif
+
+
+private:
+ BLK_MGR m_blkmgr;
+ BLK_DESC m_bdHandleTable;
+
+ // handle table related stuff
+ nonvirt TIPERROR GetNewHandleFromTable(HTE *phte);
+ nonvirt VOID InitHandleTable(HTE hteFreeTableEntry);
+ nonvirt VOID InvalidateHandle(sTE *pte);
+ nonvirt VOID UpdateHandleTable(HTE hte, HCHUNK hchunkMemBlock);
+ nonvirt VOID RemoveHandleFromTable(HTE hte);
+ nonvirt HCHUNK HchunkOfHandleTableEntry(HTE hte) const;
+ nonvirt BOOL IsValidHandleTableEntry(TE te) const;
+ nonvirt UINT IndexOfHte(HTE hte) const;
+ nonvirt HTE HteOfIndex(UINT iHte) const;
+ nonvirt UINT CbSizeChunk(TE teTable) const;
+ nonvirt UINT CbSizeOldChunk(TE teTable) const;
+ nonvirt sTE *RgteHandleTable() const;
+
+#ifdef DBLKMGR_VTABLE
+#pragma VTABLE_EXPORT
+#endif
+};
+
+
+// inline methods
+//
+
+
+
+/***
+*PUBLIC DYN_BLK_MGR::~DYN_BLK_MGR - destructor
+*Purpose:
+* Destroys a dynamic block manager.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+inline DYN_BLK_MGR::~DYN_BLK_MGR()
+{
+ // Do nothing, block will vanish when the heap is destructed.
+}
+
+
+/***
+*PUBLIC DYN_BLK_MGR::IsValidHandleTableEntry - is table entry valid?
+*Purpose:
+* Is table entry valid?
+*
+*Implementation Notes:
+*
+*Entry:
+* te - Handle table entry
+*
+*Exit:
+*
+***********************************************************************/
+
+inline BOOL DYN_BLK_MGR::IsValidHandleTableEntry(TE teTable) const
+{
+ return (teTable & 1) == 0;
+}
+
+
+/***
+*PRIVATE DYN_BLK_MGR::InvalidateHandle - Invalidates a handle.
+*Purpose:
+* Invalidates a handle.
+*
+*Implementation Notes"
+* Invalidates by simply setting low bit.
+*
+*Entry:
+* pte ptr to table entry to invalidate (IN/OUT)
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID DYN_BLK_MGR::InvalidateHandle(sTE *pte)
+{
+ DebAssert(pte != NULL, "bad param.");
+
+ *pte |= 1;
+
+ DebAssert(IsValidHandleTableEntry(*pte) == FALSE,
+ "handle table entry should be invalid.");
+}
+
+
+/***
+*PUBLIC DYN_BLK_MGR::IsValid - Tests if dynamic block manager in valid state.
+*Purpose:
+* Tests if dynamic block manager is valid -- i.e. has been allocated
+* a block. Defers to blkdesc member.
+*
+*Entry:
+* None.
+*
+*Exit:
+* Returns TRUE if valid, else FALSE.
+*
+***********************************************************************/
+
+inline BOOL DYN_BLK_MGR::IsValid() const
+{
+ return m_bdHandleTable.IsValid() && m_blkmgr.IsValid();
+}
+
+
+/***
+*PUBLIC DYN_BLK_MGR::RgteHandleTable - gets handle table as array.
+*Purpose:
+* Gets handle table as array.
+*
+*Entry:
+* None.
+*
+*Exit:
+* Returns ptr to start of handle table.
+*
+***********************************************************************/
+
+inline sTE *DYN_BLK_MGR::RgteHandleTable() const
+{
+ return (sTE *)m_bdHandleTable.QtrOfBlock();
+}
+
+
+/***
+*PRIVATE DYN_BLK_MGR::IndexOfHte - maps handle to index.
+*Purpose:
+* Maps handle of table entry to index into "array".
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+inline UINT DYN_BLK_MGR::IndexOfHte(HTE hteTable) const
+{
+ return hteTable / sizeof(sHCHUNK);
+}
+
+
+/***
+*PRIVATE DYN_BLK_MGR::HchunkOfHandleTableEntry - get hchunk from handle.
+*Purpose:
+* get hchunk from external handle.
+*
+*Implementation Notes:
+* Assumes param is offset into handle table.
+*
+*Entry:
+* hte - handle (offset) into handle table.
+*
+*Exit:
+* Returns hchunk of internal mem block.
+* m_blkmgr.QtrOfHandle() of this will point to size field of chunk.
+*
+*Errors:
+*
+***********************************************************************/
+
+inline HCHUNK DYN_BLK_MGR::HchunkOfHandleTableEntry(HTE hte) const
+{
+ return (HCHUNK)RgteHandleTable()[IndexOfHte(hte)];
+}
+
+
+/***
+*PUBLIC DYN_BLK_MGR::QtrOfHandle - Converts handle to pointer.
+*Purpose:
+* Converts a chunk handle into a pointer. A Nil handle is
+* *NOT* converted to a NULL pointer (asserts).
+*
+*Implementation notes:
+* In a segmented architecture:
+* We assume that the handle table's memblock and the blkmgr's
+* memblock are contiguous and thus we assert this accordingly
+* at initialization time.
+*
+* Thus we can simply get the handle table's ptr and then add
+* in the table's size + the contents of the table entry
+* to produce the ptr.
+*
+* In non-segmented archs:
+* We fetch the HCHUNK from the handle table and then
+* defer to the BLK_MGR for the ptr.
+*
+* Note in either case we add an extra DBLKMGR_HEADER_SIZE
+* to skip over the chunk size.
+*
+*Entry:
+* hte - Handle to a chunk.
+*
+*Exit:
+* Returns a pointer to that chunk.
+*
+***********************************************************************/
+
+inline BYTE *DYN_BLK_MGR::QtrOfHandle(HTE hte) const
+{
+ DebAssert(hte != HCHUNK_Nil, "DYN_BLK_MGR::QtrOfHandle: Nil handle.");
+
+ DebAssert(IsValid(), "DYN_BLK_MGR::QtrOfHandle: invalid block.");
+
+ DebAssert((UINT)hte < m_bdHandleTable.CbSize(),
+ "DYN_BLK_MGR::QtrOfHandle: handle out of bounds.");
+
+ DebAssert(IsValidHandleTableEntry((TE)HchunkOfHandleTableEntry(hte)),
+ "table entry should be valid.");
+
+ // If we're in debug mode we always do the
+ // double indirection becuase of the extra shift bytes.
+ // CONSIDER: we're exercising different code in debug vs.
+ // release versions -- maybe we should consolidate the two.
+ //
+#if ID_DEBUG || !(OE_SEGMENTED || OE_MACNATIVE)
+ // do the vanilla double dereference thing...
+ HCHUNK hchunkMemBlock = HchunkOfHandleTableEntry(hte);
+ return m_blkmgr.QtrOfHandle(hchunkMemBlock) + DBLKMGR_HEADER_SIZE;
+#else
+ sTE *pteHandleTable;
+
+ // get handle table array.
+ pteHandleTable = RgteHandleTable();
+
+ return (BYTE *)pteHandleTable +
+ m_bdHandleTable.CbSize() +
+ *((sHTE *)(((BYTE *)pteHandleTable) + hte)) +
+ DBLKMGR_HEADER_SIZE;
+#endif
+}
+
+
+/***
+*PUBLIC DYN_BLK_MGR::CteTable - handle table cardinality.
+*Purpose:
+* Handle table cardinality.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+inline UINT DYN_BLK_MGR::CteTable() const
+{
+ // since sizeof(sHCHUNK) is a power of two, optimizer
+ // will just shift right here (hopefully).
+ //
+ return m_bdHandleTable.CbSize() / sizeof(sHCHUNK);
+}
+
+
+/***
+*PRIVATE DYN_BLK_MGR::CbSizeChunk - chunk size given table entry.
+*Purpose:
+* Returns chunk size given handle.
+*
+*Implementation Notes:
+* Since the chunk size is stored in the first two bytes of
+* of the chunk we simply deref the table entry
+* (i.e. interpret as an HCHUNK), and read the USHORT there.
+* NOTE: can't use during compaction -- use CbSizeOldChunk.
+*
+*Entry:
+* teTable - entry in handle table (IN).
+*
+*Exit:
+* UINT (chunk size)
+***********************************************************************/
+
+inline UINT DYN_BLK_MGR::CbSizeChunk(TE teTable) const
+{
+ DebAssert((m_blkmgr.m_pbBlkCopy == NULL) &&
+ (m_blkmgr.m_pbBitmap == NULL),
+ "DYN_BLK_MGR::CbSizeChunk: compacting - use CbSizeOldChunk.");
+
+ DebAssert(IsValidHandleTableEntry(teTable), "bad handle.");
+
+ return *((USHORT *)m_blkmgr.QtrOfHandle((HCHUNK)teTable));
+}
+
+
+/***
+*PRIVATE DYN_BLK_MGR::CbSizeOldChunk - chunk size given table entry.
+*Purpose:
+* Returns chunk size given handle.
+*
+*Implementation Notes:
+* Since the chunk size is stored in the first two bytes of
+* of the chunk we simply deref the table entry
+* (i.e. interpret as an HCHUNK), and read the USHORT there.
+* NOTE: only can be used during compaction -- else use CbSizeChunk.
+*
+*Entry:
+* teTable - entry in handle table (IN).
+*
+*Exit:
+* UINT (chunk size)
+***********************************************************************/
+
+inline UINT DYN_BLK_MGR::CbSizeOldChunk(TE teTable) const
+{
+ DebAssert((m_blkmgr.m_pbBlkCopy != NULL) &&
+ (m_blkmgr.m_pbBitmap != NULL),
+ "DYN_BLK_MGR::CbSizeOldChunk: not compacting - use CbSizeChunk.");
+
+ DebAssert(IsValidHandleTableEntry(teTable), "bad handle.");
+
+ return *((USHORT *)m_blkmgr.QtrOfOldHandle((HCHUNK)teTable));
+}
+
+
+/***
+*PRIVATE DYN_BLK_MGR::HteOfIndex - maps index to handle.
+*Purpose:
+* Maps index to handle of table entry.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+inline UINT DYN_BLK_MGR::HteOfIndex(UINT iHte) const
+{
+ return iHte * sizeof(sHCHUNK);
+}
+
+
+/***
+*PUBLIC DYN_BLK_MGR::CbSize - size of chunk given table entry handle.
+*Purpose:
+* Size of chunk.
+*
+*Implementation Notes:
+* Defers to blkmgr.
+* NOTE: doesn't include size prefix.
+*
+*Entry:
+* hteTable - handle of chunk.
+*
+*Exit:
+*
+***********************************************************************/
+
+inline UINT DYN_BLK_MGR::CbSize(HTE hteTable)
+{
+ return CbSizeChunk((TE)HchunkOfHandleTableEntry(hteTable));
+}
+
+
+/***
+*PUBLIC DYN_BLK_MGR::Lock
+*Purpose:
+* Lock the block.
+*
+*Implementation Notes:
+* Defers to blkmgr.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID DYN_BLK_MGR::Lock()
+{
+ DebAssert(IsValid(), "DYN_BLK_MGR::Lock: Block invalid.");
+
+ m_blkmgr.Lock();
+}
+
+
+/***
+*PUBLIC DYN_BLK_MGR::Unlock
+*Purpose:
+* Unlock the block.
+*
+*Implementation Notes:
+* Defers to blkmgr.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID DYN_BLK_MGR::Unlock()
+{
+ DebAssert(IsValid(), "DYN_BLK_MGR::Unlock: Block invalid.");
+
+ m_blkmgr.Unlock();
+}
+
+
+/***
+*PUBLIC DYN_BLK_MGR::IsLocked
+*Purpose:
+* Tests if block is locked.
+*
+*Implementation Notes:
+* Defers to blkmgr.
+*
+*Entry:
+*
+*Exit:
+* TRUE if block is locked -- i.e. at least one lock.
+***********************************************************************/
+
+inline BOOL DYN_BLK_MGR::IsLocked() const
+{
+ DebAssert(IsValid(), "DYN_BLK_MGR::IsLocked: Block invalid.");
+
+ return m_blkmgr.IsLocked();
+}
+
+
+/***
+*PUBLIC DYN_BLK_MGR::Lock
+*Purpose:
+* Lock a chunk.
+*
+*Implementation Notes:
+* Defers to Lock/0. Locking a chunk locks its block.
+*
+*Entry:
+* hte Handle of chunk to lock.
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID DYN_BLK_MGR::Lock(HTE hte)
+{
+ DebAssert(IsValid(), "DYN_BLK_MGR::Lock: Block invalid.");
+ DebCheckHandle(hte);
+
+ Lock();
+}
+
+
+/***
+*PUBLIC DYN_BLK_MGR::Unlock
+*Purpose:
+* Unlock the block.
+*
+*Implementation Notes:
+* Defers to Unlock()/0. Unlocking a chunk, unlocks its block.
+*
+*Entry:
+* hte Handle of chunk to lock.
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID DYN_BLK_MGR::Unlock(HTE hte)
+{
+ DebAssert(IsValid(), "DYN_BLK_MGR::Unlock: Block invalid.");
+ DebCheckHandle(hte);
+
+ Unlock();
+}
+
+
+/***
+*PUBLIC DYN_BLK_MGR::IsLocked
+*Purpose:
+* Tests if chunk is locked.
+*
+*Implementation Notes:
+* Defers to IsLocked()/0
+*
+*Entry:
+* hte Handle of chunk to lock.
+*
+*Exit:
+* TRUE if chunk is locked -- i.e. at least one lock.
+***********************************************************************/
+
+inline BOOL DYN_BLK_MGR::IsLocked(HTE hte) const
+{
+ DebAssert(IsValid(), "DYN_BLK_MGR::IsLocked: Block invalid.");
+ DebCheckHandle(hte);
+
+ return IsLocked();
+}
+
+
+/***
+*PUBLIC DYN_BLK_MGR::IsEmpty
+*Purpose:
+* Tests if blk is empty.
+*
+*Implementation Notes:
+* Defers to contained blkmgr.
+*
+*Entry:
+*
+*Exit:
+* TRUE if block is empty -- i.e. no allocated chunks.
+***********************************************************************/
+
+inline BOOL DYN_BLK_MGR::IsEmpty() const
+{
+ // CONSIDER: at least assert that if empty then the handle table
+ // is empty, i.e. no allocated handles, or v.v.
+ //
+ return m_blkmgr.IsEmpty();
+}
+
+#if ID_TEST
+
+/***
+*PUBLIC DYN_BLK_MGR::IsValidHte - Is table entry valid given handle?
+*Purpose:
+* Is there a valid hte at the entry referenced by an hte?
+*
+*Implementation Notes:
+* ID_TEST only.
+*
+*Entry:
+* hte - handle to table entry
+*
+*Exit:
+*
+***********************************************************************/
+
+inline BOOL DYN_BLK_MGR::IsValidHte(HTE hte) const
+{
+ return IsValidHandleTableEntry(RgteHandleTable()[IndexOfHte(hte)]);
+}
+
+#endif
+
+
+#if ID_DEBUG
+
+// Checks if chunk handle is valid: even and within bounds.
+//
+inline VOID DYN_BLK_MGR::DebCheckHandle(HTE hte) const
+{
+ DebAssert(((hte & 1) == 0) &&
+ hte < m_bdHandleTable.CbSize(),
+ "bad handle.");
+}
+
+#endif // ID_DEBUG
+
+#endif // ! DBLKMGR_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/debug.h b/private/oleauto/src/typelib/debug.h
new file mode 100644
index 000000000..71fedaf9d
--- /dev/null
+++ b/private/oleauto/src/typelib/debug.h
@@ -0,0 +1,234 @@
+/***
+*debug.h - Silver debugging macros
+*
+* Copyright (C) 1990-1992, Microsoft Corporation
+*
+*Purpose:
+* This file defines debugging macros used by Silver source files.
+* Documentation for these macros and other useful coding techniques to
+* reduce buggage are in \silver\doc\codestd\debug.doc.
+*
+*Note:
+* All function prototypes in this file are defined in debug.cxx.
+*
+*Revision History:
+*
+* 13-May-92 w-peterh: File created.
+*
+*******************************************************************************/
+
+#ifndef DEBUG_H_INCLUDED
+#define DEBUG_H_INCLUDED
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#if ID_DEBUG
+
+// the file names passed to DebAssertFailed are all listed in dassert.c
+// so we don't get multiple copies of each string. Define macros so header
+// files can be included by either .C or .CPP files
+
+#ifdef __cplusplus
+#define ASSERTNAME(filename) extern "C" char FAR filename[];
+#else //__cplusplus
+#define ASSERTNAME(filename) extern char FAR filename[];
+#endif
+#endif //ID_DEBUG
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szDEBUG_H)
+#define SZ_FILE_NAME g_szDEBUG_H
+#endif
+
+// "debug" routines that can be used by test drivers.
+// Their implementations are in "debug.cxx". Test drivers
+// must link with "debug.obj" explicitly since the release version
+// of "misc.lib" doesn't build with "debug.obj".
+//
+// NOTE: DO NOT DEFINE NON-EMPTY INLINE FUNCTIONS HERE
+// (if you do, they'll end up being included in actual release
+// code).
+//
+#include <stdio.h>
+
+#if OE_WIN32
+BOOL DebParseAndInit(int *pargc, unsigned short ***pargv);
+#else
+BOOL DebParseAndInit(int *pargc, char ***pargv);
+#endif
+int DebPrintf(const char *szFmt, ...);
+int DebConsoleOutput(const char *szFmt, ...);
+//void PrintfIfNotNull(FILE *pfile, const char *szFmt, ...);
+char* DebGets(char *buffer);
+//char* DebFgets(char *buffer, FILE *pfile);
+
+BOOL FIsBadReadPtr(const void FAR* pv, UINT cb);
+BOOL FIsBadWritePtr(void FAR* pv, UINT cb);
+BOOL FIsBadCodePtr(void FAR* pv);
+BOOL FIsBadInterface(void FAR* pv, UINT cMethods);
+
+#if ID_DEBUG
+
+// make sure that this is surrounded by a #if ID_DEBUG.
+// g_fHeapChk is defined in debug.cxx
+extern BOOL g_fHeapChk;
+
+#if OE_WIN16
+#define DebHeapChk() \
+ { \
+ if ((g_fHeapChk) && (_fheapchk() != _HEAPOK)) \
+ DebExamineHeap(); \
+ };
+#elif OE_WIN32
+#define DebHeapChk()
+#else
+#define DebHeapChk() \
+ { \
+ if ((g_fHeapChk) && (_heapchk() != _HEAPOK)) \
+ DebExamineHeap(); \
+ };
+#endif
+
+
+VOID DebExamineHeap();
+
+int DebAssertFailed(SZ_CONST szFileName,
+ USHORT wLine);
+int DebAssertNumFailed(SZ_CONST szFileName,
+ USHORT wLine,
+ int nErr);
+void DebHalted(SZ_CONST szFileName, USHORT wLine);
+
+
+// Note that we must use #define, not inline, to use the __LINE__
+// macro properly.
+
+#define DebHalt(szComment) \
+ DebHalted((SZ_CONST) SZ_FILE_NAME, __LINE__)
+
+// UNDONE OA95: we overflow DGROUP if we include the expression. For
+// UNDONE OA95: now we don't include the expression in the assert;
+// UNDONE OA95: we should fix the DGROUP problem instead.
+
+#if OE_WIN
+#define DebAssert(fExpr, szComment) \
+ if (!(fExpr)) \
+ DebAssertFailed((SZ_CONST) SZ_FILE_NAME, __LINE__); \
+ else 0 /* useless statement */
+#else // !OE_WIN
+#define DebAssert(fExpr, szComment) \
+ if (!(fExpr)) \
+ DebAssertFailed((SZ_CONST) SZ_FILE_NAME, __LINE__); \
+ else 0 /* useless statement */
+
+#define DebAssertNum(fExpr, szComment, nErr) \
+ if (!(fExpr)) \
+ DebAssertNumFailed((SZ_CONST) SZ_FILE_NAME, __LINE__, nErr); \
+ else 0 /* useless statement */
+#endif
+
+#define DebPrintfIf(fPrint, Args) \
+ if (fPrint) \
+ DebPrintf Args; \
+ else 0 /* useless statement */
+
+
+void DebStartError_(void);
+void DebStartErrorCode_(TIPERROR err);
+void DebStopError_(void);
+BOOL DebErrorNow_(TIPERROR err);
+
+#define DebStartError() DebStartError_()
+#define DebStartErrorCode(err) DebStartErrorCode_(err)
+#define DebStopError() DebStopError_()
+#define DebErrorNow(err) DebErrorNow_(err)
+
+VOID DebAddInstTable_(VOID *pInstance);
+VOID DebRemInstTable_(VOID *pInstance);
+VOID DebInInstTable_(VOID *pInstance);
+VOID DebInstTableEmpty_();
+
+#define DebAddInstTable(p) DebAddInstTable_(p)
+#define DebRemInstTable(p) DebRemInstTable_(p)
+#define DebInInstTable(p) DebInInstTable_(p)
+#define DebInstTableEmpty() DebInstTableEmpty_()
+
+// Use this for statements that should only be executed in
+// debug versions. e.g. DEBONLY( phvdefn = 0; )
+#define DEBONLY(x) x
+
+#else // !ID_DEBUG
+
+// Eliminate all debugging code.
+// NOTE: DO NOT DEFINE NON-EMPTY INLINE FUNCTIONS HERE
+// (if you do, they'll end up being included in actual release
+// code).
+//
+
+#define DebHeapChk()
+#define DebHalt(szComment)
+#define DebAssert(expr, szComment)
+#define DebAssertNum(fExpr, szComment, nErr)
+#define DebPrintfIf(fPrint, Args)
+
+#define DebStartError()
+#define DebStartErrorCode(err)
+#define DebStopError()
+#define DebErrorNow(err) 0
+
+#define DebAddInstTable(p)
+#define DebRemInstTable(p)
+#define DebInInstTable(p)
+#define DebInstTableEmpty()
+#define DebExamineHeap()
+
+#define DEBONLY(x)
+
+#endif // !ID_DEBUG
+
+// NoAssertRetail is used in places where you need the expression to
+// be evaluated on both Retail and Debug build. On Debug build
+// we also check to make sure that the expression evaluates to true.
+#if ID_DEBUG
+#define NoAssertRetail(fExpr, szComment) DebAssert(fExpr, szComment)
+#else
+#define NoAssertRetail(fExpr, szComment) (fExpr)
+#endif
+
+#if ID_DEBUG
+// DebAssertInterfaceAvail is to assert that a certain interface is available
+// for a certain object. The following QueryProtocol assert:
+//
+// is eqivalent to the following QueryInterface assert:
+// DebAssertInterfaceAvail((TYPEINFO *)pbtinfo, BASIC_TYPEINFO,
+// IID_BASIC_TYPEINFO, "SaveAsText");
+#define DebAssertInterfaceAvail(pobj, dclass, id, szComment) \
+ { dclass *pobjtmp; \
+ if (pobj->QueryInterface(id, (LPVOID *) &pobjtmp) == NOERROR) \
+ pobjtmp->Release(); \
+ else \
+ DebAssertFailed((SZ_CONST) SZ_FILE_NAME, __LINE__); \
+ }
+
+#define DebAssertInterfaceEq(pobj, dclass, id, szComment) \
+ { dclass *pobjtmp; \
+ if (pobj->QueryInterface(id, (LPVOID *) &pobjtmp) == NOERROR && \
+ pobj == pobjtmp) \
+ pobjtmp->Release(); \
+ else \
+ DebAssertFailed((SZ_CONST) SZ_FILE_NAME, __LINE__); \
+ }
+#else //ID_DEBUG
+#define DebAssertInterfaceAvail(pobj, dclass, id, szComment)
+#define DebAssertInterfaceEq(pobj, dclass, id, szComment)
+#endif //ID_DEBUG
+
+#ifdef __cplusplus
+} /* extern "C" */
+#endif
+
+#endif // !DEBUG_H_INCLUDED
diff --git a/private/oleauto/src/typelib/debug.hxx b/private/oleauto/src/typelib/debug.hxx
new file mode 100644
index 000000000..1c9421424
--- /dev/null
+++ b/private/oleauto/src/typelib/debug.hxx
@@ -0,0 +1,175 @@
+/***
+*debug.hxx - Silver debugging macros
+*
+* Copyright (C) 1990-1992, Microsoft Corporation
+*
+*Purpose:
+* This file defines debugging macros used by Silver source files.
+* Documentation for these macros and other useful coding techniques to
+* reduce buggage are in \silver\doc\codestd\debug.doc.
+*
+*Revision History:
+*
+* 15-AUG-90 petergo: File created.
+* 31-Mar-91 ilanc: Added DebGets()
+* 22-Apr-91 petergo: Change ternary ops to ifs.
+* 30-May-91 alanc: Add address table support and eliminate
+* exception generation support
+* 22-Jan-92 jamieb: Added DebConsoleOutput()
+* 13-May-92 w-peterh: Moved all non-c++ stuff to debug.h
+* 03-Aug-92 rajivk: changed error generation macros and functions
+*
+*******************************************************************************/
+
+#ifndef DEBUG_HXX_INCLUDED
+#define DEBUG_HXX_INCLUDED
+
+#include "debug.h"
+#include "validate.h"
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szDEBUG_HXX)
+#define SZ_FILE_NAME g_szDEBUG_HXX
+#endif
+
+// "debug" routines that can be used by test drivers.
+// Their implementations are in "debug.cxx". Test drivers
+// must link with "debug.obj" explicitly since the release version
+// of "misc.lib" doesn't build with "debug.obj".
+//
+// NOTE: DO NOT DEFINE NON-EMPTY INLINE FUNCTIONS HERE
+// (if you do, they'll end up being included in actual release
+// code).
+//
+
+#ifdef __cplusplus
+#if ID_DEBUG
+
+
+//
+// Error generation support
+
+#pragma code_seg(CS_INIT)
+class ERROR_GENERATOR
+{
+public:
+ virtual void Init();
+ virtual BOOL fNow(TIPERROR err);
+ virtual BOOL fContinue(TIPERROR err);
+
+ LPVOID operator new(size_t cbSize)
+ { return MemAlloc(cbSize); }
+ void operator delete(LPVOID pv)
+ { MemFree(pv); }
+
+ UINT m_cErrorGen; // keeps count of error that has been forced
+ UINT m_cNextError;
+ UINT m_cNextErrorReset;
+ BOOL m_fErrorGen; // is set if the current error is a forced error
+ BOOL m_fHandled; // is set if the current error's been handled.
+ BOOL m_fOldHandled;
+
+ TIPERROR m_errOnly;
+#ifdef ERROR_GENERATOR_VTABLE
+#pragma VTABLE_EXPORT
+#endif
+};
+#pragma code_seg()
+
+// resets the flag m_fHandled
+#define HandleErr() \
+ { \
+ if (g_perrorgen) { \
+ g_perrorgen->m_fOldHandled = g_perrorgen->m_fHandled; \
+ g_perrorgen->m_fHandled = TRUE; \
+ } \
+ }
+
+// re-set the flag m_fHandled
+#define UnHandleErr() \
+ { \
+ if (g_perrorgen) { \
+ g_perrorgen->m_fHandled = g_perrorgen->m_fOldHandled; \
+ } \
+ }
+
+// starts error generation: If any error is not passed back (i.e.
+// is ignored) it will assert, and print out the number of times
+// error was forced before being ignored.
+// WARNING: It assumes that error is not generated while handling an
+// error.
+// To Debug:Look at the comments for DEBUGGING HINT at
+// ERROR_GENERATOR:fNow
+//
+#define DoWithErr( func ) \
+ { \
+ DebStartError_(); \
+ while(err = func) { \
+ DebAssert(g_perrorgen != NULL, ""); \
+ if (!g_perrorgen->fContinue(err)) { \
+ break; \
+ } \
+ } \
+ DebStopError_(); \
+ }
+
+// Use the following if you want to verify the error handling
+// while handling another error.
+//
+#define RecDoWithErr( func ) \
+ { \
+ ERROR_GENERATOR *perrorgenSave = NULL; \
+ \
+ if (g_perrorgen != NULL) { \
+ perrorgenSave = g_perrorgen; \
+ g_perrorgen = NULL; \
+ \
+ DoWithErr( func ); \
+ \
+ g_perrorgen = perrorgenSave; \
+ } \
+ }
+
+extern ERROR_GENERATOR FAR *g_perrorgen;
+extern UINT g_fDisableErrorGen;
+
+#define DebSuspendError()
+#define DebResumeError()
+
+// DON'T USE THESE ANYMORE!
+// Use DebSuspendError and DebResumeError instead.
+//
+// DebDisableError: causes DebErrorNow to not fire until reenabled
+// DebEnableError: undoes invocation of DebDisableError
+//#define DebDisableError() g_fDisableErrorGen = TRUE
+//#define DebEnableError() g_fDisableErrorGen = FALSE
+
+// Use this for statements that should only be executed in
+// debug versions. e.g. DEBONLY( phvdefn = 0; )
+#define DEBONLY(x) x
+
+
+
+#else // !ID_DEBUG
+
+// Eliminate all debugging code.
+// NOTE: DO NOT DEFINE NON-EMPTY INLINE FUNCTIONS HERE
+// (if you do, they'll end up being included in actual release
+// code).
+//
+
+#define DEBONLY(x)
+
+#define DebErrorNow(err) 0
+#define DebSuspendError()
+#define DebResumeError()
+//#define DebDisableError()
+//#define DebEnableError()
+#define DoWithErr( func ) func
+#define HandleErr()
+#define UnHandleErr()
+#endif // !ID_DEBUG
+#endif // __cplusplus
+
+#endif // !DEBUG_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/debug2.cxx b/private/oleauto/src/typelib/debug2.cxx
new file mode 100644
index 000000000..7f80a5a27
--- /dev/null
+++ b/private/oleauto/src/typelib/debug2.cxx
@@ -0,0 +1,164 @@
+/***
+*debug2.cxx
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Replacement debug.cxx - *NOT* dependent on Ebapp... etc.
+*
+*Revision History:
+*
+* [00] 13-Nov-92 bradlo: Created.
+*
+*Implementation Notes:
+* <additional documentation, as needed>
+*
+*****************************************************************************/
+
+#include "typelib.hxx"
+#include "silver.hxx"
+
+#include "mem.hxx"
+#include "sheapmgr.hxx"
+#include "blkmgr.hxx"
+
+#include <stdlib.h>
+#include <stdarg.h>
+
+#pragma hdrstop(RTPCHNAME)
+
+#if ID_DEBUG
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+char szOleDebugCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleDebugCxx
+#else
+static char szDebugCxx[] = __FILE__;
+#define SZ_FILE_NAME szDebugCxx
+#endif
+#endif //ID_DEBUG
+
+
+extern "C" void
+FnAssertCover(LPSTR lpstrExpr, LPSTR lpstrMsg, LPSTR lpstrFileName, UINT iLine);
+
+BOOL g_fHeapChk = FALSE;
+
+
+BOOL g_fSheapShakingOn = FALSE;
+
+static char chOutputBuf[256];
+
+extern "C" int
+DebPrintf(const char *szFormat, ...)
+{
+ va_list args;
+
+ va_start(args, szFormat);
+
+ vsprintf(chOutputBuf, szFormat, args);
+
+ // REVIEW: should make sure we didnt overflow our buffer.
+
+#if !OE_MAC
+ OutputDebugString(chOutputBuf);
+#endif //!OE_MAC
+
+ return 0;
+}
+
+#if FV_UNICODE_OLE
+#define szTYPELIBASSERT "OLEAUT32.DLL assertion"
+#define szTYPELIBHALT "Halt in OLEAUT32.DLL"
+#else //FV_UNICODE_OLE
+#if OE_MAC
+#define szTYPELIBASSERT "Typelib assertion"
+#define szTYPELIBHALT "Halt in TYPELIB"
+#else //OE_MAC
+#define szTYPELIBASSERT "TYPELIB.DLL assertion"
+#define szTYPELIBHALT "Halt in TYPELIB.DLL"
+#endif //OE_MAC
+#endif //FV_UNICODE_OLE
+extern "C" int
+DebAssertFailed(const char *szFilename, WORD wLine)
+{
+ // use the Ole2 internal assertion mechanism
+ FnAssertCover("", szTYPELIBASSERT, (LPSTR)szFilename, wLine);
+ return 0;
+}
+
+extern "C" void
+DebHalted(const char *szFilename, WORD wLine)
+{
+ FnAssertCover("", szTYPELIBHALT, (LPSTR)szFilename, wLine);
+}
+
+#pragma code_seg(CS_RARE)
+extern "C" void
+DebExamineHeap()
+{ }
+
+extern "C" void
+DebAddInstTable_(void *pv)
+{ }
+
+extern "C" void
+DebRemInstTable_(void *pv)
+{ }
+#pragma code_seg()
+
+#pragma code_seg(CS_INIT)
+BOOL
+DebErrorNow_(TIPERROR err)
+{
+ return FALSE;
+}
+#pragma code_seg()
+
+extern "C" void
+FnAssertCover(LPSTR lpstrExpr, LPSTR lpstrMsg, LPSTR lpstrFileName, UINT iLine)
+{
+
+ char szMsg[256];
+
+#if OE_WIN16 || OE_WIN32
+
+ // Can't use the the Ole2 internal assertion mechanism anymore, because
+ // if we're using the retail OLE, it doesn't assert. So put up a message
+ // box asking abort/retry/ignore.
+
+ sprintf(szMsg, "%s\nFile %s, line %d", lpstrMsg, lpstrFileName, iLine);
+#define szAssertTitle "Abort = UAE, Retry = INT 3, Ignore = Continue"
+ switch (MessageBox(NULL, szMsg, szAssertTitle, MB_ICONHAND | MB_ABORTRETRYIGNORE)) {
+ case IDABORT:
+ FatalAppExit(0, lpstrMsg);
+ break;
+ case IDRETRY:
+#if OE_RISC
+ DebugBreak();
+#else
+ _asm {
+ int 3
+ }
+#endif
+ break;
+ default:
+ break; // just continue
+ }
+
+#else // OE_MAC
+ // Can't use the the Ole2 internal assertion mechanism anymore, because
+ // if we're using the retail OLE, it doesn't assert. So we do it ourselves
+ //FnAssert(lpstrExpr, lpstrMsg, lpstrFileName, iLine);
+
+ *szMsg = sprintf(szMsg+1, "Typelib assertion: File %s, line %d", lpstrFileName, iLine);
+ DebugStr((const unsigned char FAR*)szMsg);
+
+#endif // OE_MAC
+}
+
+#endif /* } */
diff --git a/private/oleauto/src/typelib/defn.hxx b/private/oleauto/src/typelib/defn.hxx
new file mode 100644
index 000000000..0b9f8fc3c
--- /dev/null
+++ b/private/oleauto/src/typelib/defn.hxx
@@ -0,0 +1,1640 @@
+/***
+*defn.hxx - DEFN header file
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+*
+*Revision History:
+*
+* 14-May-92 w-peterh: Created from tdata.hxx.
+* 12-Jun-92 w-peterh: Added RECTYPE_DEFN
+* 23-Jun-92 w-peterh: Added HDEFN_Nil
+* 02-Jul-92 w-peterh: added DEFNKIND member to defns
+* 06-Jul-92 davebra: added PtdefnBase() to TYPE_DEFN
+* 30-Jul-92 w-peterh: added access member to rectypedefn
+* 12-Nov-92 w-peterh: added HFUNCDEFN_Nil
+* 18-Jan-93 w-peterh: added constants MAX_CARGS, MAX_CARGSOPT, OPTARGS_LIST
+* 15-Jan-93 RajivK: added Code resource support for MAC
+* 12-Feb-93 w-peterh: vardefn::isDispatch, funcdefn::isRestricted
+* 12-Apr-93 w-jeffc: made DEFN data members private;
+* added layout strings for byte swapping
+*
+*Implementation Notes:
+* A DEFN is the struct used for the internal storage of an INFO
+*
+* DEFN
+* |
+* ---------------------------------------------
+* | | |
+* RECTYPE_DEFN VAR_DEFN MEMBER_DEFN |
+* | | | |
+* ----------| | -------------
+* | ----------- |
+* | | FUNC_DEFN
+* PARAM_DEFN MBR_VAR_DEFN |
+* VIRTUAL_FUNC_DEFN
+*
+* A DEFN really only has a single link field (to simplify
+* list manipulation) and an hlnam field.
+*
+* All of the DEFN structs (except MEMBER_DEFN) inherit from the
+* DEFN struct. In addition, those structs that represent object
+* members (i.e. MBR_VAR_DEFN, FUNC_DEFN, and VIRTUAL_FUNC_DEFN)
+* also inherit from MEMBER_DEFN. VAR_DEFN and PARAM_DEFN only
+* inherit from DEFN.
+*
+* This design allows us to share the commonalities between locals,
+* params and data members (member variables) and in addition, treat
+* params like locals (where appropriate).
+*
+*****************************************************************************/
+
+#ifndef DEFN_HXX_INCLUDED
+#define DEFN_HXX_INCLUDED
+
+#include "typelib.hxx"
+
+class DYN_TYPEBIND; // dtbind.hxx
+class TYPE_DATA; // tdata.hxx
+class PCODE_TYPEROOT; // ptinfo.hxx
+
+
+#include "cltypes.hxx"
+
+
+#include "tdesck.hxx" // for TYPEDESCKIND
+#include "rtarray.h" // for HARRAY_DESC
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szDEFN_HXX)
+#define SZ_FILE_NAME g_szDEFN_HXX
+#endif
+
+
+// Layout string for VARIANT struct. We can't layout the data
+// member of the variant, however, because it can contain so many
+// different types of data. It is swapped manually in TYPE_DATA.
+//
+#define VARIANT_LAYOUT "ssss"
+
+// Do this here, even though this only needs be done to
+// ones that are serialized.
+//
+#pragma pack(2)
+
+#define CC_HRESULT CC_RESERVED
+
+// HDEFN - hdefn
+// HFUNC_DEFN - hfdefn
+// HVIRTUAL_FUNC_DEFN - hvfdefn
+// HMEMBER_DEFN - hmdefn
+// HVAR_DEFN - hvdefn
+// HPARAM_DEFN - hparamdefn
+// HMBR_VAR_DEFN - hmvdefn
+
+
+typedef HCHUNK HDEFN;
+typedef sHCHUNK sHDEFN;
+const HDEFN HDEFN_Nil = (HDEFN) HCHUNK_Nil;
+
+typedef HCHUNK HFUNC_DEFN;
+typedef sHCHUNK sHFUNC_DEFN;
+const HFUNC_DEFN HFUNCDEFN_Nil = (HFUNC_DEFN) HCHUNK_Nil;
+
+typedef HCHUNK HVIRTUAL_FUNC_DEFN;
+typedef sHCHUNK sHVIRTUAL_FUNC_DEFN;
+const HVIRTUAL_FUNC_DEFN HVIRTUALFUNCDEFN_Nil =
+ (HVIRTUAL_FUNC_DEFN) HCHUNK_Nil;
+
+typedef HCHUNK HMEMBER_DEFN;
+typedef sHCHUNK sHMEMBER_DEFN;
+const HMEMBER_DEFN HMEMBERDEFN_Nil = (HMEMBER_DEFN) HCHUNK_Nil;
+
+typedef HCHUNK HVAR_DEFN;
+typedef sHCHUNK sHVAR_DEFN;
+const HVAR_DEFN HVARDEFN_Nil = (HVAR_DEFN) HCHUNK_Nil;
+
+typedef HCHUNK HPARAM_DEFN;
+typedef sHCHUNK sHPARAM_DEFN;
+const HPARAM_DEFN HPARAMDEFN_Nil = (HPARAM_DEFN) HCHUNK_Nil;
+
+typedef HCHUNK HMBR_VAR_DEFN;
+typedef sHCHUNK sHMBR_VAR_DEFN;
+const HMBR_VAR_DEFN HMBRVARDEFN_Nil = (HMBR_VAR_DEFN) HCHUNK_Nil;
+
+typedef HCHUNK HBIND_DESC;
+typedef sHCHUNK sHBIND_DESC;
+const HBIND_DESC HBINDESC_Nil = (HBIND_DESC) HCHUNK_Nil;
+
+// HST - hst
+typedef HCHUNK HST;
+typedef sHCHUNK sHST;
+const HST HST_Nil = (HST) HCHUNK_Nil;
+
+// HRECTYPE_DEFN - hrtdefn
+typedef HCHUNK HRECTYPE_DEFN;
+typedef sHCHUNK sHRECTYPE_DEFN;
+const HRECTYPE_DEFN HRECTYPEDEFN_Nil = (HRECTYPE_DEFN) HCHUNK_Nil;
+
+// HTYPE_DEFN - htdefn
+typedef HCHUNK HTYPE_DEFN;
+typedef sHCHUNK sHTYPE_DEFN;
+const HTYPE_DEFN HTYPEDEFN_Nil = (HTYPE_DEFN) HCHUNK_Nil;
+
+// HFUNC_TYPE_DEFN - hftdefn
+typedef HCHUNK HFUNC_TYPE_DEFN;
+typedef sHCHUNK sHFUNC_TYPE_DEFN;
+const HFUNC_TYPE_DEFN HFUNCTYPEDEFN_Nil = (HFUNC_TYPE_DEFN) HCHUNK_Nil;
+
+
+
+// HDLLENTRY_DEFN - hdllentrydefn
+typedef HCHUNK HDLLENTRY_DEFN;
+typedef sHCHUNK sHDLLENTRY_DEFN;
+const HDLLENTRY_DEFN HDLLENTRYDEFN_Nil = (HDLLENTRY_DEFN) HCHUNK_Nil;
+
+
+
+typedef INT (FAR PASCAL * LPDLLENTRYPOINT)(); // should be FARPROC
+
+/***
+*class DLLENTRY_DEFN - 'dllentry_defn': Describes DLL entry point.
+*
+* CONSIDER: make DLLENTRY_DEFN derive from DEFN
+*Purpose:
+* Structure identifying a DLL entry point.
+*
+* *** if you modify this structure, also update the layout string below
+* (see SwapStruct() for more info)
+*
+***********************************************************************/
+
+class DLLENTRY_DEFN
+{
+public:
+
+ // PCODE_TYPEROOT::ForEachHlnam needs the
+ // address of m_hlnamDllName and m_hlnamDllEntry
+ // (just using a friend function created include file dependency problems)
+ //
+ friend class PCODE_TYPEROOT;
+
+ // ctor
+ DLLENTRY_DEFN() {
+ m_hasOrdinal = FALSE;
+ // set the bit to indicate that this declared is switched in.
+ // Lowest bit is set if the declare is switched out.
+ m_hlnamDllName = HLNAM_Nil & 0xfffe;
+ m_hchunkDllEntry = HCHUNK_Nil;
+ m_hdllentrydefnNext = (sHDLLENTRY_DEFN) HDLLENTRYDEFN_Nil;
+ m_lpDllEntryPoint = NULL;
+ m_hLibrary = 0;
+ }
+
+ // accessors
+ // getters:
+ //
+ BOOL HasOrdinal() const { return m_hasOrdinal; }
+ HLNAM HlnamDllName() const { return (HLNAM)(m_hlnamDllName & 0xfffe); }
+ HCHUNK HchunkDllEntry() const { return (HCHUNK)m_hchunkDllEntry; }
+ USHORT UDllOrdinal() const { return m_uDllOrdinal; }
+ HDLLENTRY_DEFN HdllentrydefnNext() const { return (HDLLENTRY_DEFN)m_hdllentrydefnNext; }
+ LPDLLENTRYPOINT LpDllEntryPoint() const { return m_lpDllEntryPoint; }
+#if OE_MAC
+ Handle HLibrary() const { return (Handle)m_hLibrary; }
+#else
+ HINSTANCE HLibrary() const { return (HINSTANCE)m_hLibrary; }
+#endif
+
+ // setters:
+ VOID SetHasOrdinal(BOOL fParm) { m_hasOrdinal = fParm; }
+ VOID SetHlnamDllName(HLNAM hlnam) { m_hlnamDllName = (sHLNAM)
+ ((m_hlnamDllName & 0x0001) | hlnam); }
+ VOID SetHchunkDllEntry(HCHUNK hchunk) { m_hchunkDllEntry = (sHCHUNK)hchunk; }
+ VOID SetUDllOrdinal(USHORT uParm) { m_uDllOrdinal = uParm; }
+ VOID SetHdllentrydefnNext(HDLLENTRY_DEFN hdllentrydefnParm)
+ { m_hdllentrydefnNext = (sHDLLENTRY_DEFN)hdllentrydefnParm; }
+ VOID SetLpDllEntryPoint(LPDLLENTRYPOINT lpdllentrypointParm)
+ { m_lpDllEntryPoint = lpdllentrypointParm; }
+#if OE_MAC
+ VOID SetHLibrary(Handle hParm) { m_hLibrary = (ULONG)hParm; }
+#else // MAC
+#if OE_WIN16
+ VOID SetHLibrary(HINSTANCE hParm) { m_hLibrary = (ULONG)((WORD)hParm); }
+#else
+ VOID SetHLibrary(HINSTANCE hParm) { m_hLibrary = (ULONG)hParm; }
+#endif
+#endif
+
+private:
+ sBOOL m_hasOrdinal;
+ // NOTE: the lowes bit of the hlnam is used to indicate if the declare
+ // has been switched out.
+ sHLNAM m_hlnamDllName;
+ union {
+ sHCHUNK m_hchunkDllEntry;
+ USHORT m_uDllOrdinal;
+ };
+ sHDLLENTRY_DEFN m_hdllentrydefnNext;
+
+ LPDLLENTRYPOINT m_lpDllEntryPoint;
+ ULONG m_hLibrary; // really a Handle/HINSTANCE
+ // but must make sure that it's
+ // the same size in all platforms
+ // (it's serialized)
+};
+// layout string for byte swapping (don't need to swap m_hLibrary)
+#define DLLENTRY_DEFN_LAYOUT "ssss"
+
+/***
+*class TYPE_DEFN - 'tdefn': Internal rep of a TYPEDESC object.
+*Purpose:
+* This struct represents the internal form of a TYPEDESC.
+* NOTE: VARIABLE LEN STRUCT.
+*
+*Implementation Notes:
+*
+* (1) A TYPE_DEFN can be packed into a single
+* (short) word.
+*
+* (2) The fields immediately following instances of a
+* TYPE_DEFN depend on the TYPEDESCKIND. For the scalar types
+* (UI1, I1, UI2, I2, UI4, I4, UI8, I8, R4, R8, R10, VOID,
+* STRING, CURRENCY, VALUE)
+* there are no following fields.
+*
+* (3) If the TYPEDESCKIND is PTR or REF then the
+* structure is followed by another TYPE_DEFN which
+* describes the type which is referenced.
+*
+* (4) If the TYPEDESCKIND is USER_DEFINED then the struct
+* is followed by an HIMPTYPE containing an himptype (the
+* internal representation of a TYPEID).
+*
+* (5) If the TYPEDESCKIND is BASIC_ARRAY then the struct
+* is followed by an sHARRAY_DESC containing the array descriptor
+* and another TYPE_DEFN for the array elements
+*
+* (6) If the TYPEDESCKIND is Fixed string, then the length
+* is in the following SHORT.
+*
+* *** if you modify this structure, also update the layout string below
+* (see SwapStruct() for more info)
+*
+***********************************************************************/
+
+class TYPE_DEFN
+{
+public:
+
+ // ctor
+ TYPE_DEFN() {
+ m_tdesckind = (USHORT) TDESCKIND_Value;
+ m_isConst = (USHORT) FALSE;
+ m_isResizable = (USHORT) FALSE;
+ m_isInRecord = (USHORT) FALSE;
+ // only used for params
+ m_isRetval = (USHORT) FALSE;
+ m_isLCID = (USHORT) FALSE;
+ m_ptrkind = (USHORT) PTRKIND_Ignore;
+ m_paramkind = PARAMKIND_In;
+ }
+
+ UINT DefnSize(); // Implemented in tdata1.cxx
+
+ // accessors
+ // Getters:
+ //
+ sHIMPTYPE *Qhimptype() const;
+ HIMPTYPE Himptype() const;
+ HIMPTYPE HimptypeActual() const;
+ TYPE_DEFN *QtdefnFoundation() const;
+ HTYPE_DEFN HtdefnFoundation(HTYPE_DEFN htdefn) const;
+ TYPE_DEFN *QtdefnBase();
+ HARRAY_DESC Harraydesc() const;
+ BOOL IsString() const;
+ BOOL IsBVariant() const;
+ BOOL IsObject() const;
+ BOOL IsUserDefined() const;
+ BOOL IsBasicPtr() const;
+ BOOL IsArray() const;
+ BOOL IsBasicArray() const;
+ BOOL IsConst() const { return (BOOL)m_isConst; }
+ BOOL IsRetval() const { return (BOOL)m_isRetval;}
+ BOOL IsResizable() const;
+ BOOL IsInRecord() const { return (BOOL)m_isInRecord;}
+ BOOL IsLCID() const { return (BOOL)m_isLCID;}
+ TYPEDESCKIND Tdesckind() const { return (TYPEDESCKIND)m_tdesckind; }
+ BOOL IsPointer() const;
+ BOOL IsLastTdefn() const;
+
+ PTRKIND Ptrkind() const { return (PTRKIND)m_ptrkind; }
+ PARAMKIND Paramkind() const { return (PARAMKIND)m_paramkind; }
+ BOOL IsModeIn() const { return Paramkind() == PARAMKIND_In; }
+ BOOL IsModeOut() const { return Paramkind() == PARAMKIND_Out; }
+ BOOL IsModeInOut() const { return Paramkind() == PARAMKIND_InOut; }
+ BOOL IsModeIgnore() const { return Paramkind() == PARAMKIND_Ignore; }
+
+ // Setters:
+ VOID SetHimptype(HIMPTYPE himptype) {
+ *Qhimptype() = (sHIMPTYPE)himptype;
+ }
+ VOID SetTdesckind(TYPEDESCKIND tdesckindParm) { m_tdesckind = (USHORT)tdesckindParm; }
+ VOID SetIsConst(BOOL fParm) { m_isConst = (USHORT)fParm; }
+ VOID SetIsRetval(BOOL fParm) { m_isRetval = (USHORT)fParm; }
+ VOID SetIsResizable(BOOL fParm) { m_isResizable = (USHORT)fParm; }
+ VOID SetIsInRecord(BOOL fParm) { m_isInRecord = (USHORT)fParm; }
+ VOID SetIsLCID(BOOL fParm) { m_isLCID = (USHORT)fParm; }
+ VOID SetPtrkind(PTRKIND ptrkindParm) { m_ptrkind = (USHORT)ptrkindParm; }
+ VOID SetParamkind(PARAMKIND paramkind) { m_paramkind = (USHORT)paramkind; }
+
+private:
+ // data members
+
+ USHORT m_tdesckind:6; // was TYPEDESCKIND
+ USHORT m_isConst:1; // was BOOL
+ USHORT m_isRetval:1; // used for params. Set on function return
+ // value if any params have this bit set.
+ USHORT m_isResizable:1; // was BOOL, used for arrays
+ USHORT m_ptrkind:3; // was PTRKIND
+ USHORT m_isInRecord:1; // TRUE ==> var is part of "Type" decl
+ USHORT m_isLCID:1; // used for params. Set on function return
+ // value if any params have this bit set.
+ USHORT m_paramkind:2; // For OLE params only:
+ // specifies whether param is one of:
+ // {IN, OUT, INOUT}.
+};
+
+// layout string for byte swapping
+#define TYPE_DEFN_LAYOUT "s"
+
+
+/***
+*PUBLIC TYPE_DEFN::Qhimptype - Gets pointer HIMPTYPE field.
+*Purpose:
+* Gets pointer to HIMPTYPE field.
+*
+*Implementation Notes:
+* HIMPTYPE field is assumed to immediately follow THIS.
+*
+*Entry:
+*
+*Exit:
+* Returns pointer to HIMPTYPE field. NULL if not USER_DEFINED.
+*
+***********************************************************************/
+
+inline sHIMPTYPE *TYPE_DEFN::Qhimptype() const
+{
+ if (m_tdesckind == TDESCKIND_UserDefined)
+ return (sHIMPTYPE *)(this+1);
+ else
+ return NULL;
+}
+
+inline HIMPTYPE TYPE_DEFN::Himptype() const
+{
+ return (HIMPTYPE)(*(Qhimptype())) & 0xFFFE;
+}
+
+inline HIMPTYPE TYPE_DEFN::HimptypeActual() const
+{
+ return (HIMPTYPE)(*(Qhimptype()));
+}
+
+// inline definition must be before usage for cfront
+
+inline BOOL TYPE_DEFN::IsBasicArray() const
+{
+ return (BOOL) (m_tdesckind == TDESCKIND_BasicArray);
+}
+
+inline BOOL TYPE_DEFN::IsArray() const
+{
+ return IsBasicArray() || (BOOL)(m_tdesckind == TDESCKIND_Carray);
+}
+
+
+
+/***
+*PUBLIC TYPE_DEFN::Harraydesc()
+*
+*Purpose:
+* returns the handle for the array descriptor
+*
+*Implementation Notes:
+* assumes it immediatly follows the typedefn
+*
+*Entry:
+*
+*Exit:
+*
+*
+***********************************************************************/
+
+inline HARRAY_DESC TYPE_DEFN::Harraydesc() const
+{
+ DebAssert(IsArray(), "Harraydesc : not array type" );
+ return (HARRAY_DESC) *((sHARRAY_DESC*)((BYTE*)this+sizeof(TYPE_DEFN)));
+}
+
+
+/***
+*PUBLIC TYPE_DEFN::Is[whatever]
+*Purpose:
+* returns TRUE if the type defn has the requested attribute
+*
+*Implementation Notes:
+*
+*
+*Entry:
+*
+*Exit:
+*
+*
+***********************************************************************/
+
+inline BOOL TYPE_DEFN::IsString() const
+{
+ return (BOOL) (Tdesckind() == TDESCKIND_String);
+}
+
+inline BOOL TYPE_DEFN::IsBVariant() const
+{
+ return (BOOL) (Tdesckind() == TDESCKIND_Value);
+}
+
+inline BOOL TYPE_DEFN::IsObject() const
+{
+ return (BOOL) (Tdesckind() == TDESCKIND_Object);
+}
+
+inline BOOL TYPE_DEFN::IsUserDefined() const
+{
+ return (BOOL) (Tdesckind() == TDESCKIND_UserDefined);
+}
+
+inline BOOL TYPE_DEFN::IsBasicPtr() const
+{
+ return (Ptrkind() == PTRKIND_Basic)
+ || (Tdesckind() == TDESCKIND_Object)
+ ;
+}
+
+inline BOOL TYPE_DEFN::IsResizable() const
+{
+ return m_isResizable;
+}
+
+inline BOOL TYPE_DEFN::IsPointer() const
+{
+ return (Tdesckind() == TDESCKIND_Ptr) || IsBasicPtr();
+}
+
+inline BOOL TYPE_DEFN::IsLastTdefn() const
+{
+ return Tdesckind() != TDESCKIND_Ptr && !IsArray();
+}
+
+/***
+*PUBLIC TYPE_DEFN::HtdefnFoundation()
+*Purpose:
+* gets handle to foundation typedefn given a handle.
+* skips over arraydesc if there is one.
+*
+*Implementation Notes:
+* assumes it directly follows this typedefn and possible hArrayDesc
+* NOTE: this only works if handles are offsets and not lookup
+* table keys.
+*
+*Entry:
+*
+*Exit:
+*
+*
+***********************************************************************/
+
+inline HTYPE_DEFN TYPE_DEFN::HtdefnFoundation(HTYPE_DEFN htdefn) const
+{
+ // Doesn't handle "Byref" case correctly. See QtdefnFoundation below.
+
+ DebAssert(!IsLastTdefn(), "must not be last one");
+ return (HTYPE_DEFN)((UINT) htdefn +
+ sizeof(TYPE_DEFN) +
+ (IsArray() ? sizeof(sHARRAY_DESC) : 0));
+}
+
+
+
+
+/***
+*PUBLIC TYPE_DEFN::QtdefnBase()
+*Purpose:
+* gets base TYPE_DEFN: this is the lowest level TYPE_DEFN and therefore
+* must be either an intrinsic type or a user-defined type.
+* If the TYPE_DEFN on which this is called is the lowest level, then
+* it is returned.
+*
+*Implementation Notes:
+* assumes it directly follows this TYPE_DEFN and possible hArrayDesc
+*
+*Entry:
+*
+*Exit:
+*
+*
+***********************************************************************/
+
+inline TYPE_DEFN *TYPE_DEFN::QtdefnBase()
+{
+ TYPE_DEFN *qtdefn = this;
+ while (!qtdefn->IsLastTdefn())
+ qtdefn = qtdefn->QtdefnFoundation();
+ return qtdefn;
+}
+
+
+/***
+*class DEFN - 'defn': Root of DEFN hierarchy.
+*Purpose:
+* Root of DEFN hierarchy.
+*
+*
+*Implementation Notes:
+* Has link field to facilitate list manipulation and name handle.
+* Layout:
+* 2 byte flag word // *** NOTE: MUST BE FIRST FIELD ***
+* Handle to next DEFN in list.
+* Local name handle.
+*
+* *** if you modify this structure, also update the layout string below
+* (see SwapStruct() for more info)
+*
+************************************************************************/
+
+class DEFN
+{
+public:
+
+ // PCODE_TYPEROOT::ForEachHlnam needs the address of m_hlnam
+ // (just using a friend function created include file dependency problems)
+ //
+ friend class PCODE_TYPEROOT;
+
+ // ctor
+ DEFN() {
+ SetHdefnNext(HDEFN_Nil);
+ SetHlnam(HLNAM_Nil);
+
+ m_fV2Flags = 0;
+ }
+
+
+ // accessors
+ // Getters:
+ //
+ HDEFN HdefnNext() const { return m_hdefnNext; }
+ HLNAM Hlnam() const { return m_hlnam; }
+ DEFNKIND Defnkind() const { return (DEFNKIND)m_defnkind; }
+ BOOL IsMemberVarDefn() const { return Defnkind() == DK_MbrVarDefn; }
+ BOOL IsRecTypeDefn() const { return Defnkind() == DK_RecTypeDefn; }
+ BOOL IsVirtualFuncDefn() const { return Defnkind() == DK_VirtualFuncDefn; }
+ BOOL IsParamDefn() const { return Defnkind() == DK_ParamDefn; }
+ BOOL IsVarDefn() const {
+ return (Defnkind() == DK_VarDefn) || IsMemberVarDefn() || IsParamDefn();
+ }
+ BOOL IsFuncDefn() const {
+ return (Defnkind() == DK_FuncDefn) || IsVirtualFuncDefn();
+ }
+ BOOL IsMemberDefn() const {
+ return IsMemberVarDefn() || IsFuncDefn();
+ }
+ ACCESS Access();
+ BOOL HasV2Flags() const {
+ return (BOOL)m_fV2Flags;
+ }
+ VOID SetHasV2Flag(BOOL f) { m_fV2Flags = (USHORT)f; }
+
+ // Setters:
+ VOID SetHdefnNext(HDEFN hdefn) { m_hdefnNext = (sHDEFN)hdefn; }
+ VOID SetDefnkind(DEFNKIND defnkind) { m_defnkind = (sDEFNKIND)defnkind; }
+ VOID SetHlnam(HLNAM hlnam) { m_hlnam = (sHLNAM)hlnam; }
+
+protected:
+ // Following bitfields pack into 16-bit USHORT.
+ // Note: we make them protected so that derived classes
+ // can get at them.
+ // NOTE: MUST BE FIRST FIELD (swapcode assumes this)
+ //
+ USHORT m_defnkind:3; // defn kind
+ USHORT m_access:1; // Private or Public
+ USHORT m_UNUSED5:1; // this bit is 0 in the V1 typelib(s).
+ // and is un-referenced in V1 typelib.dll
+ USHORT m_fV2Flags:1; // if set then it means that there are
+ // 2 trailing bytes at the end of the defn
+
+ // DEFNKIND specific stuff FUNC_DEFN VAR_DEFN
+ USHORT m_kind:3; // either FUNC_KIND or VAR_KIND
+
+ USHORT m_isPureOrSimpleType:1; // IsPure IsSimpleType
+ USHORT m_isStatic:1; // IsStaticLocalVars IsStatic
+ // IsRestricted IsSimpleConst
+ USHORT m_isRestrictedOrSimpleConst:1;
+
+ // WARNING:
+ // The following are reserved by defn deriviations
+ // in whatever way it is appropriate. Do not use them for something
+ // else at this level.
+ //
+ USHORT m_UNUSED1:1;
+ USHORT m_UNUSED2:1;
+ USHORT m_UNUSED3:1;
+ USHORT m_UNUSED4:1;
+
+private:
+ // data members
+ sHDEFN m_hdefnNext;
+ sHLNAM m_hlnam; // Low bit is UNUSED6.
+};
+
+// layout string for byte swapping
+#define DEFN_LAYOUT "sss"
+
+
+
+/***
+*class MEMBER_DEFN - 'mdefn': Base class for MBR_VAR_DEFN and FUNC_DEFN
+*Purpose:
+* This struct represents the commonalities between
+* MBR_VAR_DEFN and FUNC_DEFN.
+*
+*Implementation Notes:
+* Intended to be base of MBR_VAR_DEFN and FUNC_DEFN.
+* MEMBER_DEFN is NOT a member of the DEFN hierarchy.
+*
+* Layout:
+* Handle to DLLENTRY_DEFN
+* Member handle.
+* Doc string handle.
+* Encoded Help context (16-bit).
+* 15th bit<--------->0th bit.
+* // bit 0 represents if the number(diff is stored here)
+* // 1 -> num is stored in the top 14 bits.
+* // 0 -> h is stored in the top 15 bits.
+* // all 15 bits 1 indicates HCHUNK_Nil
+* //
+* if the num is stored then bit 1 represents if the num is -ve or +ve
+* // 1 -> number is positive.
+* // 0 -> number is negative.
+*
+* *** if you modify this structure, also update the layout string below
+* (see SwapStruct() for more info)
+*
+************************************************************************/
+
+class MEMBER_DEFN
+{
+public:
+ // ctor
+ MEMBER_DEFN() {
+ m_hmember = HMEMBER_Nil;
+ m_hstDocumentation = HST_Nil;
+ m_usHelpContext = 0xfffe; // this indicates that the hchunk stored is
+ // HCHUNK_Nil;
+ }
+
+ // accessors
+ // getters:
+ //
+ HMEMBER Hmember() const { return m_hmember; }
+ HST HstDocumentation() const { return m_hstDocumentation; }
+ WORD WHelpContext() const { return m_usHelpContext; }
+
+ // setters:
+ VOID SetHmember(HMEMBER hmemberParm) { m_hmember = (sHMEMBER)hmemberParm; }
+ VOID SetHstDocumentation(HST hstParm) { m_hstDocumentation = (sHST)hstParm; }
+
+ VOID SetWHelpContext(USHORT uParm) { m_usHelpContext = uParm; }
+
+private:
+
+ // data members
+ sHMEMBER m_hmember; // this is a DWORD
+
+ USHORT m_usHelpContext;
+
+ sHST m_hstDocumentation;
+};
+
+// layout string for byte swapping
+#define MEMBER_DEFN_LAYOUT "lss"
+
+
+/***
+*class VAR_DEFN - 'vdefn': Shared root for locals and params.
+*Purpose:
+* This struct represents the internal form of the shared
+* attributes of datamembers and locals and params for VBA.
+*
+*Implementation Notes:
+* VAR_DEFN does not inherit from MEMBER_DEFN because it is mainly
+* used for locals and parameters. It inherits from DEFN for the
+* link and the hlnam.
+*
+* NOTE!!!! VAR_DEFN is also used for BASIC datamembers so that
+* they can be lighter than regular datamembers. The reason that
+* this can happen is because the only extra information that a
+* BASIC datamember needs above what is in VAR_DEFN is an hmember.
+* We happen to ensure that the oVar field of a BASIC datamember
+* is also its hmember, so we don't actually need an explicit
+* hmember field.
+*
+* Layout:
+* Following reserved bits defined in DEFN are
+* used as following in VAR_DEFN
+*
+* USHORT m_UNUSED1:1; // m_hasConstVal
+* USHORT m_UNUSED2:1; // m_hasNew
+* USHORT m_UNUSED3:1; // m_isDispatch
+* USHORT m_UNUSED4:1; // m_isReadOnly
+*
+* Embedded fixed sized "simple" TYPEDEFN XOR
+* Handle to heap-allocated TYPEDEFN (if "complex").
+*
+* NOTE: this above member *wants* to be a union, but can't be
+* since TYPE_DEFN has a constructor.
+*
+* Offset of non-const var on stack frame if local or
+* of member in instance if non-const datamember XOR
+* Handle to heap-allocated const val if constant var
+* (datamember or local).
+*
+* NOTE: Constant datamembers do not have an oVar/hmember.
+*
+* NOTE: The isTypeSimple flag is used to 'tag' the TYPE_DEFN union.
+*
+* NOTE: can't make varlen since used as base class.
+*
+* *** if you modify this structure, also update the layout string below
+* (see SwapStruct() for more info)
+*
+************************************************************************/
+
+class VAR_DEFN : public DEFN
+{
+public:
+ // ctor
+ VAR_DEFN() {
+ SetDefnkind(DK_VarDefn);
+ m_access = ACCESS_Private;
+ m_UNUSED5 = 0;
+ m_fV2Flags = 0;
+ m_kind = VKIND_DataMember;
+
+ m_isRestrictedOrSimpleConst = FALSE; // really isSimpleConst for VARs
+ m_isStatic = FALSE; // really isStatic for VARs
+ m_isPureOrSimpleType = TRUE; // really isSimpleType for VARs
+ m_UNUSED1 = FALSE; // m_hasConstVal
+ m_UNUSED2 = FALSE; // m_hasNew
+ m_UNUSED3 = FALSE; // m_isDispatch
+ m_UNUSED4 = FALSE; // m_isReadOnly
+
+ m_oVar = 0xffff; // m_hchunkConstVal = -1
+
+
+ DebAssert(sizeof(m_htdefn) == sizeof(TYPE_DEFN),
+ "bad sizes in wannabe union.");
+
+ m_htdefn = (sHTYPE_DEFN)HTYPEDEFN_Nil;
+ }
+
+ // accessors
+ // getters:
+ //
+ ACCESS Access() const { return (ACCESS)m_access; }
+ BOOL IsPublic() const { return Access() == ACCESS_Public; }
+ BOOL IsPrivate() const { return Access() == ACCESS_Private; }
+ VAR_KIND Vkind() const { return (VAR_KIND)m_kind; }
+ BOOL IsDataMember() const { return Vkind() == VKIND_DataMember; }
+ BOOL IsBase() const { return Vkind() == VKIND_Base; }
+ BOOL IsEnumerator() const { return Vkind() == VKIND_Enumerator; }
+ BOOL IsFormal() const { return Vkind() == VKIND_Formal; }
+ USHORT GetOVar() const { return m_oVar; };
+ SHORT GetSConstVal() const { return m_sConstVal; };
+ USHORT GetImplTypeFlags() const;
+ BOOL HasConstVal() const { return (BOOL)m_UNUSED1; }
+ BOOL IsSimpleConst() const { return (BOOL)m_isRestrictedOrSimpleConst; }
+ BOOL IsStatic() const { return (BOOL)m_isStatic; }
+ BOOL IsSimpleType() const { return (BOOL)m_isPureOrSimpleType; }
+
+ BOOL IsDispatch() const { return (BOOL)m_UNUSED3; }
+ BOOL IsReadOnly() const { return (BOOL)m_UNUSED4; }
+
+ BOOL HasNew() const { return (BOOL)m_UNUSED2; }
+
+ HCHUNK HchunkConstVal() const {
+ return m_UNUSED1 ? m_hchunkConstVal : HCHUNK_Nil;
+ }
+
+ HTYPE_DEFN Htdefn() const { return m_htdefn; }
+
+
+ TYPE_DEFN *QtdefnOfSimpleType() const {
+ DebAssert(IsSimpleType(), "should be simple type.");
+ return (TYPE_DEFN *)&m_htdefn;
+ }
+
+ HMEMBER Hmember() {
+ // CONSIDER: make the whole function EI_OB only since OLE
+ // should never call VAR_DEFN::Hmember().
+ //
+ return HMEMBER_Nil;
+ }
+
+ // The following return "illegal" values. There are defined here
+ // so that basic members which use VAR_DEFN's can share code
+ // with non-basic members that use MBR_VAR_DEFNs.
+ // CONSIDER: maybe we don't really need this...
+ //
+ HDLLENTRY_DEFN Hdllentrydefn() const { return HDLLENTRYDEFN_Nil; }
+ HST HstDocumentation() const { return HST_Nil; }
+ ULONG WHelpContext() const { return 0; }
+
+
+ // setters:
+ VOID SetAccess(ACCESS accessParm) { m_access = (USHORT)accessParm; }
+ VOID SetVkind(VAR_KIND vkindParm) { m_kind = (USHORT)vkindParm; }
+ VOID SetHasConstVal(BOOL fParm) { m_UNUSED1 = (USHORT)fParm; }
+ VOID SetIsSimpleConst(BOOL fParm) { m_isRestrictedOrSimpleConst = (USHORT)fParm; }
+ VOID SetIsStatic(BOOL fParm) { m_isStatic = (USHORT)fParm; }
+ VOID SetIsSimpleType(BOOL fParm) { m_isPureOrSimpleType = (USHORT)fParm; }
+ VOID SetIsDispatch(BOOL fParm) { m_UNUSED3 = (USHORT)fParm; }
+ VOID SetIsReadOnly(BOOL fParm) { m_UNUSED4 = (USHORT)fParm; }
+
+ VOID SetHasNew(BOOL fParm) { m_UNUSED2 = (USHORT)fParm; }
+ VOID SetHtdefn(HTYPE_DEFN htdefnParm) { m_htdefn = (sHTYPE_DEFN)htdefnParm; }
+ VOID SetOVar(USHORT usParm) { m_oVar = usParm; }
+ VOID SetSConstVal(SHORT sParm) { m_sConstVal = sParm; }
+ VOID SetHchunkConstVal(HCHUNK hchunkParm) { m_hchunkConstVal = (sHCHUNK)hchunkParm; }
+
+ VOID SetImplTypeFlags(USHORT wFlags);
+
+
+protected:
+ // Note: protected so that derived classes can get at them.
+ union {
+ USHORT m_oVar;
+ SHORT m_sConstVal;
+ sHCHUNK m_hchunkConstVal;
+
+ USHORT m_fImplType;
+ };
+
+private:
+ sHTYPE_DEFN m_htdefn;
+};
+
+// layout string for byte swapping
+#define VAR_DEFN_LAYOUT DEFN_LAYOUT "ss"
+
+// Special bit to note that ImplTypeFlags were explictly set to SOME value.
+// The m_impltypeflags field we are using is the unused m_ovar/m_hchunkconstval
+// field of the defn. In old typelibs (those created before we added the
+// support for impltypeflags), this field was either 0 (for the first impltype)
+// or -1 (for subsequent impltypes).
+//
+ #define IMPLTYPEFLAG_FSET 0x8000
+
+//NOTE: we OR-in and AND-off our special bit (and do checks for old typelibs
+// here rather than in the wrappers, because the binding code calls
+// these methods directly.
+
+inline VOID VAR_DEFN::SetImplTypeFlags(USHORT wFlags)
+{
+ DebAssert((wFlags & IMPLTYPEFLAG_FSET) == 0, "bogus flags");
+ m_fImplType = wFlags | IMPLTYPEFLAG_FSET;
+}
+
+//
+inline USHORT VAR_DEFN::GetImplTypeFlags() const
+{
+ USHORT fImplType = m_fImplType;
+
+ // Hack for old typelibs -- if no flags were set, then set the
+ // default bit for the first impltype
+ if (fImplType == 0) {
+ return IMPLTYPEFLAG_FDEFAULT;
+ }
+
+ // In old typelibs, non-first impltypes will have -1 for the flags
+ if (fImplType == 0xffff) { // correct flags from old typelib
+ return 0;
+ }
+
+ // new typelib -- strip off our magic bit.
+ return (fImplType & ~IMPLTYPEFLAG_FSET);
+}
+
+/***
+*class RECTYPE_DEFN - 'rtdefn': Describes a nested type
+*Purpose:
+* Structure Identifiing a nested type
+*
+* *** if you modify this structure, also update the layout string below
+* (see SwapStruct() for more info)
+*
+***********************************************************************/
+
+class RECTYPE_DEFN : public DEFN
+{
+public:
+ // ctor
+ RECTYPE_DEFN() {
+ SetDefnkind(DK_RecTypeDefn);
+ m_hvdefnFirstMember = (sHVAR_DEFN) HVARDEFN_Nil;
+ m_himptype = (sHIMPTYPE) HIMPTYPE_Nil;
+ }
+
+ // accessors
+ // getters:
+ //
+ HVAR_DEFN HvdefnFirstMember() {return m_hvdefnFirstMember; }
+ HIMPTYPE Himptype() { return m_himptype; }
+ ACCESS Access() { return (ACCESS)m_access; }
+
+ // setters:
+ VOID SetAccess(ACCESS accessParm) { m_access = (sACCESS)accessParm; }
+ VOID SetHvdefnFirstMember(HVAR_DEFN hvdefnParm) { m_hvdefnFirstMember = (sHVAR_DEFN)hvdefnParm; }
+ VOID SetHimptype(HIMPTYPE himptypeParm) { m_himptype = (sHIMPTYPE)himptypeParm; }
+
+private:
+ // data members
+ sHVAR_DEFN m_hvdefnFirstMember;
+ sHIMPTYPE m_himptype;
+ sACCESS m_access;
+};
+
+// layout string for byte swapping
+#define RECTYPE_DEFN_LAYOUT DEFN_LAYOUT "sss"
+
+/***
+*class MBR_VAR_DEFN - 'mvdefn': Internal rep of a VARINFO object.
+*Purpose:
+* This struct represents the internal form of a VARINFO. Used
+* to represent a datamember.
+*
+*Implementation Notes:
+* MBR_VAR_DEFN is used to represent all members except
+* BASIC datamembers. This is for space reasons: see VAR_DEFN
+* for more details.
+*
+* Derives from VAR_DEFN and MEMBER_DEFN.
+* Layout:
+* [Inherited VAR_DEFN]
+* [Inherited MEMBER_DEFN]
+* If const or enum then literal binary const val.
+*
+* Note that constants/enums are ULONG length prefixed always -- both
+* for fixed-len datatypes and varlen types.
+*
+* *** if you modify this structure, also update the layout string below
+* (see SwapStruct() for more info)
+*
+************************************************************************/
+
+class MBR_VAR_DEFN : public VAR_DEFN, public MEMBER_DEFN
+{
+public:
+ // ctor
+ MBR_VAR_DEFN() {
+ SetDefnkind(DK_MbrVarDefn);
+ // Do not initialize this data member as it is not always present.
+ // m_fVarFlags = 0;
+ }
+
+ // accessors
+ // getters:
+ //
+ HCHUNK HchunkConstMbrVal() const {
+ return ((IsDataMember() && HasConstVal()) || IsEnumerator() ?
+ m_hchunkConstVal : // from VAR_DEFN
+ HCHUNK_Nil);
+ }
+
+ // setters:
+ VOID SetHchunkConstMbrVal(HCHUNK hchunk) {
+ m_hchunkConstVal = (sHCHUNK)hchunk;
+ }
+
+ HMEMBER Hmember() const { return MEMBER_DEFN::Hmember(); }
+ HST HstDocumentation() const { return MEMBER_DEFN::HstDocumentation(); }
+ USHORT WHelpContext() const { return MEMBER_DEFN::WHelpContext(); }
+ VOID SetHmember(HMEMBER hmember) { MEMBER_DEFN::SetHmember(hmember); }
+ VOID SetHstDocumentation(HST hst) { MEMBER_DEFN::SetHstDocumentation(hst); }
+
+ VOID SetWHelpContext(USHORT wHelpContext) {
+ MEMBER_DEFN::SetWHelpContext(wHelpContext);
+ }
+
+ // V2 flags.
+ VOID SetWVarFlags(USHORT wFlags) {
+ m_fVarFlags = wFlags;
+ }
+
+ USHORT WVarFlags() const { return m_fVarFlags; }
+
+
+
+// CONSIDER: vba2
+// HCHUNK HchunkVbasePos() const {
+// return IsVirtualBase() ? m_hchunkVbasePos : HCHUNK_Nil;
+// }
+// CONSIDER: vba2
+// VOID SetHchunkVbasePos(HCHUNK hchunkParm)
+// { m_hchunkVbasePos = (sHCHUNK)hchunkParm; }
+private:
+ // Note: no introduced members.
+ // The following data member is added for V2
+ USHORT m_fVarFlags;
+
+};
+
+// layout string for byte swapping (only non-VAR_DEFN part)
+#define MBR_VAR_DEFN_LAYOUT VAR_DEFN_LAYOUT MEMBER_DEFN_LAYOUT ""
+
+#define MBR_VAR_DEFN_V2_LAYOUT MBR_VAR_DEFN_LAYOUT "s"
+
+
+#pragma code_seg(CS_CORE)
+
+/***
+*class PARAM_DEFN - 'paramdefn': Internal parameter for OLE/typelib.
+*Purpose:
+* This struct represents the internal form of a parameter for typelib
+*
+* Layout:
+* m_hlnam // Note: the lsb of hlnam is used to store isSimple flag.
+* //
+* // hlnam:15; Handle to the name of the parameter.
+* // Note: since hlnams are always even, these 15 bits
+* // are the "normalized" hlnam.
+* // IsSimple:1; the parameter is of simple type.
+* m_htdefn // USHORT : handle to the TYPE_DEFN
+*
+* All other param defn flags are stored in the TYPE_DEFN itself.
+* They are for now just: PARAMKIND
+*
+* NOTE: Following flag are not needed for PARAM DEFN in OLE.
+* VARKIND is always VKIND_Formal.
+* DEFNKIND is always DK_ParamDefn.
+*
+* WARNING: if you modify this structure, also update the layout string below
+*
+*
+***********************************************************************/
+
+class PARAM_DEFN
+{
+public:
+ // ctor
+ PARAM_DEFN() {
+ m_hlnam = 0xfffe; // HCHUNK_Nil and isSimpleType is flase.
+ m_htdefn = (sHTYPE_DEFN)HTYPEDEFN_Nil;
+ }
+
+ // accessors
+ // getters:
+ //
+ BOOL IsSimpleType() const { return (BOOL)(m_hlnam & 0x0001); }
+ HLNAM Hlnam() const {
+ // if all bits are 0 then we need to return HLNAM_Nil
+ if ((m_hlnam & ~0x0001) == 0xfffe)
+ return HLNAM_Nil;
+ else
+ return (HLNAM) (m_hlnam & ~0x0001);
+ }
+ HTYPE_DEFN Htdefn() const { return m_htdefn; }
+ TYPE_DEFN *QtdefnOfSimpleType() const {
+ DebAssert(IsSimpleType(), "should be simple type.");
+ return (TYPE_DEFN *)&m_htdefn;
+ }
+ PARAM_DEFN *QparamdefnNext() {
+ // This function assumes that OLE PARAM_DEFNs are always laidout
+ // contiguously in an array.
+ //
+ return (PARAM_DEFN *) (this + 1);
+ }
+
+ // setters:
+ VOID SetHtdefn(HTYPE_DEFN htdefn) {
+ m_htdefn = (sHTYPE_DEFN)htdefn;
+ }
+ VOID SetIsSimpleType(BOOL fSimple) {
+ m_hlnam = fSimple ? (m_hlnam | 0x0001) : (m_hlnam & ~0x0001);
+ }
+ VOID SetHlnam(HLNAM hlnam) {
+ DebAssert(hlnam != 0xfffe, " cannot store this handle ");
+
+ if (hlnam == HCHUNK_Nil) {
+ hlnam &= 0xfffe;
+ }
+
+ DebAssert(!(hlnam & 0x0001), "Hlnam is assumed to be even");
+ // set the hlnam preserving the isSimple bit.
+ m_hlnam = IsSimpleType() ? (hlnam | 0x0001) : hlnam;
+ }
+
+private:
+ USHORT m_hlnam; // Hlnam of the parameter. isSimple is stored in
+ // the lsb.
+ USHORT m_htdefn; // handle to the TYPE_DEFN
+
+};
+// layout string for byte swapping the param defn
+#define PARAM_DEFN_LAYOUT "ss"
+
+
+#pragma code_seg()
+
+
+
+/***
+*class FUNC_TYPE_DEFN - 'ftdefn': Internal rep of a FUNCDESC object.
+*Purpose:
+* This struct represents the internal form of a FUNCDESC.
+*
+*Implementation Notes:
+* Layout:
+* Calling convention:2
+* Arg count:6 (effectively limits to 64)
+*
+* used to be: TYPE_DEFN handle for THIS ptr.
+* TYPE_DEFN handle for RESULT parameter.
+* OB: PARAM_DEFN handle for listhead of first PARAM_DEFN in list
+* of formal params.
+* OLE: PARAM_DEFN handle for first element of PARAM_DEFN array
+* of formal params.
+*
+* *** if you modify this structure, also update the layout string below
+* (see SwapStruct() for more info)
+*
+* Munging:
+* In order for a basic funcdefn to handle both OLE and OB
+* requirements, we 'munge' the funcdefn by having both a
+* retval parameter and a return type. When the user requests
+* information, we either give them the retval parameter (and
+* set the return type to HRESULT) or give them the actual
+* return type (and reduce CArgs by one). Of course, this means
+* that we can no longer blindly loop over the paramdefns.
+*
+* Note that these 'Unmunged' routines boil down to the
+* normal accessor functions when compiled under OLE. This
+* reduces the number of #if's in the code.
+*
+***********************************************************************/
+
+// ARGS_BITS is the number of bits we use for the cArgs field
+// OPTARGS_BITS is the number of bits we use for the cArgsOpt field
+// OPTARGS_LIST is the value to put in the cArgsOpt field to indicate
+// that the last parameter in the function is a list of
+// parameters (i.e. ParamArray in Basic)
+// MAX_CARGS is the max number of args a function can have
+// MAX_CARGSOPT is the max number of optional args a function can have--
+// it is OPTARGS_LIST-1 because a) zero means none and
+// b) all bits on means that we have an OPTARGS_LIST--
+// this means that we have OPTARGS_LIST-1 combinations
+// left to store the number of optional args
+//
+#define ARGS_BITS 6
+#define OPTARGS_BITS 6
+#define OPTARGS_LIST ((1<<(OPTARGS_BITS))-1)
+#define MAX_CARGS 60
+#define MAX_CARGSOPT 60
+
+class FUNC_TYPE_DEFN
+{
+public:
+
+ // public data member since its address is used
+ //
+ sHDEFN m_hdefnFormalFirst; // OB: actually listhead
+ // OLE: first element in array.
+
+ // methods
+
+ // ctor
+ FUNC_TYPE_DEFN() {
+ m_cc = CC_MSCPASCAL;
+ m_cArgs = 0;
+ m_cArgsOpt = 0;
+ m_isSimpleTypeResult = FALSE;
+ m_htdefnResult = (sHTYPE_DEFN)HTYPEDEFN_Nil;
+ m_hdefnFormalFirst = (sHDEFN)HDEFN_Nil;
+
+ }
+
+ // accessors
+ // getters:
+ //
+
+ BOOL HasRetval() const {
+ // For speed, the retval and/or the lcid bits are set on the
+ // function return type if any of the parameters have these
+ // bits set.
+ //
+ return IsSimpleTypeResult()
+ && QtdefnOfSimpleTypeResult()->IsRetval();
+ }
+
+ BOOL HasLcid() const {
+ // For speed, the retval and/or the lcid bits are set on the
+ // function return type if any of the parameters have these
+ // bits set.
+ //
+ return IsSimpleTypeResult()
+ && QtdefnOfSimpleTypeResult()->IsLCID();
+ }
+
+ CALLINGCONVENTION CcUnmunged() const {
+ return (CALLINGCONVENTION)m_cc;
+ }
+
+ CALLINGCONVENTION Cc() const
+ {
+
+ return (CALLINGCONVENTION)m_cc;
+ }
+
+ BOOL IsCcMscPascal() const
+ {
+ return Cc() == CC_MSCPASCAL
+ ;
+ }
+ BOOL IsCcMacPascal() const
+ {
+ return Cc() == CC_MACPASCAL
+ ;
+ }
+ BOOL IsCcCdecl() const
+ {
+ return Cc() == CC_CDECL
+ ;
+ }
+ BOOL IsCcStdcall() const
+ {
+ return Cc() == CC_STDCALL
+ ;
+ }
+
+ BOOL IsParamArray() const { return (BOOL)(m_cArgsOpt == OPTARGS_LIST); }
+
+ UINT CArgsUnmunged() const {
+ return m_cArgs;
+ }
+
+ UINT CArgs() const
+ {
+ INT r = m_cArgs;
+
+ if (HasRetval()) r--;
+ if (HasLcid()) r--;
+
+ DebAssert(r >= 0, "bit set when not enough args");
+
+ return r;
+ }
+
+ INT CArgsOpt() const { return (IsParamArray() ? -1 : m_cArgsOpt); }
+
+ BOOL IsSimpleTypeResultUnmunged() const {
+
+ return m_isSimpleTypeResult;
+ }
+
+ BOOL IsSimpleTypeResult() const
+ {
+ return (BOOL)m_isSimpleTypeResult;
+ }
+
+ HTYPE_DEFN HtdefnResultUnmunged() const
+ {
+
+ return (HTYPE_DEFN)m_htdefnResult;
+ }
+
+
+ HTYPE_DEFN HtdefnResult() const
+ {
+ return (HTYPE_DEFN)m_htdefnResult;
+ }
+
+ TYPE_DEFN *QtdefnOfSimpleTypeResultUnmunged() const {
+ DebAssert(IsSimpleTypeResultUnmunged(),
+ "result type should be simple.");
+
+
+ return (TYPE_DEFN *)&m_htdefnResult;
+ }
+
+ TYPE_DEFN *QtdefnOfSimpleTypeResult() const {
+ DebAssert(IsSimpleTypeResult(), "result type should be simple.");
+
+ return (TYPE_DEFN *)&m_htdefnResult;
+ }
+
+ // setters:
+ VOID SetCc(CALLINGCONVENTION ccParm) { m_cc = (USHORT)ccParm; }
+ VOID SetCArgs(UINT cParm) { m_cArgs = (USHORT)cParm; }
+ VOID SetCArgsOpt(INT cParm) { m_cArgsOpt = (USHORT)cParm; }
+ VOID SetIsSimpleTypeResult(BOOL fParm) { m_isSimpleTypeResult = (USHORT)fParm; }
+ VOID SetHtdefnResult(HTYPE_DEFN htdefnParm) { m_htdefnResult = (sHTYPE_DEFN)htdefnParm; }
+
+
+private:
+ // data members
+ USHORT m_cc:3; // was CALLINGCONVENTION
+ USHORT m_cArgs:ARGS_BITS; // was BYTE
+ USHORT m_cArgsOpt:OPTARGS_BITS; // was BYTE
+ USHORT m_isSimpleTypeResult:1; // was BOOL
+
+ sHTYPE_DEFN m_htdefnResult;
+};
+
+// layout string for byte swapping
+#define FUNC_TYPE_DEFN_LAYOUT "sss"
+
+
+
+/***
+*class FUNC_DEFN - 'fdefn': Internal rep of a FUNCINFO object.
+*Purpose:
+* This struct represents the internal form of a FUNCINFO.
+*
+*Implementation Notes:
+* Derives from DEFN and MEMBER_DEFN.
+*
+* Used for all non-virtual functions, including BASIC functions
+* and BASIC declares.
+*
+* Layout:
+* [Inherited DEFN and MEMBER_DEFN]
+* Embedded FUNC_TYPE_DEFN.
+* VBA-only: Embedded EXMGR_FUNCDEFN (managed by excode generator).
+* Access
+* Declaration kind
+* Function kind
+* Is pure flag
+* Has static locals flag
+* // Following bit fields are declared in DEFN and are used here
+* // to store the INVOKE_KIND.
+* //
+* USHORT m_UNUSED1 == INVOKE_FUNC
+* USHORT m_UNUSED2 == INVOKE_PROPERTYGET
+* USHORT m_UNUSED3 == INVOKE_PROPERTYPUT
+* USHORT m_UNUSED4 == INVOKE_PROPERTYPUTREF
+*
+* Number of lines in function
+*
+* Prologue delta (to adjust this pointer with).
+*
+* *** if you modify this structure, also update the layout string below
+* (see SwapStruct() for more info)
+*
+**********************************************************************/
+
+class FUNC_DEFN : public DEFN, public MEMBER_DEFN
+{
+public:
+
+ // these data members are left public since their address is passed
+ // as parms to some functions
+ //
+
+ FUNC_TYPE_DEFN m_ftdefn;
+
+ // ctor
+ FUNC_DEFN() {
+ SetDefnkind(DK_FuncDefn);
+ m_hdllentrydefn = (sHDLLENTRY_DEFN)HDLLENTRYDEFN_Nil;
+ m_access = ACCESS_Public;
+ m_UNUSED5 = 0;
+ m_fV2Flags = 0;
+ m_kind = FKIND_NonVirtual; // FUNC_KIND
+ m_isPureOrSimpleType = FALSE; // isPure
+ m_isStatic = FALSE; // isStaticLocalVars
+ m_isRestrictedOrSimpleConst = FALSE; // isRestricted
+ m_UNUSED1 = INVOKE_FUNC; // INVOKEKIND
+ m_UNUSED2 = m_UNUSED3 = m_UNUSED4 = 0;
+
+
+ // Do not initialize this data member as it is not always present.
+ // m_fFuncFlags = 0;
+ }
+
+ // accessors
+ // getters:
+ //
+ ACCESS Access() const { return (ACCESS)m_access; }
+ BOOL IsPublic() const { return Access() == ACCESS_Public; }
+ BOOL IsPrivate() const { return Access() == ACCESS_Private; }
+
+ FUNC_KIND Fkind() const { return (FUNC_KIND)m_kind; }
+ BOOL IsVirtual() const { return Fkind() == FKIND_Virtual; }
+ BOOL IsNonVirtual() const { return Fkind() == FKIND_NonVirtual; }
+ BOOL IsStatic() const { return Fkind() == FKIND_Static; }
+ BOOL IsDispatch() const { return Fkind() == FKIND_Dispatch; }
+ INVOKEKIND InvokeKind() const {return (INVOKEKIND)(
+ (USHORT) (((USHORT) ((USHORT)m_UNUSED4 << 3)) |
+ ((USHORT) ((USHORT)m_UNUSED3 << 2)) |
+ ((USHORT) ((USHORT)m_UNUSED2 << 1)) |
+ ((USHORT) m_UNUSED1) )); }
+
+ BOOL IsMethod() const { return (BOOL)m_UNUSED1; }
+ BOOL IsPropertyGet() const {
+ return (BOOL)m_UNUSED2;
+ }
+ BOOL IsPropertyLet() const {
+ return (BOOL)m_UNUSED3;
+ }
+ BOOL IsPropertySet() const {
+ return (BOOL)m_UNUSED4;
+ }
+ BOOL IsPure() const { return (BOOL)m_isPureOrSimpleType; }
+ BOOL IsStaticLocalVars() const { return (BOOL)m_isStatic; }
+ BOOL IsRestricted() const { return (BOOL)m_isRestrictedOrSimpleConst;}
+
+ BOOL HasRetval() const {
+ return m_ftdefn.HasRetval();
+ }
+ BOOL HasLcid() const {
+ return m_ftdefn.HasLcid();
+ }
+
+
+ USHORT WFuncFlags() const { return (USHORT)m_fFuncFlags; };
+ HDLLENTRY_DEFN Hdllentrydefn() const {
+ return IsVirtual() ? HDLLENTRYDEFN_Nil : m_hdllentrydefn;
+ }
+ UINT Ovft() const {
+ return (UINT)m_oVft;
+ }
+
+ BOOL IsHresultSub() const
+ {
+ TYPE_DEFN *qtdefn;
+
+ if (IsSub())
+ return TRUE;
+
+ if (!m_ftdefn.IsSimpleTypeResult())
+ return FALSE;
+
+ qtdefn = m_ftdefn.QtdefnOfSimpleTypeResult();
+
+ return qtdefn->Tdesckind() == TDESCKIND_HResult
+ && !qtdefn->IsRetval();
+ }
+
+ BOOL IsSub() const
+ {
+ TYPE_DEFN *qtdefn;
+
+ if (!m_ftdefn.IsSimpleTypeResult()) {
+ return m_ftdefn.HtdefnResult() == HTYPEDEFN_Nil;
+ }
+
+ qtdefn = m_ftdefn.QtdefnOfSimpleTypeResult();
+
+ return qtdefn->Tdesckind() == TDESCKIND_Void
+ && qtdefn->Ptrkind() == PTRKIND_Ignore;
+ }
+
+ // The following two are simple wrappers on the ftdefn to make
+ // fdefn client's life easier.
+ //
+ UINT CArgs() const { return m_ftdefn.CArgs(); }
+ INT CArgsOpt() const { return m_ftdefn.CArgsOpt(); }
+ UINT CArgsUnmunged() const { return m_ftdefn.CArgsUnmunged(); }
+
+ // setters:
+ VOID SetAccess(ACCESS access) { m_access = (USHORT)access; }
+ VOID SetFkind(FUNC_KIND fkind) { m_kind = (USHORT)fkind; }
+ VOID SetIsPure(BOOL fPure) { m_isPureOrSimpleType = (USHORT)fPure; }
+ VOID SetIsStaticLocalVars(BOOL fStatic) { m_isStatic = (USHORT)fStatic; }
+ VOID SetIsRestricted(BOOL fRestricted) {
+ m_isRestrictedOrSimpleConst = (USHORT)fRestricted;
+ }
+ VOID SetHdllentrydefn(HDLLENTRY_DEFN hdllentrydefn) {
+ DebAssert(!IsVirtual(), "shouldn't be virtual.");
+ m_hdllentrydefn = (sHDLLENTRY_DEFN)hdllentrydefn;
+ }
+
+ VOID SetWFuncFlags(USHORT wFlags) {
+ m_fFuncFlags = wFlags;
+ }
+
+ VOID SetInvokeKind(INVOKEKIND invkind) {
+ m_UNUSED1 = (invkind == INVOKE_FUNC),
+ m_UNUSED2 = (invkind == INVOKE_PROPERTYGET),
+ m_UNUSED3 = (invkind == INVOKE_PROPERTYPUT),
+ m_UNUSED4 = (invkind == INVOKE_PROPERTYPUTREF); }
+
+ VOID SetOvft(UINT oVft) {
+ m_oVft = (USHORT)oVft;
+ }
+
+
+protected:
+ union {
+ // proteced so that derived classes can access structure members
+ USHORT m_oVft; // offset in Virtual function table.
+ sHDLLENTRY_DEFN m_hdllentrydefn;
+ };
+
+private:
+
+ // The following data member is added for V2
+ USHORT m_fFuncFlags;
+
+
+};
+
+// layout string for byte swapping
+// (different versions for OB & !OB because of EXMGR_FUNCDEFN)
+//
+#define FUNC_DEFN_LAYOUT DEFN_LAYOUT MEMBER_DEFN_LAYOUT \
+ FUNC_TYPE_DEFN_LAYOUT "s"
+
+#define FUNC_DEFN_V2FLAGS_LAYOUT "s" // extra flags word
+
+
+
+
+/***
+*class VIRTUAL_FUNC_DEFN - 'vfdefn'
+*Purpose:
+* This struct represents the internal form of a FUNCINFO for
+* a virtual function.
+*
+*Implementation Notes:
+* Derives from FUNC_DEFN.
+*
+* A virtual function is tagged by FUNC_KIND = FKIND_Virtual.
+* Clients will never know the difference; all code that cares
+* whether it is dealing with a FUNC_DEFN or a VIRTUAL_FUNC_DEFN
+* will check the tag.
+*
+* Layout:
+* [Inherited FUNC_DEFN]
+* Embedded virtual method position descriptor.
+*
+* *** if you modify this structure, also update the layout string below
+* (see SwapStruct() for more info)
+*
+**********************************************************************/
+
+class VIRTUAL_FUNC_DEFN : public FUNC_DEFN
+{
+public:
+
+ // ctor
+ VIRTUAL_FUNC_DEFN() {
+ SetDefnkind(DK_VirtualFuncDefn);
+ }
+
+ // accessors
+ // getters:
+ //
+ // setters:
+
+private:
+//WARNING: Note we have added a USHORT in FUNC_DEFN for our V2 release. So
+// if you add a data member here, it may break the compatibity with
+// V1.
+};
+
+// layout string for byte swapping (non FUNC_DEFN part)
+#define VIRTUAL_FUNC_DEFN_LAYOUT ""
+
+
+// Inline methods that depend on forward declarations.
+//
+inline ACCESS DEFN::Access()
+{
+ if (IsVarDefn())
+ return ((VAR_DEFN *)this)->Access();
+ else if (IsFuncDefn())
+ return ((FUNC_DEFN *)this)->Access();
+ else {
+ DebAssert(IsRecTypeDefn(), "should be nested type.");
+ return ((RECTYPE_DEFN *)this)->Access();
+ }
+}
+
+#pragma pack() // reset to default
+
+
+#endif // DEFN_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/dfntbind.cxx b/private/oleauto/src/typelib/dfntbind.cxx
new file mode 100644
index 000000000..db99a8ba1
--- /dev/null
+++ b/private/oleauto/src/typelib/dfntbind.cxx
@@ -0,0 +1,80 @@
+/***
+*dfntbind.cxx - DEFN_TYPEBIND class implementation
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Root protocol for Object Basic specific implementations
+* of TYPEBIND -- specifically, those that are implemented
+* in terms of DEFNs.
+*
+*Revision History:
+*
+* 27-May-92 ilanc: Created
+* 30-Jul-92 w-peterh: Moved IsMatchOfVisibility to cltypes.hxx
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "silver.hxx"
+
+#define DEFN_TYPEBIND_VTABLE
+#include "dfntbind.hxx"
+#include "xstring.h"
+
+
+#pragma hdrstop(RTPCHNAME)
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+char szOleDfntbindCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleDfntbindCxx
+#else
+static char szDfntbindCxx[] = __FILE__;
+#define SZ_FILE_NAME szDfntbindCxx
+#endif
+#endif //ID_DEBUG
+
+
+
+LPOLESTR DEFN_TYPEBIND::szProtocolName = WIDE("MS-DEFN_TYPEBIND");
+LPOLESTR DEFN_TYPEBIND::szBaseName = WIDE("MS-TYPEBIND");
+
+
+// QueryProtocol method
+//
+LPVOID DEFN_TYPEBIND::QueryProtocol(LPOLESTR szInterfaceName)
+{
+ if (szInterfaceName == szProtocolName ||
+ ostrcmp(szInterfaceName, szProtocolName) == 0 ||
+ ostrcmp(szInterfaceName, szBaseName) ==0)
+ return this;
+ else
+ return NULL;
+}
+
+
+// Following virtual methods are stubbed as NOPs essentially
+// and aren't implemented further in the DEFN derivatives.
+//
+LONG DEFN_TYPEBIND::GetOPvft()
+{
+ return 0xFFFFFFFF;
+}
+
+
+USHORT DEFN_TYPEBIND::GetCbSizeVft()
+{
+ return 0;
+}
+
+
+TIPERROR DEFN_TYPEBIND::BindType(HGNAM hgnamType, LPSTR szTidType, UINT cMax)
+{
+ return TIPERR_None;
+}
+
+
diff --git a/private/oleauto/src/typelib/dfntbind.hxx b/private/oleauto/src/typelib/dfntbind.hxx
new file mode 100644
index 000000000..9891f8eb6
--- /dev/null
+++ b/private/oleauto/src/typelib/dfntbind.hxx
@@ -0,0 +1,272 @@
+/***
+*dfntbind.hxx - DEFN_TYPEBIND header file
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This protocol is intended to be a base class for
+* the Object Basic implementation of TYPEBIND for
+* - modules (DYN_TYPEBIND)
+* - nested types (REC_TYPEBIND)
+* - projects (PROJ_TYPEBIND).
+*
+* It stubs the true TYPEBIND protocol and provides
+* implementations in terms of internal DEFN structs and
+* BIND_DESC structs.
+*
+* It provides some implementation which is shared between
+* nested types (REC_TYPEBIND) and classes (DYN_TYPEBIND).
+*
+*Revision History:
+*
+* 27-May-92 ilanc: Stub created.
+* 30-Jul-92 w-peterh: removed function overloading
+*
+*Implementation Notes:
+*****************************************************************************/
+
+#ifndef DEFN_TYPEBIND_HXX_INCLUDED
+#define DEFN_TYPEBIND_HXX_INCLUDED
+
+#include "stream.hxx"
+#include "defn.hxx" // for DEFN binding structs.
+
+
+
+class EXBIND;
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szDFNTBIND_HXX)
+#define SZ_FILE_NAME g_szDFNTBIND_HXX
+#endif
+
+class DYN_TYPEROOT;
+
+/***
+*class DEFN_TYPEBIND - 'dfntbind': Type bind implementation
+*Purpose:
+* The class defines type bind in terms of DEFN structs.
+*
+***********************************************************************/
+
+class DEFN_TYPEBIND
+{
+public:
+ DEFN_TYPEBIND();
+
+ // redeclared pure virtuals
+ virtual ~DEFN_TYPEBIND() = 0;
+ virtual VOID Release() = 0;
+ virtual VOID AddRef() = 0;
+
+ virtual TIPERROR GetTypeInfo(TYPEINFO **lplptinfo) = 0;
+ virtual TYPEKIND GetTypeKind() = 0;
+ virtual USHORT GetCbSize() = 0;
+ virtual USHORT GetAlignment() = 0;
+
+ // overridden virtuals
+ virtual LPVOID QueryProtocol(LPOLESTR szInterfaceName);
+ virtual LONG GetOPvft();
+ virtual USHORT GetCbSizeVft();
+ virtual TIPERROR BindType(HGNAM hgnamType, LPSTR szTidType, UINT cMax);
+
+ // introduce non-virtuals.
+ nonvirt HMEMBER HmemberConstructor();
+ nonvirt HMEMBER HmemberDestructor();
+ nonvirt HMEMBER HmemberAssign();
+ nonvirt HMEMBER HmemberCopy();
+ nonvirt VOID SetHmemberDestructor(HMEMBER hmember);
+ nonvirt VOID SetHmemberAssign(HMEMBER hmember);
+ nonvirt VOID SetHmemberCopy(HMEMBER hmember);
+
+
+ virtual TIPERROR BindDefnStr(LPSTR szName,
+ UINT fuInvokeKind,
+ ACCESS access,
+ EXBIND *pexbind) = 0;
+
+ virtual TIPERROR BindTypeDefnStr(LPSTR szName,
+ UINT fuInvokeKind,
+ ACCESS access,
+ EXBIND *pexbind) = 0;
+
+
+ virtual TIPERROR BindDefnProjLevelStr(LPSTR szName,
+ UINT fuInvokeKind,
+ ACCESS access,
+ ACCESS accessProj,
+ EXBIND *pexbind) = 0;
+
+ virtual TIPERROR BindTypeDefnProjLevelStr(LPSTR szName,
+ UINT, // fuInvokeKind: unused
+ ACCESS access,
+ ACCESS accessProj,
+ EXBIND *pexbind) = 0;
+
+
+ // Public data members
+ static LPOLESTR szProtocolName;
+ static LPOLESTR szBaseName;
+
+protected:
+ sHMEMBER m_hmemberConst; // hmembers of special functions.
+ sHMEMBER m_hmemberDest; // should be serialized
+ sHMEMBER m_hmemberAssign;
+ sHMEMBER m_hmemberCopy;
+
+#ifdef DEFN_TYPEBIND_VTABLE
+#pragma VTABLE_EXPORT
+#endif
+};
+
+inline DEFN_TYPEBIND::~DEFN_TYPEBIND() {}
+
+
+
+/***
+*PUBLIC DEFN_TYPEBIND::HmemberConstructor()
+*Purpose:
+*
+*Entry:
+*
+*Exit:
+* return HMEMBER for constructor function
+*
+***********************************************************************/
+
+inline HMEMBER DEFN_TYPEBIND::HmemberConstructor()
+{
+ return m_hmemberConst;
+}
+
+
+/***
+*PUBLIC DEFN_TYPEBIND::HmemberDestructor()
+*Purpose:
+*
+*Entry:
+*
+*Exit:
+* return HMEMBER for destructor function
+*
+***********************************************************************/
+
+inline HMEMBER DEFN_TYPEBIND::HmemberDestructor()
+{
+ return m_hmemberDest;
+}
+
+
+/***
+*PUBLIC DEFN_TYPEBIND::HmemberAssign()
+*Purpose:
+*
+*Entry:
+*
+*Exit:
+* return HMEMBER for assign function
+*
+***********************************************************************/
+
+inline HMEMBER DEFN_TYPEBIND::HmemberAssign()
+{
+ return m_hmemberAssign;
+}
+
+
+/***
+*PUBLIC DEFN_TYPEBIND::HmemberCopy()
+*Purpose:
+*
+*Entry:
+*
+*Exit:
+* return HMEMBER for copy function
+*
+***********************************************************************/
+
+inline HMEMBER DEFN_TYPEBIND::HmemberCopy()
+{
+ return m_hmemberCopy;
+}
+
+
+
+
+/***
+*PUBLIC DEFN_TYPEBIND::SetHmemberDestructor()
+*Purpose:
+* Sets the Destructor hmember.
+*
+*Entry:
+* hmember - HMEMBER for Destructor function
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID DEFN_TYPEBIND::SetHmemberDestructor(HMEMBER hmember)
+{
+ m_hmemberDest = hmember;
+}
+
+
+
+/***
+*PUBLIC DEFN_TYPEBIND::SetHmemberAssign()
+*Purpose:
+* Sets the Assign hmember.
+*
+*Entry:
+* hmember - HMEMBER for Assign function
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID DEFN_TYPEBIND::SetHmemberAssign(HMEMBER hmember)
+{
+ m_hmemberAssign = hmember;
+}
+
+
+
+/***
+*PUBLIC DEFN_TYPEBIND::SetHmemberCopy()
+*Purpose:
+* Sets the Copy hmember.
+*
+*Entry:
+* hmember - HMEMBER for Copy function
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID DEFN_TYPEBIND::SetHmemberCopy(HMEMBER hmember)
+{
+ m_hmemberCopy = hmember;
+}
+
+
+/***
+*PUBLIC DEFN_TYPEBIND::DEFN_TYPEBIND()
+*Purpose:
+* Constructor
+*Entry:
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+inline DEFN_TYPEBIND::DEFN_TYPEBIND()
+{
+ m_hmemberConst = m_hmemberDest = m_hmemberAssign = m_hmemberCopy =
+ HMEMBER_Nil;
+}
+
+
+#endif // ! DEFN_TYPEBIND_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/dfntcomp.cxx b/private/oleauto/src/typelib/dfntcomp.cxx
new file mode 100644
index 000000000..0887208a1
--- /dev/null
+++ b/private/oleauto/src/typelib/dfntcomp.cxx
@@ -0,0 +1,569 @@
+/***
+*dfntcomp.cxx - CDefnTypeComp class implementation
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Root protocol for Object Basic specific implementations
+* of ITypeComp -- specifically, those that are implemented
+* in terms of DEFNs.
+*
+*Revision History:
+*
+* 24-Jan-93 ilanc: Created
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "silver.hxx"
+#include "dfntcomp.hxx"
+#include "nammgr.hxx"
+#include "tdata.hxx"
+#include "exbind.hxx"
+#include "dfntbind.hxx"
+#include "gptbind.hxx"
+#include "gdtinfo.hxx"
+
+#pragma hdrstop(RTPCHNAME)
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+char szOleDfntcompCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleDfntcompCxx
+#else
+static char szDfntcompCxx[] = __FILE__;
+#define SZ_FILE_NAME szDfntcompCxx
+#endif
+#endif //ID_DEBUG
+
+TIPERROR IsFunkyDispinterface(GEN_DTINFO *pgdtinfo,
+ BOOL *pisFunkyDispinterface);
+
+/***
+*PUBLIC CDefnTypeComp ctor
+*Purpose:
+* Construct an instance of CDefnTypeComp
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+CDefnTypeComp::CDefnTypeComp()
+{
+ m_pdfntbind = NULL;
+ m_cRefs = 0;
+}
+
+
+/***
+*PUBLIC CDefnTypeComp dtor
+*Purpose:
+* Destruct an instance of CDefnTypeComp
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+CDefnTypeComp::~CDefnTypeComp()
+{
+ // release the single DEFN_TYPEBIND reference that was added
+ // when this instance was inited.
+ //
+ m_pdfntbind->Release();
+}
+
+
+/***
+*static PUBLIC CDefnTypeComp::Create
+*Purpose:
+* Static method to create and init instance.
+*
+*Entry:
+* ppdfntcomp OUT
+* pdfntbind IN
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR CDefnTypeComp::Create(CDefnTypeComp **ppdfntcomp,
+ DEFN_TYPEBIND *pdfntbind)
+{
+ TIPERROR err;
+
+ DebAssert(ppdfntcomp != NULL && pdfntbind != NULL, "null params.");
+
+ // alloc and construct instanc.
+ if ((*ppdfntcomp = MemNew(CDefnTypeComp)) != NULL) {
+ // Init instance
+ ::new (*ppdfntcomp) CDefnTypeComp;
+ err = (*ppdfntcomp)->Init(pdfntbind);
+ if (err != TIPERR_None) {
+ (*ppdfntcomp)->CDefnTypeComp::~CDefnTypeComp();
+ MemFree(*ppdfntcomp);
+ *ppdfntcomp = NULL;
+ }
+ return err;
+ }
+ else {
+ return TIPERR_OutOfMemory;
+ }
+}
+
+
+/***
+*static PUBLIC CDefnTypeComp::Init
+*Purpose:
+* Method to init instance.
+*
+*Entry:
+* pdfntbind IN
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR CDefnTypeComp::Init(DEFN_TYPEBIND *pdfntbind)
+{
+ m_pdfntbind = pdfntbind;
+
+ // add a single reference to the contained DEFN_TYPEBIND
+ // which will be released when this instance is deleted.
+ //
+ m_pdfntbind->AddRef();
+
+ // init ref count
+ m_cRefs = 1;
+
+ return TIPERR_None;
+}
+
+
+/***
+*PUBLIC CDefnTypeComp::QueryInterface
+*Purpose:
+* Implementation of QueryInterface method.
+*
+*Entry:
+* riid - Interface GUID
+* ppvObj - LPVOID * that receives the requested protocol.
+*
+*Exit:
+* Return NOERROR or ReportResult(0, E_NOINTERFACE, 0, 0)
+***********************************************************************/
+HRESULT CDefnTypeComp::QueryInterface(REFIID riid, LPVOID FAR* ppvObj)
+{
+ if (IIDEQ(riid, IID_CDefnTypeComp)) {
+ *ppvObj = (LPVOID) (CDefnTypeComp *)this;
+ AddRef();
+ return NOERROR;
+ }
+
+ if (IIDEQ(riid, IID_ITypeCompA)) {
+ *ppvObj = (LPVOID) (ITypeCompA *)this;
+ AddRef();
+ return NOERROR;
+ }
+
+ if (IIDEQ(riid, IID_IUnknown)) {
+ *ppvObj = (LPVOID) (IUnknown *)(ITypeLibA *)this;
+ AddRef();
+ return NOERROR;
+ }
+
+ *ppvObj = NULL; // required by OLE
+ return ReportResult(0, E_NOINTERFACE, 0, 0);
+}
+
+/***
+*PUBLIC CDefnTypeComp::AddRef
+*Purpose:
+* Add an external reference to the CDefnTypeComp.
+* Defer to wrapped DEFN_TYPEBIND.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+ULONG CDefnTypeComp::AddRef()
+{
+ m_cRefs++;
+ DebAssert(m_cRefs > 0, "overflow.");
+
+ return m_cRefs;
+}
+
+
+/***
+*PUBLIC CDefnTypeComp::Release
+*Purpose:
+* Release an external reference to the CDefnTypeComp.
+* Defer to wrapped DEFN_TYPEBIND.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+ULONG CDefnTypeComp::Release()
+{
+ ULONG cRefs;
+
+ DebAssert(m_cRefs > 0, "underflow.");
+ m_cRefs--;
+
+ cRefs = m_cRefs;
+
+ if (m_cRefs == 0) {
+ this->CDefnTypeComp::~CDefnTypeComp();
+ MemFree(this);
+ }
+
+ return cRefs;
+}
+
+
+/***
+*PUBLIC CDefnTypeComp::Bind
+*Purpose:
+* Binds to a non-type identifier.
+*
+*Entry:
+* szName IN
+* lHashVal IN
+* fuInvokeKind IN
+* pptinfo OUT
+* pdesckind OUT
+* ppv OUT
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+HRESULT CDefnTypeComp::Bind(LPOLESTR szName,
+ ULONG lHashVal,
+ WORD fuInvokeKind,
+ ITypeInfoA FAR* FAR* pptinfo,
+ DESCKIND FAR* pdesckind,
+ BINDPTRA FAR *pbindptr)
+{
+ EXBIND exbind;
+ VARDESCA *pvardesc;
+ FUNCDESC *pfuncdesc;
+ BIND_KIND bkind;
+ DEFN_TYPEBIND *pdfntbind;
+ CDefnTypeComp *pdfntcomp;
+ GENPROJ_TYPEBIND *pgptbind;
+ DYN_TYPEBIND *pdtbind = NULL;
+ NAMMGR *pnammgr;
+ HGNAM hgnam;
+ TIPERROR err;
+#if OE_WIN32
+ HRESULT hresult;
+ CHAR FAR *szNameA = NULL;
+#endif //OE_WIN32
+
+ if (!szName || !pptinfo || !pdesckind || !pbindptr) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+ if ((fuInvokeKind & ~(INVOKE_FUNC | INVOKE_PROPERTYGET | INVOKE_PROPERTYPUT | INVOKE_PROPERTYPUTREF)) != 0) {
+ // ensure no stray bits are set -- 0 is now allowed
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+ DebAssert(m_pdfntbind != NULL, "uninitialized.");
+
+#if OE_WIN32
+ IfOleErrRet(ConvertStringToA(szName, &szNameA));
+#else //OE_WIN32
+ #define szNameA szName
+#endif //OE_WIN32
+
+ // Note that for (non-OB) typelibs we use the proj-level-only binder
+ if ((pgptbind = (GENPROJ_TYPEBIND *)m_pdfntbind->
+ QueryProtocol(GENPROJ_TYPEBIND::szProtocolName)) != NULL) {
+ // Use the hashval
+ IfErrGo(pgptbind->Pgtlibole()->GetNamMgr(&pnammgr));
+ IfErrGo(pnammgr->GetHgnamOfStrLhash(szNameA, lHashVal, &hgnam));
+ if (hgnam != HGNAM_Nil) {
+ IfErrGo(pgptbind->BindProjLevel(FALSE,
+ hgnam,
+ fuInvokeKind,
+ ACCESS_Public,
+ ACCESS_Public,
+ pgptbind->Compstate(),
+ &exbind));
+ }
+ }
+ else {
+ NoAssertRetail(
+ pdtbind = (DYN_TYPEBIND *)m_pdfntbind->
+ QueryProtocol(DYN_TYPEBIND::szProtocolName),
+ "should be DYN_TYPEBIND.");
+
+ // Use the hashval.
+ IfErrGo(pdtbind->Ptdata()->Pnammgr()->GetHgnamOfStrLhash(szNameA,
+ lHashVal,
+ &hgnam));
+ if (hgnam != HGNAM_Nil) {
+ IfErrGo(pdtbind->BindIdDefn(FALSE,
+ hgnam,
+ fuInvokeKind,
+ ACCESS_Public,
+ &exbind));
+ }
+ }
+ bkind = exbind.BindKind();
+ switch (bkind) {
+ case BKIND_Error:
+ DebHalt("Should never happen");
+ break;
+
+ case BKIND_NoMatch:
+ *pdesckind = DESCKIND_NONE;
+ break;
+
+ case BKIND_ImplicitAppobjMatch:
+ *pdesckind = DESCKIND_IMPLICITAPPOBJ;
+ goto CommonAppobjVarMatch;
+
+ case BKIND_OneVarMatch:
+ *pdesckind = DESCKIND_VARDESC;
+
+CommonAppobjVarMatch:
+ IfErrGoTo(exbind.Ptdata()->GetVarDescOfHvdefn(exbind.Hdefn(), &pvardesc),
+ Error2);
+ pbindptr->lpvardesc = pvardesc;
+ goto CommonMatch;
+
+ case BKIND_FuncMatch:
+ IfErrGoTo(exbind.Ptdata()->GetFuncDescOfHfdefn(exbind.Hdefn(),
+ &pfuncdesc),
+ Error2);
+ // Note that if we actually bound to a function of a "pseudo-base"
+ // interface of a dispinterface then we have to pretend that
+ // the function is a disp function...
+ //
+ if (exbind.IsDispatch()) {
+ // Since the IsDispatch flag is only set in the funky
+ // dispinterface, we assert that the FUNCKIND is other
+ // than FUNC_DISPATCH.
+ //
+ // Convert this funcdesc from an Interface funcdesc to a
+ // Dispinterface funcdesc.
+ InterfaceFuncdescToDispatch(pfuncdesc);
+ }
+ pbindptr->lpfuncdesc = pfuncdesc;
+ *pdesckind = DESCKIND_FUNCDESC;
+ // fall through...
+
+CommonMatch:
+ // Get the typeinfo from the dfntbind, if we can, so we
+ // can determine if it's a funky dispinterface or not.
+ //
+
+ // if m_pdfntbind is not a GENPROJ_TYPEBIND, the QueryProtocol was already
+ // done, so don't re-do it
+ if (pdtbind == NULL)
+ pdtbind = (DYN_TYPEBIND *)m_pdfntbind->QueryProtocol(DYN_TYPEBIND::szProtocolName);
+
+ if (pdtbind != NULL) {
+ BOOL isFunky;
+ GEN_DTINFO *pgdtinfo = pdtbind->Pdtroot()->Pgdtinfo();
+
+ IfErrGoTo(::IsFunkyDispinterface(pgdtinfo, &isFunky), Error2);
+
+ // If it is funky, replace the exbind we return with the typeinfo
+ // for the current interface.
+ //
+ if (isFunky) {
+ *pptinfo = pgdtinfo;
+ pgdtinfo->AddRef();
+ exbind.Ptinfo()->Release();
+ break;
+ }
+ }
+
+ *pptinfo = exbind.Ptinfo(); // already addref'ed.
+ break;
+
+ case BKIND_DynTypeBindMatch:
+ case BKIND_ProjTypeBindMatch:
+ case BKIND_NestedTypeBindMatch:
+ pdfntbind = exbind.Pdfntbind();
+
+ DebAssert(pdfntbind != NULL, "bad DEFN_TYPEBIND.");
+
+ // Create a CDefnTypeComp to return to the user who must
+ // must release it eventually...
+ //
+ IfErrGoTo(CDefnTypeComp::Create(&pdfntcomp, pdfntbind), Error2);
+ pbindptr->lptcomp = pdfntcomp;
+ *pdesckind = DESCKIND_TYPECOMP;
+ *pptinfo = NULL;
+ break;
+
+ default:
+ DebHalt("bad BIND_KIND.");
+ break;
+ } // switch
+
+ goto Error;
+
+Error2:
+ exbind.Ptinfo()->Release();
+
+ // fall through
+Error:
+#if OE_WIN32
+ ConvertStringFree(szNameA);
+#else
+ #undef szNameA
+#endif //OE_WIN32
+ return HresultOfTiperr(err);
+}
+
+
+/***
+*PUBLIC CDefnTypeComp::BindType
+*Purpose:
+* Binds to a type identifier.
+* CONSIDER: share code with Bind -- ala BindIdDefn.
+*
+*Entry:
+* szName IN
+* lHashVal IN
+* pptinfo OUT - caller must release.
+* pptcomp OUT -- for now always NULL
+* will be non-NULL for nested types.. maybe...
+* Caller must release.
+*Exit:
+* None.
+*
+***********************************************************************/
+
+HRESULT CDefnTypeComp::BindType(LPOLESTR szName,
+ ULONG lHashVal,
+ ITypeInfoA FAR* FAR* pptinfo,
+ ITypeCompA FAR* FAR* pptcomp)
+{
+ EXBIND exbind;
+ BIND_KIND bkind;
+ DEFN_TYPEBIND *pdfntbind;
+ DYN_TYPEBIND *pdtbind;
+ GENPROJ_TYPEBIND *pgptbind;
+ NAMMGR *pnammgr;
+ HGNAM hgnam;
+ TIPERROR err;
+#if OE_WIN32
+ HRESULT hresult;
+ CHAR FAR *szNameA;
+#else //OE_WIN32
+ #define szNameA szName
+#endif //OE_WIN32
+
+ if (szName == NULL || pptinfo == NULL || pptcomp == NULL) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+#if OE_WIN32
+ IfOleErrRet(ConvertStringToA(szName, &szNameA));
+#endif //OE_WIN32
+
+ DebAssert(m_pdfntbind != NULL, "uninitialized.");
+
+ if ((pgptbind = (GENPROJ_TYPEBIND *)m_pdfntbind->
+ QueryProtocol(GENPROJ_TYPEBIND::szProtocolName)) != NULL) {
+ // Use the hashval.
+ IfErrGo(pgptbind->Pgtlibole()->GetNamMgr(&pnammgr));
+ IfErrGo(pnammgr->GetHgnamOfStrLhash(szNameA, lHashVal, &hgnam));
+ if (hgnam != HGNAM_Nil) {
+ IfErrGo(pgptbind->BindProjLevel(TRUE,
+ hgnam,
+ 0, // ignored
+ ACCESS_Public,
+ ACCESS_Public,
+ pgptbind->Compstate(),
+ &exbind));
+ }
+ }
+ else {
+ // Return no match otherwise
+ exbind.SetBindKind(BKIND_NoMatch);
+ }
+ bkind = exbind.BindKind();
+ switch (bkind) {
+ case BKIND_Error:
+ DebHalt("Should never happen.");
+ break;
+
+ case BKIND_NoMatch:
+ *pptinfo = NULL;
+ *pptcomp = NULL;
+ err = TIPERR_None;
+ break;
+
+ case BKIND_OneVarMatch:
+ case BKIND_FuncMatch:
+
+ DebHalt("Tried to bind to a type, but got a Var/Func");
+ break;
+
+ case BKIND_DynTypeBindMatch:
+ case BKIND_ProjTypeBindMatch:
+ pdfntbind = exbind.Pdfntbind();
+
+ DebAssert(pdfntbind != NULL, "bad DEFN_TYPEBIND.");
+
+ *pptcomp = NULL;
+ if (bkind == BKIND_DynTypeBindMatch) {
+ pdtbind = (DYN_TYPEBIND *)
+ pdfntbind->QueryProtocol(DYN_TYPEBIND::szProtocolName);
+ DebAssert(pdtbind != NULL, "should be DYN_TYPEBIND.");
+ *pptinfo = pdtbind->Pdtroot()->Pgdtinfo();
+ }
+ else if (bkind == BKIND_ProjTypeBindMatch) {
+ pgptbind = (GENPROJ_TYPEBIND *)
+ pdfntbind->QueryProtocol(GENPROJ_TYPEBIND::szProtocolName);
+ DebAssert(pgptbind != NULL, "should be GENPROJ_TYPEBIND.");
+ *pptinfo = NULL;
+ }
+ if (*pptinfo != NULL) {
+ (*pptinfo)->AddRef(); // caller must release
+ }
+ break;
+
+ default:
+ DebHalt("bad BIND_KIND.");
+ break;
+ } // switch
+
+Error:
+#if OE_WIN32
+ ConvertStringFree(szNameA);
+#endif //OE_WIN32
+ return HresultOfTiperr(err);
+}
diff --git a/private/oleauto/src/typelib/dfntcomp.hxx b/private/oleauto/src/typelib/dfntcomp.hxx
new file mode 100644
index 000000000..d2e212f94
--- /dev/null
+++ b/private/oleauto/src/typelib/dfntcomp.hxx
@@ -0,0 +1,92 @@
+/***
+*dfntcomp.hxx - TYPEINFO header file
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Implementation of ITypeComp for modules and classes.
+*
+*Revision History:
+*
+* 22-Jan-93 ilanc: Created.
+*
+*Implementation Notes:
+* Implemented by deferring to an instance of DEFN_TYPEBIND that
+* is produced for a record, module or project.
+*
+*****************************************************************************/
+
+#ifndef DFNTCOMP_HXX_INCLUDED
+#define DFNTCOMP_HXX_INCLUDED
+
+#include "cltypes.hxx"
+
+
+class DEFN_TYPEBIND;
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szDFNTCOMP_HXX)
+#define SZ_FILE_NAME g_szDFNTCOMP_HXX
+#endif
+
+
+/***
+*class CDefnTypeComp - 'dfntcomp': Type comp implementation
+*Purpose:
+* This class implements the ITypeComp protocol.
+*
+***********************************************************************/
+
+class CDefnTypeComp : public ITypeCompA
+{
+public:
+
+ STDMETHOD(QueryInterface) (THIS_ REFIID riid, LPVOID FAR* ppvObj);
+ STDMETHOD_(ULONG,AddRef) (THIS);
+ STDMETHOD_(ULONG,Release) (THIS);
+
+ // Creation method
+ static TIPERROR Create(CDefnTypeComp **ppdfntcomp,
+ DEFN_TYPEBIND *pdfntbind);
+
+ // Overridden virtual methods
+ STDMETHOD(Bind)(THIS_ LPOLESTR szName,
+ ULONG lHashVal,
+ WORD wflags,
+ ITypeInfoA FAR* FAR* lplptinfo,
+ DESCKIND FAR* lpdesckind,
+ BINDPTRA FAR* lpbindptr);
+
+ STDMETHOD(BindType)(THIS_ LPOLESTR szName,
+ ULONG lHashVal,
+ ITypeInfoA FAR* FAR* lplptinfo,
+ ITypeCompA FAR* FAR* lplptcomp);
+
+ // ctor
+ CDefnTypeComp();
+
+ // dtor
+ virtual ~CDefnTypeComp();
+
+ // Accessor
+ DEFN_TYPEBIND *Pdfntbind() const;
+
+protected:
+ nonvirt TIPERROR Init(DEFN_TYPEBIND *pdfntbind);
+
+private:
+ DEFN_TYPEBIND *m_pdfntbind;
+ USHORT m_cRefs;
+};
+
+
+// inline accessor
+inline DEFN_TYPEBIND *CDefnTypeComp::Pdfntbind() const
+{
+ return m_pdfntbind;
+}
+
+
+#endif // DFNTCOMP_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/dfstream.cxx b/private/oleauto/src/typelib/dfstream.cxx
new file mode 100644
index 000000000..df84ebec1
--- /dev/null
+++ b/private/oleauto/src/typelib/dfstream.cxx
@@ -0,0 +1,408 @@
+/***
+*dfstream.cxx - implementation of DOCFILE_STREAM
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Revision History:
+*
+* [00] 27-Jan-93 mikewo: Created.
+*
+*****************************************************************************/
+
+#define DFSTREAM_VTABLE
+
+#include "silver.hxx"
+#include "typelib.hxx"
+#include "dfstream.hxx"
+#include "gtlibole.hxx"
+
+
+#pragma hdrstop(RTPCHNAME)
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+char szOleDfstreamCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleDfstreamCxx
+#else
+static char szDfstreamCxx[] = __FILE__;
+#define SZ_FILE_NAME szDfstreamCxx
+#endif
+#endif //ID_DEBUG
+
+
+#pragma code_seg(CS_INIT)
+TIPERROR DOCFILE_STREAM::Open(IStorageA **ppstg, IStorageA **ppstgContainer, GenericTypeLibOLE *pgtlibole, UINT hte, BOOL isHost, LPOLESTR szName, STREAM_OPEN_MODE som, STREAM **ppstrm)
+{
+ TIPERROR err;
+
+ IfErrRet(Open(ppstg, ppstgContainer, isHost, szName, som, ppstrm));
+
+ (*(DOCFILE_STREAM **)ppstrm)->m_pgtlibole = pgtlibole;
+ (*(DOCFILE_STREAM **)ppstrm)->m_hte = hte;
+ if (pgtlibole != NULL)
+ pgtlibole->Qte(hte)->m_pdfstrm = *(DOCFILE_STREAM **)ppstrm;
+
+ return TIPERR_None;
+}
+#pragma code_seg( )
+
+/***
+* Open - Opens a DOCFILE_STREAM in an IStorage.
+*
+* Purpose:
+* This is used to create a DOCFILE_STREAM instance by opening the
+* specified IStream (creating it if necessary) for the specified
+* permissions.
+*
+* Inputs:
+* *ppstg - The address of an m_pstg of the object requesting the stream.
+* This is released and set to NULL upon this STREAM's closure,
+* if that performs the final release of the IStorage.
+* *ppstgContainer - If NULL, this is ignored. Otherwise, it is the address
+* of *ppstg's container IStorage which also needs to be released.
+* szName - The name of the IStream within that IStorage.
+* som - The permissions with which to open the stream. May be one of:
+* SOM_Read - Open for reading only. The named stream must exist.
+* SOM_Write - Create for read/write. Destroys the data in any
+* existing stream of the same name.
+* SOM_Append - Open for read/write. The named stream must exist.
+*
+* Outputs:
+* *ppstrm is set to the new STREAM and TIPERR_None is returned if
+* successful.
+*
+* *ppstrm is not modified on failure.
+*
+* On failure, *ppstg and *ppstgContainer are released and set to NULL if
+* that was the final release.
+**************************************************************************/
+#pragma code_seg( CS_INIT )
+TIPERROR DOCFILE_STREAM::Open(IStorageA **ppstg, IStorageA **ppstgContainer, BOOL isHost, LPOLESTR szName, STREAM_OPEN_MODE som, STREAM **ppstrm)
+{
+ HRESULT hresult;
+ DWORD stgm;
+ DOCFILE_STREAM *pdfstrm;
+ TIPERROR err;
+
+ if ((pdfstrm = MemNew(DOCFILE_STREAM)) == NULL) {
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+
+ ::new (pdfstrm) DOCFILE_STREAM;
+
+ // Determine the stgm mode constant that corresponds to som's value.
+ switch (som) {
+ case SOM_Read:
+ stgm = STGM_READ | STGM_SHARE_EXCLUSIVE;
+ break;
+
+ case SOM_Write:
+ stgm = STGM_READWRITE | STGM_SHARE_EXCLUSIVE | STGM_CREATE;
+ break;
+
+ case SOM_Append:
+ stgm = STGM_READWRITE | STGM_SHARE_EXCLUSIVE;
+ break;
+#if ID_DEBUG
+ default:
+ DebHalt("unsupported som");
+#endif //ID_DEBUG
+ }
+
+ // If SOM_Write, create the stream.
+ if (som == SOM_Write)
+ hresult = (*ppstg)->CreateStream(szName, stgm, 0L, 0L, &pdfstrm->m_pistrm);
+
+ // Otherwise, open the stream.
+ else
+ hresult = (*ppstg)->OpenStream(szName, NULL, stgm, 0L, &pdfstrm->m_pistrm);
+
+ if (hresult != NOERROR) {
+ pdfstrm->Release();
+ err = TiperrOfHresult(hresult);
+ goto Error;
+ }
+
+ pdfstrm->m_ppstg = ppstg;
+ pdfstrm->m_ppstgContainer = ppstgContainer;
+ pdfstrm->m_isHost = isHost;
+
+ *ppstrm = pdfstrm;
+ return TIPERR_None;
+
+Error:
+ if (!(*ppstg)->Release())
+ *ppstg = NULL;
+ if (ppstgContainer != NULL && *ppstgContainer != NULL
+ && !(*ppstgContainer)->Release())
+ *ppstgContainer = NULL;
+ return err;
+}
+#pragma code_seg()
+
+
+
+#pragma code_seg(CS_INIT)
+DOCFILE_STREAM::DOCFILE_STREAM()
+{
+ m_pistrm = NULL;
+ m_ppstg = NULL;
+ m_cbReadBufferLeft = 0;
+ m_cbWriteBufferLeft = sizeof(m_rgbIOBuffer);
+ m_pbBuffer = m_rgbIOBuffer;
+ m_isHost = FALSE;
+ m_dontRelease = FALSE;
+ m_cRefs = 1;
+ m_pgtlibole = NULL;
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_INIT)
+DOCFILE_STREAM::~DOCFILE_STREAM()
+{
+ // Do nothing
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_INIT)
+TIPERROR DOCFILE_STREAM::Read(VOID *buffer, ULONG cbSize)
+{
+ BYTE HUGE *hpb = (BYTE HUGE *)buffer;
+ TIPERROR err;
+
+ // Do nothing if nothing is requested.
+ if (cbSize == 0)
+ return TIPERR_None;
+
+ DebAssert(m_cbWriteBufferLeft == sizeof(m_rgbIOBuffer) || m_cbReadBufferLeft == 0, "Read");
+
+ // Empty the I/O buffer into the output buffer and refill it
+ // until the I/O buffer holds enough to finish the requested read.
+ while ((ULONG)m_cbReadBufferLeft < cbSize) {
+ memcpy(hpb, (BYTE HUGE *)m_pbBuffer, m_cbReadBufferLeft);
+ cbSize -= (ULONG)m_cbReadBufferLeft;
+ hpb += m_cbReadBufferLeft;
+ IfErrRet(FillBuffer());
+ }
+
+#if OE_WIN16
+ DebAssert(cbSize <= (ULONG)(USHORT)USHRT_MAX, "whoops! overflow.");
+#endif // VBA2 && OE_WIN16
+
+ // Finish the requested read.
+ memcpy(hpb, (BYTE HUGE *)m_pbBuffer, (UINT)cbSize);
+ m_cbReadBufferLeft -= (UINT)cbSize;
+ m_pbBuffer += (UINT)cbSize;
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+TIPERROR DOCFILE_STREAM::Write(const VOID *buffer, ULONG cbSize)
+{
+ BYTE HUGE *hpb = (BYTE HUGE *)buffer;
+ TIPERROR err;
+
+ DebAssert(m_cbWriteBufferLeft == sizeof(m_rgbIOBuffer) || m_cbReadBufferLeft == 0, "Write");
+
+ // Fill the I/O buffer into the output buffer and flush it
+ // until the I/O is more than big enough to finish the requested
+ // write.
+ while ((ULONG)m_cbWriteBufferLeft <= cbSize) {
+ memcpy((BYTE HUGE *)m_pbBuffer, hpb, m_cbWriteBufferLeft);
+ cbSize -= (ULONG)m_cbWriteBufferLeft;
+ hpb += m_cbWriteBufferLeft;
+ m_cbWriteBufferLeft = 0;
+ IfErrRet(FlushBuffer());
+ }
+ // Finish the requested write. Note that this is guaranteed to
+ // not completely fill the I/O buffer. This important so that
+ // we don't get the situation of a full, but unflushed buffer
+ // (which would be indistinguishable from an empty but unfilled
+ // buffer).
+ //
+#if OE_WIN16
+ DebAssert(cbSize <= (ULONG)(USHORT)USHRT_MAX, "whoops! overflow.");
+#endif // VBA2 && OE_WIN16
+
+ memcpy((BYTE HUGE *)m_pbBuffer, hpb, (UINT)cbSize);
+ m_cbWriteBufferLeft -= (UINT)cbSize;
+ DebAssert(m_cbWriteBufferLeft > 0, "Read");
+ m_pbBuffer += (UINT)cbSize;
+ m_cbReadBufferLeft = 0;
+ return TIPERR_None;
+}
+
+
+#pragma code_seg(CS_INIT)
+TIPERROR DOCFILE_STREAM::ReadTextLine(XSZ szLine, UINT cchMax)
+{
+ DebHalt("Not implemented");
+ return HresultOfScode(E_NOTIMPL);
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_INIT)
+TIPERROR DOCFILE_STREAM::FillBuffer()
+{
+ ULONG cb;
+ HRESULT hresult;
+ TIPERROR err;
+
+ DebAssert(m_cbWriteBufferLeft == sizeof(m_rgbIOBuffer) || m_cbReadBufferLeft == 0, "FillBuffer");
+
+ // If we have something in the write buffer at this time, flush it.
+ if (m_cbWriteBufferLeft != sizeof(m_rgbIOBuffer)) {
+ IfErrRet(FlushBuffer());
+ }
+
+ // Set things up to indicate we're using the I/O buffer as a read buffer.
+ m_cbWriteBufferLeft = sizeof(m_rgbIOBuffer);
+
+ // Fill the I/O buffer.
+ hresult = m_pistrm->Read(m_rgbIOBuffer, sizeof(m_rgbIOBuffer), &cb);
+
+ if (hresult != NOERROR)
+ return TiperrOfHresult(hresult);
+
+ // If we obtained no bytes at all from the read, return EOF.
+ if (cb == 0)
+ return TIPERR_Eof;
+
+ // Otherwise, record the number of bytes placed into the buffer.
+ m_cbReadBufferLeft = (UINT)cb;
+ m_pbBuffer = m_rgbIOBuffer;
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+TIPERROR DOCFILE_STREAM::FlushBuffer()
+{
+ ULONG cb, cbWritten;
+ HRESULT hresult;
+
+ DebAssert(m_cbWriteBufferLeft == sizeof(m_rgbIOBuffer) || m_cbReadBufferLeft == 0, "FlushBuffer");
+
+ // Set things up to indicate we're using the I/O buffer as a write buffer.
+ m_cbReadBufferLeft = 0;
+
+ cb = sizeof(m_rgbIOBuffer)-m_cbWriteBufferLeft;
+
+ // Perform the write only if the write buffer isn't empty.
+ if (cb != 0) {
+ hresult = m_pistrm->Write(m_rgbIOBuffer, cb, &cbWritten);
+
+ if (GetScode(hresult) == STG_E_REVERTED || cb != cbWritten)
+ return TIPERR_WriteFault;
+
+ if (hresult != NOERROR)
+ return TiperrOfHresult(hresult);
+ }
+
+ m_pbBuffer = m_rgbIOBuffer;
+ m_cbWriteBufferLeft = sizeof(m_rgbIOBuffer);
+ return TIPERR_None;
+}
+
+#pragma code_seg(CS_INIT)
+TIPERROR DOCFILE_STREAM::GetPos(LONG *plPos)
+{
+ HRESULT hresult;
+ LARGE_INTEGER li;
+ ULARGE_INTEGER uli;
+
+ LISet32(li, 0L);
+ hresult = m_pistrm->Seek(li, STREAM_SEEK_CUR, &uli);
+ DebAssert(hresult == NOERROR, "GetPos");
+ *plPos = (LONG)uli.LowPart;
+
+ DebAssert(m_cbWriteBufferLeft == sizeof(m_rgbIOBuffer) || m_cbReadBufferLeft == 0, "Read");
+
+ // If the I/O buffer holds read bytes, subtract the number of
+ // as-yet-unused bytes in the I/O buffer from the file offset.
+ // If the I/O buffer holds written bytes, add the number of
+ // bytes placed in the I/O buffer but not yet flushed.
+ *plPos += (INT)(sizeof(m_rgbIOBuffer)-m_cbWriteBufferLeft-m_cbReadBufferLeft);
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+#pragma code_seg( CS_CORE )
+TIPERROR DOCFILE_STREAM::SetPos(LONG lPos)
+{
+ HRESULT hresult;
+ LARGE_INTEGER li;
+ TIPERROR err;
+
+ // Flush the write buffer if there's anything in it.
+ if (m_cbWriteBufferLeft != sizeof(m_rgbIOBuffer)) {
+ IfErrRet(FlushBuffer());
+ }
+
+ // In any case, reset the I/O buffer to be empty.
+ m_cbReadBufferLeft = 0;
+ m_cbWriteBufferLeft = sizeof(m_rgbIOBuffer);
+ m_pbBuffer = m_rgbIOBuffer;
+
+ LISet32(li, lPos);
+ hresult = m_pistrm->Seek(li, STREAM_SEEK_SET, NULL);
+ DebAssert(hresult == NOERROR, "SetPos");
+
+ return TIPERR_None;
+}
+#pragma code_seg( )
+
+#pragma code_seg( CS_INIT )
+void DOCFILE_STREAM::AddRef()
+{
+ m_cRefs++;
+}
+#pragma code_seg( )
+
+#pragma code_seg(CS_INIT)
+TIPERROR DOCFILE_STREAM::Release()
+{
+ TIPERROR err = TIPERR_None;
+
+ if (--m_cRefs != 0)
+ return TIPERR_None;
+
+ if (m_pgtlibole != NULL) {
+ m_pgtlibole->Qte(m_hte)->m_pdfstrm = NULL;
+ }
+
+ // Flush the write buffer if there's anything in it.
+ if (m_cbWriteBufferLeft != sizeof(m_rgbIOBuffer)) {
+ err = FlushBuffer();
+ }
+
+ if (m_pistrm != NULL) {
+ m_pistrm->Release();
+ }
+
+ if (m_ppstg != NULL) {
+ if (!(*m_ppstg)->Release())
+ *m_ppstg = NULL;
+ if (m_ppstgContainer != NULL && *m_ppstgContainer != NULL
+ && !(*m_ppstgContainer)->Release())
+ *m_ppstgContainer = NULL;
+ }
+
+ // Only delete this instance if m_dontRelease is FALSE. m_dontRelease
+ // will only be TRUE when created with the NewWrapper method.
+ if (!m_dontRelease) {
+ this->DOCFILE_STREAM::~DOCFILE_STREAM();
+ MemFree(this);
+ }
+
+
+ return err;
+}
+
+#pragma code_seg()
diff --git a/private/oleauto/src/typelib/dfstream.hxx b/private/oleauto/src/typelib/dfstream.hxx
new file mode 100644
index 000000000..7e5581e35
--- /dev/null
+++ b/private/oleauto/src/typelib/dfstream.hxx
@@ -0,0 +1,77 @@
+/***
+*dfstream.hxx - declaration of DOCFILE_STREAM
+*
+* Copyright (C) 1990, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* To provide a wrapper on IStream.
+*
+*****************************************************************************/
+
+#ifndef DFSTREAM_HXX_INCLUDED
+#define DFSTREAM_HXX_INCLUDED
+
+#include "stream.hxx"
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szDFSTREAM_HXX)
+#define SZ_FILE_NAME g_szDFSTREAM_HXX
+#endif
+
+
+class GenericTypeLibOLE;
+
+/***
+*class DOCFILE_STREAM : DOCFILE implementation of Stream protocol.
+*Purpose:
+* Implementation of the STREAM protocol using OLE DOCFILE streams.
+*
+***********************************************************************/
+
+class DOCFILE_STREAM : public STREAM
+{
+public:
+ static TIPERROR Open(IStorageA **ppstg, IStorageA **ppstgContainer, GenericTypeLibOLE *pgtlibole, UINT hte, BOOL isHost, LPOLESTR szName, STREAM_OPEN_MODE som, STREAM **ppstrm);
+ static TIPERROR Open(IStorageA **ppstg, IStorageA **ppstgContainer, BOOL isHost, LPOLESTR szName, STREAM_OPEN_MODE som, STREAM **ppstrm);
+
+ static TIPERROR NewWrapper(DOCFILE_STREAM **ppdfstrm, BOOL fDontRelease);
+
+ nonvirt void InitWrapper(IStorageA **ppstg, IStorageA **ppstgContainer, IStreamA *pistrm, BOOL isHost);
+ nonvirt void FreeWrapper();
+ nonvirt void AddRef();
+
+ virtual TIPERROR Read(VOID *buffer, ULONG cbsize);
+ virtual TIPERROR Write(const VOID *buffer, ULONG cbsize);
+ virtual TIPERROR ReadTextLine(XSZ szLine, UINT cchMax);
+ virtual TIPERROR GetPos(LONG *plPos);
+ virtual TIPERROR SetPos(LONG lPos);
+ virtual TIPERROR Release();
+
+protected:
+ IStorageA **m_ppstg, **m_ppstgContainer;
+ GenericTypeLibOLE *m_pgtlibole;
+ UINT m_hte;
+ IStreamA *m_pistrm;
+ UINT m_cRefs;
+ BOOL m_isHost;
+ BOOL m_dontRelease;
+ UINT m_cbReadBufferLeft;
+ UINT m_cbWriteBufferLeft;
+ BYTE *m_pbBuffer;
+ BYTE m_rgbIOBuffer[512];
+
+ nonvirt TIPERROR FillBuffer();
+ nonvirt TIPERROR FlushBuffer();
+ ~DOCFILE_STREAM(); // Included so clients can't use delete on a stream
+ DOCFILE_STREAM(); // Included to avoid warning
+
+
+#ifdef DFSTREAM_VTABLE
+#pragma VTABLE_EXPORT
+#endif
+};
+
+
+#endif // !DFSTREAM_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/dstrmgr.cxx b/private/oleauto/src/typelib/dstrmgr.cxx
new file mode 100644
index 000000000..d9f510b27
--- /dev/null
+++ b/private/oleauto/src/typelib/dstrmgr.cxx
@@ -0,0 +1,1692 @@
+/***
+*dstrmg.cxx - Doc string manager.
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* The Doc, String Manager handles all the help strings in the typelib.
+* In this implementation we huffman encode all the words.
+*
+*Implementation Notes: Steps:
+* 1. Parse all the Doc strings that are passed in and return a handle to the
+* client. This handle is used latter to get the encoded doc string by calling
+* GetEncodedDocStrOfHst(). Note that the encoded doc string is serialized in
+* TYPE_DATA's block manager.
+* 2. Each word of the string hashed and a frequency count is maintained in
+* WORD_ENTRY for that word.
+* 3. For each passed in string cache a SEMI_ENCODED_STRING that
+* represents the original string.
+* 4. When all the strings are parsed Doc string sorts all the WORD ENTRY
+* according to the Frequency using QuickSort.
+* 5. Form a forest of Huffman trees (one of each WORD_ENTRY). (maitain the
+* sorted order)
+* 6. Create a huffman tree using the sub trees with the least frequency.
+* Insert the new tree in the sorted list (using Insert sort).
+* 7. Repeat 6 to create the HUFFMAN TREE.
+*
+*
+*Revision History:
+*
+* 18-July-93 rajivk: Created.
+*
+*Implementation Notes:
+*
+*
+*
+*****************************************************************************/
+
+#include "silver.hxx"
+#include "typelib.hxx"
+#include <stddef.h>
+#include "xstring.h"
+#include <stdlib.h>
+#include <new.h>
+#include "typelib.hxx"
+#include "cltypes.hxx"
+#include "stream.hxx"
+#include "blkmgr.hxx"
+#include "dstrmgr.hxx"
+#include "clutil.hxx"
+#include "tls.h"
+
+#pragma hdrstop(RTPCHNAME)
+
+#undef tolower
+#undef toupper // Don't use unsafe macro forms
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+char szDSTRMgrCxx[] = __FILE__;
+#define SZ_FILE_NAME szDSTRMgrCxx
+#endif
+
+#if ID_DEBUG
+const ULONG UL_MASK = 0xff800000;
+#endif
+
+
+const XCHAR xchNull = '\0';
+
+#define MAX_ENCODING_ALLOWED 64
+
+#define DS_cStrTableInit 256 // initial assumed # of strings
+#define DS_cStrTableGrow 512 // # of string we grow by
+
+const XCHAR xchSpace = ' ';
+
+
+// ____________________________
+// |1| BYTE ..... |8| ------> .... ---->
+// ----------------------------
+// ^ ^
+// 1st bit 8th bit
+
+
+#define FIRST_BIT 0x80
+#define SECOND_BIT 0x40
+#define THIRD_BIT 0x20
+#define FOURTH_BIT 0x10
+#define FIFTH_BIT 0x08
+#define SIXTH_BIT 0x04
+#define SEVENTH_BIT 0x02
+#define EIGHTH_BIT 0x01
+
+#define Get1stBit(b) (b & FIRST_BIT)
+#define Get2ndBit(b) (b & SECOND_BIT)
+#define Get3rdBit(b) (b & THIRD_BIT)
+#define Get4thBit(b) (b & FOURTH_BIT)
+#define Get5thBit(b) (b & FIFTH_BIT)
+#define Get6thBit(b) (b & SIXTH_BIT)
+#define Get7thBit(b) (b & SEVENTH_BIT)
+#define Get8thBit(b) (b & EIGHTH_BIT)
+
+#define Set1stBit(b,v) b = (v) ? (b | FIRST_BIT) : (b & ~FIRST_BIT)
+#define Set2ndBit(b,v) b = (v) ? (b | SECOND_BIT) : (b & ~SECOND_BIT)
+#define Set3rdBit(b,v) b = (v) ? (b | THIRD_BIT) : (b & ~THIRD_BIT)
+#define Set4thBit(b,v) b = (v) ? (b | FOURTH_BIT) : (b & ~FOURTH_BIT)
+#define Set5thBit(b,v) b = (v) ? (b | FIFTH_BIT) : (b & ~FIFTH_BIT)
+#define Set6thBit(b,v) b = (v) ? (b | SIXTH_BIT) : (b & ~SIXTH_BIT)
+#define Set7thBit(b,v) b = (v) ? (b | SEVENTH_BIT) : (b & ~SEVENTH_BIT)
+#define Set8thBit(b,v) b = (v) ? (b | EIGHTH_BIT) : (b & ~EIGHTH_BIT)
+
+VOID ZeroFill(VOID HUGE * pv, ULONG ubSize);
+
+/***
+*PUBLIC DOCSTR_MGR::DOCSTR_MGR - constructor
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+DOCSTR_MGR::DOCSTR_MGR()
+{
+
+ m_uStrCount = 0;
+ m_uMaxStrCount = 0;
+ m_uWordCount = 0;
+ m_ulCmptSizeOfTree = 0;
+ m_ulCurrentOffset = 0;
+ m_usMaxStrLen = 0;
+ m_pvHuffmanCmpt = NULL;
+ m_phtmRoot = NULL;
+ m_uWordCount = 0;
+ m_ppsesHelpStr = NULL;
+ m_ppweHashTbl = NULL;
+
+
+#if ID_DEBUG
+ m_uDebTotalStrSize = 0;
+ m_uDebTotalEncodedStrSize = 0;
+ m_uDebTotalWord = 0;
+#endif
+
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC DOCSTR_MGR::~DOCSTR_MGR - destructor
+*Purpose:
+* Releases the resources owned by the docstrmgr.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+DOCSTR_MGR::~DOCSTR_MGR()
+{
+ UINT i;
+ SEMI_ENCODED_STRING *pses;
+ IMalloc *pmalloc = Pmalloc();
+
+
+ // release the table allocate for the hash table;
+ if (m_ppweHashTbl != NULL) {
+
+ pmalloc->Free(m_ppweHashTbl);
+ }
+
+ // release the table allocate for the strings;
+ if (m_ppsesHelpStr != NULL) {
+ // Walk the table and release all the
+ for (i = 0; i < m_uStrCount; i++) {
+ if ((pses = m_ppsesHelpStr[i]) != NULL) {
+ if (pses->m_ppweStrTbl)
+ pmalloc->Free(pses->m_ppweStrTbl);
+
+
+ pmalloc->Free(pses);
+
+ } //if
+ } //for
+
+ pmalloc->Free(m_ppsesHelpStr);
+ }
+
+ // release the table allocate for the huffman tree
+ if (m_pvHuffmanCmpt != NULL) {
+ pmalloc->Free(m_pvHuffmanCmpt);
+ }
+
+ if (m_uStrCount) {
+ if (m_phtmRoot != NULL)
+ ReleaseHuffmanTree(m_phtmRoot);
+ }
+
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC DOCSTR_MGR::Init - initialize the help manager
+*Purpose:
+* Initializes the doc string manager. Allocates space for the HASH TABLE
+* and the initial space for storing the SEMI_ENCODED strings that are
+* passed in.
+*
+*
+*Entry:
+*
+*Exit:
+* Return TIPERROR indicating success/failure.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR DOCSTR_MGR::Init()
+{
+ TIPERROR err=TIPERR_None;
+
+
+ m_uMaxStrCount = DS_cStrTableInit;
+
+ // initialize the help string array for DS_cStrTableInit entries. We
+ // reallocate more entries as required (this is done in ParseString() ).
+ if ((m_ppsesHelpStr = (SEMI_ENCODED_STRING **)
+ Pmalloc()->Alloc(m_uMaxStrCount*sizeof(SEMI_ENCODED_STRING*))) == NULL) {
+ return TIPERR_OutOfMemory;
+ }
+
+ // initilize the memory to 0
+ ZeroFill(m_ppsesHelpStr, m_uMaxStrCount*sizeof(SEMI_ENCODED_STRING*));
+
+ // initialize the bucket table.
+ if ((m_ppweHashTbl = (WORD_ENTRY **) Pmalloc()->Alloc(DS_cBuckets*sizeof(WORD_ENTRY *))) == NULL)
+ return TIPERR_OutOfMemory;
+
+ // initilize the memory to 0
+ ZeroFill(m_ppweHashTbl, DS_cBuckets*sizeof(WORD_ENTRY *));
+
+ return err;
+
+}
+#pragma code_seg()
+
+/***
+*PUBLIC DOCSTR_MGR::Read
+*Purpose:
+* Reads the serialized doc string Manager. This function also releases
+* the resources that will not be required since we are reading the
+* serialized doc string manager.
+*
+*IMPLEMENTATION Notes:- Since the huffman tree that is serialized could be
+* bigger than 64K and the Stream cannot Read/Write > 64K, we break up the
+* tree into chunks of 32K each.
+*Entry:
+* psstream : Pointer to the STREAM to read from.
+*
+*
+*Exit:
+** TIPERROR
+*
+***********************************************************************/
+TIPERROR DOCSTR_MGR::Read(STREAM *pstrm)
+{
+ TIPERROR err;
+ USHORT uSizeToRead = 0xffff;
+ LONG lSizeRemaining;
+ VOID HUGE *pv;
+
+ DebAssert(m_usMaxStrLen == 0 &&
+ m_ulCmptSizeOfTree == 0 &&
+ m_phtmRoot == NULL &&
+ m_pvHuffmanCmpt == NULL, " Dstrmgr not initialized ");
+
+ // Write out the maximum size of the string that was compacted.
+ IfErrRet(pstrm->ReadUShort(&m_usMaxStrLen));
+
+ // Read the size of the huffman tree.
+ IfErrRet(pstrm->ReadULong(&m_ulCmptSizeOfTree));
+
+ if (m_ulCmptSizeOfTree > 0) {
+
+ // Allocate space for reading the huffman tree.
+ if ((m_pvHuffmanCmpt = (VOID HUGE *) Pmalloc()->Alloc((size_t)m_ulCmptSizeOfTree)) == NULL) {
+ // in case of error release the memory allocated so far.
+ return TIPERR_OutOfMemory;
+ }
+
+
+ lSizeRemaining = (LONG) m_ulCmptSizeOfTree;
+ pv = m_pvHuffmanCmpt;
+
+ while (lSizeRemaining > 0) {
+ uSizeToRead =(USHORT) ((lSizeRemaining > 0xffff) ? 0xffff : lSizeRemaining);
+
+ // serialize the huffman tree as a stream of bytes.
+ IfErrRet(pstrm->Read((VOID *)pv, uSizeToRead));
+
+ pv = (BYTE *)pv + uSizeToRead;
+ lSizeRemaining -= uSizeToRead;
+ }
+ }
+
+
+ // since we are reading the serialized doc string manager we will not
+ // build it.
+ // so release the table allocate for the hash table;
+ if (m_ppweHashTbl != NULL) {
+ Pmalloc()->Free(m_ppweHashTbl);
+ m_ppweHashTbl = NULL;
+ }
+
+ // release the table allocate for the strings;
+ if (m_ppsesHelpStr != NULL) {
+ Pmalloc()->Free(m_ppsesHelpStr);
+ m_ppsesHelpStr = NULL;
+ }
+
+
+ return TIPERR_None;
+}
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC DOCSTR_MGR::Write
+*Purpose:
+* Serializes doc string Manager
+*
+*IMPLEMENTATION Notes:- Since the huffman tree that is serialized could be
+* bigger than 64K and the Stream cannot Read/Write > 64K, we break up the
+* tree into chunks of 32K each.
+*Entry:
+* psstream : Pointer to the STREAM to write to.
+*
+*
+*Exit:
+** TIPERROR
+*
+***********************************************************************/
+TIPERROR DOCSTR_MGR::Write(STREAM *pstrm)
+{
+ TIPERROR err;
+ USHORT uSizeToWrite = 0xffff;
+ LONG lSizeRemaining;
+ VOID HUGE *pv;
+
+ // Write out the maximum size of the string that was compacted.
+ IfErrRet(pstrm->WriteUShort(m_usMaxStrLen));
+
+ // Write out the size of the huffman tree.
+ IfErrRet(pstrm->WriteULong(m_ulCmptSizeOfTree));
+
+ // do not write the tree if there was no helpstring.
+ if (m_ulCmptSizeOfTree > 0) {
+
+ lSizeRemaining = (LONG) m_ulCmptSizeOfTree;
+ pv = m_pvHuffmanCmpt;
+
+ while (lSizeRemaining > 0) {
+ uSizeToWrite = (USHORT) ((lSizeRemaining > 0xffff) ? 0xffff : lSizeRemaining);
+
+ // serialize the huffman tree as a stream of bytes.
+ IfErrRet(pstrm->Write((VOID *)pv, uSizeToWrite));
+
+ pv = (BYTE *)pv + uSizeToWrite;
+ lSizeRemaining -= uSizeToWrite;
+ }
+
+ DebAssert(lSizeRemaining == 0, " write failed ");
+
+ }
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC DOCSTR_MGR::ParseString
+*Purpose:
+* Parse a string. Returns an array of words that forms the string. We
+* ignore the irst blank. Starting from the 2nd space till the end of the
+* next word forms a word.
+* e.g. "This is an example string" will get prased as following 5 words.
+* 1st word "This"
+* 2nd word "is"
+* 3rd word " a"
+* 4th word " sample"
+* 5th word " string"
+*
+*Entry:
+* szStr : string to parse.
+*
+*
+*Exit:
+* rglstr : array of strings containging the words that forms szStr.
+* uWordCount : size of the array rglstr;
+*
+***********************************************************************/
+
+TIPERROR DOCSTR_MGR::ParseString(XSZ_CONST szStr, BSTRA **lplpbstr, UINT *puWordCount)
+{
+ UINT uLen=0;
+ XSZ_CONST szWordStart;
+ TIPERROR err=TIPERR_None;
+ UINT uchWordLen=0;
+ UINT uWordMax=0;
+ UINT i;
+ UINT uStrLen;
+ BSTRA *lpbstrNew;
+
+ DebAssert(lplpbstr != NULL && puWordCount != NULL, " invalid parameter ");
+
+ *puWordCount=0;
+ *lplpbstr = NULL;
+
+ // if the passed in string is NULL then return
+ if (szStr == NULL)
+ return TIPERR_None;
+
+ // save the max str length
+ uStrLen = strlen(szStr) + 1;
+
+ if (uStrLen > m_usMaxStrLen)
+ m_usMaxStrLen = uStrLen;
+
+#if ID_DEBUG
+ m_uDebTotalStrSize += uStrLen;
+#endif
+
+ // extract all the words out of the string. We terminate when
+ // we get a null word.
+ for (;;) {
+
+ uchWordLen = 0;
+
+ // Remove the first space if it is not the beginning of the Doc Str
+ //
+ if ((*szStr == xchSpace) && *puWordCount)
+ szStr++;
+
+ // mark the begining of the next word.
+ szWordStart = szStr;
+
+ // Check if we have reached the end of the string
+ if (*szStr == xchNull) {
+ uchWordLen = 1;
+ }
+
+ // space preceeding the word becomes part of the next word.
+ while(*szStr == xchSpace) {
+ uchWordLen++;
+ szStr++;
+ }
+
+
+ // if we have not reached the end of the string then extract the
+ // word out of the string.
+ if (*szStr != xchNull) {
+ while ((*szStr != xchSpace) && (*szStr != xchNull)) {
+ uchWordLen++;
+ szStr++;
+ }
+ }
+ else {
+ // throw away the trailing blank characters.
+ // Go for the next iteration
+ if (*szWordStart != xchNull) {
+ continue;
+ }
+ }
+
+#define CWORDSGROW 8 // # of words to grow by -- should be a
+ // multiple of 4 so that CWORDSGROW * sizeof(BSTRA)
+ // is an multiple of a paragraph
+ // if we do not have any empty entry in rglstr then allocate more space.
+ if (uWordMax == *puWordCount) {
+ if ((lpbstrNew = (BSTRA *)Pmalloc()->Realloc(*lplpbstr,
+ (uWordMax+CWORDSGROW)*sizeof(BSTRA)))==NULL) {
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+
+ *lplpbstr = lpbstrNew;
+ uWordMax += CWORDSGROW;
+ }
+
+ if (((*lplpbstr)[*puWordCount] = AllocBstrLenA((LPSTR)szWordStart, uchWordLen)) == NULL) {
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+
+ // inc the count of words
+ *puWordCount += 1;
+
+ // break out if we have reached the end of the string.
+ if (*szWordStart == xchNull)
+ break;
+
+
+ } // for
+
+#if ID_DEBUG
+ m_uDebTotalWord += *puWordCount;
+#endif
+
+ return err;
+Error:
+ if (lplpbstr != NULL) {
+ for (i=0; i < *puWordCount; i++) {
+ DebAssert((*lplpbstr)[i] != NULL, " should not be null ");
+ FreeBstrA((*lplpbstr)[i]);
+ }
+ Pmalloc()->Free(*lplpbstr);
+ }
+
+ return err;
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC DOCSTR_MGR::AddWord
+*Purpose:
+* Add a word to the hash table and bump the reference count of the word.
+*
+*Entry:
+* szWord : Word to Add.
+*
+*
+*Exit:
+* pwe : pointer to the word entry structure for the word(szWord) passed in.
+* TIPERROR : (TIPERR_OutOfMemory)
+*
+***********************************************************************/
+TIPERROR DOCSTR_MGR::AddWord(BSTRA bstrWord, WORD_ENTRY **ppwe)
+{
+ TIPERROR err;
+ ULONG lHash=0;
+ WORD_ENTRY *pwe;
+ UINT uIndex=0;
+
+ lHash = LHashValOfNameA(0x0000, (LPSTR)bstrWord);
+
+ // get the corresponding index in the hash table for whash.
+ uIndex = IndexOfHash(lHash);
+
+ pwe = *(m_ppweHashTbl+uIndex);
+
+ // walk the link list and see if the word is in the list.
+ while (pwe != NULL) {
+ // does this entry contain the word we are looking for
+ if (!strcmp(bstrWord, pwe->m_bstrWord)) {
+ pwe->m_uFreq++;
+ *ppwe = pwe;
+ break;
+ } // if
+ // get the next Word Entry
+ pwe = pwe->m_pweNext;
+
+ } // while
+
+
+ // if the word does not appear in the table then add a new entry.
+ if (pwe == NULL)
+ IfErrRet(AddNewWord(bstrWord, ppwe));
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC DOCSTR_MGR::AddNewWord
+*Purpose:
+* Add a new entry for the word passed in. Return a pointer to the Word_Entry
+* that got added.
+*
+*Entry:
+* szWord : Word for which a new WORD_ENTRY needs to be added.
+*
+*
+*Exit:
+* pwe : pointer to the word entry structure for the word(szWord) passed in.
+* TIPERROR : (TIPERR_OutOfMemory)
+*
+***********************************************************************/
+TIPERROR DOCSTR_MGR::AddNewWord(BSTRA bstrWord, WORD_ENTRY **ppwe)
+{
+ ULONG lHash=0;
+ WORD_ENTRY *pwe=NULL;
+ UINT uIndex=0;
+
+
+ lHash = LHashValOfNameA(0x0000, (LPSTR)bstrWord);
+
+ // Allocate a new WORD_ENTRY structure for this word.
+ if ((pwe = (WORD_ENTRY *)Pmalloc()->Alloc(sizeof(WORD_ENTRY))) == NULL)
+ return TIPERR_OutOfMemory;
+
+ // initilize the memory to 0
+ ZeroFill(pwe, sizeof(WORD_ENTRY));
+
+ // initialize the structure
+ pwe->m_uFreq = 1;
+ pwe->m_bstrWord = AllocBstrA(bstrWord);
+
+ uIndex = IndexOfHash(lHash);
+
+ // link this node in the hash table.
+ pwe->m_pweNext = *(m_ppweHashTbl+uIndex);
+ *(m_ppweHashTbl+uIndex) = pwe;
+
+ // bump up the count of the words.
+ m_uWordCount++;
+
+ // set the return parameter
+ *ppwe = pwe;
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC DOCSTR_MGR::GetHstOfHelpString
+*Purpose:
+* This function process a doc string(text form). It returns a handle
+* for the string. This handle is a temporary handle. After all the
+* string is processed we visit all the funcdefn and replaced this
+* handle by hchunk in the TYPE_DATA's blockmgr.
+*
+*Entry:
+* szDocStr : DocString that needs to be encoded.
+*
+*
+*Exit:
+* HST : handle for the doc string.
+* TIPERROR : (TIPERR_OutOfMemory)
+*
+***********************************************************************/
+TIPERROR DOCSTR_MGR::GetHstOfHelpString(XSZ_CONST szDocStr, HST *phst)
+{
+
+ TIPERROR err=TIPERR_None;
+ UINT uWords, i;
+ BSTRA *lpbstr;
+ SEMI_ENCODED_STRING *ses;
+ SEMI_ENCODED_STRING **ppsesHelpStrNew;
+ WORD_ENTRY *pwe;
+
+ DebAssert(szDocStr != NULL && phst != NULL, " invalid parameter ");
+
+ // if we do not have any empty entry for any string then allocate.
+ //
+ if (m_uMaxStrCount == m_uStrCount) {
+
+ m_uMaxStrCount += DS_cStrTableGrow;
+
+ if ((ppsesHelpStrNew = (SEMI_ENCODED_STRING **)
+ Pmalloc()->Realloc(m_ppsesHelpStr, m_uMaxStrCount*sizeof(SEMI_ENCODED_STRING*))) == NULL) {
+
+ m_uMaxStrCount -= DS_cStrTableGrow;
+ return TIPERR_OutOfMemory;
+ }
+ m_ppsesHelpStr = ppsesHelpStrNew;
+
+ }
+
+
+ // Parse the string.
+ IfErrRet(ParseString(szDocStr, &lpbstr, &uWords));
+
+ // allcate space for (semi) encoding the string.
+ if ((ses = (SEMI_ENCODED_STRING *)
+ Pmalloc()->Alloc(sizeof(SEMI_ENCODED_STRING))) == NULL) {
+
+ return TIPERR_OutOfMemory;
+ }
+
+ // initilize the memory to 0
+ ZeroFill(ses, sizeof(SEMI_ENCODED_STRING));
+
+ // allocate space for saving pointers to WORD_ENTRY for each word in the
+ // doc string.
+ if ((ses->m_ppweStrTbl = (WORD_ENTRY **)
+ Pmalloc()->Alloc(uWords*sizeof(WORD_ENTRY*))) == NULL) {
+
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+
+ // initilize the memory to 0
+ ZeroFill(ses->m_ppweStrTbl, uWords*sizeof(WORD_ENTRY*));
+
+ // save the count of words
+ ses->m_uWords = uWords;
+
+ // put each word in the hash table.
+ for (i=0; i < uWords; i++) {
+ IfErrGo(AddWord(*(lpbstr+i), &pwe));
+
+ // cache the pointer to the word entry
+ *(ses->m_ppweStrTbl + i) = pwe;
+ }
+
+
+ // We are done with the words. Free them.
+ for (i=0; i < uWords; i++) {
+ FreeBstrA(*(lpbstr+i));
+
+ }
+
+ Pmalloc()->Free(lpbstr);
+
+ // save the encoding
+ *(m_ppsesHelpStr + m_uStrCount) = ses;
+
+ // return the index of the string to the client.
+ *phst = m_uStrCount;
+
+ // update count of strings and words
+ m_uStrCount++;
+
+ return TIPERR_None;
+
+
+Error:
+ // Cleanup.
+
+ // Free the ses
+ Pmalloc()->Free(ses);
+
+ return err;
+
+}
+#pragma code_seg()
+
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC DOCSTR_MGR::CreateSubTree
+*Purpose:
+* Takes the left sub tree and the right sub tree and create a new
+* sub tree.
+*
+*Entry:
+* phtmLeft : Pointer the left sub tree.
+* phtmRight : Pointer the left right sub tree.
+*
+*Exit:
+* pphtmSubTree : points to the tree that was created.
+* TIPERROR_OutOfMemory.
+*
+***********************************************************************/
+TIPERROR DOCSTR_MGR::CreateSubTree(HUFFMAN_TREE_MEM *phtmLeft,
+ HUFFMAN_TREE_MEM *phtmRight,
+ HUFFMAN_TREE_MEM **pphtmSubTree)
+{
+ TIPERROR err = TIPERR_None;
+
+
+ DebAssert(((phtmLeft != NULL) && (phtmRight != NULL)), " NULL pointers ");
+
+ if ((*pphtmSubTree = (HUFFMAN_TREE_MEM *)
+ Pmalloc()->Alloc(sizeof(HUFFMAN_TREE_MEM))) == NULL) {
+ return TIPERR_OutOfMemory;
+ }
+
+ // initilize the memory to 0
+ ZeroFill(*pphtmSubTree, sizeof(HUFFMAN_TREE_MEM));
+
+
+ // initialize the entries
+ (*pphtmSubTree)->m_pweLeaf = NULL;
+ (*pphtmSubTree)->m_uFreq = phtmLeft->m_uFreq + phtmRight->m_uFreq;
+ (*pphtmSubTree)->m_phtmLeft = phtmLeft;
+ (*pphtmSubTree)->m_phtmRight = phtmRight;
+
+ // calculate the size of the compact representation of the Huffman Tree.
+ m_ulCmptSizeOfTree += sizeof(HT_NON_TERMINAL);
+ return err;
+}
+#pragma code_seg()
+
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC DOCSTR_MGR::BuildHuffmanTree
+*Purpose:
+* Builds the intial representation of Huffman Tree.
+
+*Note:- This huffman tree is not serialized. This is created to generate the
+* compact representation of the huffman tree and to encode all the
+* strings.
+*
+*Entry:
+* ppweTbl : table of all the word entries.
+* puFreqTbl : Table of the frequency of occurance of each word.
+* puIndexTbl : Index for each entry.
+*
+*
+*Exit:
+* TIPERROR : (TIPERR_OutOfMemory)
+*
+***********************************************************************/
+TIPERROR DOCSTR_MGR::BuildHuffmanTree( WORD_ENTRY **ppweTbl,
+ LONG *puFreqTbl,
+ UINT *puIndexTbl)
+{
+ HUFFMAN_TREE_MEM **pphtmForest;
+ UINT i, uIndexNext,uInsert;
+ TIPERROR err;
+ HUFFMAN_TREE_MEM *phtmSubTree;
+ HUFFMAN_TREE_MEM *phtmLeft;
+ HUFFMAN_TREE_MEM *phtmRight;
+ HUFFMAN_TREE_MEM *phtmTmp;
+ UINT uhtmToFree;
+
+ // create the forest containing the HUFFMAN subtrees.
+ //
+ if ((pphtmForest = (HUFFMAN_TREE_MEM **)
+ Pmalloc()->Alloc(m_uWordCount*sizeof(HUFFMAN_TREE_MEM *))) == NULL) {
+ return TIPERR_OutOfMemory;
+ }
+
+ // initilize the memory to 0
+ ZeroFill(pphtmForest, m_uWordCount*sizeof(HUFFMAN_TREE_MEM *));
+
+
+ // instantiate one sub tree for each word entry.
+ for (i=0; i < m_uWordCount; i++) {
+ if ((*(pphtmForest+i) = (HUFFMAN_TREE_MEM *)
+ Pmalloc()->Alloc(sizeof(HUFFMAN_TREE_MEM))) == NULL) {
+
+ // We need t Free uhtmToFree # of Huffman trees.
+ uhtmToFree = i-1;
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+
+ phtmTmp = *(pphtmForest+i);
+ // initialize the entries
+ phtmTmp->m_pweLeaf = *(ppweTbl + *(puIndexTbl + i));
+ phtmTmp->m_uFreq = (UINT) *(puFreqTbl + i);
+ DebAssert(phtmTmp->m_uFreq == phtmTmp->m_pweLeaf->m_uFreq,
+ " frequencies should match ");
+ phtmTmp->m_phtmLeft = NULL;
+ phtmTmp->m_phtmRight = NULL;
+
+ // calculate the size of the compact representation of the Huffman Tree.
+ m_ulCmptSizeOfTree += sizeof(HT_TERMINAL) + strlen(phtmTmp->m_pweLeaf->
+ m_bstrWord);
+
+ }
+
+ // if there is only 1 word then we already have the Huffman
+ if (m_uWordCount == 1) {
+ m_phtmRoot = *pphtmForest;
+ return TIPERR_None;
+ }
+
+ // indicates the next subtree that needs to be combined.
+ uIndexNext = 0;
+
+ for(;;) {
+ // form a sub tree out of the first 2 sub trees in the forest.
+ // The first entries are the one with the minimum freq.
+
+ // left sub tree
+ phtmLeft = *(pphtmForest+uIndexNext);
+ uIndexNext++;
+ // right sub tree
+ phtmRight = *(pphtmForest+uIndexNext);
+
+ if (err = CreateSubTree(phtmLeft, phtmRight, &phtmSubTree)) {
+ // We need t Free uhtmToFree # of Huffman trees.
+ uhtmToFree = m_uWordCount;
+ goto Error;
+ }
+
+ // Check if we have processed all the sub trees.
+ // If we have processed all the entries then break out of the while loop.
+ if ((uIndexNext+1) == m_uWordCount)
+ break;
+
+ // insert the new sub tree in the forest.
+ // Note: we do a insertion sort to keep every thing in order.
+ // INSERTION SORT!!!
+ uInsert = uIndexNext+1;
+ phtmTmp = *(pphtmForest+uInsert);
+
+ while ((uInsert < m_uWordCount) &&
+ (phtmSubTree->m_uFreq > phtmTmp->m_uFreq)) {
+ pphtmForest[uInsert-1] = pphtmForest[uInsert];
+ uInsert++;
+
+ // if we just shifted the last element of the array then break out
+ // of the while loop.
+ if (uInsert == m_uWordCount)
+ break;
+
+ phtmTmp = *(pphtmForest+uInsert);
+ } // while
+
+ // insert the subtree in that location
+ pphtmForest[uInsert-1] = phtmSubTree;
+
+ } // while
+
+ // Done!!!!!
+ //
+ m_phtmRoot = phtmSubTree;
+
+ Pmalloc()->Free(pphtmForest);
+
+ return err;
+Error:
+ // Free up all the allocate memory
+ for (i=0; i < uhtmToFree; i++) {
+ DebAssert(*(pphtmForest+i) != NULL, " Should not be Null ");
+ Pmalloc()->Free(*(pphtmForest+i));
+ }
+
+ return err;
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC DOCSTR_MGR::BuildCmptHuffmanTree
+*Purpose:
+* Builds the compact representation of Huffman Tree.
+*
+*Entry:
+* phtmRoot : pointer to the tree to encode.
+*
+*
+*Exit:
+* TIPERROR : (TIPERR_OutOfMemory)
+*
+***********************************************************************/
+TIPERROR DOCSTR_MGR::BuildCmptHuffmanTree(HUFFMAN_TREE_MEM *phtmRoot)
+{
+
+ HT_TERMINAL *phtt;
+ HT_NON_TERMINAL *phtnt;
+ TIPERROR err = TIPERR_None;
+
+
+ // if this is terminal node then encode that and save the string
+ // Check if this is a leaf node.
+ if ((phtmRoot->m_phtmLeft == NULL) &&
+ (phtmRoot->m_phtmRight == NULL)) {
+ phtt = (HT_TERMINAL *) (((BYTE *)m_pvHuffmanCmpt) + m_ulCurrentOffset);
+ // flag the entry to be a terminal node.
+ Set1stBit(phtt->m_byte, Off);
+ // copy the string
+ strcpy(phtt->m_rgText, phtmRoot->m_pweLeaf->m_bstrWord);
+
+ // addjust the current offsetto free space.
+ m_ulCurrentOffset += (sizeof(HT_TERMINAL) +
+ strlen(phtmRoot->m_pweLeaf->m_bstrWord));
+
+ return TIPERR_None;
+ }
+
+ // the root is a non terminal node.
+ DebAssert(phtmRoot->m_pweLeaf == NULL, " should be NULL ");
+
+ // Allocate space for left branch
+ phtnt = new(((BYTE *)m_pvHuffmanCmpt) + m_ulCurrentOffset) HT_NON_TERMINAL;
+
+ // addjust the current offset to free space.
+ m_ulCurrentOffset += sizeof(HT_NON_TERMINAL);
+
+
+ // process the right branch.
+ IfErrGo(BuildCmptHuffmanTree(phtmRoot->m_phtmRight));
+
+ // process the left branch.
+ //
+ // flag the entry to be non terminal node.
+ DebAssert(!(UL_MASK & m_ulCurrentOffset), " can handle offset upto 23 bits only ");
+
+ // save the offset to the left branch
+ phtnt->m_byteL = (BYTE) m_ulCurrentOffset;
+ phtnt->m_byteH = (BYTE) (m_ulCurrentOffset >> CHAR_BIT);
+ phtnt->m_byte = (BYTE) (m_ulCurrentOffset >> 2*CHAR_BIT);
+ Set1stBit(phtnt->m_byte, On);
+
+ IfErrGo(BuildCmptHuffmanTree(phtmRoot->m_phtmLeft));
+
+
+ return TIPERR_None;
+
+Error:
+ m_ulCurrentOffset = 0;
+ return err;
+
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC DOCSTR_MGR::ProcessDocStrings
+*Purpose:
+* This function build the Huffman Trees.
+*
+*
+*Entry:
+* None.
+*
+*
+*Exit:
+* TIPERROR : (TIPERR_OutOfMemory)
+*
+***********************************************************************/
+TIPERROR DOCSTR_MGR::ProcessDocStrings()
+{
+ TIPERROR err = TIPERR_None;
+ WORD_ENTRY **ppweTbl;
+ WORD_ENTRY *pwe;
+ UINT *puIndexTbl;
+ ULONG *puFreqTbl;
+ UINT i;
+ UINT uCount=0;
+
+ // If there are no doc strings to be processed then return.
+ if (m_uStrCount == 0)
+ return TIPERR_None;
+
+ // Build 3 tables.
+ // Tbl1 : Contains the WORD_ENTRY
+ if ((ppweTbl = (WORD_ENTRY **) Pmalloc()->Alloc(m_uWordCount*sizeof(WORD_ENTRY *))) == NULL)
+ return TIPERR_OutOfMemory;
+
+ // initilize the memory to 0
+ ZeroFill(ppweTbl, m_uWordCount*sizeof(WORD_ENTRY *));
+
+ // initialize the table
+ for (i=0; i < DS_cBuckets; i++) {
+ pwe = m_ppweHashTbl[i];
+
+ // walk the link list and count
+ while (pwe != NULL) {
+ ppweTbl[uCount++] = pwe;
+ pwe = pwe->m_pweNext;
+ } // while
+ } // for
+
+ DebAssert(uCount == m_uWordCount, " # of words should not consistent ");
+
+ // Tbl2 : Table conainting the freq of each word entry
+ if ((puFreqTbl = (ULONG *) Pmalloc()->Alloc(m_uWordCount*sizeof(ULONG))) == NULL) {
+ // in case of error release the memory allocated so far.
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+
+
+ // initialize the table
+ for (i=0; i < m_uWordCount; i++)
+ puFreqTbl[i] = ppweTbl[i]->m_uFreq;
+
+ // Tbl3 : Table conainting the index for each frequency
+ if ((puIndexTbl = (UINT *) Pmalloc()->Alloc(m_uWordCount*sizeof(UINT))) == NULL) {
+ // in case of error release the memory allocated so far.
+ err = TIPERR_OutOfMemory;
+ IfErrGoTo(err, Error1);
+ }
+
+ // initialize the table
+ for (i=0; i < m_uWordCount; i++)
+ puIndexTbl[i] = i;
+
+
+ // Quick Sort the frequency table. Pass in the index table also.
+ // Index table helps in tracking down the original place where the entry
+ // is stored.
+ QuickSortIndex(puFreqTbl, puIndexTbl, m_uWordCount);
+
+ // Build the huffman tree.
+ //
+ IfErrGoTo(BuildHuffmanTree(ppweTbl, (LONG *)puFreqTbl, puIndexTbl), Error2);
+
+ // Walk the tree and encode each word.
+ //
+ IfErrGoTo(EncodeWords(), Error2);
+
+ // Build the compact representation of the Huffman Tree.
+ //
+ // allocate space for the tree.
+ if ((m_pvHuffmanCmpt = (VOID HUGE *) Pmalloc()->Alloc((size_t)m_ulCmptSizeOfTree)) == NULL) {
+ // in case of error release the memory allocated so far.
+ err = TIPERR_OutOfMemory;
+ IfErrGoTo(err, Error2);
+ }
+
+ err = BuildCmptHuffmanTree(m_phtmRoot);
+
+ // fall through ...
+ //
+
+Error2:
+ // Release resources allocated for this function.
+ Pmalloc()->Free(puIndexTbl);
+
+Error1:
+ Pmalloc()->Free(puFreqTbl);
+
+Error:
+ Pmalloc()->Free(ppweTbl);
+
+ return err;
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC DOCSTR_MGR::EncodeWords
+*Purpose:
+* Walks the Huffman tree and encodes each word(at the leaf).
+*
+*Entry:
+* phtmRoot : Pointer the root of the Huffman tree.
+*
+*
+*Exit:
+** TIPERROR : (TIPERR_OutOfMemory)
+*
+***********************************************************************/
+TIPERROR DOCSTR_MGR::EncodeWords()
+{
+ UINT uBits;
+ BYTE rgbCode[MAX_ENCODING_ALLOWED];
+ UINT i;
+ TIPERROR err = TIPERR_None;
+
+ for (i=0; i < MAX_ENCODING_ALLOWED; i++)
+ rgbCode[i] = 0x00;
+
+ uBits = 0;
+
+ IfErrRet(TraverseHuffmanTree(m_phtmRoot, rgbCode, uBits));
+
+ return err;
+}
+#pragma code_seg()
+
+
+
+
+#pragma code_seg(CS_CREATE)
+
+// enable stack checking on this sucker -- it's potentially massivly recursive
+#pragma check_stack(on)
+
+/***
+*PUBLIC DOCSTR_MGR::TraverseHuffmanTree
+*Purpose:
+* Walks the Huffman tree and encodes each word(at the leaf).
+*
+*Entry:
+* phtmRoot : Pointer the root of the Huffman tree.
+*
+*
+*Exit:
+** TIPERROR : (TIPERR_OutOfMemory)
+*
+***********************************************************************/
+TIPERROR DOCSTR_MGR::TraverseHuffmanTree(HUFFMAN_TREE_MEM *phtmRoot,
+ BYTE *rgbHCode,
+ UINT uBits)
+{
+ TIPERROR err=TIPERR_None;
+ WORD_ENTRY *pwe;
+ UINT uByte;
+
+ // Check if this is a leaf node.
+ if ((phtmRoot->m_phtmLeft == NULL) &&
+ (phtmRoot->m_phtmRight == NULL)) {
+
+ // save the encoding in the WORD ENTRY.
+ pwe = phtmRoot->m_pweLeaf;
+ DebAssert(pwe != NULL, " should not be NULL ");
+ pwe->m_uBits = uBits;
+ // # of bytes to copy
+ uByte = (uBits/CHAR_BIT) + 1;
+ if ((pwe->m_bstrHCode = AllocBstrLenA((LPSTR)rgbHCode, uByte)) == NULL) {
+ return TIPERR_OutOfMemory;
+ }
+
+ // return
+ return TIPERR_None;
+ }
+
+ DebAssert( phtmRoot->m_phtmLeft != NULL && phtmRoot->m_phtmRight != NULL,
+ " non leaf should have both the child ");
+
+ // process left child.
+ // set the next bit to 0
+ SetNthBit(uBits, rgbHCode, Off);
+ IfErrRet(TraverseHuffmanTree(phtmRoot->m_phtmLeft, rgbHCode, uBits+1));
+
+ // process right child
+ // set the next bit to 1
+ SetNthBit(uBits, rgbHCode, On);
+ IfErrRet(TraverseHuffmanTree(phtmRoot->m_phtmRight, rgbHCode, uBits+1));
+
+ return TIPERR_None;
+
+}
+#pragma check_stack() // return to the default
+
+#pragma code_seg()
+
+/***
+*PUBLIC DOCSTR_MGR::GetNthBit
+*Purpose:
+* Sets the nth bit in the byte array (b) to the value hc.
+* ____________
+* |0th bit |
+* | |
+* ~ ~
+* | |
+* | |<- nth bit
+*
+*
+*Entry:
+* phtmRoot : Pointer the root of the Huffman tree.
+* n : can take the value 0 to _UINT_MAX
+*
+*Exit:
+** TIPERROR : (TIPERR_OutOfMemory)
+*
+***********************************************************************/
+HCODE DOCSTR_MGR::GetNthBit(UINT n, BYTE *rgb)
+{
+
+ UINT uByte;
+ UINT uBitNum;
+ BYTE *b;
+ CHAR ch = 0x00;
+
+ uByte = n/CHAR_BIT;
+
+ // byte to change
+ b = rgb + uByte;
+
+ // get the bit num (in b)
+ uBitNum = (n % CHAR_BIT)+1;
+
+ switch (uBitNum) {
+ case 1:
+ ch = (HCODE) Get1stBit(*b);
+ break;
+ case 2:
+ ch = (HCODE) Get2ndBit(*b);
+ break;
+ case 3:
+ ch = (HCODE) Get3rdBit(*b);
+ break;
+ case 4:
+ ch = (HCODE) Get4thBit(*b);
+ break;
+ case 5:
+ ch = (HCODE) Get5thBit(*b);
+ break;
+ case 6:
+ ch = (HCODE) Get6thBit(*b);
+ break;
+ case 7:
+ ch = (HCODE) Get7thBit(*b);
+ break;
+ case 8:
+ ch = (HCODE) Get8thBit(*b);
+ break;
+ default:
+ DebAssert(0, " 8 is the max bit # ");
+ break;
+
+ }
+
+ return ((ch) ? On : Off);
+}
+
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC DOCSTR_MGR::SetNthBit
+*Purpose:
+* Sets the nth bit in the byte array (b) to the value hc.
+*
+* ____________
+* |0th bit |
+* | |
+* ~ ~
+* | |
+* | |<- nth bit
+*
+*
+*Entry:
+* phtmRoot : Pointer the root of the Huffman tree.
+* n : can take value from 0 to UINT_MAX;
+*
+*Exit:
+** TIPERROR : (TIPERR_OutOfMemory)
+*
+***********************************************************************/
+VOID DOCSTR_MGR::SetNthBit(UINT n, BYTE *rgb, HCODE hc)
+{
+
+ UINT uByte;
+ UINT uBitNum;
+ BYTE *b;
+
+ uByte = n/CHAR_BIT;
+
+ // byte to change
+ b = rgb + uByte;
+
+ // get the bit num (in b)
+ uBitNum = (n % CHAR_BIT)+1;
+
+ switch (uBitNum) {
+ case 1:
+ Set1stBit(*b, hc);
+ break;
+ case 2:
+ Set2ndBit(*b, hc);
+ break;
+ case 3:
+ Set3rdBit(*b, hc);
+ break;
+ case 4:
+ Set4thBit(*b, hc);
+ break;
+ case 5:
+ Set5thBit(*b, hc);
+ break;
+ case 6:
+ Set6thBit(*b, hc);
+ break;
+ case 7:
+ Set7thBit(*b, hc);
+ break;
+ case 8:
+ Set8thBit(*b, hc);
+ break;
+ default:
+ DebAssert(0, " 8 is the max bit # ");
+
+ }
+
+}
+#pragma code_seg()
+
+
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC DOCSTR_MGR::GetEncodedDocStrOfHst
+*Purpose:
+* Returns huffman encoding for the string whose index(in m_ppsesHelpStr)
+* is hst.
+*
+*Entry:
+* hst : handle of the string whose encoded string has to be returned
+*
+*
+*Exit:
+* lplpstr (out) : pointer to the encode string.
+*
+* TIPERROR : (TIPERR_OutOfMemory)
+*
+***********************************************************************/
+TIPERROR DOCSTR_MGR::GetEncodedDocStrOfHst(HST hst, LPSTR *lplpstr, UINT *puLen)
+{
+ SEMI_ENCODED_STRING *pses;
+ WORD_ENTRY *pwe;
+ UINT uWords, uBits;
+ LPSTR lpstr;
+ UINT uBitPos;
+
+ DebAssert(hst < m_uStrCount, " invalid index");
+ DebAssert(m_ulCmptSizeOfTree > 0, " There are no DocString " );
+ DebAssert(lplpstr != NULL && puLen != NULL, " invalid parameter ");
+
+ // allocate space for the encoded string.
+ if ((lpstr = (LPSTR) Pmalloc()->Alloc(m_usMaxStrLen)) == NULL)
+ return TIPERR_OutOfMemory;
+
+ // get the semi encoded string for this index.
+ pses = *(m_ppsesHelpStr + hst);
+
+ uBitPos = 0;
+
+ // CONSIDER : we can optimze this step.
+ // encode the string;
+ //
+ // for each word in the string
+ for (uWords=0; uWords < pses->m_uWords; uWords++) {
+ pwe = *(pses->m_ppweStrTbl + uWords);
+ for (uBits=0; uBits < pwe->m_uBits; uBits++) {
+ SetNthBit(uBitPos++,
+ (BYTE *)lpstr,
+ GetNthBit(uBits, (BYTE *)(pwe->m_bstrHCode)));
+ } // for
+ } // for
+
+
+ // set up the out parameter
+ *lplpstr = lpstr;
+ *puLen = (uBitPos/CHAR_BIT) +1;
+
+#if ID_DEBUG
+ // get the total size of the encoded strings.
+ m_uDebTotalEncodedStrSize += *puLen;
+#endif
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC DOCSTR_MGR::GetWord
+*Purpose:
+* This function decodes the bit sequence (pbEncodedStr) to extract one
+* word from the encoding starting from the *puBit position. This
+* function increments the count in *puBit to point to the next word position.
+*
+* This function rrecurses until a terminal node is found.
+*
+*Entry:
+* pbEncodedStr : pointer to the encoded doc. string.
+* *puBit (IN/OUT) : specifies the bit position from where to extract the
+* next word. This bit count is increment to indicate
+* the postion of the next word encoding.
+*
+*Exit:
+* lpstr (out) : pointer to the word extracted.
+*
+* TIPERROR : (TIPERR_OutOfMemory)
+*
+***********************************************************************/
+TIPERROR DOCSTR_MGR::GetWord(VOID *pRoot,
+ BYTE *pbEncodedStr,
+ UINT *puBit,
+ LPSTR lpstr)
+{
+ ULONG ulNextOffset = 0;
+ HT_TERMINAL *phtt;
+ HT_NON_TERMINAL *phtnt;
+ TIPERROR err = TIPERR_None;
+
+ // if the root is a terminal node then return the string stored there.
+ if (!Get1stBit(*(BYTE *)pRoot)) {
+ phtt = (HT_TERMINAL *) pRoot;
+ // Copy the string
+ strcpy(lpstr, phtt->m_rgText);
+ return TIPERR_None;
+ }
+
+ // The root is a terminal node
+ phtnt = (HT_NON_TERMINAL *) pRoot;
+ //
+ // Check the next bit and then move to the next node.
+ if (!GetNthBit(*puBit, pbEncodedStr)) {
+ // move to the left direction
+ *puBit += 1;
+ // calculate the offset stored
+ ulNextOffset = (((ULONG)(phtnt->m_byte & 0x7f)) << 2*CHAR_BIT) |
+ (((ULONG)phtnt->m_byteH) << CHAR_BIT) |
+ (((ULONG)phtnt->m_byteL));
+
+ return GetWord((VOID *) ((BYTE*)m_pvHuffmanCmpt + ulNextOffset),
+ pbEncodedStr,
+ puBit,
+ lpstr);
+
+ }
+ else {
+ // move to the right sub tree
+ *puBit += 1;
+
+ return GetWord((VOID *) ((BYTE*)pRoot + sizeof(HT_NON_TERMINAL)),
+ pbEncodedStr,
+ puBit,
+ lpstr);
+
+
+ }
+
+ return TIPERR_None;
+}
+
+
+/***
+*PUBLIC DOCSTR_MGR::GetDecodedDocStrOfHst
+*Purpose:
+* Returns the decoded version of the encoding pointed at by pbDocStr.
+*
+*Entry:
+* pDocStr : pointer to the encoded doc. string.
+*
+*
+*Exit:
+* lplpstr (out) : pointer to the decoded string.
+*
+* TIPERROR : (TIPERR_OutOfMemory)
+*
+***********************************************************************/
+TIPERROR DOCSTR_MGR::GetDecodedDocStrOfHst(BYTE *pbDocStr, BSTR *lpbstr)
+{
+
+ TIPERROR err = TIPERR_None;
+ LPSTR lpstrDoc;
+ LPSTR lpstrWord;
+ UINT uBit = 0;
+#if OE_WIN32
+ int cchUnicode;
+#endif
+
+ DebAssert(m_ulCmptSizeOfTree > 0, " There are no DocString " );
+ DebAssert(pbDocStr != NULL && lpbstr != NULL, " invalid parameter ");
+
+ // allocate space for the decoded string.
+ if ((lpstrWord = (LPSTR) Pmalloc()->Alloc(m_usMaxStrLen)) == NULL)
+ return TIPERR_OutOfMemory;
+
+
+
+ // allocate space for each word
+ if ((lpstrDoc = (LPSTR) Pmalloc()->Alloc(m_usMaxStrLen)) == NULL) {
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+ lpstrDoc[0] = NULL;
+
+ // get the Next string until we get a NULL;
+ for (;;) {
+ IfErrGoTo(GetWord((VOID *)m_pvHuffmanCmpt,
+ pbDocStr,
+ &uBit,
+ lpstrWord), Error1);
+
+
+ // if the word is a NULL then we are done.
+ if (strlen(lpstrWord) == 0)
+ break;
+
+ // if this is not the the first word then add a blank at the end
+ if (strlen(lpstrDoc) != 0) {
+ strcat(lpstrDoc, " ");
+ }
+
+ // concatenate the word.
+ strcat(lpstrDoc, lpstrWord);
+
+ }
+
+
+ // set up the out parameter
+#if OE_WIN32
+ cchUnicode = MultiByteToWideChar(CP_ACP, 0, lpstrDoc, m_usMaxStrLen, NULL, 0);
+ if (cchUnicode == 0) {
+ err = TIPERR_OutOfMemory;
+ goto Error1;
+ }
+ *lpbstr = AllocBstrLen(NULL, cchUnicode);
+ if (*lpbstr == NULL) {
+ err = TIPERR_OutOfMemory;
+ goto Error1;
+ }
+
+ NoAssertRetail(MultiByteToWideChar(CP_ACP, 0, lpstrDoc, m_usMaxStrLen, *lpbstr, cchUnicode), "");
+#else
+ *lpbstr = AllocBstrLen(lpstrDoc, m_usMaxStrLen);
+
+ if (*lpbstr == NULL) {
+ err = TIPERR_OutOfMemory;
+ }
+#endif
+
+ // fall through ...
+
+Error1:
+ Pmalloc()->Free(lpstrDoc);
+
+Error:
+
+ Pmalloc()->Free(lpstrWord);
+ return err;
+
+}
+
+
+/***
+*PUBLIC DOCSTR_MGR::ReleaseHuffmanTree
+*Purpose:
+* Walks the tree passed in and releases all the resources associated
+* with the HUFFMAN_TREE. Does a recursive call to free the left and
+* the right subtree before releasing the node.
+*
+*Entry:
+* phtmRoot : root of the tree whose resources has to be released.
+*
+*
+*Exit:
+* None.
+***********************************************************************/
+VOID DOCSTR_MGR::ReleaseHuffmanTree(HUFFMAN_TREE_MEM *phtmRoot)
+{
+
+ // Check if this is a leaf node.
+ if ((phtmRoot->m_phtmLeft == NULL) &&
+ (phtmRoot->m_phtmRight == NULL)) {
+
+ // Free resources owned by WORD_ENTRY
+ FreeBstrA(phtmRoot->m_pweLeaf->m_bstrWord);
+ FreeBstrA(phtmRoot->m_pweLeaf->m_bstrHCode);
+
+ // Free the WordEntry itself
+ Pmalloc()->Free(phtmRoot->m_pweLeaf);
+
+ }
+ else {
+ // free the the left and right sub tree
+ ReleaseHuffmanTree(phtmRoot->m_phtmLeft);
+
+ ReleaseHuffmanTree(phtmRoot->m_phtmRight);
+ }
+
+ // Free this Huffman node.
+ Pmalloc()->Free(phtmRoot);
+
+ return;
+}
+
+
+//
+
+/***
+*PUBLIC ZeroFill
+*Purpose:
+* Zero fills the memory
+*
+*Entry:
+* pv : Pointer to the memory that needs to be zero initilized
+* ubSize : Size of the memory passed in.
+*
+*Exit:
+* None.
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+VOID ZeroFill(VOID HUGE * pv, ULONG ubSize)
+{
+ UINT i;
+
+ for (i=0; i < ubSize; i++)
+ *((BYTE HUGE *)pv+i) = 0;
+
+}
+#pragma code_seg()
+
+
diff --git a/private/oleauto/src/typelib/dstrmgr.hxx b/private/oleauto/src/typelib/dstrmgr.hxx
new file mode 100644
index 000000000..f91331da7
--- /dev/null
+++ b/private/oleauto/src/typelib/dstrmgr.hxx
@@ -0,0 +1,196 @@
+/***
+*nammgr.hxx - Name Manager
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* The Help Manager handles all the help strings in the typelib/project.
+* In this implementation we huffman encode all the words.
+*
+*Revision History:
+*
+* 18-July-93 rajivk: Created.
+*
+*
+*****************************************************************************/
+
+#ifndef DSTRMGR_HXX_INCLUDED
+#define DSTRMGR_HXX_INCLUDED
+
+#include "silver.hxx"
+#include "cltypes.hxx"
+#include "blkmgr.hxx"
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szDSTRMGR_HXX)
+#define SZ_FILE_NAME g_szDSTRMGR_HXX
+#endif
+
+
+// This constant defines the number of buckets used in the hash
+// table.
+#define DS_cBuckets 2048
+#define DS_cchMaxName 41 // max chars in a name, including terminator
+#define MAX_SEGMENTS 128 // max seven bits for storing the segment #
+
+typedef enum HCODE {
+ Off = 0, // set for left traversal
+ On = 1 // set for right traversal
+};
+
+// These structs define the layout of the structure which
+// keeps track of the frequency by which the word appears.
+// name : we;
+struct WORD_ENTRY //we
+{
+ UINT m_uFreq; // Frequency of the word.
+ BSTRA m_bstrWord; // the word
+ UINT m_uBits; // # of bits needed for the huffman code
+ BSTRA m_bstrHCode; // Huffman code for the bstr.
+ WORD_ENTRY *m_pweNext; // pointer to the next WORD_ENTRY
+};
+
+
+// Im memory representation of HUFFMAN_TREE. This exist only when we are
+// encoding the strings.
+struct HUFFMAN_TREE_MEM //stm
+{
+ WORD_ENTRY *m_pweLeaf; // This NULL for non-leaf nodes.
+ UINT m_uFreq; // cumulative freq of the subtree
+ HUFFMAN_TREE_MEM *m_phtmLeft; // This is null for leaf nodes.
+ HUFFMAN_TREE_MEM *m_phtmRight; // This is null for leaf nodes.
+};
+
+
+struct SEMI_ENCODED_STRING // ses
+{
+ UINT m_uWords;
+ WORD_ENTRY **m_ppweStrTbl;
+};
+
+//
+// name: htt
+struct HT_TERMINAL // nodes containing the string.
+{
+ BYTE m_byte; // the highest bit is 0 for terninal nodes.
+ // the next 7 bits are not used.
+ CHAR m_rgText[1]; // stores the word.
+};
+
+// name: htnt
+struct HT_NON_TERMINAL // nodes containing the string.
+{
+ BYTE m_byte; // the highest bit is set for non terninal nodes.
+ BYTE m_byteH; // this 2 bytes + the 7 bits in the m_byte forms
+ BYTE m_byteL; // forms the offset to the next entry.
+ // Offset is formed of 23 bits.
+ HT_NON_TERMINAL() {
+ m_byte = 0x00;
+ m_byteH = 0x00;
+ m_byteL = 0x00;
+ };
+
+};
+
+
+/***
+*class DOCSTR_MGR - 'dsmgr': documentation string manager
+*Purpose:
+* The class implements the help manager. This class is owned by the
+* GenericTypeLibOle.
+*
+*
+***********************************************************************/
+
+class DOCSTR_MGR
+{
+public:
+ DOCSTR_MGR();
+ ~DOCSTR_MGR();
+
+ TIPERROR Init();
+ nonvirt TIPERROR Read(STREAM *psstrm);
+ nonvirt TIPERROR Write(STREAM *psstrm);
+ nonvirt TIPERROR GetHstOfHelpString(XSZ_CONST szDocStr, HST *hst);
+ nonvirt TIPERROR ProcessDocStrings();
+ nonvirt TIPERROR GetEncodedDocStrOfHst(HST hst, LPSTR *lplpstr, UINT *uLen);
+ nonvirt TIPERROR GetDecodedDocStrOfHst(BYTE *pbDocStr, BSTR *lpbstr);
+
+
+private:
+
+ nonvirt TIPERROR AddWord(BSTRA bstrWord, WORD_ENTRY **ppwe);
+ nonvirt TIPERROR AddNewWord(BSTRA bstrWord, WORD_ENTRY **ppwe);
+ nonvirt TIPERROR BuildHuffmanTree();
+ nonvirt TIPERROR ParseString(XSZ_CONST szStr, BSTRA **lplpbstr, UINT *uWordCount);
+ nonvirt UINT IndexOfHash(ULONG lHash);
+ nonvirt TIPERROR BuildHuffmanTree(WORD_ENTRY **ppweTbl,
+ LONG *puFreqTbl,
+ UINT *puIndexTbl);
+ nonvirt TIPERROR BuildCmptHuffmanTree(HUFFMAN_TREE_MEM *phtmRoot);
+ nonvirt TIPERROR CreateSubTree(HUFFMAN_TREE_MEM *phtmLeft,
+ HUFFMAN_TREE_MEM *phtmRight,
+ HUFFMAN_TREE_MEM **pphtmSubTree);
+ nonvirt TIPERROR EncodeWords();
+ nonvirt TIPERROR TraverseHuffmanTree(HUFFMAN_TREE_MEM *phtmRootphtmRoot,
+ BYTE *rgbCode,
+ UINT uBits);
+ nonvirt VOID SetNthBit(UINT n, BYTE *b, HCODE hc);
+ nonvirt HCODE GetNthBit(UINT n, BYTE *b);
+ nonvirt VOID ReleaseHuffmanTree(HUFFMAN_TREE_MEM *phtmRoot);
+ nonvirt TIPERROR GetWord(VOID *pRoot,
+ BYTE *pbEncodedStr,
+ UINT *puBit,
+ LPSTR lpstr);
+
+ // Serialized DataMember.
+ ULONG m_ulCmptSizeOfTree;
+ USHORT m_usMaxStrLen;
+ VOID HUGE * m_pvHuffmanCmpt;
+
+
+ // Data Member that are NOT serialized.
+ // the following data members are used only while we are building the
+ // huffman tree and compacting the help strings.
+ UINT m_uMaxStrCount;
+ UINT m_uStrCount;
+ UINT m_uWordCount;
+ SEMI_ENCODED_STRING **m_ppsesHelpStr; // Table of semi encoded strings (help strings)
+ WORD_ENTRY **m_ppweHashTbl; // Hash table containing the frequency of each word.
+ UINT *m_puFreqOfWords; // for each entry in m_ppWord table
+ // this table contains the freq.
+ HUFFMAN_TREE_MEM *m_phtmRoot; // Huffman tree for encoding
+ ULONG m_ulCurrentOffset; // Current next free offset;
+
+#if ID_DEBUG
+ ULONG m_uDebTotalStrSize;
+ ULONG m_uDebTotalEncodedStrSize;
+ ULONG m_uDebTotalWord;
+#endif
+
+
+};
+
+
+
+/***
+*PUBLIC IsValid - tests if DOCSTR_MGR valid
+*Purpose:
+* returns the index in the buckect table for the passed in hash value.
+*
+*Entry:
+*
+*Exit:
+* TRUE if has been initialized, else false.
+*
+***********************************************************************/
+inline UINT DOCSTR_MGR::IndexOfHash(ULONG lHash)
+{
+ return (UINT)(WHashValOfLHashVal(lHash) % DS_cBuckets);
+}
+
+
+#endif // ! DSTRMGR_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/dtbind.cxx b/private/oleauto/src/typelib/dtbind.cxx
new file mode 100644
index 000000000..ae2c840cf
--- /dev/null
+++ b/private/oleauto/src/typelib/dtbind.cxx
@@ -0,0 +1,1210 @@
+/***
+*dtbind.cxx - DYN_TYPEBIND class implementation
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Class for type binding class.
+*
+*Revision History:
+*
+* 13-Mar-91 ilanc: Created
+* 03-Apr-92 martinc: changed m_hdefn to m_varaccess.m_hdefn
+* (this change was required for cfront)
+* 29-Apr-92 ilanc: Added GetFuncInfoOfHmember() method:
+* used by TipGetFuncInfo(functionid, phfinfo)
+* 30-Jul-92 w-peterh: removed function overloading
+* 30-Apr-93 w-jeffc: made DEFN data members private
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "silver.hxx"
+#include "typelib.hxx"
+#define DYN_TYPEBIND_VTABLE
+#include "dtbind.hxx"
+#include "tdata.hxx"
+#include "gdtinfo.hxx"
+#include "dtmbrs.hxx"
+
+#include "clutil.hxx" // for IsSimpleType()
+#include "exbind.hxx"
+
+
+#pragma hdrstop(RTPCHNAME)
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+char szOleDtbindCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleDtbindCxx
+#else
+static char szDtbindCxx[] = __FILE__;
+#define SZ_FILE_NAME szDtbindCxx
+#endif
+#endif //ID_DEBUG
+
+
+LPOLESTR DYN_TYPEBIND::szProtocolName = WIDE("MS-DYN_TYPEBIND");
+// LPOLESTR DYN_TYPEBIND::szBaseName = WIDE("MS-DEFN_TYPEBIND");
+
+CONSTDATA UINT DYN_TYPEBIND::oDbindnametbl =
+ offsetof(DYN_TYPEBIND, m_dbindnametbl);
+
+/***
+*PUBLIC DYN_TYPEBIND::Initializer - initialize an instance.
+*Purpose:
+* initializes a DYN_TYPEBIND instance.
+*
+*Implementation Notes:
+*
+*Entry:
+* pdtroot - Pointer to a DYN_TYPEROOT (IN).
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR DYN_TYPEBIND::Init(BLK_MGR *pblkmgr, DYN_TYPEROOT *pdtroot)
+{
+ TIPERROR err;
+ DebAssert(pdtroot != NULL, "DYN_TYPEBIND: pdtroot uninitialized.");
+ DebAssert(pblkmgr != NULL, "DYN_TYPEBIND: pblkmgr uninitialized.");
+
+ m_pdtroot = pdtroot;
+
+ // Init block manager member.
+ IfErrRet(m_dbindnametbl.Init(pblkmgr, pdtroot));
+
+ return err;
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC DYN_TYPEBIND::Constructor - Construct an instance.
+*Purpose:
+* Constructs a DYN_TYPEBIND instance.
+*
+*Implementation Notes:
+* Sets all contained pointers to sub-objects to NULL.
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+DYN_TYPEBIND::DYN_TYPEBIND()
+{
+ m_pdtroot= NULL;
+ m_isProtocol = FALSE;
+ m_isBeingLaidOut = FALSE;
+
+ m_cbSize = (USHORT)~0;
+ m_cbAlignment = (USHORT)~0;
+ m_oPvft = -1; // by default, no vft
+ m_cbPvft = 0;
+ m_hvtdPrimary = HCHUNK_Nil;
+
+ m_cbSizeDataMembers = (USHORT)~0;
+}
+#pragma code_seg( )
+
+
+// Dtor: do nothing... we are embedded.
+//
+#pragma code_seg( CS_CORE )
+DYN_TYPEBIND::~DYN_TYPEBIND() {}
+#pragma code_seg( )
+
+
+LPVOID DYN_TYPEBIND::QueryProtocol(LPOLESTR szInterfaceName)
+{
+ if (szInterfaceName == szProtocolName ||
+ ostrcmp(szInterfaceName, szProtocolName) == 0)
+ return this;
+ else
+ return DEFN_TYPEBIND::QueryProtocol(szInterfaceName);
+}
+
+
+/***
+*PUBLIC DYN_TYPEBIND::AddRef
+*Purpose:
+* Adds external ref.
+*
+*Implementation Notes:
+* Defers to DYN_TYPEMEMBERS.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+VOID DYN_TYPEBIND::AddRef()
+{
+ Pdtmbrs()->AddRef();
+}
+
+
+/***
+*PUBLIC DYN_TYPEBIND::AddInternalRef
+*Purpose:
+* Implementation of AddInternalRef method.
+*
+*Implementation Notes:
+* Defers to DYN_TYPEMEMBERS
+*
+*Entry:
+*
+*Exit:
+***********************************************************************/
+
+VOID DYN_TYPEBIND::AddInternalRef()
+{
+ Pdtmbrs()->AddInternalRef();
+}
+
+
+/***
+*PUBLIC DYN_TYPEBIND::RelInternalRef
+*Purpose:
+* Implementation of RelInternalRef method.
+*
+*Implementation Notes:
+* Defers to DYN_TYPEMEMBERS.
+*
+*Entry:
+*
+*Exit:
+***********************************************************************/
+
+VOID DYN_TYPEBIND::RelInternalRef()
+{
+ Pdtmbrs()->RelInternalRef();
+}
+
+
+/***
+*PUBLIC DYN_TYPEBIND::Release
+*Purpose:
+* Implementation of Release method.
+*
+*Implementation Notes:
+* Defers to containing DYN_TYPEROOT (which is responsible
+* for tracking DYN_TYPEMEMBERS references).
+*
+*Entry:
+*
+*Exit:
+***********************************************************************/
+
+VOID DYN_TYPEBIND::Release()
+{
+ m_pdtroot->ReleaseDtmbrs();
+}
+
+
+/***
+*PUBLIC DYN_TYPEBIND::Pdtmbrs - accessor for DYN_TYPEMEMBERS.
+*Purpose:
+* Gets DYN_TYPEMEMBERS ptr.
+*
+*Implementation Notes:
+* Wants to be inline but because of hxxtoinc problem with
+* unresolved externs and the fact that is needed by other
+* modules we make it outline.
+*
+*Entry:
+*
+*Exit:
+* DYN_TYPEMEMBERS *
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+DYN_TYPEMEMBERS *DYN_TYPEBIND::Pdtmbrs() const
+{
+ return (DYN_TYPEMEMBERS *)((BYTE *)this - DYN_TYPEMEMBERS::oDtbind);
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC DYN_TYPEBIND::GetTypeInfo
+*Purpose:
+* Gets containing typeinfo.
+*
+*Implementation Notes:
+* Defers to containing typeroot. Increments refcount.
+* Client must release.
+*
+*Entry:
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR DYN_TYPEBIND::GetTypeInfo(TYPEINFO **pptinfo)
+{
+ DebAssert(pptinfo, "bad param.");
+
+ *pptinfo = Pdtroot()->Pgdtinfo();
+ (*pptinfo)->AddRef();
+ return TIPERR_None;
+}
+
+
+#if ID_DEBUG
+/***
+*PUBLIC DYN_TYPEBIND::IsValid - is binding table valid?
+*Purpose:
+* Is binding table valid
+*
+*Implementation Notes:
+* Valid iff containing DYN_TYPEMEMBERS is laid out.
+*
+*Entry:
+*
+*Exit:
+* BOOL
+*
+***********************************************************************/
+
+BOOL DYN_TYPEBIND::IsValid() const
+{
+ return Pdtmbrs()->IsLaidOut() && m_dbindnametbl.IsValid();
+}
+#endif //EI_OB || ID_DEBUG
+
+
+/***
+*PUBLIC DYN_TYPEBIND::BuildBindNameTable - build bindnametbl
+*Purpose:
+* Builds bindnametbl
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR DYN_TYPEBIND::BuildBindNameTable()
+{
+ TIPERROR err;
+
+ IfErrRet(m_dbindnametbl.BuildTable());
+
+ DebAssert(m_dbindnametbl.IsValid(), "bad bindnametbl.");
+
+ return err;
+}
+
+/***
+*PUBLIC DYN_TYPEBIND::BindBase - Bind to base given hvdefn.
+*Purpose:
+* Bind to base class.
+*
+*Implementation Notes:
+* Need flag to indecate that restricted functions should be ignored
+* (i.e. as if they don't exist) so that when using this function in
+* the "embedded macro interface" mode we can correctly implement
+* dispinterface restricted semantics (i.e. dispinterfaces don't support
+* restricted funcs thus they shoulnd't exist when "inherited").
+*
+*Entry:
+* fWantType TRUE if they want to bind to a type id, else FALSE (IN).
+* hvdefnBase base to bind to.
+* hgnam Name of id to bind. (IN)
+* fuInvokeKind Kind of invocation (func/var/prop): ignored for types (IN).
+* access Visibility attr: private means everything etc. (IN)
+* pexbind Pointer to caller-allocated struct for EXBIND (IN/OUT).
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+* An "unsuitable match" error is returned if a matching name is
+* found but it's unsuitable wrt INVOKEKIND.
+*
+***********************************************************************/
+
+TIPERROR DYN_TYPEBIND::BindBase(BOOL fWantType,
+ HVAR_DEFN hvdefnBase,
+ UINT oBase,
+ HGNAM hgnam,
+ UINT fuInvokeKind,
+ ACCESS access,
+ EXBIND *pexbind,
+ GenericTypeLibOLE *pgtlibole)
+{
+ TYPE_DATA *ptdata = NULL;
+ VAR_DEFN * qvdefnBase;
+ DYN_TYPEBIND *pdtbindBase; // TYPEBIND for base class
+ GEN_DTINFO *pgdtinfo;
+ TIPERROR err = TIPERR_None;
+
+ ptdata = Pdtmbrs()->Ptdata(); // don't bump refcount
+ DebAssert(ptdata != NULL, "bad TYPE_DATA.");
+
+ qvdefnBase = ptdata->QvdefnOfHvdefn(hvdefnBase);
+ if (IsMatchOfVisibility((ACCESS)qvdefnBase->Access(), access)) {
+ IfErrRet(ptdata->GetDynTypeBindOfHvdefn(hvdefnBase,
+ &pdtbindBase,
+ NULL));
+ DebAssert(pdtbindBase != NULL, "Unsupported base member");
+ // Our current containing project is in pgtlibole
+ // so we get the base's containing project and compare
+ // for identity -- if different, we're cross-project, and we
+ // can't use our existing hgnam.
+ //
+ // Ok to use the non-public interfaces to get the base class's
+ // containing typeinfo, because we know that we're dealing
+ // with one of our own typeinfo's here (GetDynTypeBindOfHvdefn
+ // ensures this).
+ //
+ pgdtinfo = pdtbindBase->Pdtroot()->Pgdtinfo();
+
+ if (pgtlibole != pgdtinfo->PgtlibOleContaining()) {
+ NAMMGR *pnammgr;
+ LPSTR szName;
+
+ // First get a nammgr
+ IfErrGo(m_pdtroot->GetNamMgr(&pnammgr));
+
+ // get the string to pass to BindDefnStr. NOTE: we can use
+ // the api that returns a pointer directly into the name table
+ // because we know that we're just going to turn around and
+ // use the string to look up the name in the typelib again.
+ szName = pnammgr->LpstrOfHgnam(hgnam);
+
+ // CONSIDER: combine BindDefnStr & BindTypeDefnStr
+ if (fWantType) {
+ err = pdtbindBase->BindTypeDefnStr(szName,
+ fuInvokeKind,
+ access,
+ pexbind);
+ }
+ else {
+ err = pdtbindBase->BindDefnStr(szName,
+ fuInvokeKind,
+ access,
+ pexbind);
+ }
+ }
+ else {
+ // We're in the same typlib/proj and we can use
+ // hgnam as is and call the BindDefn interface.
+ //
+ err = pdtbindBase->BindIdDefn(fWantType,
+ hgnam,
+ fuInvokeKind,
+ access,
+ pexbind);
+ }
+
+Error:
+ // Fall through even in error case...
+ pexbind->AdjustOfs(oBase);
+ pdtbindBase->Release();
+ } // of if IsMatchOfVisibility
+ return err;
+}
+
+
+/***
+*PUBLIC DYN_TYPEBIND::BindIdDefn - Bind to id, produce DEFN.
+*Purpose:
+* Bind to non-type or type id, produce DEFN.
+*
+*Implementation Notes:
+* Defers to BindDefnCur.
+**
+*Entry:
+* fWantType TRUE if they want to bind to a type id, else FALSE (IN).
+* hgnam Name of id to bind. (IN)
+* fuInvokeKind
+* Kind of invocation (func/var/prop): ignored for types (IN).
+* NOTE: fuInvokeKind == 0 means: "bind to first thing".
+* access Visibility attr: private means everything etc. (IN)
+* pexbind Pointer to caller-allocated struct for EXBIND (IN/OUT).
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+* An "unsuitable match" error is returned if a matching name is
+* found but it's unsuitable wrt INVOKEKIND.
+*
+***********************************************************************/
+
+TIPERROR DYN_TYPEBIND::BindIdDefn(BOOL fWantType,
+ HGNAM hgnam,
+ UINT fuInvokeKind,
+ ACCESS access,
+ EXBIND *pexbind)
+{
+ TYPE_DATA *ptdata = NULL;
+ HDEFN hdefnMatch = HDEFN_Nil;
+ TYPEKIND tkind;
+ HVAR_DEFN hvdefnBaseCur, hvdefnBaseFirst, hvdefnBaseNext;
+ VAR_DEFN * qvdefnBase;
+ UINT ityp;
+ GEN_DTINFO *pgdtinfo;
+ GenericTypeLibOLE *pgtlibole;
+
+ NAMMGR *pnammgr;
+ TIPERROR err = TIPERR_None;
+
+ pgdtinfo = Pdtroot()->Pgdtinfo();
+ pgtlibole = pgdtinfo->PgtlibOleContaining();
+ IfErrRet(pgtlibole->GetTypeBind()); // We need the name cache
+
+ // Note that in the OLE case, we can't bind to types in base classes
+ // because we don't support nested types.
+ //
+ DebAssert(fWantType == FALSE, "OLE doesn't have nested types.");
+
+
+ DebAssert((pexbind != NULL), "bad param.");
+ pexbind->SetBindKind(BKIND_NoMatch); // be pessimistic.
+
+ ptdata = Pdtmbrs()->Ptdata(); // don't bump refcount
+ DebAssert(ptdata != NULL, "bad TYPE_DATA.");
+
+ DebAssert(m_dbindnametbl.IsValid(), "bad bindnametbl.");
+
+ IfErrRet(m_pdtroot->GetNamMgr(&pnammgr));
+
+ IfErrRet(BindDefnCur(fWantType, hgnam, fuInvokeKind, access, pexbind));
+
+ // If we didn't find anything, recurse onto the base classes.
+ if (pexbind->IsNoMatch()) {
+
+ // No match. If we have base classes, recursive search for
+ // match in the base classes.
+ // For now, we only do single inheritance,
+ // which simplifies things because we only recurse once, and
+ // we don't have to deal with ambiguity.
+ // After binding, we must adjust
+ // the offset by the offset of the base class.
+ //
+ // But first, check to see if the name we are looking for is in
+ // the name cache for the CURRENT typeinfo. This will tell us if
+ // the name MIGHT be in the base class in those cases where we have
+ // not checked the name cache yet. If we have already checked the
+ // name cache (in BindProjLevel because we're binding "outside-in"),
+ // this section is redundant for the
+ // first base class, but will help for any subsequent base classes.
+ //
+ // Get the name cache's index
+ ityp = pgdtinfo->GetIndex();
+
+ // Look up the name, leave if it isn't here
+ if (!pgtlibole->IsValidNameCache(ityp) ||
+ pgtlibole->IsNameInCache(ityp, hgnam)) {
+
+ // The following is weird but...
+ // For dispinterfaces, we first bind to the
+ // 2nd class and only then to the first "true" base.
+ // For other typekinds we bind "normally" to the 1st base.
+ //
+ tkind = GetTypeKind();
+ hvdefnBaseCur = hvdefnBaseFirst = ptdata->HvdefnFirstBase();
+ if (tkind == TKIND_COCLASS) {
+ // For coclasses, we attempt to bind to the DEFAULT
+ // dispinterface which isn't necessarily the first base
+ //
+ while (hvdefnBaseCur != HDEFN_Nil) {
+ qvdefnBase = ptdata->QvdefnOfHvdefn(hvdefnBaseCur);
+ hvdefnBaseNext = qvdefnBase->HdefnNext();
+ // Is this the DEFAULT dispinterface?
+ if (qvdefnBase->GetImplTypeFlags() == IMPLTYPEFLAG_FDEFAULT) {
+ break;
+ }
+ hvdefnBaseCur = hvdefnBaseNext;
+ }
+ }
+ else if (tkind == TKIND_DISPATCH) {
+ // for dispinterfaces we do the funky "start to bind at
+ // the 2nd base" thing of which there can only be one.
+ // In VBA1 we only support a single "embedded" interface.
+ // We ultimately bind to the 1st base.
+ //
+ DebAssert(hvdefnBaseCur != HDEFN_Nil,
+ "dispinterfaces must have a base class.");
+ hvdefnBaseCur = ptdata->QvdefnOfHvdefn(hvdefnBaseCur)->HdefnNext();
+ }
+ if (hvdefnBaseCur != HDEFN_Nil) {
+ qvdefnBase = ptdata->QvdefnOfHvdefn(hvdefnBaseCur);
+ IfErrRet(BindBase(FALSE,
+ hvdefnBaseCur,
+ qvdefnBase->GetOVar(),
+ hgnam,
+ fuInvokeKind,
+ access,
+ pexbind,
+ pgtlibole));
+
+ // For dispinterfaces, if we matched in the "pseudo-base"
+ // then we need to indicate such.
+ //
+ if ((tkind == TKIND_DISPATCH) && (!pexbind->IsNoMatch())) {
+ DebAssert(pexbind->IsFuncMatch(), "should be function.");
+
+ // Return the dispinterface's typeinfo
+ pexbind->SetIsDispatch(TRUE);
+ pexbind->Ptinfo()->Release();
+ pexbind->SetPtinfo(pgdtinfo);
+ pgdtinfo->AddRef();
+ } // if match
+ else {
+ DebAssert(tkind == TKIND_COCLASS ||
+ pexbind->IsDispatch() == FALSE,
+ "should have been ctor'ed to FALSE.");
+ }
+ } // of if hvdefnBaseCur
+ // If dispinterface then
+ // if no match yet, then
+ // then finally bind to first base.
+ //
+ if (tkind == TKIND_DISPATCH) {
+ if (pexbind->IsNoMatch()) {
+ DebAssert(hvdefnBaseFirst != HDEFN_Nil,
+ "dispinterface must have base.");
+ qvdefnBase = ptdata->QvdefnOfHvdefn(hvdefnBaseFirst);
+ IfErrRet(BindBase(FALSE,
+ hvdefnBaseFirst,
+ qvdefnBase->GetOVar(),
+ hgnam,
+ fuInvokeKind,
+ access,
+ pexbind,
+ pgtlibole));
+ } // if no match
+ } // if dispinterface
+ } // if invalid name cache or hit
+
+ }
+
+ return err;
+}
+
+
+/***
+*PUBLIC DYN_TYPEBIND::BindDefnCur - Bind to id in current module only.
+*Purpose:
+* Bind to non-type or type id, produce DEFN.
+*
+*Implementation Notes:
+* Defers to BINDNAME_TABLE.
+**
+*Entry:
+* fWantType TRUE if they want to bind to a type id, else FALSE (IN).
+* hgnam Name of id to bind. (IN)
+* fuInvokeKind
+* Kind of invocation (func/var/prop): ignored for types (IN).
+* NOTE: fuInvokeKind == 0 means: "bind to first thing".
+* access Visibility attr: private means everything etc. (IN)
+* pexbind Pointer to caller-allocated struct for EXBIND (IN/OUT).
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+* An "unsuitable match" error is returned if a matching name is
+* found but it's unsuitable wrt INVOKEKIND.
+*
+***********************************************************************/
+
+TIPERROR DYN_TYPEBIND::BindDefnCur(BOOL fWantType,
+ HGNAM hgnam,
+ UINT fuInvokeKind,
+ ACCESS access,
+ EXBIND *pexbind)
+{
+ TYPE_DATA *ptdata = NULL;
+ USHORT indexMatch;
+ HDEFN hdefn, hdefnMatch = HDEFN_Nil;
+ DEFN *qdefn;
+ FUNC_DEFN *qfdefn;
+ INVOKEKIND invokekindMatch;
+ BOOL fMatchProperty, fMatchFunc;
+ HLNAM hlnam;
+ NAMMGR *pnammgr;
+ TIPERROR err = TIPERR_None;
+
+ // Note that in the OLE case, we can't bind to types in base classes
+ // because we don't support nested types.
+ //
+ DebAssert(fWantType == FALSE, "OLE doesn't have nested types.");
+
+
+ DebAssert(pexbind != NULL, "bad param.");
+ pexbind->SetBindKind(BKIND_NoMatch); // be pessimistic.
+
+ ptdata = Pdtmbrs()->Ptdata();
+ DebAssert(ptdata != NULL, "bad TYPE_DATA.");
+
+ DebAssert(m_dbindnametbl.IsValid(), "bad bindnametbl.");
+
+ IfErrRet(m_pdtroot->GetNamMgr(&pnammgr));
+
+ // Be pessimistic about funcs and properties...
+ fMatchFunc = fMatchProperty = FALSE;
+
+ // get first matching name
+ hlnam = pnammgr->HlnamOfHgnam(hgnam);
+ indexMatch = m_dbindnametbl.IndexFirstOfHlnam(hlnam);
+
+ // If we're looking for a type then skip over any
+ // non-type ids (we ignore INVOKEKIND in this case),
+ // otherwise we're looking for a non-type id so skip
+ // over any type ids (only one actually) and then
+ // make sure we've got the right INVOKEKIND.
+ // Note: non-types and types are in different namespaces.
+ //
+ while (indexMatch != BIND_INVALID_INDEX) {
+ // Get the qdefn of our match
+ hdefn = m_dbindnametbl.HdefnOfIndex(indexMatch);
+ qdefn = m_dbindnametbl.QdefnOfHdefn(hdefn);
+
+ // - switch on match kind (var/func/type etc.)
+ // - in each case determine if what they want (invokekind flags)
+ // are what we got
+ // - if so break else determine if there could be something
+ // legitimately overloaded,
+ // - if so getnext
+ // else issue appropriate error msg (type mismatch)
+ //
+ if (qdefn->IsRecTypeDefn()) {
+ if (fWantType) {
+ // Matched a nestedtype of which there can only be one,
+ // so we break out of the loop.
+ //
+ break;
+ }
+ // else we don't a want a type so we fall through to
+ // the bottom to get next.
+ }
+ else if (qdefn->IsVarDefn()) {
+ if (!fWantType) {
+ // Only case that we don't match a variable is if *only*
+ // INVOKE_FUNC specified or if not INVOKE_PROPERTYGET and this
+ // variable is marked as read-only. Note,
+ // fuInvokeKind == 0 is special-case of != INVOKE_FUNC
+ // (thus we match) and exit.
+ //
+ if (fuInvokeKind == (UINT)INVOKE_FUNC) {
+ // else we want a function so we issue an error and return.
+ return TIPERR_ExpectedFuncNotVar;
+ }
+ else if (fuInvokeKind && !(fuInvokeKind & (UINT)INVOKE_PROPERTYGET)
+ && ((VAR_DEFN *)qdefn)->IsReadOnly()) {
+
+ return TIPERR_UnsuitableFuncPropMatch;
+ }
+
+ // Matched a variable of which there can only be one,
+ // so we break out of the loop.
+ //
+ break;
+ }
+ // else we don't want a variable so we fall through to
+ // the bottom to get next.
+ }
+ else if (qdefn->IsFuncDefn()) {
+ if (!fWantType) {
+ // Get the invokekind from the FUNC_DEFN we matched.
+ qfdefn = (FUNC_DEFN *)qdefn;
+ invokekindMatch = qfdefn->InvokeKind();
+ // Note: we special-case fuInvokeKind == 0 to mean match.
+ if ((fuInvokeKind == 0) || (fuInvokeKind & invokekindMatch)) {
+ // Match the appropriate kind of function of which there
+ // can only be one, so we remember that we've already
+ // matched and if this is the first match we remember it
+ // and attempt to match perhaps some other property,
+ // if we do again then it's an ambiguity and we issue
+ // the appropriate error. Note that this can happen e.g.
+ // if there's a Propery Get and Set and we pass in both
+ // the INVOKE_PropertyGet and INVOKE_PropertyPut flags.
+ //
+ if (fMatchProperty) {
+ return TIPERR_AmbiguousName;
+ }
+ else {
+ // Save the matching hdefn cos we might have to
+ // go through the loop again for ambiguity reasons etc..
+ //
+ hdefnMatch = hdefn;
+ fMatchProperty = TRUE;
+ }
+ // and fall through to get next...
+ } // if
+ // else we don't want this property/function or we need to
+ // ensure there's not another suitable match (which would
+ // be an ambiguity), so we fall through to the bottom
+ // to get next.
+ // We do however remember that we matched some kind of
+ // func (perhaps property) so that we can issue the
+ // appropriate if don't find what we're looking for.
+ //
+ fMatchFunc = TRUE;
+ // Since we special-case fuInvokeKind == 0 to mean match the
+ // first thing you find, we prematurely break out of the loop
+ // here with our first match.
+ //
+ if (fuInvokeKind == 0)
+ break;
+ } // if !fWantType
+ // else we don't want a function so we fall through to
+ // the bottom to get next.
+ } // if IsFuncMatch()
+ else {
+ // should never happen: modules only have nested types, vars,
+ // and funcs/props.
+ //
+ DebHalt("bad match.");
+ }
+
+ // get next...
+ indexMatch = m_dbindnametbl.IndexNextOfHlnam(hlnam, indexMatch);
+ } // of while
+
+ // At this point one of 4 conditions holds:
+ // (1) We matched a single property but indexMatch is null
+ // cos we continued to search for ambiguities, however
+ // indexMatch contains saved match.
+ // (2) indexMatch is non-null
+ // (3) indexMatch is NULL and didn't match property but
+ // we did match some other (unsuitable) function.
+ // (4) indexMatch is NULL and didn't match property and
+ // we didn't even match a function.
+ //
+
+ // Well, do we have a suitable match??
+ if ((indexMatch == BIND_INVALID_INDEX) && (fMatchProperty == FALSE)) {
+ if (fMatchFunc == TRUE) {
+ // unsuitable match case -- issue error
+ return (TIPERROR)(fWantType ?
+ TIPERR_UndefinedType :
+ TIPERR_UnsuitableFuncPropMatch);
+ }
+ }
+ else {
+ // Either indexMatch is non-NULL or fMatchProperty is TRUE,
+ // if the latter then we saved the relevant match in
+ // hdefnMatch already.
+ //
+ if (!fMatchProperty) {
+ hdefnMatch = hdefn;
+ }
+
+ // Get the qdefn of the stored match
+ qdefn = m_dbindnametbl.QdefnOfHdefn(hdefnMatch);
+
+ // Functions and Variables.
+ if (qdefn->IsFuncDefn() || qdefn->IsVarDefn()) {
+ // check visibility
+ if (IsMatchOfVisibility((ACCESS)qdefn->Access(), access)) {
+ // update TYPE_DATA member. No need to worry about
+ // releasing since containing typeinfo's lifetime is
+ // at least as long.
+ //
+ pexbind->SetBindKind(qdefn->IsFuncDefn() ? BKIND_FuncMatch
+ : BKIND_OneVarMatch);
+ pexbind->SetHdefn(hdefnMatch);
+ pexbind->SetPtdata(ptdata);
+ ITypeInfoA *ptinfo = ptdata->Pdtroot()->Pgdtinfo();
+ pexbind->SetPtinfo(ptinfo);
+ ptinfo->AddRef(); // client must release
+ }
+ }
+
+ else {
+ DebHalt("unreachable");
+ }
+ }
+
+ return err;
+}
+
+
+/***
+*PUBLIC DYN_TYPEBIND::HvdefnPredeclared.
+*Purpose:
+* returns the predeclared VAR_DEFN
+*
+*
+*Entry:
+* None.
+*
+*Exit:
+* HVAR_DEFN
+*
+***********************************************************************/
+
+HVAR_DEFN DYN_TYPEBIND::HvdefnPredeclared()
+{
+ return Pdtmbrs()->Ptdata()->HvdefnPredeclared();
+}
+
+
+/***
+*PUBLIC DYN_TYPEBIND::GetTypeData.
+*Purpose:
+* returns the TYPE_DATA
+*
+*
+*Entry:
+* None.
+*
+*Exit:
+* TYPE_DATA
+*
+***********************************************************************/
+TYPE_DATA *DYN_TYPEBIND::Ptdata()
+{
+
+ return Pdtmbrs()->Ptdata();
+}
+
+
+/***
+*PUBLIC DYN_TYPEBIND::BindDefnStr - Bind to id.
+*Purpose:
+* Bind to non-type id given string (as opposed to hgnam).
+*
+*Implementation Notes:
+* Converts string to hgnam and then defers to BindDefn.
+* CONSIDER: share code with BindTypeDefnStr
+*
+*Entry:
+* bstrName Name of id to bind. (IN)
+* fuInvokeKind Flags: Kind of invocation (IN).
+* access Visibility attr: private means everything etc. (IN)
+* pexbind Pointer to caller-allocated struct for EXBIND (IN/OUT).
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR DYN_TYPEBIND::BindDefnStr(LPSTR szName,
+ UINT fuInvokeKind,
+ ACCESS access,
+ EXBIND *pexbind)
+{
+ HLNAM hlnam;
+ HGNAM hgnam;
+ NAMMGR *pnammgr;
+ TIPERROR err;
+
+ // extract hgnam from string
+ // First get a nammgr
+ //
+ IfErrRet(m_pdtroot->GetNamMgr(&pnammgr));
+
+ // Get the hlnam without adding it to the name manager if it isn't
+ // already there.
+ //
+ hlnam = pnammgr->HlnamOfStrIfExist(szName);
+
+ // If the hlnam == HLNAM_Nil, then the name doesn't exist
+ // in this project.
+ //
+ if (hlnam == HLNAM_Nil) {
+ // We matched nothing
+ pexbind->SetBindKind(BKIND_NoMatch);
+
+ return TIPERR_None;
+ }
+
+ // get the hgnam to pass to BindDefn
+ IfErrRet(pnammgr->HgnamOfHlnam(hlnam, &hgnam));
+
+ // defer to BindIdDefn
+ return BindIdDefn(FALSE, hgnam, fuInvokeKind, access, pexbind);
+}
+
+
+/***
+*PUBLIC DYN_TYPEBIND::BindTypeDefnStr - Bind to a type.
+*Purpose:
+* Bind to type id given string (as opposed to hgnam).
+*
+*Implementation Notes:
+* Converts string to hgnam and then defers to BindTypeDefn.
+* CONSIDER: share code with BindTypeDefnStr
+*
+*Entry:
+* bstrName Name of id to bind. (IN)
+* fuInvokeKind Flags: Kind of invocation (IN).
+* access Visibility attr: private means everything etc. (IN)
+* pexbind Pointer to caller-allocated struct for EXBIND (IN/OUT).
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR DYN_TYPEBIND::BindTypeDefnStr(LPSTR szName,
+ UINT fuInvokeKind,
+ ACCESS access,
+ EXBIND *pexbind)
+{
+ HLNAM hlnam;
+ HGNAM hgnam;
+ NAMMGR *pnammgr;
+ TIPERROR err;
+
+ // extract hgnam from string
+ // First get a nammgr
+ //
+ IfErrRet(m_pdtroot->GetNamMgr(&pnammgr));
+
+ // Get the hlnam without adding it to the name manager if it isn't
+ // already there.
+ //
+ hlnam = pnammgr->HlnamOfStrIfExist(szName);
+
+ // If the hlnam == HLNAM_Nil, then the name doesn't exist
+ // in this project.
+ //
+ if (hlnam == HLNAM_Nil) {
+ // We matched nothing
+ pexbind->SetBindKind(BKIND_NoMatch);
+
+ return TIPERR_None;
+ }
+
+ // get the hgnam to pass to BindDefn
+ IfErrRet(pnammgr->HgnamOfHlnam(hlnam, &hgnam));
+
+ // defer to BindTypeDefn
+ return BindIdDefn(TRUE, hgnam, 0, access, pexbind);
+}
+
+
+// Stub implementations
+//
+
+
+TYPEKIND DYN_TYPEBIND::GetTypeKind()
+{
+ DebAssert(m_pdtroot->Pgdtinfo() != NULL, "bad TYPEINFO.");
+
+ return m_pdtroot->Pgdtinfo()->GetTypeKind();
+}
+
+
+USHORT DYN_TYPEBIND::GetCbSize()
+{
+ DebAssert(m_cbSize != ~0, "bad size attr.");
+ return m_cbSize;
+}
+
+
+USHORT DYN_TYPEBIND::GetAlignment()
+{
+ DebAssert(m_cbAlignment != ~0, "bad alignment attr.");
+ return m_cbAlignment;
+}
+
+
+/***
+*PUBLIC DYN_TYPEBIND::Read - Read serialized image of DYN_TYPEBIND.
+*Purpose:
+* Read serialized image of DYN_TYPEBIND.
+*
+*Implementation Notes:
+* Serialized format:
+* isProtocol flag
+* cbSize
+* cbAlignment
+* oPvft
+* bindnamtbl
+*
+*Entry:
+* pstrm - STREAM to read image from (IN).
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR DYN_TYPEBIND::Read(STREAM *pstrm)
+{
+ USHORT isProtocol;
+ USHORT cbSize;
+ USHORT cbAlignment;
+ LONG oPvft;
+ TIPERROR err;
+
+ DebAssert(pstrm != NULL, "bad param.");
+
+ // Then Deserialize DYN_TYPEBIND meta-info.
+ // (dougf) why read into locals & then assign?
+ // Because some are bitfields.
+ //
+ IfErrRet(pstrm->ReadUShort(&isProtocol));
+ IfErrRet(pstrm->ReadUShort(&cbSize));
+ IfErrRet(pstrm->ReadUShort(&cbAlignment));
+ IfErrRet(pstrm->ReadULong((ULONG *)&oPvft));
+ IfErrRet(pstrm->ReadUShort(&m_cbPvft));
+ IfErrRet(pstrm->ReadULong(&m_hmemberConst));
+ IfErrRet(pstrm->ReadULong(&m_hmemberDest));
+ // Note: don't serialize m_hmemberCopy/Assign, because only
+ // records have copy/assign function, and these are handled
+ // by REC_TYPEBIND
+
+ // deserialize BINDNAME_TABLE embedded member
+ IfErrRet(m_dbindnametbl.Read(pstrm));
+
+ m_isProtocol = (BOOL)isProtocol;
+ m_isBeingLaidOut = FALSE;
+ m_cbSize = cbSize;
+ m_cbAlignment = cbAlignment;
+ m_oPvft = oPvft;
+
+ return TIPERR_None;
+}
+
+
+/***
+*PUBLIC DYN_TYPEBIND::Write - Write image of DYN_TYPEBIND.
+*Purpose:
+* Write image of DYN_TYPEBIND.
+*
+*Implementation Notes:
+* Serialized format:
+* isProtocol flag
+* cbSize
+* cbAlignment
+* oPvft
+* bindnametbl
+*
+*Entry:
+* pstrm - STREAM to read image to (IN).
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR DYN_TYPEBIND::Write(STREAM *pstrm)
+{
+ USHORT isProtocol = (m_isProtocol != 0);
+ TIPERROR err;
+
+ DebAssert(pstrm != NULL, "bad param.");
+
+ // Then serialize DYN_TYPEBIND meta-info.
+ // CONSIDER: this should be rewritten to write out a contiguous set
+ // CONSIDER: of members of DYN_TYPEBIND in a single write
+ //
+ IfErrRet(pstrm->WriteUShort(isProtocol));
+ IfErrRet(pstrm->WriteUShort(m_cbSize));
+ IfErrRet(pstrm->WriteUShort(m_cbAlignment));
+ IfErrRet(pstrm->WriteULong(m_oPvft));
+ IfErrRet(pstrm->WriteUShort(m_cbPvft));
+ IfErrRet(pstrm->WriteULong(m_hmemberConst));
+ IfErrRet(pstrm->WriteULong(m_hmemberDest));
+ // Note: don't serialize m_hmemberCopy/Assign, because only
+ // records have copy/assign function, and these are handled
+ // by REC_TYPEBIND
+
+ // serialize BINDNAME_TABLE embedded member
+ IfErrRet(m_dbindnametbl.Write(pstrm));
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+#if 0
+
+
+
+
+
+
+#endif // 0
+
+
+
+
+
+TIPERROR DYN_TYPEBIND::BindDefnProjLevelStr(LPSTR,
+ UINT,
+ ACCESS,
+ ACCESS,
+ EXBIND *)
+{
+ DebAssert(FALSE, "can't call.");
+ return TIPERR_None;
+}
+
+
+TIPERROR DYN_TYPEBIND::BindTypeDefnProjLevelStr(LPSTR,
+ UINT,
+ ACCESS,
+ ACCESS,
+ EXBIND *)
+{
+ DebAssert(FALSE, "can't call.");
+ return TIPERR_None;
+}
+
+#if ID_DEBUG
+
+VOID DYN_TYPEBIND::DebCheckState(UINT uLevel) const
+{
+ if (m_pdtroot->CompState() > CS_UNDECLARED) {
+ m_dbindnametbl.DebCheckState(uLevel);
+ }
+}
+
+
+VOID DYN_TYPEBIND::DebShowState(UINT uLevel) const
+{
+ DebPrintf("*** DYN_TYPEBIND ***\n");
+
+ DebPrintf("isProtocol: %u\n", m_isProtocol);
+ DebPrintf("isIsBeingLaidOut: %u\n", m_isBeingLaidOut);
+
+ DebPrintf("m_cbSize: %u\n", m_cbSize);
+ DebPrintf("m_Alignment: %u\n", m_cbAlignment);
+ DebPrintf("m_oPvft: %u\n", m_oPvft);
+ m_dbindnametbl.DebShowState(uLevel);
+}
+
+
+#endif // ID_DEBUG
diff --git a/private/oleauto/src/typelib/dtbind.hxx b/private/oleauto/src/typelib/dtbind.hxx
new file mode 100644
index 000000000..b8f0d0f42
--- /dev/null
+++ b/private/oleauto/src/typelib/dtbind.hxx
@@ -0,0 +1,282 @@
+/***
+*dtbind.hxx - DYN_TYPEBIND header file
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+*
+*Revision History:
+*
+* 03-Apr-91 ilanc: Stub created.
+* 30-Jul-92 w-peterh: removed function overloading
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#ifndef DYN_TYPEBIND_HXX_INCLUDED
+#define DYN_TYPEBIND_HXX_INCLUDED
+
+#include "stream.hxx"
+#include "dfntbind.hxx" // derives from DEFN_TYPEBIND
+#include "defn.hxx" // for DEFN binding structs.
+#include "dbindtbl.hxx" // for DYN_BINDNAME_TABLE
+#include "tdata.hxx"
+
+
+class EXBIND;
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szDTBIND_HXX)
+#define SZ_FILE_NAME g_szDTBIND_HXX
+#endif
+
+class DYN_TYPEROOT;
+
+/***
+*class DYN_TYPEBIND - 'dtbind': Type bind implementation
+*Purpose:
+* The class defines type bind.
+*
+***********************************************************************/
+
+class DYN_TYPEBIND : public DEFN_TYPEBIND
+{
+ friend class DYN_TYPEMEMBERS;
+
+public:
+ DYN_TYPEBIND();
+ nonvirt TIPERROR Init(BLK_MGR *pblkmgr, DYN_TYPEROOT *pdtroot);
+
+ // overridden methods
+ virtual ~DYN_TYPEBIND();
+ virtual LPVOID QueryProtocol(LPOLESTR szInterfaceName);
+ virtual VOID AddRef();
+ virtual VOID Release();
+
+ virtual TIPERROR GetTypeInfo(TYPEINFO **lplptinfo);
+ virtual TYPEKIND GetTypeKind();
+ virtual USHORT GetCbSize();
+ virtual USHORT GetAlignment();
+ virtual USHORT GetCbSizeVft();
+ virtual LONG GetOPvft();
+
+ virtual TIPERROR BindDefnStr(LPSTR szName,
+ UINT fuInvokeKind,
+ ACCESS access,
+ EXBIND *pexbind);
+
+ virtual TIPERROR BindTypeDefnStr(LPSTR szName,
+ UINT fuInvokeKind,
+ ACCESS access,
+ EXBIND *pexbind);
+
+ virtual TIPERROR BindDefnProjLevelStr(LPSTR szName,
+ UINT fuInvokeKind,
+ ACCESS access,
+ ACCESS accessProj,
+ EXBIND *pexbind);
+
+ virtual TIPERROR BindTypeDefnProjLevelStr(LPSTR szName,
+ UINT, // fuInvokeKind: unused
+ ACCESS access,
+ ACCESS accessProj,
+ EXBIND *pexbind);
+
+
+
+ // introduced methods
+ nonvirt VOID AddInternalRef();
+ nonvirt VOID RelInternalRef();
+ nonvirt TIPERROR Read(STREAM *pstrm);
+ nonvirt TIPERROR Write(STREAM *pstrm);
+ nonvirt BOOL IsValid() const;
+ nonvirt TIPERROR BuildBindNameTable();
+
+ nonvirt TIPERROR BindIdDefn(BOOL fWantType,
+ HGNAM hgnam,
+ UINT fuInvokeKind,
+ ACCESS access,
+ EXBIND *pexbind);
+
+ nonvirt HVAR_DEFN HvdefnPredeclared();
+ nonvirt TYPE_DATA *Ptdata();
+
+ nonvirt TIPERROR BindDefnCur(BOOL fWantType,
+ HGNAM hgnam,
+ UINT fuInvokeKind,
+ ACCESS access,
+ EXBIND *pexbind);
+
+ nonvirt DYN_BINDNAME_TABLE *Pdbindnametbl();
+ nonvirt DYN_TYPEMEMBERS *Pdtmbrs() const;
+ nonvirt DYN_TYPEROOT *Pdtroot() const;
+ nonvirt BOOL IsBeingLaidOut();
+
+ // Public data members
+ static LPOLESTR szProtocolName;
+ static LPSTR szBaseName;
+
+ static CONSTDATA UINT oDbindnametbl;
+
+#if ID_DEBUG
+ nonvirt VOID DebCheckState(UINT uLevel) const;
+ nonvirt VOID DebShowState(UINT uLevel) const;
+#else //!ID_DEBUG
+ nonvirt VOID DebCheckState(UINT uLevel) const {}
+ nonvirt VOID DebShowState(UINT uLevel) const {}
+#endif //!ID_DEBUG
+
+protected:
+ nonvirt VOID Invalidate();
+ nonvirt TIPERROR BindBase(BOOL fWantType,
+ HVAR_DEFN hvdefnBase,
+ UINT oBase,
+ HGNAM hgnam,
+ UINT fuInvokeKind,
+ ACCESS access,
+ EXBIND *pexbind,
+ GenericTypeLibOLE *pgtlibole);
+
+private:
+ DYN_TYPEROOT *m_pdtroot;
+
+ // following bitfields pack into single USHORT
+ BOOL m_isProtocol:1;
+ BOOL m_isBeingLaidOut:1;
+ USHORT undone:14;
+
+ USHORT m_cbSize; // instance size (top-level)
+ USHORT m_cbAlignment; // alignment
+ LONG m_oPvft; // offset of primary vft.
+ USHORT m_cbPvft; // size of primary vft.
+ sHCHUNK m_hvtdPrimary;
+
+ // DYN_BINDNAME_TABLE embedded instance
+ DYN_BINDNAME_TABLE m_dbindnametbl;
+
+ // size of the data member block within a basic class
+ USHORT m_cbSizeDataMembers;
+
+#ifdef DYN_TYPEBIND_VTABLE
+#pragma VTABLE_EXPORT
+#endif
+};
+
+
+
+/***
+*PUBLIC DYN_TYPEBIND::IsBeingLaidOut.
+*Purpose:
+* returns TRUE if the modules is being laid out.
+*
+*
+***********************************************************************/
+
+inline BOOL DYN_TYPEBIND::IsBeingLaidOut()
+{
+ return (BOOL) m_isBeingLaidOut;
+}
+
+/***
+*PUBLIC DYN_TYPEBIND::Pbindnametbl - accessor for BINDNAME_TABLE.
+*Purpose:
+* Gets BINDNAME_TABLE ptr.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* BINDNAME_TABLE *
+*
+***********************************************************************/
+
+inline DYN_BINDNAME_TABLE *DYN_TYPEBIND::Pdbindnametbl()
+{
+ return &m_dbindnametbl;
+}
+
+
+/***
+*PUBLIC DYN_TYPEBIND::Invalidate - Invalidate.
+*Purpose:
+* Invalidate by deferring to contained binding table.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* None
+*
+***********************************************************************/
+
+inline VOID DYN_TYPEBIND::Invalidate()
+{
+ m_dbindnametbl.ReleaseTable();
+}
+
+
+/***
+*PUBLIC DYN_TYPEBIND::Pdtroot - accessor for DYN_TYPEROOT.
+*Purpose:
+* Gets containing DYN_TYPEROOT.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* DYN_TYPEROOT *
+*
+***********************************************************************/
+
+inline DYN_TYPEROOT *DYN_TYPEBIND::Pdtroot() const
+{
+ return m_pdtroot;
+}
+
+
+/***
+*PUBLIC DYN_TYPEBIND::GetCbSizePvft - get size of vft
+*Purpose:
+* Returns the size of the primary virtual function table.
+*
+*Entry:
+* None.
+*
+*Exit:
+* Returns size in bytes.
+*
+***********************************************************************/
+
+inline USHORT DYN_TYPEBIND::GetCbSizeVft()
+{
+ return m_cbPvft;
+}
+
+
+/***
+*PUBLIC DYN_TYPEBIND::GetOPvft - get offset of primary vft
+*Purpose:
+* Returns the offset of the primary vft. This is
+* -1 if no virtual function table exists.
+*
+*Entry:
+* None.
+*
+*Exit:
+* returns offset or -1.
+*
+***********************************************************************/
+
+inline LONG DYN_TYPEBIND::GetOPvft()
+{
+ return m_oPvft;
+}
+
+
+#endif // ! DYN_TYPEBIND_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/dtmbrs.cxx b/private/oleauto/src/typelib/dtmbrs.cxx
new file mode 100644
index 000000000..a48b95b01
--- /dev/null
+++ b/private/oleauto/src/typelib/dtmbrs.cxx
@@ -0,0 +1,3285 @@
+/***
+*dtmbrs.cxx - DYN_TYPEMEMBERS
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This is the interface for DYN_TYPEMEMBERS (Silver implementation
+* of the TYPEMEMBERS protocol).
+* Also provides implementation of "list" protocol used
+* by TYPEMEMBERS (in the form of macros).
+*
+*Revision History:
+*
+* 05-Mar-91 ilanc: Created.
+* 11-Mar-91 ilanc: Deleted constructor definition (not needed).
+* 03-Sep-91 ilanc: Reset DYN_TYPEMEMBERS::m_szDocumentation in Read.
+* 19-Sep-91 ilanc: Added GetMemberInfoOfHmember/HlnamOfHmember
+* 17-Oct-91 ilanc: Implement <LIST>::SetAtPosition
+* 03-Mar-92 ilanc: Init embedded DYN_TYPEBIND with pdtroot as well.
+* 10-Apr-92 alanc: MakeLaidOut now builds bind table
+* 12-Apr-92 ilanc: DebCheckState impl
+* 16-Apr-92 ilanc: Set isBeingLaidOut at outset of Layout()
+* so that if ConstructMemberLists() calls
+* back into TYPECOMPILER (e.g. while evaling a
+* const expr) we can do the right thing.
+* 05-May-92 ilanc: Fixed LayoutDataMembers -- don't alloc
+* instance memory for const datamembers.
+* 02-Jul-92 w-peterh: merged data member/type list in tdata
+* 10-Jul-92 w-peterh: added layout of nested types
+* 30-Jul-92 w-peterh: flag as being laid out before constants are evaled
+* 11-Aug-92 w-peterh: set ptrkindofUDT()
+* 18-Aug-92 w-peterh: only assign hmembers if they are required
+* 15-Nov-92 RajivK: added GetSize and DebGetSize
+* 18-Jan-93 w-peterh: use new tdesckind enum
+* 01-Mar-93 w-peterh: remove named base classes
+* layout OLE virtual functions
+* layout OLE bases
+* layout arrays correctly
+* layout OLE properties correctly
+* 02-Mar-93 w-peterh: fix layout of TKIND_ENUM
+* 24-Mar-93 dougf: Add TDESCKIND_LPSTR to GetSizeAlignmentOfHtdefnNonUdt.
+* 30-Apr-93 w-jeffc: made DEFN data members private
+*
+*Implementation Notes:
+* Contains a TYPE_DATA object that manages DEFNs with a Silver
+* Block Manager (that in turn defers to a Silver Heap Mgr).
+* Note that the TYPE_DATA object is embedded in the DYN_TYPEMEMBERS
+* which implies that the DYN_TYPEMEMBERS is itself embedded
+* in a Silver Heap. The allocating DYN_TYPEINFO (or more
+* precisely DYN_TYPEROOT) is responsible for allocating
+* the DYN_TYPEMEMBERS in a Silver Heap (and likewise deallocating).
+*
+* POSITION is implemented as a VAR_DEFN handle for OOB_VARINFOLIST
+* and FUNC_DEFN handle for OOB_FUNCINFOLIST.
+* Note: currently list mods can't be made while there are any
+* outstanding iterations. Each list has a count of active iterators,
+* incremented by BeginIterate() and decremented by EndIterate().
+*
+*****************************************************************************/
+
+#include "typelib.hxx"
+#include "silver.hxx"
+#include "mem.hxx"
+#include "cltypes.hxx"
+#include "blkmgr.hxx"
+#include "entrymgr.hxx"
+#define DTMBRS_VTABLE // export vtable
+#include "dtmbrs.hxx"
+#include "clutil.hxx"
+#include "tdata.hxx"
+#include "gdtinfo.hxx"
+#include "dtbind.hxx"
+#include "impmgr.hxx"
+#include "exbind.hxx" // for EXBIND
+#include "nammgr.hxx" // for NAMMGR
+
+#include <malloc.h>
+#include "xstring.h"
+#include <stdlib.h>
+
+
+#pragma hdrstop(RTPCHNAME)
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+static char szOleDtmbrsCxx[] = __FILE__;
+char szOleDtmbrs[] = __FILE__;
+#define SZ_FILE_NAME szOleDtmbrsCxx
+#else
+static char szDtmbrsCxx[] = __FILE__;
+#define SZ_FILE_NAME szDtmbrsCxx
+#endif
+#endif //ID_DEBUG
+
+#define CBMAX_FARPTR_HEAPREQ 0xFFE8
+
+CONSTDATA UINT DYN_TYPEMEMBERS::oDtbind = offsetof(DYN_TYPEMEMBERS, m_dtbind);
+
+// Defined in gdtinfo.cxx
+extern TIPERROR IsFunkyDispinterface(GEN_DTINFO *pgdtinfo,
+ BOOL *pisFunkyDispinterface);
+extern HRESULT GetTypeInfoOfImplType(GEN_DTINFO *pgdtinfo,
+ UINT uImplType,
+ ITypeInfoA **pptinfo);
+
+
+
+// This enum defines the layout order of properties
+// NOTE: this should only be used by this file.
+enum PROPKIND {
+ PROPERTY_Method = 0,
+ PROPERTY_Get,
+ PROPERTY_Let,
+ PROPERTY_Set,
+};
+
+
+
+// Maps INVOKEKIND --> PROPKIND
+inline PropkindOfInvokekind(INVOKEKIND invokekind)
+{
+ switch (invokekind) {
+ case INVOKE_FUNC:
+ return PROPERTY_Method;
+ case INVOKE_PROPERTYGET:
+ return PROPERTY_Get;
+ case INVOKE_PROPERTYPUT:
+ return PROPERTY_Let;
+ case INVOKE_PROPERTYPUTREF:
+ return PROPERTY_Set;
+ default:
+ DebHalt("bad invokekind.");
+ return INVOKE_FUNC;
+ }
+}
+
+// Local struct used to link together properties by name
+// per module.
+// Note: lookup is by name.
+//
+struct PROPERTY_NODE
+{
+ PROPERTY_NODE *m_pnodeNext;
+ HLNAM m_hlnamProperty; // lookup key
+ HMEMBER m_hmemberProperty;
+ HFUNC_DEFN m_rghfdefn[PROPERTY_Set+1]; // for tracking properties.
+
+#pragma code_seg(CS_CREATE)
+ // ctor
+ PROPERTY_NODE() {
+ UINT ihfdefn;
+ m_pnodeNext = NULL;
+ m_hlnamProperty = HLNAM_Nil;
+ m_hmemberProperty = HMEMBER_Nil;
+ for (ihfdefn = PROPERTY_Method;
+ ihfdefn < PROPERTY_Set+1;
+ ihfdefn++) {
+ m_rghfdefn[ihfdefn] = HFUNCDEFN_Nil;
+ }
+ }
+
+ // dtor
+ ~PROPERTY_NODE() {
+ if (m_pnodeNext != NULL) {
+ m_pnodeNext->PROPERTY_NODE::~PROPERTY_NODE();
+ MemFree(m_pnodeNext);
+ }
+ }
+
+ // Lookup method
+ PROPERTY_NODE *PnodeOfHlnam(HLNAM hlnam) {
+ if (hlnam == m_hlnamProperty)
+ return this;
+ else if (m_pnodeNext != NULL)
+ return m_pnodeNext->PnodeOfHlnam(hlnam);
+ else
+ return NULL;
+ }
+
+ // Get next
+ PROPERTY_NODE *PnodeNext() {
+ return m_pnodeNext;
+ }
+#pragma code_seg()
+};
+
+#pragma code_seg(CS_CREATE)
+/***
+*TIPERROR VerifyTwoProperties
+*Purpose:
+* Verifies that two properties have compatible formal params.
+*
+*Implementation Notes:
+*
+*Entry:
+* pdtroot The defining type (IN).
+* pnodeProperty Pointer to a property node (IN).
+* propkind1
+* propkind2 Must not be PROPERTY_Get
+*
+*Exit:
+* TIPERROR
+***********************************************************************/
+
+TIPERROR VerifyTwoProperties(DYN_TYPEROOT *pdtroot,
+ TYPE_DATA *ptdata,
+ HFUNC_DEFN hfdefn1,
+ PROPKIND propkind1,
+ HFUNC_DEFN hfdefn2,
+ PROPKIND propkind2)
+{
+ FUNC_TYPE_DEFN ftdefn1, ftdefn2;
+ HPARAM_DEFN hparamdefn1, hparamdefn2;
+ PARAM_DEFN *qparamdefn1, *qparamdefn2;
+ TYPE_DEFN *qtdefn;
+ BOOL fEqual;
+ TIPERROR err = TIPERR_None;
+ BOOL fObject = FALSE;
+ ITypeInfoA *ptinfo = NULL;
+
+ UINT i;
+ UINT cArgs;
+
+ DebAssert(propkind2 != PROPERTY_Get, "bad propkind.");
+
+ ftdefn1 = ptdata->QfdefnOfHfdefn(hfdefn1)->m_ftdefn;
+ ftdefn2 = ptdata->QfdefnOfHfdefn(hfdefn2)->m_ftdefn;
+ hparamdefn1 = (HPARAM_DEFN)ftdefn1.m_hdefnFormalFirst;
+ hparamdefn2 = (HPARAM_DEFN)ftdefn2.m_hdefnFormalFirst;
+
+ // Walk the parameters...and ignore the LCID/RETVAL parameters
+ // if we're in basic. But look at them if we're in OLE.
+ //
+ cArgs = ptdata->QfdefnOfHfdefn(hfdefn1)->CArgs();
+
+ if (propkind1 != PROPERTY_Get) {
+ // if comparing Let with Set, then we don't want to look at the last arg
+ DebAssert(propkind1 == PROPERTY_Let && propkind2 == PROPERTY_Set, "");
+ DebAssert(cArgs > 0, "caller should check for this");
+ cArgs--;
+ }
+
+ for (i=0; i < cArgs; i++) {
+ qparamdefn1 = ptdata->QparamdefnOfIndex(hparamdefn1, i);
+
+ // If this is a retval parameter, we're done looking.
+ if (i == cArgs - 1 && propkind1 == PROPERTY_Get) {
+ qtdefn = qparamdefn1->IsSimpleType()
+ ? qparamdefn1->QtdefnOfSimpleType()
+ : ptdata->QtdefnOfHtdefn(qparamdefn1->Htdefn());
+
+ if (qtdefn->IsRetval()) {
+ break;
+ }
+ }
+
+ qparamdefn2 = ptdata->QparamdefnOfIndex(hparamdefn2, i);
+
+ // Now compare names...
+ if (qparamdefn1->Hlnam() != qparamdefn2->Hlnam()) {
+ err = TIPERR_InconsistentPropFuncs;
+ goto Error;
+ }
+ // ... and types
+ IfErrGo(EquivTypeDefns(ptdata,
+ qparamdefn1->IsSimpleType(),
+ qparamdefn1->Htdefn(),
+ ptdata,
+ qparamdefn2->IsSimpleType(),
+ qparamdefn2->Htdefn(),
+ FEQUIVIGNORE_NULL,
+ &fEqual));
+ if (!fEqual) {
+ err = TIPERR_InconsistentPropFuncs;
+ goto Error;
+ }
+ } // for
+
+ if ((propkind1 == PROPERTY_Get) && (propkind2 == PROPERTY_Let)) {
+ // Note that at this point we know that there must be one more
+ // PARAM_DEFN left to process in the PROPERTY_Let.
+ // In the OB case, hparamdefn2 will reference the last param
+ // of the proplet since we used a while loop to iterate over
+ // the propget's paramlist.
+ // In the OLE case we have to explicitly get proplet's last
+ // param using QparamdefnOfIndex().
+ //
+ DebAssert(ptdata->QfdefnOfHfdefn(hfdefn1)->CArgs()+1
+ == ptdata->QfdefnOfHfdefn(hfdefn2)->CArgs(),
+ "whoops! Let should have one more param than Get.");
+
+ // Last param for proplet is at ordinal CArgs-1, 0-based.
+ qparamdefn2 = ptdata->QparamdefnOfIndex(
+ hparamdefn2,
+ ptdata->QfdefnOfHfdefn(hfdefn2)
+ ->CArgsUnmunged()-1);
+
+ // So far so good. What about return type of Get and last param of Let?
+ // Note we ignore byref vs. byval of the return type vs. the last param.
+ //
+ BOOL fIsSimpleType1;
+ HTYPE_DEFN htdefn1;
+
+ // assume to compare against the return type of the Get
+ fIsSimpleType1 = ftdefn1.IsSimpleTypeResult();
+ htdefn1 = ftdefn1.HtdefnResult();
+
+ TYPE_DEFN * qtdefn1;
+ // if a retval param is given on the propget, compare against this type
+ // instead of against the propget return type
+ qtdefn1 = ptdata->QtdefnResultOfHfdefn(hfdefn1);
+ DebAssert(qtdefn1 != NULL, "return value should have been set");
+ if (qtdefn1->IsRetval()) {
+ // Retval param for propget is at ordinal CArgs()-1, 0-based.
+ qparamdefn1 = ptdata->QparamdefnOfIndex(
+ hparamdefn1,
+ ptdata->QfdefnOfHfdefn(hfdefn1)->CArgsUnmunged()-1);
+ fIsSimpleType1 = qparamdefn1->IsSimpleType();
+ htdefn1 = qparamdefn1->Htdefn();
+ }
+
+ // Special case, if the get is an object or a typeinfo,
+ // the let case should require a variant.
+ //
+ qtdefn = fIsSimpleType1 ? (TYPE_DEFN *)&htdefn1
+ : ptdata->QtdefnOfHtdefn(htdefn1);
+
+ // Only do the following check if we're dealing with
+ // an object of some sort...not for an ENUM or RECORD
+ // or whatnot.
+ //
+ if (qtdefn->Tdesckind() == TDESCKIND_UserDefined) {
+ ITypeLibA *ptlib;
+ UINT ityp;
+ TYPEATTR *ptypeattr;
+ TYPEKIND tkind;
+
+ IfErrRet(ptdata->Pimpmgr()->GetTypeInfo(qtdefn->Himptype(),
+ DEP_None,
+ &ptinfo));
+
+ // Try to get the typekind using the GetTypeInfoType API
+ // to avoid forward typeinfo references.
+ //
+ if (ptinfo->GetContainingTypeLib(&ptlib, &ityp) == NOERROR) {
+ err = TiperrOfHresult(ptlib->GetTypeInfoType(ityp, &tkind));
+
+ ptlib->Release();
+
+ if (err != TIPERR_None) {
+ goto Error;
+ }
+ }
+
+ // If the call to getcontainingtypelib failed, we know we're
+ // not dealing with another typeinfo in this typelib, so we
+ // are free to call GetTypeAttr.
+ //
+ else {
+ IfErrGo(TiperrOfHresult(ptinfo->GetTypeAttr(&ptypeattr)));
+
+ tkind = ptypeattr->typekind;
+ ptinfo->ReleaseTypeAttr(ptypeattr);
+ }
+
+ ptinfo->Release();
+ ptinfo = NULL;
+
+ fObject = tkind == TKIND_COCLASS
+ || tkind == TKIND_DISPATCH
+ || tkind == TKIND_INTERFACE;
+ }
+
+ fEqual = FALSE;
+ if (qtdefn->Tdesckind() == TDESCKIND_Object
+ || fObject
+ ) {
+
+ // Make sure the input parameter is a variant.
+ qtdefn = qparamdefn2->IsSimpleType()
+ ? qparamdefn2->QtdefnOfSimpleType()
+ : ptdata->QtdefnOfHtdefn(qparamdefn2->Htdefn());
+
+ if (qtdefn->Tdesckind() == TDESCKIND_Value) {
+ fEqual = TRUE;
+ }
+ }
+
+ if (!fEqual) {
+ IfErrGo(EquivTypeDefnsIgnoreByRef(ptdata,
+ fIsSimpleType1,
+ htdefn1,
+ ptdata,
+ qparamdefn2->IsSimpleType(),
+ qparamdefn2->Htdefn(),
+ FEQUIVIGNORE_HasLcid,
+ &fEqual,
+ TRUE));
+ if (!fEqual) {
+ err = TIPERR_InconsistentPropFuncs;
+ goto Error;
+ }
+ }
+ }
+ return TIPERR_None;
+
+Error:
+ if (ptinfo != NULL) {
+ ptinfo->Release();
+ }
+
+ return err;
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*TIPERROR VerifyProperties
+*Purpose:
+* Verifies that properties get/let/set have compatible formal params.
+*
+*Implementation Notes:
+*
+*Entry:
+* pdtroot The defining type (IN).
+* pnodeProperty Pointer to a property node (IN).
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR VerifyProperties(DYN_TYPEROOT *pdtroot, PROPERTY_NODE *pnodeProperty)
+{
+ HFUNC_DEFN hfdefnGet = HFUNCDEFN_Nil;
+ HFUNC_DEFN hfdefnLet = HFUNCDEFN_Nil;
+ HFUNC_DEFN hfdefnSet = HFUNCDEFN_Nil;
+ HFUNC_DEFN hfdefnOther, hfdefnErr;
+ FUNC_DEFN *qfdefnGet, *qfdefnLet, *qfdefnSet;
+ UINT cArgsGet, cArgsLet, cArgsSet, cArgsOther;
+ TYPE_DATA *ptdata;
+ PROPKIND propkindOther;
+ TIPERROR err = TIPERR_None;
+
+ ptdata = pdtroot->Pdtmbrs()->Ptdata();
+
+ // PROPERTY_Get info
+ if ((hfdefnGet = pnodeProperty->m_rghfdefn[PROPERTY_Get]) != HFUNCDEFN_Nil) {
+ hfdefnErr = hfdefnGet;
+ qfdefnGet = ptdata->QfdefnOfHfdefn(hfdefnGet);
+
+
+ // Ensure a function and has no optional params
+ if (qfdefnGet->IsSub()
+ ) {
+ err = TIPERR_InconsistentPropFuncs;
+ goto Error;
+ }
+ cArgsGet = qfdefnGet->CArgs(); // ignore LCID/RETVAL in count
+ }
+
+ // PROPERTY_Let info
+ if ((hfdefnLet = pnodeProperty->m_rghfdefn[PROPERTY_Let]) != HFUNCDEFN_Nil) {
+ hfdefnErr = hfdefnLet;
+ qfdefnLet = ptdata->QfdefnOfHfdefn(hfdefnLet);
+
+
+ // Ensure no optional params and ensure a sub or it returns a hresult
+ if (
+ !qfdefnLet->IsHresultSub()) {
+
+ err = TIPERR_InconsistentPropFuncs;
+ goto Error;
+ }
+
+ cArgsLet = qfdefnLet->CArgs(); // ignore LCID/RETVAL in count
+ if (hfdefnGet != HFUNCDEFN_Nil) {
+ // Should have one more arg than Get
+ if (cArgsLet != cArgsGet+1) {
+ err = TIPERR_InconsistentPropFuncs;
+ goto Error;
+ }
+ IfErrGo(VerifyTwoProperties(pdtroot,
+ ptdata,
+ hfdefnGet,
+ PROPERTY_Get,
+ hfdefnLet,
+ PROPERTY_Let));
+ } // if hfdefnGet
+ } // if Let
+
+ // Get and Let are ok -- finally test set.
+ // PROPERTY_Set info
+ //
+ if ((hfdefnSet = pnodeProperty->m_rghfdefn[PROPERTY_Set]) != HFUNCDEFN_Nil) {
+ hfdefnErr = hfdefnSet;
+ qfdefnSet = ptdata->QfdefnOfHfdefn(hfdefnSet);
+
+
+ // Ensure no optional params and ensure a sub or it has a [retval] arg
+ if (
+ !qfdefnSet->IsHresultSub()) {
+
+ err = TIPERR_InconsistentPropFuncs;
+ goto Error;
+ }
+
+ if (hfdefnGet != HFUNCDEFN_Nil) {
+ hfdefnOther = hfdefnGet;
+ propkindOther = PROPERTY_Get;
+ cArgsOther = cArgsGet;
+ }
+ else if (hfdefnLet != HFUNCDEFN_Nil) {
+ hfdefnOther = hfdefnLet;
+ propkindOther = PROPERTY_Let;
+ cArgsOther = cArgsLet-1; // normalize to cArgsGet
+ }
+ else { // no get or let -- just return
+ return TIPERR_None;
+ }
+ cArgsSet = qfdefnSet->CArgs(); // ignore LCID/RETVAL in count
+
+ // Should have one more arg than Get or Let
+ if (cArgsSet != cArgsOther+1) {
+ err = TIPERR_InconsistentPropFuncs;
+ goto Error;
+ }
+ IfErrGo(VerifyTwoProperties(pdtroot,
+ ptdata,
+ hfdefnOther,
+ propkindOther,
+ hfdefnSet,
+ PROPERTY_Set));
+ } // if set
+ return TIPERR_None;
+
+Error:
+ return err;
+}
+#pragma code_seg()
+
+// Class methods - DYN_TYPEMEMBERS
+//
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::Destructor - Destruct an instance.
+*Purpose:
+* Destructs a DYN_TYPEMEMBERS instance.
+*
+*Implementation Notes:
+* Destructs the three lists, TYPEDESC of the Pvft and frees
+* the doc string.
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE )
+DYN_TYPEMEMBERS::~DYN_TYPEMEMBERS()
+{
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC DYN_TYPEMEMBERS:: AddRef
+*Purpose:
+* Implementation of AddRef method.
+*
+*Implementation Notes:
+* Defers to containing DYN_TYPEROOT (which is responsible
+* for tracking DYN_TYPEMEMBERS references).
+*
+*Entry:
+*
+*Exit:
+***********************************************************************/
+
+VOID DYN_TYPEMEMBERS::AddRef()
+{
+ m_pdtroot->AddRefDtmbrs();
+}
+
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::Release
+*Purpose:
+* Implementation of Release method.
+*
+*Implementation Notes:
+* Defers to containing DYN_TYPEROOT (which is responsible
+* for tracking DYN_TYPEMEMBERS references).
+*
+*Entry:
+*
+*Exit:
+***********************************************************************/
+
+VOID DYN_TYPEMEMBERS::Release()
+{
+ // note: do not need to release cached pstlib since
+ // it wasn't obtained through GetContainingTypeLib
+
+ m_pdtroot->ReleaseDtmbrs();
+}
+
+
+/***
+*PUBLIC DYN_TYPEMEMBERS:: AddInternalRef
+*Purpose:
+* Implementation of AddInternalRef method.
+*
+*Implementation Notes:
+* Defers to containing GEN_DTINFO.
+* CONSIDER: implementing a separately managed internal refcount
+* for DYN_TYPEMEMBERS. This would enable the
+* separate *unloading* of DYN_TYPEMEMBERS/DYN_TYPEBIND.
+*
+*Entry:
+*
+*Exit:
+***********************************************************************/
+
+VOID DYN_TYPEMEMBERS::AddInternalRef()
+{
+ m_pdtroot->Pgdtinfo()->AddInternalRef();
+}
+
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::RelInternalRef
+*Purpose:
+* Implementation of RelInternalRef method.
+*
+*Implementation Notes:
+* Defers to containing GEN_DTINFO.
+* CONSIDER: implementing a separately managed internal refcount
+* for DYN_TYPEMEMBERS. This would enable the
+* separate *unloading* of DYN_TYPEMEMBERS/DYN_TYPEBIND.
+*
+*Entry:
+*
+*Exit:
+***********************************************************************/
+
+VOID DYN_TYPEMEMBERS::RelInternalRef()
+{
+ m_pdtroot->Pgdtinfo()->RelInternalRef();
+}
+
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::Constructor - Construct an instance.
+*Purpose:
+* Constructs a DYN_TYPEMEMBERS instance.
+*
+*Implementation Notes:
+* Sets all contained pointers to sub-objects to NULL.
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+DYN_TYPEMEMBERS::DYN_TYPEMEMBERS()
+{
+ m_pdtroot= NULL;
+ m_uFlags = 0; // m_isLaidOut, m_nestDepth
+ m_pnammgr = NULL;
+ m_pentmgr = NULL;
+ m_pimpmgr = NULL;
+ m_pgtlibole = NULL;
+ m_uOffsetOfNextStaticVar=0;
+
+ m_ptinfoCopy = NULL;
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::Initializer - initialize an instance.
+*Purpose:
+* initializes a DYN_TYPEMEMBERS instance.
+*
+*Implementation Notes:
+*
+*Entry:
+* psheapgmr - Pointer to SHEAP_MGR (IN).
+* pdtroot - Pointer to a DYN_TYPEROOT (IN).
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR DYN_TYPEMEMBERS::Init(SHEAP_MGR *psheapmgr, DYN_TYPEROOT *pdtroot)
+{
+ TIPERROR err;
+
+ DebAssert(pdtroot != NULL, "bad param.");
+
+ m_pdtroot = pdtroot;
+
+ // Get NAMMGR
+ IfErrRet(pdtroot->GetNamMgr(&m_pnammgr));
+
+ // Get ENTRYMGR
+ IfErrRet(m_pdtroot->GetEntMgr(&m_pentmgr));
+
+ // Get IMPMGR
+ IfErrRet(m_pdtroot->GetImpMgr(&m_pimpmgr));
+
+ // Cache the type's project.
+ // NOTE: this doesn't bump ref count.
+ //
+ m_pgtlibole = m_pdtroot->Pgdtinfo()->PgtlibOleContaining();
+
+ IfErrRet(m_tdata.Init(psheapmgr, pdtroot));
+ IfErrRet(m_dtbind.Init(&(m_tdata.m_blkmgr), pdtroot));
+ return TIPERR_None;
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::GetDefnTypeBind - Get DEFN_TYPEBIND
+*Purpose:
+* Get (embedded) DEFN_TYPEBIND
+*
+*Implementation Notes:
+* Ensures that class is in at least CS_SEMIDECLARED state, so
+* that MakeLaidOut() can do its thing.
+*
+* Bumps DYN_TYPEMEMBERS ref count.
+* Note: client must Release() the TYPEBIND.
+*
+*Entry:
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+TIPERROR DYN_TYPEMEMBERS::GetDefnTypeBind(DEFN_TYPEBIND **ppdfntbind)
+{
+ TIPERROR err = TIPERR_None;
+
+ DebAssert(ppdfntbind != NULL, "bad param.");
+
+ DebAssert(m_pdtroot->CompState() >= CS_DECLARED,
+ "GetDefnTypeBind: bad compstate");
+
+ AddRef();
+ *ppdfntbind = Pdtbind();
+ return TIPERR_None;
+}
+
+
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::MakeLaidOut
+*Purpose:
+* Lays out the class
+*
+*Implementation Notes:
+* Bumps DYN_TYPEMEMBERS ref count.
+* Note: client must Release() the TYPEBIND.
+*
+*Entry:
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_LAYOUT)
+TIPERROR DYN_TYPEMEMBERS::MakeLaidOut()
+{
+ COMPSTATE compstate;
+
+ TIPERROR err;
+
+ compstate = m_pdtroot->CompState();
+
+ DebAssert(compstate >= CS_SEMIDECLARED,
+ "no binding table yet.");
+
+ DebAssert(m_dtbind.Pdbindnametbl()->IsValid(),
+ "no binding table yet.");
+
+ if (m_dtbind.m_isBeingLaidOut)
+ return TIPERR_CircularType;
+
+ if (!m_isLaidOut) {
+ // (0) Flag DYN_TYPEBIND as being laid out
+ // so that circular definitions can be detected.
+ //
+ m_dtbind.m_isBeingLaidOut = TRUE;
+
+
+ // Now finally lay it out...
+ IfErrGo(Layout());
+ m_dtbind.m_isBeingLaidOut = FALSE;
+ m_isLaidOut = TRUE;
+ }
+
+ DebAssert(m_dtbind.IsValid(), "bad DYN_TYPEBIND.");
+
+ return TIPERR_None;
+
+Error:
+
+ m_dtbind.m_isBeingLaidOut = FALSE;
+
+
+ // undo side effects of laying out the class
+ m_pentmgr->Decompile(compstate);
+ return err;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::GetTypeKind - Get type's kind.
+*Purpose:
+* Get type's kind.
+*
+*Implementation Notes:
+* Defers to containing TYPEINFO for TYPEKIND.
+*
+*Entry:
+*
+*Exit:
+* TYPEKIND
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TYPEKIND DYN_TYPEMEMBERS::GetTypeKind()
+{
+ DebAssert(m_pdtroot->Pgdtinfo() != NULL, "bad TYPEINFO.");
+
+ return m_pdtroot->Pgdtinfo()->GetTypeKind();
+}
+#pragma code_seg( )
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::IsLaidOut - Is type laidout?
+*Purpose:
+* Tests whether type definition is laid out (i.e. compiled).
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* BOOL
+*
+***********************************************************************/
+
+BOOL DYN_TYPEMEMBERS::IsLaidOut()
+{
+ return (BOOL)m_isLaidOut;
+}
+
+
+
+
+
+
+
+
+
+
+
+/***
+*PRIVATE DYN_TYPEMEMBERS::AllocHmembers - Allocate HMEMBERs.
+*Purpose:
+* Allocate HMEMBERs for each method in class and
+* for Constructor/Destructor/Assign/Copy functions for records
+* VBA2: handles event handlers:
+* For all event sources in base class (form template) allocate
+* pvft in the instance. This is needed for E&C, i.e. so that
+* (private) event handlers can be added dynamically.
+* Generates an error if signature doesn't match that of
+* handler defined in event set/source.
+* Calls NewNativeEntry with opvft, which is used to generate
+* adjustment thunk for invoking the handler.
+* Adds an override entry to override list for the vtabledefn.
+*
+* Like LayoutDataMembers Issues error if class attempts to override
+* name introduced in base class.
+*
+*Implementation Notes:
+* uses:
+* NewNativeEntry() for Basic functions, i.e. functions
+* that aren't implemented in a DLL.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CREATE )
+TIPERROR DYN_TYPEMEMBERS::AllocHmembers()
+{
+ HFUNC_DEFN hfdefn, hfdefnNext;
+ FUNC_DEFN *qfdefn;
+ ENTRYMGR *pentrymgr;
+ HMEMBER hmember;
+
+ INVOKEKIND invokekind;
+ PROPERTY_NODE *pnodeList, *pnodeProperty;
+ HLNAM hlnamProperty;
+ TYPEKIND tkind = GetTypeKind();
+ PROPERTY_NODE *pnodeCur;
+ TIPERROR err = TIPERR_None;
+ ITypeInfoA *ptinfoBase = NULL;
+
+ UINT iFunc, iVar;
+
+ HMBR_VAR_DEFN hmvdefn;
+ MBR_VAR_DEFN *qmvdefn;
+
+ // get entrymgr to allocate hmembers in
+ IfErrRet(m_pdtroot->GetEntMgr(&pentrymgr));
+
+ // Note: hmembers for nested types are allocated
+ // in the main layout loop, namely LayoutDataMembers.
+
+
+ // We iterate twice over the functions -- the first
+ // time we're just interested in laying out property functions,
+ // which must be laid out contiguously and then the second
+ // time we layout the public functions. Finally, we layout the
+ // private functions.
+ //
+ DebAssert((PROPERTY_Method == 0) &&
+ (PROPERTY_Get == PROPERTY_Method+1) &&
+ (PROPERTY_Let == PROPERTY_Get+1) &&
+ (PROPERTY_Set == PROPERTY_Let+1),
+ "whoops! bad PROPKIND enum.");
+
+ // (1) Alloc hmembers for properties and verify udts in function.
+ hfdefn = m_tdata.HfdefnFirstAvailMeth();
+ pnodeList = NULL;
+
+ iFunc = 0;
+
+ // Iterate over func defn list
+ while (hfdefn != HFUNCDEFN_Nil) {
+
+ qfdefn = m_tdata.QfdefnOfHfdefn(hfdefn);
+
+
+ // for properties only, where the hmember has not yet been chosen
+ if (!qfdefn->IsMethod()) {
+ invokekind = qfdefn->InvokeKind();
+ hlnamProperty = qfdefn->Hlnam();
+ pnodeProperty = (pnodeList != NULL) ?
+ pnodeList->PnodeOfHlnam(hlnamProperty) :
+ NULL;
+ if (pnodeProperty == NULL) {
+ // need to create new node and cons it to list.
+ IfNullMemErr(pnodeProperty = MemNew(PROPERTY_NODE));
+ ::new (pnodeProperty) PROPERTY_NODE;
+ pnodeProperty->m_pnodeNext = pnodeList;
+ pnodeProperty->m_hlnamProperty = hlnamProperty;
+
+ // save first hfdefn in defn list so ole can use it later
+ // in allocating the hmember
+ pnodeProperty->m_hmemberProperty = (HMEMBER) iFunc;
+
+ pnodeList = pnodeProperty;
+ }
+ // Getting to semi-declared, i.e. construction of the binding
+ // tables will have already ensured unambiguous props.
+ //
+ DebAssert(
+ pnodeProperty->
+ m_rghfdefn[PropkindOfInvokekind(invokekind)] == HFUNCDEFN_Nil,
+ "whoops! ambiguity");
+
+ // save hfdefn of property
+ pnodeProperty->
+ m_rghfdefn[PropkindOfInvokekind(invokekind)] = hfdefn;
+ }
+
+ iFunc++;
+
+ hfdefn = m_tdata.HfdefnNextAvailMeth(hfdefn);
+ } /* while */
+
+
+ // Ensure that formal param lists of property get/set/let are
+ // compatible -- we do this both for OB and OLE.
+ //
+ pnodeCur = pnodeList;
+ while (pnodeCur != NULL) {
+ IfErrGo(VerifyProperties(m_pdtroot, pnodeCur));
+ pnodeCur = pnodeCur->PnodeNext();
+ }
+
+
+ // Get the typeinfo of our base class, if any (used within subsequent loop)
+ if (m_tdata.CBase() > 0) { // if we have base classe(s)
+ IfErrGo(m_tdata.GetTypeInfoOfHvdefn(m_tdata.HvdefnFirstBase(),
+ &ptinfoBase,
+ NULL));
+ DebAssert(ptinfoBase != NULL, "Base not valid");
+ // NOTE: we only support single inheritance here
+ }
+
+ // (2) allocate hmembers for all public non-property functions
+ hfdefn = m_tdata.HfdefnFirstAvailMeth();
+
+ iFunc = 0;
+
+ // Iterate over func defn list
+ //
+ while (hfdefn != HFUNCDEFN_Nil) {
+ hfdefnNext = m_tdata.HfdefnNextAvailMeth(hfdefn);
+
+ qfdefn = m_tdata.QfdefnOfHfdefn(hfdefn);
+
+
+ // We don't assign hmembers for OLE types where the user has
+ // specified the ID for us
+ // NOTE explict casting to a LONG to work around C7 optimizer bug that
+ // caused -1 to go the the default case.
+ switch ((long)(qfdefn->Hmember())) {
+ case DISPID_UNKNOWN:
+ // user didn't pick the id -- we get to assign it
+ if (qfdefn->IsMethod()) {
+ // not a property function
+ // We just use the iFunc in the loword.
+ hmember = (HMEMBER)iFunc;
+ } // IsMethod()
+ else {
+ // property function -- we've already worked out
+ // the hmember.
+ DebAssert(pnodeList != NULL, "whops! where's the prop list");
+ pnodeProperty = pnodeList->PnodeOfHlnam(qfdefn->Hlnam());
+ DebAssert(pnodeProperty != NULL, "whoops! where's the prop?");
+ hmember = pnodeProperty->m_hmemberProperty;
+ DebAssert(hmember != HMEMBER_Nil, "hmember not set!");
+ } /* if */
+
+ qfdefn->SetHmember(FunctionHmemberOfOffset((USHORT)hmember,
+ m_nestDepth));
+ break;
+
+ case DISPID_VALUE:
+ if (tkind == TKIND_INTERFACE) {
+ // cache the hfdefn for value property of interface funcs for speed
+ if (m_tdata.m_hfdefnValue == HFUNCDEFN_Nil) {
+ // if not already set, set this to the hfdefn of the first
+ // function of this name (we don't care if it's a property
+ // function or not).
+ m_tdata.m_hfdefnValue = (sHFUNC_DEFN) hfdefn;
+ }
+ }
+ // fall through to check for a duplicate id
+
+ default:
+ // user picked the ID -- ensure it's not already in use by some other
+ // function in the inheritance heirarchy.
+ //
+ if (ptinfoBase != NULL) { // if we have base classe(s)
+ // see if there's a function with this hmember in the base classe(s)
+ if (ptinfoBase->GetDocumentation(qfdefn->Hmember(), NULL,
+ NULL, NULL, NULL) == NOERROR) {
+ err = TIPERR_DuplicateId;
+ goto Error;
+ }
+ }
+ } // switch
+
+ iFunc++;
+
+ hfdefn = hfdefnNext;
+ } /* while */
+
+
+ // Allocate the hmembers for the data members.
+ iVar = 0;
+
+ hmvdefn = m_tdata.HdefnFirstDataMbrNestedType();
+
+ while (hmvdefn != HMBRVARDEFN_Nil) {
+ qmvdefn = m_tdata.QmvdefnOfHmvdefn(hmvdefn);
+
+ DebAssert(qmvdefn->IsMemberVarDefn(), "Bad defn");
+
+ if (qmvdefn->Hmember() == DISPID_UNKNOWN) {
+ // Set the hmember of this data member.
+ qmvdefn->SetHmember(DataHmemberOfOffset(iVar++,
+ m_nestDepth));
+ }
+
+ hmvdefn = qmvdefn->HdefnNext();
+ }
+
+
+
+Error:
+ // free PROPERTY_NODE list
+ if (pnodeList != NULL) {
+ pnodeList->PROPERTY_NODE::~PROPERTY_NODE();
+ MemFree(pnodeList);
+ }
+ if (ptinfoBase != NULL) {
+ ptinfoBase->Release();
+ }
+ return err;
+}
+#pragma code_seg()
+
+
+/***
+*PRIVATE DYN_TYPEMEMBERS::LayoutBases - Layout bases.
+*Purpose:
+* This function lays out three things within an instance:
+* 1: If not inherited, a virtual function table pointer for classes
+* 2: All inherited base classes.
+* 3: For Basic classes, a USHORT member to hold a reference count.
+*
+*Implementation Notes:
+* Only single inheritance is currently supported.
+* Note that while we support multiple bases on the base list
+* only the first one is laid out.
+*
+*Entry:
+* tkind - The kind of the type (module or class)
+* puOffset - Current offset within instance (IN/OUT).
+* puAlignment - Current alignment requirement (IN/OUT)
+*
+*Exit:
+* returns TIPERROR.
+***********************************************************************/
+
+#pragma code_seg(CS_LAYOUT)
+TIPERROR DYN_TYPEMEMBERS::LayoutBases(TYPEKIND tkind,
+ UINT *puOffset,
+ UINT *puAlignment)
+{
+ UINT cBase; // number of base classes.
+ HVAR_DEFN hvdefnBase; // var defn of 1st base
+ DYN_TYPEBIND *pdtbindBase = NULL; // type bind of 1st base
+ USHORT oVarBase;
+ TIPERROR err = TIPERR_None;
+ SYSKIND syskind;
+
+ MBR_VAR_DEFN *qmvdefn;
+ UINT iBase;
+
+
+ cBase = m_tdata.CBase();
+#if ID_DEBUG
+ if (tkind == TKIND_DISPATCH) {
+ DebAssert(cBase > 0, "Dispatch must derive from an interface");
+ }
+#endif
+ DebAssert(tkind == TKIND_INTERFACE ||
+ tkind == TKIND_DISPATCH ||
+ tkind == TKIND_COCLASS, "Bad module kind");
+
+ // DebAssert(cBase <= 1, "no multiple inheritance");
+
+ // offset within instance of primary interface vtable
+ m_dtbind.m_oPvft = 0;
+
+ // Check to see if any base classes have vft we can share.
+ // since base classes are sorted, just need to check
+ // if leftmost base has a vft to share.
+ //
+ if (cBase == 0) {
+ // cBase == 0, we don't have a pvft yet -- let's alloc one.
+ // allocate space for new vft.
+ //
+ DebAssert(m_pgtlibole == m_pdtroot->Pgdtinfo()->PgtlibOleContaining(),
+ "whoops! where are we now?");
+ syskind = m_pgtlibole->GetSyskind();
+ #define SYSATTR ,syskind
+ DebAssert(*puOffset == 0, "primary vft must be at offset 0");
+ *puOffset += SizeofTdesckind(TDESCKIND_Ptr SYSATTR);
+ *puAlignment = max(*puAlignment, AlignmentTdesckind(TDESCKIND_Ptr));
+ }
+
+ if (cBase > 0) {
+ // 11-Feb-93: note this means for now cBase == 1.
+ hvdefnBase = m_tdata.HvdefnFirstBase();
+ // CONSIDER: for multiple inheritance, iterate over all base classes.
+
+ // Note we need an extra variable here since LayoutVarOfHvdefn
+ // has to be passed a USHORT rather than a UINT (which is
+ // what *puOffset is).
+ //
+ oVarBase = (USHORT)*puOffset;
+
+ // CONSIDER w-peterh 17-Feb-1993 : check to ensure that the
+ // typekind of the base is consistent with the typekind of this
+
+ // layout base
+ IfErrRet(LayoutVarOfHvdefn(tkind,
+ hvdefnBase,
+ &oVarBase,
+ puAlignment,
+ FALSE, // not a stack frame.
+ 0)); // ignored.
+
+ // Update output param.
+ *puOffset = oVarBase;
+
+ // Set the hmember of each base class.
+ //
+ for (iBase = 0;
+ hvdefnBase != HVARDEFN_Nil;
+ hvdefnBase = (HVAR_DEFN)qmvdefn->HdefnNext(), iBase++) {
+
+ qmvdefn = m_tdata.QmvdefnOfHmvdefn((HMBR_VAR_DEFN)hvdefnBase);
+
+ DebAssert(qmvdefn->IsMemberVarDefn(), "Bad defn");
+
+ if (qmvdefn->Hmember() == DISPID_UNKNOWN) {
+ qmvdefn->SetHmember(DataHmemberOfOffset(iBase+m_tdata.CDataMember(),
+ m_nestDepth));
+ }
+ }
+ }
+
+ return err;
+}
+#pragma code_seg()
+
+
+
+
+
+
+
+
+
+/***
+*PRIVATE DYN_TYPEMEMBERS::GetSizeAlignmentOfHtdefnUdt
+*Purpose:
+* Get size and alignment for udt.
+*
+*Implementation Notes:
+*
+*Entry:
+* htdefn - Handle to type to layout (IN).
+* pcbSizeType - Size of type (OUT).
+* pcbAlignment - Alignment for type (OUT).
+*
+*Exit:
+* No errors possible.
+*
+***********************************************************************/
+
+TIPERROR DYN_TYPEMEMBERS::GetSizeAlignmentOfHtdefnUdt(HTYPE_DEFN htdefn,
+ UINT *pcbSizeType,
+ UINT *pcbAlignment)
+{
+ UINT cbSizeType;
+ UINT cbAlignment;
+ TYPE_DEFN *qtdefn;
+ sHIMPTYPE himptypeEmbedded;
+ ITypeInfoA *ptinfoEmbedded = NULL;
+ TIPERROR err = TIPERR_None;
+ TYPEATTR *ptypeattr = NULL;
+
+ DebAssert(pcbSizeType != NULL && pcbAlignment != NULL, "null param.");
+
+ // Get the TYPE_DEFN.
+ qtdefn = m_tdata.QtdefnOfHtdefn(htdefn);
+
+ DebAssert(qtdefn->IsUserDefined() && !qtdefn->IsBasicPtr(),
+ "expected UDT.");
+
+ // If this is really an embedded type then...
+ // i.e. it isn't really a *reference* to a UDT.
+ //
+ himptypeEmbedded = qtdefn->Himptype();
+ DebAssert(qtdefn->Qhimptype() != NULL, "whoops! bad type.");
+
+ // Get TYPEINFO for embedded member.
+ IfErrRet(m_pimpmgr->GetTypeInfo(himptypeEmbedded,
+ DEP_Layout,
+ &ptinfoEmbedded));
+
+ // Get the TypeAttr
+ IfErrGo(TiperrOfHresult(ptinfoEmbedded->GetTypeAttr(&ptypeattr)));
+
+
+ DebAssert(ptypeattr->cbSizeInstance <= CBMAX_FARPTR_HEAPREQ, "cbSizeInstance > 64K");
+ cbSizeType = LOWORD(ptypeattr->cbSizeInstance);
+
+#if 0
+ DebAssert(cbSizeType != 0xFFFF,
+ "whoops! can't layout this embedded member.");
+#endif //0
+
+ cbAlignment = ptypeattr->cbAlignment;
+
+ DebAssert(cbAlignment != 0xFFFF,
+ "whoops! can't have undefined alignment attribute.");
+
+ // Setup output params.
+ *pcbSizeType = cbSizeType;
+ *pcbAlignment = cbAlignment;
+
+ ptinfoEmbedded->ReleaseTypeAttr(ptypeattr);
+
+ // fall through...
+
+Error:
+
+ RELEASE(ptinfoEmbedded);
+ return err;
+}
+
+
+/***
+*PRIVATE DYN_TYPEMEMBERS::GetSizeAlignmentOfArray
+*Purpose:
+* Get size and alignment for array
+*
+*Implementation Notes:
+*
+*Entry:
+* tkind - Kind of type (IN).
+* htdefn - Handle to TYPE_DEFN (IN).
+* pcbSizeType - Size of type (OUT).
+* pcbAlignment - Alignment (for embedded UDT) (OUT).
+*
+*Exit:
+* No errors possible.
+*
+***********************************************************************/
+
+TIPERROR DYN_TYPEMEMBERS::GetSizeAlignmentOfArray(TYPEKIND tkind,
+ HTYPE_DEFN htdefn,
+ UINT *pcbSizeType,
+ UINT *pcbAlignment)
+{
+ UINT cbSizeTypeArrayElem;
+ TYPEDESCKIND tdesckind;
+ SAFEARRAY *qad;
+ UINT cDims, cbPad;
+ HTYPE_DEFN htdefnArrayElem;
+ HARRAY_DESC harraydesc;
+ TYPE_DEFN *qtdefn;
+ TIPERROR err = TIPERR_None;
+ SYSKIND syskind;
+
+ qtdefn = m_tdata.QtdefnOfHtdefn(htdefn);
+ tdesckind = qtdefn->Tdesckind();
+
+ // Get array descriptor and number of dimensions.
+ harraydesc = qtdefn->Harraydesc();
+ qad = m_tdata.QarraydescOfHarraydesc(harraydesc);
+ cDims = qad->cDims;
+
+ // Note: that we must update the cbElement field of the AD here.
+ // So, we get the type of the element and recursively
+ // call the appropriate GetSizeOfHtdefn method.
+ //
+ htdefnArrayElem = qtdefn->HtdefnFoundation(htdefn);
+
+ IfErrRet(GetSizeAlignmentOfHtdefn(tkind,
+ FALSE, // never simple.
+ htdefnArrayElem,
+ &cbSizeTypeArrayElem,
+ pcbAlignment)); // used for records
+ // and carrays
+ // give error if this is 'void' (size/alignment for void is 0)
+ // can't have arrays of 'void'
+ if (cbSizeTypeArrayElem == 0) {
+ DebAssert(*pcbAlignment == 0, "alignment should be 0");
+ return TIPERR_TypeMismatch;
+ }
+ DebAssert(*pcbAlignment != 0, "alignment shouldn't be 0");
+
+ // Redereference.
+ qtdefn = m_tdata.QtdefnOfHtdefn(htdefn);
+ qad = m_tdata.QarraydescOfHarraydesc(harraydesc);
+
+ // Figure out how much padding we need to ensure that the elements
+ // are always properly aligned.
+ //
+ cbPad = *pcbAlignment - cbSizeTypeArrayElem % *pcbAlignment;
+
+ if (cbPad == *pcbAlignment) {
+ cbPad = 0;
+ }
+
+ // Update AD with element size.
+ qad->cbElements = (USHORT)(cbSizeTypeArrayElem += cbPad);
+
+ // Work out if we're resizable.
+ if (qtdefn->IsResizable()) {
+ // ensure we're not a carray
+ DebAssert(tdesckind != TDESCKIND_Carray, "Carrays can't be resizable");
+ // Reference type-level or module-level growable array.
+ // We just have a pointer to an arraydesc so use default
+ //
+ syskind = m_pgtlibole->GetSyskind();
+ *pcbSizeType = SizeofTdesckind(tdesckind, syskind);
+ *pcbAlignment = AlignmentTdesckind(tdesckind);
+ }
+ else {
+ DebAssert(tkind == TKIND_MODULE ||
+ tkind == TKIND_RECORD ||
+ tdesckind == TDESCKIND_Carray, "layout: bad typekind.");
+
+ // we want Carrays to be embedded like in a record
+ if (tdesckind == TDESCKIND_Carray || tkind == TKIND_RECORD) {
+ // NOTE: ilanc: for now we assume that
+ // arrays in OB are always tagged as BasicArray,
+ // since however fixed arrays in records are
+ // actually themselves embedded, it perhaps would
+ // be better to type them as Carrays -- this way
+ // MkTypLib could handle C structs with embedded
+ // C arrays. If this were the case, then
+ // ConstructMemberLists would have to change.
+ //
+ ULONG uSizeType;
+ UINT iDim;
+ ULONG cElements;
+
+ // Here we know that we have a fixed-size array
+ // in a record. Since it will be embedded in the
+ // record, we need to set FADF_EMBEDDED in the
+ // feature flags of the array descriptor.
+ // (StevenL 12-Jan-93)
+ //
+ qad->fFeatures |= FADF_EMBEDDED;
+
+ // get number of elements in array
+ cElements = 1;
+ for (iDim = 0; iDim < cDims; iDim++) {
+ cElements *= qad->rgsabound[iDim].cElements;
+ if (cElements > CBMAX_FARPTR_HEAPREQ) {
+ return TIPERR_SizeTooBig;
+ }
+ }
+
+ // size is size of element * number of elements
+ uSizeType = cElements * cbSizeTypeArrayElem;
+ if (uSizeType > CBMAX_FARPTR_HEAPREQ) {
+ return TIPERR_SizeTooBig;
+ }
+ *pcbSizeType = (USHORT)uSizeType;
+ }
+ else {
+ // Embedded module-level non-growable array:
+ // The ARRAY_DESC is embedded in the object at top-level.
+ //
+ *pcbSizeType = CbSizeArrayDesc(cDims);
+ // NOTE: we really want to get the "true" alignment of
+ // of an ARRAYDESC however we don't have a way of learning
+ // what the alignment attribute is of a C structure, so
+ // we choose the closest TDESCKIND, which is TDESCKIND_BasicArray
+ // which assumes by default that a basicarray is implemented
+ // as a pointer to an ARRAYDESC, but lo and behold an ARRAYDESC
+ // itself just contains a bunch of longs, shorts and pointers
+ // so it turns out that the TDESCKIND_BasicArray's alignment
+ // is good enough. Yeah.. it's a hack...
+ //
+ *pcbAlignment = AlignmentTdesckind(tdesckind);
+ }
+ }
+ return err;
+}
+
+
+/***
+*PRIVATE DYN_TYPEMEMBERS::GetSizeAlignmentOfHtdefn
+*Purpose:
+* Get size and alignment for UDT
+* Get size for non-UDT.
+*
+*Implementation Notes:
+*
+*Entry:
+* tkind - Kind of type (IN).
+* isEmbeddedTypeDefn - TRUE if htdefn is literal TYPE_DEFN (IN).
+* htdefn - Handle to TYPE_DEFN (IN).
+* pcbSizeType - Size of type (OUT).
+* pcbAlignment - Alignment (for embedded UDT) (OUT).
+*
+*Exit:
+* No errors possible.
+*
+***********************************************************************/
+
+TIPERROR DYN_TYPEMEMBERS::GetSizeAlignmentOfHtdefn(TYPEKIND tkind,
+ BOOL isEmbeddedTypeDefn,
+ HTYPE_DEFN htdefn,
+ UINT *pcbSizeType,
+ UINT *pcbAlignment)
+{
+ UINT cbSizeTypeArray, cbAlignmentArray;
+ BOOL isUserDefined, isBasicPtr, isSimpleType;
+ sHTYPE_DEFN htdefnActual;
+ TYPE_DEFN *qtdefn;
+ TYPEDESCKIND tdesckind;
+ TIPERROR err = TIPERR_None;
+ SYSKIND syskind;
+
+ // TYPE_DEFNs are really 16-bit things on both mac and win.
+ // so in the simple case we have to ensure that we take
+ // the address of a 16-bit thing!
+ //
+ htdefnActual = (sHTYPE_DEFN)htdefn;
+
+ // for typedefn Alias isEmbedded may not equal isSimpleType
+ qtdefn = isEmbeddedTypeDefn ?
+ (TYPE_DEFN *)&htdefnActual :
+ m_tdata.QtdefnOfHtdefn(htdefn);
+ isSimpleType = IsSimpleType(qtdefn->Tdesckind());
+
+ isUserDefined = qtdefn->IsUserDefined();
+ isBasicPtr = qtdefn->IsBasicPtr();
+ tdesckind = qtdefn->Tdesckind();
+
+#if ID_DEBUG
+ if (isUserDefined) {
+ DebAssert(!isSimpleType, "bad simple type.");
+ }
+#endif // ID_DEBUG && !EI_OB
+
+ if (isUserDefined && !isBasicPtr) {
+ IfErrRet(GetSizeAlignmentOfHtdefnUdt(htdefn,
+ pcbSizeType,
+ pcbAlignment));
+
+ }
+ else if (isUserDefined || isBasicPtr) {
+ // CONSIDER: ilanc: i think the first clause of disjunction is
+ // tautological.
+ // This is the case of reference to a class/record or intrinsic.
+ DebAssert(isBasicPtr, "whoops! should be basicptr.");
+
+ // NOTE: 03-Jun-93 ilanc: we have to specially process pointers
+ // to arrays here so that their array descriptors get updated
+ // correctly. In particular the problem is that of formal arrays
+ // (params).
+ //
+ if (tdesckind == TDESCKIND_Carray ||
+ tdesckind == TDESCKIND_BasicArray) {
+ IfErrRet(GetSizeAlignmentOfArray(tkind,
+ htdefn,
+ &cbSizeTypeArray,
+ &cbAlignmentArray));
+ }
+
+ // Pretend we're a pointer.
+ syskind = m_pgtlibole->GetSyskind();
+ *pcbSizeType = SizeofTdesckind(TDESCKIND_Ptr, syskind);
+ *pcbAlignment = AlignmentTdesckind(TDESCKIND_Ptr);
+ }
+ else {
+ // Non-UDT: either a simple type or fixedstring/array etc.
+ if (IsSimpleType(tdesckind)) {
+ syskind = m_pgtlibole->GetSyskind();
+ *pcbSizeType = SizeofTdesckind(tdesckind, syskind);
+ *pcbAlignment = AlignmentTdesckind(tdesckind);
+ }
+ else {
+ IfErrRet(GetSizeAlignmentOfHtdefnNonUdt(tkind,
+ isSimpleType,
+ htdefn,
+ pcbSizeType,
+ pcbAlignment));
+ }
+ } // if non-UDT
+
+ // we'll return 0 for 'void'
+ DebAssert(*pcbAlignment != 0xFFFF, "Alignment not set");
+#if 0
+ DebAssert(*pcbSizeType != 0xFFFF, "Size not set");
+#endif //0
+
+ return err;
+}
+
+
+/***
+*PRIVATE DYN_TYPEMEMBERS::GetSizeAlignmentOfHtdefnNonUdt
+*Purpose:
+* Get size for non-udt variable but not simple type.
+* E.g. arrays and fixed-strings.
+*
+*Implementation Notes:
+*
+*Entry:
+* hvdefn - Handle to variable to layout (IN).
+* pcbSizeType - Size of type (OUT).
+*
+*Exit:
+* No errors possible.
+*
+***********************************************************************/
+
+TIPERROR DYN_TYPEMEMBERS::GetSizeAlignmentOfHtdefnNonUdt(TYPEKIND tkind,
+ BOOL isSimpleType,
+ HTYPE_DEFN htdefn,
+ UINT *pcbSizeType,
+ UINT *pcbAlignment)
+{
+ TYPEDESCKIND tdesckind;
+ TYPE_DEFN *qtdefn;
+ sHTYPE_DEFN htdefnActual;
+#if ID_DEBUG
+ PTRKIND ptrkind;
+#endif
+ TIPERROR err = TIPERR_None;
+ SYSKIND syskind;
+
+ DebAssert(pcbSizeType != NULL, "null param.");
+
+ // TYPE_DEFNs are really 16-bit things on both mac and win.
+ // so in the simple case we have to ensure that we take
+ // the address of a 16-bit thing!
+ //
+ htdefnActual = (sHTYPE_DEFN)htdefn;
+
+ // Deref handle.
+ qtdefn = isSimpleType ?
+ (TYPE_DEFN *)&htdefnActual :
+ m_tdata.QtdefnOfHtdefn(htdefn);
+ tdesckind = qtdefn->Tdesckind();
+
+ // calculate default alignment
+ // will get overridden if this isn't correct
+ *pcbAlignment = AlignmentTdesckind(tdesckind);
+
+ // Calculate size of instance non-UDT or of reference to UDT.
+ switch (tdesckind) {
+ case TDESCKIND_Ptr:
+ case TDESCKIND_UserDefined:
+ // NOTE: 08-Jan-93 ilanc: I think the Ptr case is only reached
+ // in the BYPTR param case... w-peterh - or VT_PTR for ItypeInfos
+ //
+ // The UserDefined case is only reached iff this is a reference
+ // to an OB UDT -- i.e. whose ptrkind basic ptr.
+ // Thus the size of such a member is the sizeof a ptr.
+ // Note that we don't actually get the UDT's typeinfo here,
+ // since we don't need it. However, it was previously
+ // loaded as a side-effect of SetPtrkind in order
+ // to determine the "record-ness"/"class-ness" of the type.
+ //
+#if ID_DEBUG
+ ptrkind = qtdefn->Ptrkind();
+ DebAssert(ptrkind == (tdesckind == TDESCKIND_UserDefined) ?
+ PTRKIND_Basic :
+ PTRKIND_Far,
+ "whoops! bad ptrkind.");
+#endif
+
+ case TDESCKIND_LPWSTR:
+ case TDESCKIND_LPSTR:
+ // We pretend we're a pointer...
+ syskind = m_pgtlibole->GetSyskind();
+ *pcbSizeType = SizeofTdesckind(TDESCKIND_Ptr, syskind);
+ *pcbAlignment = AlignmentTdesckind(TDESCKIND_Ptr);
+ break;
+
+ case TDESCKIND_BasicArray:
+ case TDESCKIND_Carray:
+ IfErrRet(GetSizeAlignmentOfArray(tkind,
+ htdefn,
+ pcbSizeType,
+ pcbAlignment));
+ break;
+
+ default:
+ DebHalt("Simple types shouldn't be here.");
+ break;
+ } // switch
+
+ // Check that we did ok
+ DebAssert((*pcbAlignment > 0) && (*pcbAlignment != 0xFFFF),
+ "Alignment not set correctly");
+ return err;
+}
+
+
+/***
+*PRIVATE DYN_TYPEMEMBERS::LayoutVarOfHvdefn
+*Purpose:
+* Layout a single var given an hvdefn. In addition adds an
+* entry to the resdesctable for the module if the var is
+* either non-local or static (i.e. includes static locals).
+*
+*Implementation Notes:
+* Defers to LayoutVar.
+*
+*Entry:
+* tkind - Kind of module (IN).
+* hvdefn - Handle to variable to layout (IN).
+* puOffset - Current offset within instance (IN/OUT).
+* Could be negative if stack frame.
+* puAlignment - Alignment so far for members (IN/OUT).
+* isStackFrame - Indicates that client is laying out frame (IN).
+* uStackAlignment - Platform-specific alignment (IN).
+* CONSIDER: could be platform/build specific.
+* fIgnoreHvdefn - Flag used by clients in cases in which they
+* want to prevent this method from registering
+* any errors using the hdefn mechanism. This
+* can happen when the client has a "fake"
+* hvdefn, i.e. one that isn't referenced
+* by the p-code (which is what the error
+* registration depends on) (IN).
+*
+*Exit:
+* No errors possible.
+*
+***********************************************************************/
+#pragma code_seg(CS_LAYOUT)
+TIPERROR DYN_TYPEMEMBERS::LayoutVarOfHvdefn(TYPEKIND tkind,
+ HVAR_DEFN hvdefn,
+ USHORT *puOffset,
+ UINT *puAlignment,
+ BOOL isStackFrame,
+ UINT uStackAlignment,
+ BOOL fIgnoreHvdefn)
+{
+ VAR_DEFN *qvdefn;
+ USHORT oVarCur, oVarNext;
+ UINT cbSizeType = 0;
+ UINT cbAlignment = 0;
+ TYPE_DEFN *qtdefn;
+ UINT cRecTypeDefn = 0;
+ HTYPE_DEFN htdefn;
+
+
+ TIPERROR err = TIPERR_None;
+
+ DebAssert((puOffset != NULL) && (puAlignment != NULL),
+ "bad params.");
+
+ // Get current offset.
+ oVarCur = *puOffset;
+
+ // Deref handle to variable.
+ qvdefn = m_tdata.QvdefnOfHvdefn(hvdefn);
+
+
+ DebAssert(qvdefn->IsVarDefn(), "only var defns allowed");
+
+ // Get the TYPE_DEFN so we can query whether it's a UDT or not etc.
+ qtdefn = m_tdata.QtdefnOfHvdefn(hvdefn);
+
+
+ // We get the actual type handle here since the various GetSize meths
+ // will need it.
+ //
+ htdefn = qvdefn->Htdefn();
+
+ // Notes:
+ // (1) all members of standard modules must be static.
+ // (2) all members of class modules (both OB and non-OB)
+ // cannot be static.
+ // (3) all constant members and locals do not have "memory"
+ // and must have an associated literal constval.
+ //
+
+#if ID_DEBUG
+ // (1) Assert if static member then standard module.
+ //
+ if (qvdefn->IsDataMember() && qvdefn->IsStatic()) {
+ DebAssert(tkind == TKIND_MODULE,
+ "whoops! must be std module.");
+ }
+
+ // (2) Assert if datamember then
+ // if std module then static.
+ //
+ if (qvdefn->IsDataMember() && (tkind == TKIND_MODULE)) {
+ DebAssert((qvdefn->IsStatic() || qtdefn->IsConst()),
+ "whoops! should be static or constant member.");
+ }
+
+ // (3) Assert if a datamember then if type IsConst then
+ // const hasConstVal
+ //
+ if (qvdefn->IsDataMember() && qtdefn->IsConst()) {
+ DebAssert(qvdefn->HasConstVal(),
+ "whoops! const datamember should have a literal const val.");
+ }
+#endif
+
+ // Note: datamember/local constants aren't laidout at all.
+ //
+ if (!qtdefn->IsConst()) {
+ // Switch on intrinsic types and userdefined.
+ // For intrinsic types we calculate the desired offset
+ // on the fly. For userdefined types we get their
+ // DYN_TYPEBIND and ask for the Size and Alignment
+ // attributes.
+ //
+
+
+ if (tkind != TKIND_DISPATCH || qvdefn->IsBase()) {
+
+ // Get size and alignment for type. Then adjust based on
+ // uStackAlignment.
+ //
+ err = GetSizeAlignmentOfHtdefn(tkind,
+ qvdefn->IsSimpleType(),
+ htdefn,
+ &cbSizeType,
+ &cbAlignment);
+
+ if (err != TIPERR_None) {
+ return err;
+ }
+
+ // give error if this is 'void' (size/alignment for void is 0)
+ if (cbSizeType == 0) {
+ DebAssert(cbAlignment == 0, "");
+ err = TIPERR_TypeMismatch;
+ goto Error;
+ }
+ DebAssert(cbAlignment != 0, "");
+
+ cbAlignment = max(uStackAlignment, cbAlignment);
+
+ // Now align member:
+ oVarNext = (USHORT)AlignMember(&oVarCur,
+ cbAlignment,
+ cbSizeType,
+ isStackFrame);
+
+ if (oVarNext == 0) {
+ // return error if we overflowed while doing the math
+ err = TIPERR_SizeTooBig;
+ goto Error;
+ }
+ }
+ else {
+ oVarNext = oVarCur;
+ oVarCur = 0;
+ }
+
+ // update VAR_DEFN
+ qvdefn = m_tdata.QvdefnOfHvdefn(hvdefn);
+ if (!qvdefn->IsBase()) { // oVar field doesn't exist for
+ qvdefn->SetOVar(oVarCur); // bases (used as impltypeflags)
+ }
+ oVarCur = oVarNext;
+
+ // setup output params.
+ // Alignment of a class is simply the maximum of the
+ // alignments of its immediate members.
+ //
+ *puOffset = oVarNext;
+ *puAlignment = max(cbAlignment, *puAlignment);
+
+ } // if !isConst
+
+ return TIPERR_None;
+
+Error:
+ // Now register the error -- but only if they don't want
+ // us to ignore the hvdefn. In that case, it's the client's
+ // responsibility to deal with it.
+ //
+
+ return err;
+}
+#pragma code_seg()
+
+
+
+
+
+
+
+
+
+
+
+
+/***
+*PRIVATE DYN_TYPEMEMBERS::LayoutDataMembers - Layout data members.
+*Purpose:
+* Layout data members.
+*
+*Implementation Notes:
+* Data members are laid out on platform-dependent boundary.
+* Note: zero-length data members (instances of zero-length
+* classes are given length 2 -- so that instance offsets
+* are never shared between members).
+*
+*Entry:
+* tkind - Kind of module (IN)
+* puOffset - Current offset within instance (IN/OUT).
+* puAlignment - Current alignment of instance
+* hdefnFirst - handle to first defn in list of var defns
+* Note: this can contain RecTypeDefns
+*
+*Exit:
+*
+***********************************************************************/
+
+#pragma code_seg(CS_LAYOUT)
+TIPERROR DYN_TYPEMEMBERS::LayoutDataMembers(TYPEKIND tkind,
+ UINT *puOffset,
+ UINT *puAlignment,
+ HDEFN hdefnFirst)
+{
+ HDEFN hdefnCur;
+ USHORT oVarCur;
+ UINT cRecTypeDefn = 0;
+ TIPERROR err = TIPERR_None;
+
+ // offset to end of current member
+ oVarCur = (USHORT)*puOffset;
+
+ // Get listhead to the VAR_DEFNs threaded by TYPE_DATA.
+ hdefnCur = hdefnFirst;
+
+ while (hdefnCur != HDEFN_Nil) {
+ DebAssert(!(m_tdata.QdefnOfHdefn(hdefnCur)->IsRecTypeDefn()), "inapplicable");
+ {
+ // layout datamember
+ IfErrRet(LayoutVarOfHvdefn(tkind,
+ hdefnCur,
+ &oVarCur,
+ puAlignment,
+ FALSE, // not a stack frame.
+ 0)); // ignored.
+
+ }
+
+ // get next
+ hdefnCur = m_tdata.QdefnOfHdefn(hdefnCur)->HdefnNext();
+ } // while
+
+ // Setup output params.
+ // Note that puAlignment is already set.
+ //
+ *puOffset = oVarCur;
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+/***
+*PRIVATE DYN_TYPEMEMBERS::LayoutMembers - Layout members.
+*Purpose:
+* Layout base and data members.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+#pragma code_seg(CS_LAYOUT)
+TIPERROR DYN_TYPEMEMBERS::LayoutMembers()
+{
+ UINT uOffset = 0;
+ UINT uAlignment = 0;
+ TYPEKIND tkind;
+ USHORT oCur;
+ TIPERROR err;
+ SYSKIND syskind;
+
+
+ tkind = GetTypeKind();
+
+ switch (tkind) {
+ case TKIND_ALIAS:
+ // if this is an alias, then layout its alias and we're done
+ DebAssert((m_tdata.CMeth() == 0) &&
+ (m_tdata.CBase() == 0) &&
+ (m_tdata.CNestedType() == 0) &&
+ (m_tdata.CDataMember() == 0), "Alias can't have members");
+
+ // Get size and alignment for type
+ // see explaination in LayoutVarOfHvdefn
+ //
+ IfErrRet(GetSizeAlignmentOfHtdefn(tkind,
+ m_tdata.IsSimpleTypeAlias(),
+ m_tdata.m_htdefnAlias,
+ &uOffset,
+ &uAlignment));
+ break;
+
+ case TKIND_ENUM:
+ // for enums just layout an int
+ DebAssert(m_pgtlibole == m_pdtroot->Pgdtinfo()->PgtlibOleContaining(),
+ "whoops! where are we now?");
+
+ syskind = m_pgtlibole->GetSyskind();
+ uOffset = SizeofTdesckind(TDESCKIND_Int, syskind);
+ uAlignment = AlignmentTdesckind(TDESCKIND_Int);
+ break;
+
+
+ case TKIND_COCLASS:
+ // Classes and coclasses flagged as an appobj have a predeclared id.
+ if (m_pdtroot->GetTypeFlags() & TYPEFLAG_FAPPOBJECT
+ || m_pdtroot->GetTypeFlags() & TYPEFLAG_FPREDECLID) {
+ IfErrRet(m_tdata.AllocVardefnPredeclared());
+ }
+ if (tkind == TKIND_COCLASS) {
+ DebAssert(m_tdata.HdefnFirstDataMbrNestedType() == HDEFN_Nil, "");
+ }
+
+ // fall through... (dispatch checks below are NOPs, and LayoutDataMembers
+ // call below will also be a NOP)
+ //
+ case TKIND_DISPATCH:
+ // Produce an error if dispinterface has more than one base class
+ // (i.e. has an embedded interface pseudo-base-class *and* has
+ // other datamembers/functions.
+ //
+ if ((m_tdata.CBase() > 1) && (m_tdata.CMeth() > 0 ||
+ m_tdata.CDataMember() > 0)) {
+ return TIPERR_BadModuleKind;
+ }
+ // fall through...
+
+ case TKIND_INTERFACE:
+ // If this is a class then layout its bases and virtual function table.
+ IfErrRet(LayoutBases(tkind, &uOffset, &uAlignment));
+
+ // fall into default processing
+
+#if ID_DEBUG
+ goto DefaultProcessing;
+#endif //ID_DEBUG
+
+ default:
+
+#if ID_DEBUG
+ DebHalt("invalid tkind");
+ case TKIND_RECORD:
+ case TKIND_MODULE:
+ case TKIND_UNION:
+DefaultProcessing:
+#endif //ID_DEBUG
+
+ oCur = uOffset;
+ IfErrRet(LayoutDataMembers(tkind,
+ &uOffset,
+ &uAlignment,
+ m_tdata.HdefnFirstDataMbrNestedType()));
+
+ // Ensure zero-length classes are at least CB_MIN_INSTANCE bytes long.
+ // (can't encounter 'void' here, so the check for 0 isn't a problem)
+ if (uOffset == 0)
+ uOffset = CB_MIN_INSTANCE;
+ if (uAlignment == 0)
+ uAlignment = CB_MIN_ALIGNMENT;
+ break;
+ }; // switch
+
+
+ // Update (embedded) DYN_TYPEBIND (we are friends!)
+ m_dtbind.m_cbSize = uOffset;
+ m_dtbind.m_cbAlignment = uAlignment;
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+
+
+/***
+*DYN_TYPEMEMBERS::GenerateOverrides() - generate vtables and overrides
+*Purpose:
+* This functions goes through every virtual functions of the
+* current class, determine which, if any, base class method
+* it overrides, and tells the entry manager the
+* about it to build the vtables.
+*
+*Entry:
+* None.
+*
+*Exit:
+* returns TIPERROR.
+*
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+TIPERROR DYN_TYPEMEMBERS::GenerateOverrides()
+{
+ HFUNC_DEFN hfdefn; // Current function
+ HFUNC_DEFN hfdefnNext; // next function
+ FUNC_DEFN * qfdefn; // " "
+ UINT cBase; // number of bases.
+ UINT ovftSlotNext; // offset of next vtable slot in primary table.
+ ITypeInfoA *ptinfo = NULL;
+ TYPEATTR *ptypeattr = NULL;
+ TIPERROR err = TIPERR_None;
+
+ // Initialize
+ cBase = m_tdata.CBase();
+
+ DebAssert(GetTypeKind() == TKIND_DISPATCH ||
+ GetTypeKind() == TKIND_INTERFACE,
+ "bad tkind for virtual functions");
+
+ // Find current size of position of primary virtual function table.
+ // VBA2: we only generate overrides for the FIRST base
+ //
+ ovftSlotNext = m_dtbind.m_cbPvft;
+
+ // Iterate over func defn list
+ hfdefn = m_tdata.HfdefnFirstMeth();
+ while (hfdefn != HFUNCDEFN_Nil) {
+ qfdefn = m_tdata.QfdefnOfHfdefn(hfdefn);
+ hfdefnNext = qfdefn->HdefnNext();
+
+ if (qfdefn->IsVirtual()) {
+
+ // Set func defn and entrymgr slot.
+ qfdefn->SetOvft(ovftSlotNext);
+
+ // Increment for next function.
+ ovftSlotNext += sizeof(void (*)());
+ }
+
+ hfdefn = hfdefnNext;
+ }
+
+ // Set primary vtable size.
+ m_dtbind.m_cbPvft = ovftSlotNext;
+
+ return err;
+}
+#pragma code_seg()
+
+
+
+/***
+*PROTECTED DYN_TYPEMEMBERS::Layout - Layout a class.
+*Purpose:
+* Layout, i.e. compile, a class.
+*
+*Implementation Notes:
+* Produce the information needed by DYN_TYPEBIND and ENTRYMGR
+* in order to layout an instance of this class. For more
+* detailed layout info, see: \silver\doc\ic\typecomp.doc
+* This method is also know as the TYPECOMPILER.
+*
+* VBA2: note that it is important that datamembers are laid out
+* first since the pvfts of the various event sources
+* in the base class (if any) must follow so that datamember
+* access be more efficient.
+* ---------------
+* | pvft |---------->Primary vft
+* |BASIC_CLASS |
+* | |
+* ---------------
+* | |
+* |compile-time |
+* |datamembers |
+* | |
+* ---------------
+* | pstaticblk |----------->------------
+* --------------- | statics |
+* | pvft1 | | ... |
+* --------------- ------------
+* | pvft2 | | dynamically-added
+* --------------- | datamembers (E&C)
+* | ... | ------------
+* ---------------
+* | pvftN |
+* ---------------
+*
+*
+* Note: flags class as being laidout, so that circular
+* definitions can be detected.
+* Note: does not set m_isLaidOut to TRUE; that is done by MakeLaidOut
+* only if the BindNameTable is successfully built
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+*Exceptions:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_LAYOUT)
+TIPERROR DYN_TYPEMEMBERS::Layout()
+{
+ TYPEKIND tkind;
+ TIPERROR err = TIPERR_None;
+
+ DebAssert(m_pentmgr != NULL, "null ENTRYMGR.");
+
+ // This class must be in at least CS_SEMIDECLARED.
+ // In principle, this method is only called by MakeLaidOut()
+ // which requires SEMIDECLARED as well... but... just in case...
+ //
+ DebAssert(m_pdtroot->CompState() >= CS_SEMIDECLARED,
+ "no binding table yet.");
+
+ tkind = GetTypeKind();
+
+ m_dtbind.m_cbPvft = 0;
+
+ // Get the typeinfo of our base class if we're not a coclass.
+ if (m_tdata.CBase() > 0 && tkind != TKIND_COCLASS) {
+ ITypeInfoA *ptinfoBase;
+ TYPEATTR *ptypeattrBase;
+
+ IfErrGo(m_tdata.GetTypeInfoOfHvdefn(m_tdata.HvdefnFirstBase(),
+ &ptinfoBase,
+ NULL));
+
+ DebAssert(ptinfoBase != NULL, "Base not valid");
+
+ // Get size of base's vft unless we're a COCLASS
+ err = TiperrOfHresult(ptinfoBase->GetTypeAttr(&ptypeattrBase));
+ if (err == TIPERR_None) {
+ switch(ptypeattrBase->typekind){
+ case TKIND_INTERFACE:
+ m_dtbind.m_cbPvft = ptypeattrBase->cbSizeVft;
+ break;
+ case TKIND_DISPATCH:
+ // 7 == NumMethods(IDispatch);
+ m_dtbind.m_cbPvft = (7 * sizeof(void(*)()));
+ break;
+ default:
+ DebAssert(0/*UNREACHED*/, "");
+ m_dtbind.m_cbPvft = 0;
+ break;
+ }
+ ptinfoBase->ReleaseTypeAttr(ptypeattrBase);
+ }
+
+ ptinfoBase->Release();
+
+ if (err != TIPERR_None) {
+ return err;
+ }
+ }
+
+ // (1) Layout non-virtual bases and immediate data members
+ IfErrGo(LayoutMembers());
+
+ // (2) Allocate HMEMBERS.
+ if (tkind != TKIND_DISPATCH) {
+
+
+ IfErrGo(AllocHmembers());
+ }
+
+ // (3) Generate overrides, really this just lays out virtual functions
+ if (tkind == TKIND_INTERFACE) {
+ IfErrGo(GenerateOverrides());
+ }
+ // fall through...
+
+Error:
+ return err;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::Read - Read serialized image of DYN_TYPEMEMBERS.
+*Purpose:
+* Read serialized image of DYN_TYPEMEMBERS.
+*
+*Implementation Notes:
+* Serialized format:
+* TYPEDATA instance.
+* DYN_TYPEBIND instance.
+* IsModifiable flag
+* IsLaidOut flag
+* PERSISTENCEKIND
+* Note: TYPEKIND is serialized by the containing TYPEINFO.
+*
+*Entry:
+* pstrm - STREAM to read image from (IN).
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR DYN_TYPEMEMBERS::Read(STREAM *pstrm)
+{
+ TIPERROR err;
+
+ DebAssert(pstrm != NULL, "bad param.");
+
+ // Then Deserialize DYN_TYPEMEMBERS meta-info.
+ IfErrRet(pstrm->ReadUShort(&m_uFlags));
+
+ // Deserialize TYPE_DATA member.
+ IfErrRet(m_tdata.Read(pstrm));
+
+ // In OB check if we are decompiling then don't read the typebind.
+ IfErrRet(m_dtbind.Read(pstrm));
+
+ return TIPERR_None;
+}
+
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::Write - Write image of DYN_TYPEMEMBERS.
+*Purpose:
+* Write image of DYN_TYPEMEMBERS.
+*
+*Implementation Notes:
+* Serialized format:
+* TYPEDATA instance.
+* DYN_TYPEBIND instance.
+* TYPEDESCKIND of enum impl (relevant for enumerations only).
+* IsModifiable flag
+* IsLaidOut flag
+* PERSISTENCEKIND
+* Note: the TYPEKIND is not serialized since the containing
+* TYPEINFO will do that.
+*
+*Entry:
+* pstrm - STREAM to read image to (IN).
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR DYN_TYPEMEMBERS::Write(STREAM *pstrm)
+{
+ TIPERROR err;
+
+ DebAssert(pstrm != NULL, "bad param.");
+
+ // Then serialize DYN_TYPEMEMBERS meta-info.
+ IfErrRet(pstrm->WriteUShort(m_uFlags));
+
+ // Serialize TYPE_DATA member.
+ IfErrRet(m_tdata.Write(pstrm));
+
+ // Serialize DYN_TYPEBIND member.
+ IfErrRet(m_dtbind.Write(pstrm));
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+
+
+
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::BuildBindNameTable - Build binding table.
+*Purpose:
+* Build binding table.
+*
+*Implementation Notes:
+* If table not already built then:
+* TYPESRC::ConstructMemberList()
+* defer to DYN_TYPEBIND.
+* Note that the latter defers in turn to BINDNAME_TABLE
+* which doesn't require class to be fully laidout -- only that
+* its member lists be constructed already.
+*
+*Entry:
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR DYN_TYPEMEMBERS::BuildBindNameTable()
+{
+
+ ITypeLibA *ptlib = NULL;
+ UINT ityp;
+ TIPERROR err;
+
+ // We only build the table if need be.
+ if (!m_dtbind.Pdbindnametbl()->IsValid()) {
+
+ // Assert that the cached pstlib is still valid.
+ // e.g. the typeinfo didn't move on us...
+ //
+ DebAssert(m_pgtlibole == m_pdtroot->Pgdtinfo()->PgtlibOleContaining(),
+ "whoops! where are we now?");
+
+ // Ensure that the NAME_CACHE array is loaded.
+ IfErrGo(m_pgtlibole->LoadNameCache());
+
+ // In any event (i.e. for both basic and non-basic classes)
+ // build the name table.
+ IfErrGo(m_dtbind.BuildBindNameTable());
+
+ // Now rebuild the module's cache...as long as we're not laying out the
+ // dispinterface portion of a dual interface, which 'inherits' the
+ // module cache of the interface portion.
+ //
+ if (m_pdtroot->Pgdtinfo()->GetTypeKind() != TKIND_DISPATCH
+ || m_pdtroot->Pgdtinfo()->PgdtinfoPartner() == NULL) {
+ // Get type's index.
+ ityp = m_pdtroot->Pgdtinfo()->GetIndex();
+
+ IfErrGo(BuildNameCache(ityp));
+ }
+
+ } // if
+ return TIPERR_None;
+
+Error:
+
+ return err;
+}
+
+/***
+*PRIVATE DYN_TYPEMEMBERS::UpdateBinderOptimization
+*Purpose:
+* Update the information in the name manager and/or
+* the name cache for the given name. These are both
+* used to optimize the binding process.
+*
+*Entry:
+* hgnam the hgnam we are to add
+* ityp the index of the current ITypeInfo
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+TIPERROR DYN_TYPEMEMBERS::UpdateBinderOptimization(HLNAM hlnam,
+ UINT ityp,
+ BOOL fType)
+{
+ HGNAM hgnam;
+ TIPERROR err = TIPERR_None;
+
+ BOOL fGlobal;
+ UINT itypNammgr;
+
+ // Add the name to the name cache
+ IfErrRet(m_pnammgr->HgnamOfHlnam(hlnam, &hgnam));
+ IfErrRet(m_pgtlibole->AddNameToCache(ityp, hgnam));
+
+ // Mark it as being a non-parameter
+ m_pnammgr->SetNonParam(hlnam, TRUE);
+
+
+ // Determine whether we're globally accessable
+ fGlobal = IsUnqualifiable(m_pdtroot->Pgdtinfo());
+ itypNammgr = m_pnammgr->ItypOfHlnam(hlnam);
+
+ // (1) Check to see if the ityp of the name is valid. If not,
+ // add this one, don't add it to the name cache and return.
+ //
+ if (!m_pnammgr->IsValidItyp(hlnam)) {
+ m_pnammgr->SetItypOfHlnam(hlnam, ityp);
+
+ m_pnammgr->SetMultiple(hlnam, FALSE);
+ m_pnammgr->SetGlobal(hlnam, fGlobal);
+
+ return TIPERR_None;
+ }
+
+ // (2) If the ityp in the nammgr is the same as this one, return.
+ //
+ if (itypNammgr == ityp) {
+ return TIPERR_None;
+ }
+
+ // (3) We know at this point that the ityp is valid and that it is
+ // not the same as the current one.
+ //
+ if (!m_pnammgr->IsMultiple(hlnam)) {
+ m_pnammgr->SetMultiple(hlnam, TRUE);
+ }
+ // fall through...
+
+ // (4) If the ityp in the name manager is GLOBAL, only replace
+ // it with this one if we are also global and our numeric
+ // value is less. Return in any case.
+ // Note: that we must in the multiple case here.
+ //
+ DebAssert(m_pnammgr->IsMultiple(hlnam), "should be multiple.");
+
+ if (m_pnammgr->IsGlobal(hlnam)) {
+ if (fGlobal) {
+ // We have multiple globals, set the ambiguous flag
+ m_pnammgr->SetAmbiguous(hlnam, TRUE);
+
+ if (ityp < itypNammgr) {
+ m_pnammgr->SetItypOfHlnam(hlnam, ityp);
+ }
+ }
+
+ return TIPERR_None;
+ }
+
+ // (5) If the current ityp is global, always place it into
+ // the name manager since the one in there isn't. Return.
+ //
+ // (6) Place the current ityp into the name manager if it is
+ // numerically less than the one currently there.
+ //
+ if (fGlobal || ityp < itypNammgr) {
+ m_pnammgr->SetItypOfHlnam(hlnam, ityp);
+ }
+
+ // If we are global, then set the global flag in the
+ // name manager.
+ //
+ if (fGlobal) {
+ m_pnammgr->SetGlobal(hlnam, TRUE);
+ }
+
+ return TIPERR_None;
+}
+
+/***
+*PRIVATE DYN_TYPEMEMBERS::UpdateNameCacheOfHdefnList
+*Purpose:
+* Traverse a list of member defns.
+* Called to traverse both data members and functions.
+*
+*Implementation Notes:
+* Incrementally adds each member to name cache -- i.e.
+* by deferring to project.
+* NOTE: only PUBLIC names are entered into the cache since
+* (1) the cache is only used at proj-level
+* (2) proj-level binding only has access to public members.
+* The implication of this is that the module-level cache cannot
+* be used for module-level binding -- this is ok, since:
+* (1) it isn't -- module-level binder uses the module's
+* binding table directly.
+* (2) it would be a pessimization to use the module's cache
+* at module-level bindtime since it would imply asking
+* the project for the cache (recall it is owned by the
+* containing project) which would potentially unnecessarily
+* load it -- unnecessary e.g. in the case in which the
+* module has no proj-level references or implicits).
+*
+*Entry:
+* hdefn listhead
+* infokind list kind: one of (var, func, base)
+* ityp index of this typeinfo.
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+TIPERROR DYN_TYPEMEMBERS::UpdateNameCacheOfHdefnList(HDEFN hdefn,
+ INFOKIND infokind,
+ UINT ityp)
+{
+ HDEFN hdefnNext;
+ DEFN *qdefn;
+ HLNAM hlnam;
+
+ TIPERROR err;
+
+ DebAssert((infokind == INFOKIND_Var) || (infokind == INFOKIND_Func),
+ "whoops! bad DEFN.");
+
+ DebAssert(m_pgtlibole == m_pdtroot->Pgdtinfo()->PgtlibOleContaining(),
+ "whoops! where are we now?");
+
+ while (hdefn != HDEFN_Nil) {
+ qdefn = m_tdata.QdefnOfHdefn(hdefn);
+
+ // cache handle of next in list so we don't have to
+ // redereference handle later.
+ //
+ hdefnNext = qdefn->HdefnNext();
+
+ // If this is a function which has been removed with
+ // conditional compilation, don't add it to the
+ // name cache.
+ //
+
+ // If visibility is PUBLIC then add name to binder optimizations.
+ if (qdefn->Access() == ACCESS_Public) {
+ hlnam = qdefn->Hlnam();
+
+ IfErrRet(UpdateBinderOptimization(hlnam,
+ ityp,
+ qdefn->IsRecTypeDefn()));
+ }
+
+ // get next
+ hdefn = hdefnNext;
+ } // end of while
+ return TIPERR_None;
+
+}
+
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::UpdateNameCacheOfBaseClass
+*Purpose:
+* Merge the namecaches of each of the base classes in the
+* Hdefn list with one.
+* NOTE: one very useful side-effect of this is that inherited member names
+* from imported/referenced typelibs/projects are added to this
+* referencing/importing project/typelib.
+*
+*Implementation Notes:
+*
+*Entry:
+* ptinfo ItypeInfo *
+* ityp index of our TypeInfo
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+TIPERROR DYN_TYPEMEMBERS::UpdateNameCacheOfBaseClass(ITypeInfoA *ptinfo,
+ UINT ityp)
+{
+ ITypeInfoA *ptinfoNext = NULL;
+ BSTRA bstrName = NULL;
+ HREFTYPE hreftype;
+ TYPEATTR *ptypeattr;
+ WORD cFuncs, cVars;
+ FUNCDESC *pfuncdesc = NULL;
+ VARDESCA *pvardesc = NULL;
+ HLNAM hlnamMbr;
+ BOOL fChange;
+ UINT cName, iImplType;
+ TIPERROR err = TIPERR_None;
+
+ // CONSIDER: If the typeinfo we have is in the same typelib that we're
+ // currently building the name cache for, simply grab the other
+ // name cache and OR it directly into this one's.
+ //
+ m_nestDepth++; // count nesting depth
+
+ // (3) Get the TYPEATTR for this ptinfo
+ //
+ IfErrRet(TiperrOfHresult(ptinfo->GetTypeAttr(&ptypeattr)));
+
+ // (4) Iterate over the functions, adding them to the
+ // binder optimizations
+ //
+ for (cFuncs = 0; cFuncs < ptypeattr->cFuncs; cFuncs++) {
+
+ // Get the funcdesc
+ IfErrGo(TiperrOfHresult(ptinfo->GetFuncDesc(cFuncs, &pfuncdesc)));
+
+ // Get the funcdesc's name
+ IfErrGoTo(TiperrOfHresult(ptinfo->GetDocumentation(
+ (HMEMBER)(pfuncdesc->memid),
+ (BSTR *)&bstrName,
+ NULL,
+ NULL,
+ NULL)),
+ Error2);
+#if OE_WIN32
+ IfErrGoTo(TiperrOfHresult(ConvertBstrToAInPlace(&bstrName)), Error2);
+#endif // OE_WIN32
+
+ // Convert the name to an Hlnam
+ IfErrGoTo(m_pnammgr->HlnamOfStr(bstrName, &hlnamMbr, FALSE, &fChange),
+ Error3);
+
+ // Add
+ IfErrGoTo(UpdateBinderOptimization(hlnamMbr, ityp, FALSE), Error3);
+
+ // Free resources
+ FreeBstrA(bstrName);
+ bstrName = NULL;
+ ptinfo->ReleaseFuncDesc(pfuncdesc);
+ pfuncdesc = NULL;
+ } // for
+
+ // (5) Iterate over the variables, adding them to the name cache
+ for (cVars = 0; cVars < ptypeattr->cVars; cVars++) {
+ // Get the vardesc
+ IfErrGoTo(TiperrOfHresult(ptinfo->GetVarDesc(cVars, &pvardesc)),
+ Error3);
+
+ // Get the vardesc's name
+ IfErrGoTo(TiperrOfHresult(ptinfo->GetNames((HMEMBER)(pvardesc->memid),
+ (BSTR *)&bstrName,
+ 1,
+ &cName)),
+ Error4);
+#if FV_UNICODE_OLE
+ IfErrGoTo(TiperrOfHresult(ConvertBstrToAInPlace(&bstrName)), Error4);
+#endif //FV_UNICODE_OLE
+
+ DebAssert(cName, "ITypeInfo member does not have a name");
+
+ // Convert the name to an Hlnam
+ IfErrGoTo(m_pnammgr->HlnamOfStr(bstrName, &hlnamMbr, FALSE, &fChange),
+ Error4);
+
+ // Add
+ IfErrGoTo(UpdateBinderOptimization(hlnamMbr, ityp, FALSE), Error4);
+
+ // Free resources
+ FreeBstrA(bstrName);
+ bstrName = NULL;
+ ptinfo->ReleaseVarDesc(pvardesc);
+ pvardesc = NULL;
+ } // for
+
+ // (6) Get this ptinfo's base class, if it exists
+ for (iImplType = 0; iImplType < ptypeattr->cImplTypes; iImplType++) {
+ IfErrGoTo(TiperrOfHresult(
+ ptinfo->GetRefTypeOfImplType(iImplType, &hreftype)),
+ Error4);
+ IfErrGoTo(TiperrOfHresult(
+ ptinfo->GetRefTypeInfo(hreftype, &ptinfoNext)),
+ Error4);
+
+ // Make recursive call...
+ IfErrGoTo(UpdateNameCacheOfBaseClass(ptinfoNext, ityp),
+ Error5);
+ RELEASE(ptinfoNext);
+ } // for each impltype
+ // fall through...
+
+Error5:
+ RELEASE(ptinfoNext);
+ // fall through...
+
+Error4:
+ if (pvardesc != NULL)
+ ptinfo->ReleaseVarDesc(pvardesc);
+ // Fall through
+
+Error3:
+ FreeBstrA(bstrName);
+ // Fall through
+
+Error2:
+ if (pfuncdesc != NULL)
+ ptinfo->ReleaseFuncDesc(pfuncdesc);
+ // Fall through
+
+Error:
+ ptinfo->ReleaseTypeAttr(ptypeattr);
+ return err;
+}
+
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::BuildNameCache
+*Purpose:
+* Builds name cache for module.
+*
+*Implementation Notes:
+* Iterates over the three members defn lists of the class.
+*
+*Entry:
+* ityp type index
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR DYN_TYPEMEMBERS::BuildNameCache(UINT ityp)
+{
+ HFUNC_DEFN hfdefnFirstFunc;
+ HVAR_DEFN hvdefnFirstDataMember;
+ HVAR_DEFN hvdefnBaseCur;
+ HIMPTYPE himptype;
+ BSTRA bstrName;
+ HLNAM hlnam;
+ BOOL isFunkyDispinterface, isCoClass, isDefaultBase;
+#if FV_UNICODE_OLE
+ HRESULT hresult;
+#endif // FV_UNICODE_OLE
+ ITypeInfoA *ptinfo;
+ TIPERROR err;
+
+ DebAssert(m_pgtlibole == m_pdtroot->Pgdtinfo()->PgtlibOleContaining(),
+ "whoops! where are we now?");
+
+ // (1) Invalidate module's cache -- doesn't invalidate proj-cache.
+ //
+ m_pgtlibole->InvalidateNameCache(ityp);
+
+ m_nestDepth = 0;
+
+ // (2) Now iterate over member lists.
+ // - data members, functions
+ //
+ hvdefnFirstDataMember = m_tdata.HdefnFirstDataMbrNestedType();
+ IfErrGo(UpdateNameCacheOfHdefnList(hvdefnFirstDataMember,
+ INFOKIND_Var,
+ ityp));
+
+
+ hfdefnFirstFunc = m_tdata.HfdefnFirstMeth();
+ IfErrGo(UpdateNameCacheOfHdefnList(hfdefnFirstFunc,
+ INFOKIND_Func,
+ ityp));
+
+ // (3) Add the globals of the base classes to this typeinfo's
+ // name cache
+ // Note that V1 only supports single-inheritance binding
+ // so we only look at the first base.
+ // OLE EXCEPTIONS:
+ // (1) funky dispinterfaces:
+ // The members of the 2nd base class
+ // are considered to be immediate members of the derived class.
+ // (2) coclasses:
+ // Only the members of the DEFAULT interface/dispinterface base are
+ // visible from the coclass.
+ //
+ IfErrGo(IsFunkyDispinterface(m_pdtroot->Pgdtinfo(),
+ &isFunkyDispinterface));
+ isCoClass = (GetTypeKind() == TKIND_COCLASS);
+ hvdefnBaseCur = m_tdata.HvdefnFirstBase();
+ while (hvdefnBaseCur != HVARDEFN_Nil) {
+ himptype = m_tdata.QtdefnOfHvdefn(hvdefnBaseCur)->Himptype();
+ // If we have a coclass, then check if this base is the DEFAULT.
+ isDefaultBase =
+ isCoClass &&
+ (m_tdata.QvdefnOfHvdefn(hvdefnBaseCur)->GetImplTypeFlags() ==
+ IMPLTYPEFLAG_FDEFAULT);
+ if (!isCoClass || isDefaultBase) {
+ IfErrGo(m_pimpmgr->GetTypeInfo(himptype, DEP_None, &ptinfo));
+ IfErrGoTo(UpdateNameCacheOfBaseClass(ptinfo, ityp), Error2);
+ ptinfo->Release();
+ // We only bother getting subsequent bases if we have a dispinterface,
+ // or we're a coclass and we haven't found the default yet,
+ // otherwise we short-circuit the iteration.
+ //
+ } // if isDefaultBase
+ if (isFunkyDispinterface || (isCoClass && !isDefaultBase)) {
+ hvdefnBaseCur = m_tdata.QvdefnOfHvdefn(hvdefnBaseCur)->HdefnNext();
+ }
+ else {
+ hvdefnBaseCur = HVARDEFN_Nil;
+ }
+ } // while
+
+ // (4) Mark the name of the typeinfo itself as a non-parameter
+ //
+ // - Marking this name as a nonparameter ensures that it can
+ // be found using IsName. Only do this for OLE because
+ // it is done automaticly when the OB projects are brought
+ // to semi-declared state.
+ //
+ IfErrRet(TiperrOfHresult(m_pdtroot->Pgdtinfo()->GetDocumentation(-1,
+ (BSTR *)&bstrName,
+ NULL,
+ NULL,
+ NULL)));
+#if FV_UNICODE_OLE
+ if ((hresult = ConvertBstrToAInPlace(&bstrName)) != TIPERR_None) {
+ FreeBstrA(bstrName);
+ return TiperrOfHresult(hresult);
+ }
+#endif //FV_UNICODE_OLE
+
+ hlnam = m_pnammgr->HlnamOfStrIfExist(bstrName);
+ DebAssert(hlnam != HLNAM_Nil, "The name of the TypeLib isn't in the nammgr!");
+
+ m_pnammgr->SetNonParam(hlnam, TRUE);
+
+ FreeBstrA(bstrName);
+
+ // (5) Make cache valid.
+ //
+ // - the project-level name cache is rebuilt before
+ // before it is used if all of the module-level
+ // name caches are valid.
+ //
+ m_pgtlibole->SetValidNameCache(ityp);
+
+ return TIPERR_None;
+
+Error2:
+ ptinfo->Release();
+ // fall through...
+
+Error:
+ m_pgtlibole->InvalidateNameCache(ityp);
+ return err;
+}
+
+
+
+
+/***
+*DYN_TYPEMEMBERS::GetSize
+*Purpose:
+* returns the total size of the DYN_TYPEMEMBERS and its subcomponent
+*Entry:
+*
+*Exit:
+* returns size
+***********************************************************************/
+UINT DYN_TYPEMEMBERS::GetSize()
+{
+ return (UINT)sizeof(DYN_TYPEMEMBERS) + (UINT)m_tdata.GetSize();
+}
+
+
+#pragma code_seg(CS_LAYOUT)
+/***
+*PRIVATE DYN_TYPEMEMBERS::AdjustForAlignment
+*Purpose:
+* Adjust offset of embedded data member given alignment.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* Returns adjusted offset.
+*
+***********************************************************************/
+
+UINT DYN_TYPEMEMBERS::AdjustForAlignment(UINT oVarCur,
+ UINT cbAlignment,
+ BOOL isStackFrame)
+{
+ UINT dbRemainder;
+
+ DebAssert(cbAlignment != 0, "bad alignment attribute.");
+
+ // We update oVarCur by the difference between the next available
+ // byte and the offset within the struct that this type
+ // wants to be allocated on for its alignment.
+ //
+ dbRemainder = oVarCur % cbAlignment;
+ if (dbRemainder) {
+ if (isStackFrame) {
+ return oVarCur - dbRemainder; // for all platforms (1/5/94 davebra)
+ }
+ else {
+ return oVarCur + (cbAlignment - dbRemainder);
+ }
+ }
+ else {
+ return oVarCur;
+ }
+}
+#pragma code_seg()
+
+
+/***
+*PRIVATE DYN_TYPEMEMBERS::AlignMember
+*Purpose:
+* Align menber
+*
+*Implementation Notes:
+*
+*Entry:
+* puOffset Points to where this member is alloced (IN/OUT).
+* cbAlignment
+* cbSizeType
+* isStackFrame
+*
+*Exit:
+* Returns offset of next available byte.
+* 0 means error -- we overflowed
+***********************************************************************/
+
+#pragma code_seg(CS_LAYOUT)
+UINT DYN_TYPEMEMBERS::AlignMember(USHORT *puOffset,
+ UINT cbAlignment,
+ UINT cbSizeType,
+ BOOL isStackFrame)
+{
+ UINT oNext;
+ ULONG lTemp;
+
+ // Now align member:
+ // If stackframe then uOffset currently addresses
+ // last "unavailable" byte -- i.e. we must alloc
+ // this var immediately "above" it, i.e. at a lower addr.
+ // So we update uOffset by cbSizeType now.
+ //
+ if (isStackFrame) {
+ lTemp = (ULONG)*puOffset - (ULONG)cbSizeType;
+
+#if OE_RISC
+
+ // On OE_RISC platforms, cbOB_Offset is 0 (i.e., no space between
+ // the frame pointer and the locals). Thus, the value of *puOffset
+ // will be 0 on the first allocation. Several assumptions:
+ //
+ // (1) A 0 *puOffset value really means 0 and not 64K (i.e., wrap).
+ // This is true because on a 64K value, this function will return an
+ // oNext value of 0 (error) and, thus, we won't be called again.
+ //
+ // (2) The value of cbSizeType can't cause an overflow when the
+ // *puOffset value is 0 (i.e., cbSizeType <= 0xFFFF).
+
+ if (*puOffset != 0)
+#endif
+ if (HIWORD(lTemp) != 0)
+ return 0; // overflow -- return 0 to signal error
+ *puOffset = LOWORD(lTemp);
+ }
+
+ oNext = AdjustForAlignment(*puOffset, cbAlignment, isStackFrame);
+
+ // Check for overflow of AdjustForAlignment. Fortunately,
+ // we know that if isStackFrame is false, the returned value will be
+ // greater than or equal to *puOffset. If not, we've overflowed.
+ //
+ if (!isStackFrame) {
+ if (oNext < *puOffset) {
+ return 0; // overflow
+ }
+ }
+ else {
+ // isStackFrame
+ if (oNext > *puOffset) {
+ return 0; // underflow
+ }
+ }
+
+
+ *puOffset = oNext;
+
+ if (!isStackFrame) {
+ // compute return value, checking for overflow
+ lTemp = (ULONG)oNext+(ULONG)cbSizeType;
+ DebAssert(lTemp != 0, ""); // we're using 0 to signal an error
+ // condition -- Our callers should
+ // guarantee we can't get 0 here
+
+ if (lTemp > CBMAX_FARPTR_HEAPREQ)
+ oNext = 0; // overflow -- return 0 to signal an error
+ else
+ oNext = LOWORD(lTemp);
+ }
+ return oNext;
+}
+#pragma code_seg()
+
+
+extern char NEARDATA g_rgcbAlignment[TDESCKIND_MAX];
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::AlignmentTdesckind
+*Purpose:
+* Determine the alignment of a tdesckind.
+*
+*Implementation Notes:
+* Uses natural alignment - gets the size of the tdesckind, returns
+* that OR the value set by ICreateTypeInfo::SetAlignment, which ever
+* is less.
+*
+*Entry:
+* tdesckind
+*
+*Exit:
+* Returns alignment value for this type.
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+USHORT DYN_TYPEMEMBERS::AlignmentTdesckind(TYPEDESCKIND tdesckind)
+{
+ USHORT cbAlignment;
+
+ if (g_rgcbAlignment[tdesckind] == -1)
+ return 0xFFFF;
+
+ cbAlignment = (USHORT)g_rgcbAlignment[tdesckind];
+
+ // If we're dealing with an INT or a UINT and this is WIN16,
+ // the alignment is only 2.
+ //
+ if ((tdesckind == TDESCKIND_Int || tdesckind == TDESCKIND_Uint)
+ && m_pgtlibole->GetSyskind() == SYS_WIN16) {
+
+ DebAssert(cbAlignment == 4, "Confused?");
+ cbAlignment = 2;
+ }
+
+ return min(cbAlignment,
+ Pdtroot()->GetAlignment());
+}
+#pragma code_seg()
+
+
+#if ID_DEBUG
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::DebCheckDefnList
+*Purpose:
+* Check a defn list: one of (var, base, func)
+*
+*Implementation Notes:
+* Note: only PUBLIC names are in cache.
+* CONSIDER: the infokind param is anachronistic, each
+* defn carries its defnkind along with it. We should remove it.
+*
+*Entry:
+* uLevel
+* hdefn listhead
+* infokind list kind: one of (var, func, base)
+* inamcache index in cache array == type index + 1.
+*
+*Exit:
+* None.
+*
+*Exceptions:
+* None.
+*
+***********************************************************************/
+
+VOID DYN_TYPEMEMBERS::DebCheckDefnList(UINT uLevel,
+ HDEFN hdefn,
+ INFOKIND infokind,
+ UINT inamcache)
+{
+ HDEFN hdefnNext;
+ DEFN *qdefn;
+ HGNAM hgnamMbr;
+ BOOL isPublic;
+ TIPERROR err;
+
+ DebAssert((infokind == INFOKIND_Var) || (infokind == INFOKIND_Func),
+ "whoops! bad DEFN.");
+ DebAssert(m_pgtlibole == m_pdtroot->Pgdtinfo()->PgtlibOleContaining(),
+ "whoops! where are we now?");
+
+ while (hdefn != HDEFN_Nil) {
+ qdefn = m_tdata.QdefnOfHdefn(hdefn);
+
+ // cache handle of next in list so we don't have to
+ // redereference handle later.
+ //
+ hdefnNext = qdefn->HdefnNext();
+
+ err = m_pnammgr->HgnamOfHlnam(qdefn->Hlnam(), &hgnamMbr);
+ DebAssert(err == TIPERR_None, "bad name.");
+
+ if (m_pgtlibole->IsValidNameCache(inamcache)) {
+ // Test if variable/type/function is public
+ isPublic = FALSE;
+ switch (qdefn->Defnkind()) {
+ case DK_VarDefn:
+ case DK_MbrVarDefn:
+ isPublic = ((VAR_DEFN *)qdefn)->IsPublic();
+ break;
+ case DK_RecTypeDefn:
+ isPublic = ((RECTYPE_DEFN *)qdefn)->Access() == ACCESS_Public;
+ break;
+ case DK_FuncDefn:
+ case DK_VirtualFuncDefn:
+ isPublic = ((FUNC_DEFN *)qdefn)->IsPublic();
+ break;
+ default:
+ DebHalt("DebCheckState: bad defnkind.");
+ } // switch
+ if (isPublic) {
+ // Check it's in the cache.
+ DebAssert(m_pgtlibole->IsNameInCache(inamcache, hgnamMbr),
+ "whoops! name missing from cache.");
+ }
+ }
+
+ // get next
+ hdefn = hdefnNext;
+ } // end of while
+}
+
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::DebCheckNameCache
+*Purpose:
+* Check type's name cache.
+*
+*Implementation Notes:
+* Looks a lot like BuildNameCache/UpdateNameCache
+*
+*Entry:
+* uLevel
+* inamcache index in cache array == type index + 1.
+*
+*Exit:
+* None.
+*
+*Exceptions:
+* None.
+*
+***********************************************************************/
+
+VOID DYN_TYPEMEMBERS::DebCheckNameCache(UINT uLevel, UINT inamcache)
+{
+ HFUNC_DEFN hfdefnFirstFunc;
+ HVAR_DEFN hvdefnFirstDataMember;
+
+ // Nothing to do if the cache is not yet valid...
+ if (!m_pgtlibole->IsValidNameCache(inamcache)) {
+ return;
+ }
+
+ // (1) Now iterate over member lists.
+ // - data members, functions
+ //
+ hvdefnFirstDataMember = m_tdata.HdefnFirstDataMbrNestedType();
+ DebCheckDefnList(uLevel,
+ hvdefnFirstDataMember,
+ INFOKIND_Var,
+ inamcache);
+
+ hfdefnFirstFunc = m_tdata.HfdefnFirstMeth();
+ DebCheckDefnList(uLevel,
+ hfdefnFirstFunc,
+ INFOKIND_Func,
+ inamcache);
+}
+
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::DebCheckState - TYPEMEMBERS state
+*Purpose:
+* Check TYPEMEMBERS state
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+*Exceptions:
+* None.
+*
+***********************************************************************/
+
+VOID DYN_TYPEMEMBERS::DebCheckState(UINT uLevel)
+{
+ UINT ityp;
+
+ m_tdata.DebCheckState(uLevel);
+ m_dtbind.DebCheckState(uLevel);
+
+ // Get type's index.
+ ityp = m_pdtroot->Pgdtinfo()->GetIndex();
+
+ // check name cache state
+ DebCheckNameCache(uLevel, ityp);
+}
+
+
+
+
+#endif // ID_DEBUG
diff --git a/private/oleauto/src/typelib/dtmbrs.hxx b/private/oleauto/src/typelib/dtmbrs.hxx
new file mode 100644
index 000000000..04205da1a
--- /dev/null
+++ b/private/oleauto/src/typelib/dtmbrs.hxx
@@ -0,0 +1,361 @@
+/***
+*dtmbrs.hxx - DYN_TYPE_MEMBERS header file
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+*
+*Revision History:
+*
+* 05-Mar-91 ilanc: created
+* 19-Sep-91 ilanc: Stubbed GetMemberInfoOfHmember()
+* HlnamOfHmember()
+* 17-Oct-91 ilanc: Implement <LIST>::SetAtPosition
+* 05-Dec-91 ilanc: Rm Get/SetDocumentation (in TYPEINFO now).
+* 10-Jul-92 w-peterh: added layout of nested types
+* 18-Jan-93 w-peterh: use TIPERRORs internally
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#ifndef DTMBRS_HXX_INCLUDED
+#define DTMBRS_HXX_INCLUDED
+
+#include "silver.hxx"
+#include <string.h>
+#include "defn.hxx" // and cltypes.hxx
+#include "dtbind.hxx"
+
+
+class COMPILETIME_SEG;
+
+class NAMMGR;
+class DYN_TYPEROOT; // forward ref. Can't include
+ // "dtinfo.hxx" (which has definition)
+ // since it includes this file!
+class ENTRYMGR;
+class GEN_DTINFO;
+class GenericTypeLibOLE;
+# define STAT_TYPELIB GEN_PROJECT
+class GEN_PROJECT;
+class EVENT_SOURCE_TABLE;
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szDTMBRS_HXX)
+#define SZ_FILE_NAME g_szDTMBRS_HXX
+#endif
+
+// CONSIDER: should be somewhere else
+class IObEvSourceInfo;
+TIPERROR TipCreateEvSourceInfo(ITypeInfoA *, IObEvSourceInfo **);
+
+/***
+*class DYN_TYPEMEMBERS - 'dtmbrs': Type members implementation.
+*Purpose:
+* The class implements type members.
+*
+***********************************************************************/
+
+class DYN_TYPEMEMBERS
+{
+ friend class COMPILETIME_SEG; // ::~COMPILETIME_SEG();
+ // friend TIPERROR DYN_TYPEROOT::GetDtmbrs(DYN_TYPEMEMBERS **pdtmbrs);
+ friend DYN_TYPEROOT;
+ // friend TIPERROR GEN_DTINFO::GetTypeMembers(TYPEMEMBERS **); // so it can invalidate.
+ friend GEN_DTINFO;
+
+ // friend VOID TYPE_DATA::SwapbmData(BOOL fSwapFirst);
+ friend TYPE_DATA;
+
+public:
+ DYN_TYPEMEMBERS();
+ nonvirt TIPERROR Init(SHEAP_MGR *psheapmgr, DYN_TYPEROOT *pdtroot);
+
+ // overridden methods
+ virtual VOID Release();
+ virtual VOID AddRef();
+ virtual TYPEKIND GetTypeKind();
+ virtual TIPERROR MakeLaidOut();
+ virtual BOOL IsLaidOut();
+ virtual UINT GetSize();
+
+ // Debug/test methods
+#if ID_DEBUG
+ nonvirt VOID DebShowState(UINT uLevel);
+ nonvirt VOID DebCheckState(UINT uLevel);
+ nonvirt UINT DebShowSize();
+ nonvirt VOID DebCheckNameCache(UINT uLevel,
+ UINT inamcache);
+ nonvirt VOID DebCheckDefnList(UINT uLevel,
+ HDEFN hdefn,
+ INFOKIND infokind,
+ UINT inamcache);
+#else
+ nonvirt VOID DebShowState(UINT uLevel) {}
+ nonvirt VOID DebCheckState(UINT uLevel) {}
+ nonvirt VOID DebShowSize() {}
+ nonvirt VOID DebCheckNameCache(UINT uLevel,
+ UINT inamcache) {}
+ nonvirt VOID DebCheckDefnList(UINT uLevel,
+ HDEFN hdefn,
+ INFOKIND infokind,
+ UINT inamcache) {}
+#endif
+
+ // introduced methods
+ nonvirt VOID AddInternalRef();
+ nonvirt VOID RelInternalRef();
+ nonvirt TIPERROR Read(STREAM *pstrm);
+ nonvirt TIPERROR Write(STREAM *pstrm);
+ nonvirt TIPERROR HlnamOfHmember(HMEMBER hmember, sHLNAM *phlnam);
+
+ nonvirt TIPERROR GetTypeData(TYPE_DATA **pptdata);
+ nonvirt TYPE_DATA *Ptdata();
+ nonvirt TIPERROR GetDefnTypeBind(DEFN_TYPEBIND **ppdfntbind);
+ nonvirt DYN_TYPEROOT *Pdtroot() const;
+
+ nonvirt TIPERROR BuildBindNameTable();
+ nonvirt TIPERROR BuildNameCache(UINT inamcache);
+ nonvirt USHORT GetNestDepth();
+
+
+ UINT LayoutVar(TYPEDESCKIND tdesckind,
+ USHORT *puOffset,
+ USHORT *puOffsetNext,
+ UINT cbSizeType,
+ BOOL isStackFrame,
+ UINT uStackAlignment);
+ TIPERROR LayoutVarOfHvdefn(TYPEKIND tkind,
+ HVAR_DEFN hvdefn,
+ USHORT *puOffset,
+ UINT *puAlignment,
+ BOOL isStackFrame,
+ UINT uStackAlignment,
+ BOOL fIgnoreHvdefn = FALSE);
+
+ TIPERROR LayoutStaticVarOfHvdefn(TYPEKIND tkind,
+ HVAR_DEFN hvdefn,
+ UINT *puAlignment);
+
+
+ nonvirt USHORT GetSizeOfStaticInstance();
+ TIPERROR GetSizeAlignmentOfHtdefnNonUdt(TYPEKIND tkind,
+ BOOL isSimpleType,
+ HTYPE_DEFN htdefn,
+ UINT *pcbSizeType,
+ UINT *pcbAlignment);
+ TIPERROR GetSizeAlignmentOfHtdefnUdt(HTYPE_DEFN htdefn,
+ UINT *pcbSizeType,
+ UINT *pcbAlignment);
+ TIPERROR GetSizeAlignmentOfHtdefn(TYPEKIND tkind,
+ BOOL isEmbeddedTypeDefn,
+ HTYPE_DEFN htdefn,
+ UINT *pcbSizeType,
+ UINT *pcbAlignment);
+ TIPERROR GetSizeAlignmentOfArray(TYPEKIND tkind,
+ HTYPE_DEFN htdefn,
+ UINT *pcbSizeType,
+ UINT *pcbAlignment);
+
+ USHORT AlignmentTdesckind(TYPEDESCKIND tdesckind);
+
+ // Public data members
+ static LPSTR szProtocolName;
+ static LPSTR szBaseName;
+
+ static CONSTDATA UINT oDtbind;
+
+protected:
+ nonvirt VOID Invalidate();
+ TIPERROR Layout();
+
+ TIPERROR UpdateBinderOptimization(HLNAM hlnam, UINT ityp, BOOL fType);
+ TIPERROR UpdateNameCacheOfHdefnList(HDEFN hdefn,
+ INFOKIND infokind,
+ UINT ityp);
+ TIPERROR UpdateNameCacheOfBaseClass(ITypeInfoA *ptinfo,
+ UINT ityp);
+
+ ~DYN_TYPEMEMBERS();
+
+ TIPERROR AllocHmembers();
+ TIPERROR LayoutMembers();
+ TIPERROR LayoutBases(TYPEKIND tkind, UINT *puOffset, UINT *puAlignment);
+ TIPERROR LayoutDataMembers(TYPEKIND tkind,
+ UINT *puOffset,
+ UINT *puAlignment,
+ HDEFN hdefnFirst);
+ TIPERROR GenerateOverrides();
+ static UINT AdjustForAlignment(UINT oVarCur,
+ UINT cbAlignment,
+ BOOL isStackFrame);
+
+ static UINT AlignMember(USHORT *puOffset,
+ UINT cbAlignment,
+ UINT cbSizeType,
+ BOOL isStackFrame);
+ DYN_TYPEBIND *Pdtbind() const;
+
+ TIPERROR VerifyValidUDT(HTYPE_DEFN htdefn,
+ BOOL isSimpleType,
+ BOOL *pisRecord,
+ BOOL *pisPrivateClass,
+ BOOL *phasCoclass,
+ BOOL *pisValidWithNew);
+
+ TIPERROR VerifyFunctionUdts(HFUNC_DEFN hfdefn);
+
+ // These two methods are OB-specific but we don't switch them
+ // out since their implementation is switched out.
+ //
+ TIPERROR AllocHmembersNestedType(UINT uOrdinal);
+ TIPERROR LayoutNestedType(HRECTYPE_DEFN hrtdefn, UINT ordinal);
+
+ TIPERROR LayoutEventSources();
+
+ TYPE_DATA m_tdata; // embedded TYPE_DATA
+ DYN_TYPEBIND m_dtbind; // embedded DYN_TYPEBIND
+ DYN_TYPEROOT *m_pdtroot;
+
+ NAMMGR *m_pnammgr; // cached name manager
+ ENTRYMGR *m_pentmgr; // cached ENTRYMGR
+ IMPMGR *m_pimpmgr; // cached IMPMGR
+ GenericTypeLibOLE *m_pgtlibole; // cached typelib.
+
+ ITypeInfoA *m_ptinfoCopy; // cached typeinfo we're copying to.
+
+ // following flags fit into a single 16-bit USHORT.
+ union {
+ struct {
+ USHORT m_isLaidOut:1;
+ USHORT m_nestDepth:HMEMBER_NestDepthSize;
+ USHORT m_undone2:(10 - HMEMBER_NestDepthSize);
+ USHORT undone:5;
+ };
+ USHORT m_uFlags;
+ };
+
+ // the following member is needed for laying out the static local variables
+ USHORT m_uOffsetOfNextStaticVar;
+
+ static USHORT uMagicNumber;
+ static USHORT uVersionCur;
+
+};
+
+
+// inline methods
+//
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::GetTypeDescKindEnumImpl
+*Purpose:
+* Returns the size of the instance for static variables for the module.
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+inline USHORT DYN_TYPEMEMBERS::GetSizeOfStaticInstance()
+{
+ return m_uOffsetOfNextStaticVar;
+}
+
+
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::Pdtroot
+*Purpose:
+* Retruns pointer to type root
+*
+*Implementation Notes:
+* Does not increment ref count -- since this is the method
+* that clients should use when they wish to cache
+* a TYPE_DATA pointer in cases in which the container's
+* lifetime is known to be at least as long as the TYPE_DATA.
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+inline DYN_TYPEROOT *DYN_TYPEMEMBERS::Pdtroot() const
+{
+ return m_pdtroot;
+}
+
+
+/***
+*PUBLIC DYN_TYPEMEMBERS::Ptdata
+*Purpose:
+* Retruns pointer to typedata.
+*
+*Implementation Notes:
+* Does not increment ref count -- since this is the method
+* that clients should use when they wish to cache
+* a TYPE_DATA pointer in cases in which the container's
+* lifetime is known to be at least as long as the TYPE_DATA.
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+inline TYPE_DATA *DYN_TYPEMEMBERS::Ptdata()
+{
+ return &m_tdata;
+}
+
+
+/***
+*PRIVATE DYN_TYPEMEMBERS::Pdtbind
+*Purpose:
+* Returns pointer to type bind. Private so that only
+* friends can use it.
+*
+*Implementation Notes:
+*Entry:
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+inline DYN_TYPEBIND *DYN_TYPEMEMBERS::Pdtbind() const
+{
+ return (DYN_TYPEBIND *)&m_dtbind;
+}
+
+/***
+*PRIVATE DYN_TYPEMEMBERS::GetNestDepth
+*Purpose:
+* Returns the nesting depth of base interfaces
+*
+*Implementation Notes:
+*Entry:
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+inline USHORT DYN_TYPEMEMBERS::GetNestDepth()
+{
+ return m_nestDepth;
+}
+
+
+
+
+
+#endif // ! DTMBRS_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/dyntinfo.hxx b/private/oleauto/src/typelib/dyntinfo.hxx
new file mode 100644
index 000000000..300e9e0b2
--- /dev/null
+++ b/private/oleauto/src/typelib/dyntinfo.hxx
@@ -0,0 +1,90 @@
+/***
+*dyntinfo.hxx - DYNTYPEINFO header file
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Defines the DYNTYPEINFO protocol.
+*
+*Revision History:
+*
+* 03-Oct-91 alanc: Created.
+* 25-Aug-92 rajivk: Support for ensuring all needed to be brought to
+* runnable state.
+* 18-Jan-93 w-peterh: removed IMPTYPEINFO
+*
+*****************************************************************************/
+
+#ifndef DYNTInfo_HXX_INCLUDED
+#define DYNTInfo_HXX_INCLUDED
+
+#include "tinfo.hxx"
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szDYNTINFO_HXX)
+#define SZ_FILE_NAME g_szDYNTINFO_HXX
+#endif
+
+
+struct TINODE;
+
+/***
+*class DYNTYPEINFO - 'dti': DYNAMIC TYPEINFO protocol
+*Purpose:
+* Dynamic TypeInfo protocol
+***********************************************************************/
+
+class DYNTYPEINFO : public TYPEINFO
+{
+public:
+ static const LPSTR szProtocolName;
+
+ STDMETHOD(QueryInterface) (THIS_ REFIID riid, LPVOID FAR* ppvObj);
+
+ virtual TIPERROR GetMemberName(HMEMBER hmember, BSTRA *plstrName) = 0;
+ virtual TIPERROR GetDynTypeMembers(LPLPDYNTYPEMEMBERS lplpDynTypeMembers) = 0;
+ virtual TIPERROR GetDefnTypeBind(LPLPDEFNTBIND lplpDefnTypeBind) = 0;
+ virtual TIPERROR GetTypeFixups(LPLPTYPEFIXUPS lplpTypeFixups) = 0;
+ // virtual TYPEKIND GetTypeKind() = 0;
+ virtual TIPERROR Reset() = 0;
+ // virtual TIPERROR GetDocumentation(BSTRA *plstr) = 0;
+ // virtual DWORD GetHelpContext() = 0;
+ // virtual TIPERROR GetHelpFileName(BSTRA *plstrFile) = 0;
+ // virtual TIPERROR GetIcon(DWORD *pdw) = 0;
+#if 0
+ virtual TIPERROR CreateInst(LPLPVOID lplpObj) = 0;
+#endif
+
+ // Introduced Methods.
+ virtual TIPERROR Read() = 0;
+ virtual TIPERROR Write() = 0;
+ // Introduced Methods for bringing all needed class to runnable.
+ virtual TIPERROR BeginDepIteration(TINODE **pptinode,
+ TINODE ***ppptinodeCycleMax) = 0;
+ virtual VOID EndDepIteration() = 0;
+ virtual TIPERROR GetNextDepTypeInfo(DYNTYPEINFO **ppdtiNext) = 0;
+ virtual BOOL IsReady() = 0;
+ virtual TIPERROR AllDepReady() = 0;
+ virtual TIPERROR NotReady() = 0;
+
+ virtual TIPERROR CommitChanges() = 0;
+
+
+/*****
+ These are disabled because our implementation make them confusing
+ since they change information stored in the TypeLib directory and
+ so require that the directory be saved
+ virtual TIPERROR SetDocumentation(LPSTR szDoc) = 0;
+ virtual TIPERROR SetHelpContext(ULONG ulHelpIndex) = 0;
+*****/
+
+#ifdef DYNTYPEINFO_VTABLE
+#pragma VTABLE_EXPORT
+#endif
+};
+
+
+#endif // DYNTInfo_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/ebvers.h b/private/oleauto/src/typelib/ebvers.h
new file mode 100644
index 000000000..96c58e64a
--- /dev/null
+++ b/private/oleauto/src/typelib/ebvers.h
@@ -0,0 +1,22 @@
+/***
+*ebvers.h - Version of OB to build
+*
+* Copyright (C) 1990, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file determines what version of OB to build.
+*
+*Revision History:
+*
+* 24-Aug-90 Created
+*
+*****************************************************************************/
+
+#ifndef EBVERS_HXX_INCLUDED
+#define EBVERS_HXX_INCLUDED
+
+// Change the following to 1 if you want to build VBA2.
+#define VBA2 1
+
+#endif // !EBVERS_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/entrymgr.cxx b/private/oleauto/src/typelib/entrymgr.cxx
new file mode 100644
index 000000000..960ec4d46
--- /dev/null
+++ b/private/oleauto/src/typelib/entrymgr.cxx
@@ -0,0 +1,1017 @@
+/**
+*cl\EntryMgr.cxx - Entry Manager
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* One instance of this class exists for every GEN_DTINFO.
+* The ENTRYMGR resides in the compile-time segment.
+* ENTRYMGR is a repository for the small subset of information
+* known to DYN_TYPEMEMBERS needed to build a TYPEFIXUPS.
+* Because this information is stored in the ENTRYMGR,
+* it is not necessary to load a DYN_TYPEMEMBERS instance in order to
+* load a class for execution.
+* ENTRYMGR builds tnative, tnativeAddr and VFT_MGR.
+*
+* The Type Compiler is responsible for invoking methods on the
+* ENTRYMGR to define the entry points
+* One NATIVEENTRYDATA exists for every introduced method in this class.
+*
+* When we bring the class to Addressable state we build up the VTABLE(s).
+* The Layout of the Vtable looks like this:
+*
+*
+* +-------+
+* -->| |__\ Pointer to the Primary Interface (VTable).
+* 0| | /
+* |-------|
+* 1| |__\ Pointer to the first Source Interface (VTable).
+* | | /
+* |-------|
+* 2| |
+* | |
+* |-------|
+* 3| |
+* | |
+* |-------|
+* | |
+* | : |
+* | : |
+* | : |__\ Pointer to the n'th Source Interface (Vtable).
+* | : | /
+* +-------+
+*
+*Revision History:
+*
+* 16-Apr-91 alanc: Created.
+* 10-Dec-91 ilanc: Override --> SetOverride
+* ClassAttr --> SetClassAttr
+* 03-Jun-92 w-peterh: Code Cleanup
+* 07-Jul-92 w-peterh: enabled linking to OB.DLL and to functions
+* in statically linked host via Declare stmnts
+* 21-Jul-92 w-peterh: enabled copying of record instanciation stubs
+* into tnative
+* 25-Aug-92 petergo: added vtable support.
+* 15-Nov-92 RajivK: added GetSize and DebGetSize
+* 14-Dec-92 w-peterh: Document AddressOfDllEntry
+* made OtexOfHmember() a release function
+* 08-Dec-92 RajivK: Support for InvokeKind
+* 08-Jan-93 RajivK: Support for Code Resource on Mac
+* 08-Jan-93 RajivK: Fixed some undone(s)
+* 15-Jan-93 RajivK: Support for late binding for DLL functions
+* 30-Apr-93 w-jeffc: made DEFN data members private
+* 22-May-93 w-barryb: Rename OB to VBA
+* 13-Jan-94 jeffrob: native entrypts Free interface changes (OE_RISC)
+*
+*****************************************************************************/
+
+#include "typelib.hxx"
+#include "switches.hxx"
+
+#include <stdlib.h>
+#include <stdio.h>
+#include <new.h>
+
+// Include windows.h for AllocDStoCSAlias and Dll functions
+// CONSIDER: adding moving this to another file
+
+#include "silver.hxx"
+#include "xstring.h"
+#include "entrymgr.hxx"
+
+#include "stream.hxx"
+#include "impmgr.hxx"
+#include "nammgr.hxx"
+
+#include "gdtinfo.hxx"
+
+#pragma hdrstop(RTPCHNAME)
+
+
+// These includes are here to support CODE RESOURCES on Mac.
+// These has to be after hdrstop pragma so that it does not
+// break the fast build on MAC.
+#if OE_MAC
+#include <types.h>
+#include <macos\memory.h>
+#include <string.h>
+#include <aslm.h>
+#include <osutils.h>
+#include <traps.h>
+#include "sysutils.h"
+
+
+
+#if OE_MACPPC
+#include <fragload.h>
+#endif
+
+extern "C" {
+USHORT NumToolboxTraps(void);
+BOOL TrapExists(USHORT sTrapNo);
+
+}
+
+
+
+#if 0
+#define HINSTANCE_SLMLIBLOADED ((Handle)-2)
+#define ForceLibMgrInit() (!g_LibMgrInited ? g_LibMgrInited = (InitLibraryManager(0,kCurrentZone,kNormalMemory) ==0), g_LibMgrInited : TRUE)
+static BOOL g_LibMgrInited=0;
+#endif //0 (ASLM has been cut)
+
+#endif // OE_MAC
+
+
+TIPERROR OvftOfInitTerm(ITypeInfo *ptinfo, BOOL fInit, int *povft);
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+char szOleEntryMgrCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleEntryMgrCxx
+#else
+static char szEntryMgrCxx[] = __FILE__;
+#define SZ_FILE_NAME szEntryMgrCxx
+#endif
+#endif //ID_DEBUG
+
+//this is a table used to map runtime function ordinals to the address of the function
+//on the Mac.
+#if OE_MAC
+extern "C" void *rgMacStrdcl[]; //generated by build process in strdcl.c
+#endif
+
+#define MAX_NAME 255
+
+// Define class constants
+CONSTDATA WORD ENTRYMGR::wFirstSerWord = 'E' * 256 + 'M';
+CONSTDATA WORD ENTRYMGR::cbSizeSerMem =
+ offsetof(ENTRYMGR, m_cbTNativeSize) -
+ offsetof(ENTRYMGR, m_hdllentrydefnFirst) +
+ sizeof(((ENTRYMGR*)NULL)->m_cbTNativeSize);
+
+CONSTDATA WORD ENTRYMGR::wCurFormat = 0;
+
+
+#define RSRCNAME_ENTRYPTS WIDE("EntryPts")
+#define RSRCNAME_DLL WIDE("DllEntryPts")
+#define RSRCNAME_IID_PREFIX WIDE("_IID_")
+#define RSRCNAME_IID_PREFIX_SIZE (5 * sizeof(OLECHAR))
+
+#define RSRCNAME_VFTEXE(a) 0
+#define RSRCTYPE 0
+
+
+#if !OE_MAC
+extern "C" {
+void PASCAL ClassTemplateStart(void);
+void PASCAL ClassTemplateStartPrimary(void);
+void PASCAL ClassTemplateFixupOFFSET(void);
+}
+#endif
+
+// constructor
+//
+#pragma code_seg( CS_CORE2 )
+ENTRYMGR::ENTRYMGR ()
+{
+}
+#pragma code_seg( )
+
+#pragma code_seg( CS_CORE )
+ENTRYMGR::~ENTRYMGR()
+{
+ // Release the Loaded libraries for non-OB libs
+ // The INSTMGR does it for OB.
+ //
+ ReleaseDllEntries(this);
+
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC ENTRYMGR::Init - Initialize an ENTRYMGR instance
+*Purpose:
+* Initializes the data member.
+*
+*Note:
+* *pinstmgr should be initialized before calling this function.
+*
+*
+*Entry:
+* psheapmgr - pointer to SHEAPMGR for initializing blocks
+* pdtroot - pointer to DYN_TYPEROOT for INSTMGR
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR ENTRYMGR::Init(SHEAP_MGR * psheapmgr,
+ DYN_TYPEROOT *pdtroot)
+{
+
+ DebAssert(psheapmgr != NULL, "ENTRYMGR::Init - invalid SHEAP_MGR");
+ DebAssert(pdtroot != NULL, "ENTRYMGR::Init : invalid DYN_TYPEROOT");
+
+ m_pdtroot = pdtroot;
+ m_cbTNativeSize = 0;
+ m_cbTExtEntrySize = 0;
+ m_cbVftbl = 0;
+ m_hdllentrydefnFirst = HDLLENTRYDEFN_Nil;
+ m_hvtdFirst = HCHUNK_Nil;
+
+
+
+ return m_bmEntryData.Init(psheapmgr);
+}
+#pragma code_seg( )
+
+/***
+*PUBLIC ENTRYMGR::DllEntryNameOfHchunk
+*Purpose:
+* Returns the name of the Dll entry point.
+*
+*Entry:
+* hchunk : Handle to the Dll entry name.
+*Exit:
+* szName : Client allocated buffer for the dll name.
+*
+*
+***********************************************************************/
+
+TIPERROR ENTRYMGR::DllEntryNameOfHchunk(HCHUNK hchunk, LPSTR lpstr, UINT cch)
+{
+ BYTE *qbStr;
+
+ // Get the qointer that points to Name of the Dll entry
+ qbStr = m_bmEntryData.QtrOfHandle(hchunk);
+
+ if (cch < xstrblen0((XCHAR *)qbStr))
+ return TIPERR_BufferTooSmall;
+
+ // Copy the string in the memory allocated.
+ xstrcpy(lpstr, (XCHAR *)qbStr);
+
+ return TIPERR_None;
+}
+
+/***
+*PUBLIC ENTRYMGR::Decompile(COMPSTATE compstate)
+*Purpose:
+* Brings this down to compstate
+*
+*Entry:
+* compstate - state to go to
+*
+*Exit:
+* None
+*
+*Note:
+* ENTRYMGR::Decompile() and INSTMGR::Decompile() should
+* allways be called together
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+VOID ENTRYMGR::Decompile(COMPSTATE compstate)
+{
+ return;
+}
+#pragma code_seg( )
+
+
+
+
+/***
+*PUBLIC ENTRYMGR::AllocDllentrydefn
+*
+*Purpose:
+* Allocates a DLLENTRY_DEFN for an entry point specified by a name
+*
+*Entry:
+* hlnamDllModule - dll module name
+* hasordinal - is the entry by ordinal
+* phdllentrydefn - return location
+*
+*Exit:
+* returns a handle to the entry point
+*
+***********************************************************************/
+
+TIPERROR ENTRYMGR::AllocDllentrydefn(HDLLENTRY_DEFN *phdllentrydefn,
+ HLNAM hlnamDllModule,
+ BOOL fHasOrdinal)
+{
+ TIPERROR err = TIPERR_None;
+ DLLENTRY_DEFN *qdllentrydefn;
+
+ DebAssert(phdllentrydefn != NULL,
+ "ENTRYMGR::AllocDllentrydefn invalid pointer");
+ DebAssert(hlnamDllModule != HLNAM_Nil,
+ "ENTRYMGR::AllocDllentrydefn invalid handle");
+
+
+ // allocate dllentrydefn in m_bmDllEntryDefns of INSTMGR for OB. But for
+ // typelib.dll we allocate it in entrymgr's blockmgr
+ IfErrRet(m_bmEntryData.AllocChunk(phdllentrydefn,
+ sizeof(DLLENTRY_DEFN)));
+
+ qdllentrydefn = QdllentrydefnOfHdllentrydefn(*phdllentrydefn);
+
+ // populate dllentrydefn
+ qdllentrydefn->SetHlnamDllName(hlnamDllModule);
+ qdllentrydefn->SetHasOrdinal(fHasOrdinal);
+ qdllentrydefn->SetLpDllEntryPoint(NULL); // native entry for DLLs are
+ // allocated in MakeAddressable.
+ qdllentrydefn->SetHLibrary(0); // Library not loaded yet.
+
+
+
+ // link it in list
+ qdllentrydefn->SetHdllentrydefnNext(m_hdllentrydefnFirst);
+ m_hdllentrydefnFirst = *phdllentrydefn;
+
+ return err;
+}
+
+
+/***
+*PUBLIC ENTRYMGR::ReleaseDllentrydefn
+*
+*Purpose:
+* Releases a dllentry defn that has been allocated with
+* AllocDllentrydefn()
+*
+*Entry:
+* hdllentrydefn - handle to release
+*
+*Exit:
+* VOID
+*
+***********************************************************************/
+
+VOID ENTRYMGR::ReleaseDllentrydefn(HDLLENTRY_DEFN hdllentrydefn)
+{
+ DLLENTRY_DEFN *qdllentrydefn;
+ HDLLENTRY_DEFN hdllentrydefnPrev, hdllentrydefnCurr;
+
+ DebAssert(hdllentrydefn != HDLLENTRYDEFN_Nil,
+ "ReleaseDllentrydefn - invalid handle");
+
+ // ensure the list exists
+ DebAssert(m_hdllentrydefnFirst != HDLLENTRYDEFN_Nil,
+ "ReleaseDllEntryDefn - invalid handle");
+
+
+ // Assert that the module's compilation state is less than ADDRESSABLE
+ // state
+ DebAssert(m_pdtroot->CompState() < CS_ADDRESSABLE,
+ " First decompile the module ");
+
+ // find defn in list
+ hdllentrydefnPrev = HDLLENTRYDEFN_Nil;
+ hdllentrydefnCurr = m_hdllentrydefnFirst;
+
+ // move hdllentrydefnPrev so that it points
+ // to the defn before the one that we want to release
+ while (hdllentrydefnCurr != hdllentrydefn) {
+ hdllentrydefnPrev = hdllentrydefnCurr;
+ hdllentrydefnCurr = QdllentrydefnOfHdllentrydefn(hdllentrydefnCurr)->
+ HdllentrydefnNext();
+
+ // ensure we haven't come to the end of the list
+ DebAssert(hdllentrydefnCurr!= HDLLENTRYDEFN_Nil,
+ "ENTRYMGR::ReleaseDllEntryDefn - invalid handle");
+ } /* while */
+
+ // unlink defn
+ qdllentrydefn = QdllentrydefnOfHdllentrydefn(hdllentrydefn);
+ if (hdllentrydefnPrev == HDLLENTRYDEFN_Nil) {
+ m_hdllentrydefnFirst = qdllentrydefn->HdllentrydefnNext();
+ }
+ else {
+ QdllentrydefnOfHdllentrydefn(hdllentrydefnPrev)->
+ SetHdllentrydefnNext(qdllentrydefn->HdllentrydefnNext());
+ }
+
+ // Free the library if it was loaded
+ // For OB, This works for Mac, Win16, Win32.
+ // MAC Typelib: supports calling SLM DLL.
+#if OE_MAC
+#if 0
+ XCHAR rgbuffer[MAX_NAME]; // CONSIDER:how big should this really be?
+ NAMMGR *pnammgr;
+ TIPERROR err;
+
+ if (qdllentrydefn->HLibrary() == HINSTANCE_SLMLIBLOADED) {
+ err = m_pdtroot->GetNamMgr(&pnammgr);
+ // UNDONE MAC: Needs to return error.
+ DebAssert(err, " Cannot handle error ");
+
+ // load library Name
+ err = pnammgr->StrOfHlnam(qdllentrydefn->HlnamDllName(), rgbuffer,
+ sizeof(rgbuffer));
+
+ DebAssert(err, " cannot handle error ");
+
+ ReleaseLibrary((Handle)rgbuffer);
+ qdllentrydefn->SetHLibrary(NULL);
+ }
+#endif //0
+#else // OE_WIN
+ ReleaseLibrary(qdllentrydefn->HLibrary());
+#endif // OE_MAC & EI_OB
+
+ // Free the Native EntryPoint if it was allocated
+
+ // free instance
+ // free dllentrydefn : dllentrydefn is allocated at a different place
+ // in case of OB and OLE.
+ m_bmEntryData.FreeChunk(hdllentrydefn, sizeof(DLLENTRY_DEFN));
+
+ return;
+}
+
+
+
+
+
+/***
+*PUBLIC ENTRYMGR::Read - read entry manager from stream
+*
+*Purpose:
+* Called by containing TYPE_INFO to read embedded ENTRYMGR
+* instance from stream.
+*
+*Entry:
+* psstrm - stream from which ENTRYMGR is read
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR ENTRYMGR::Read(STREAM *pstrm)
+{
+ WORD w;
+ TIPERROR err;
+
+ DebAssert(pstrm != NULL, "ENTRYMGR::Read - invalid stream");
+
+ DebAssert(((m_cbTNativeSize == 0)
+ && (m_hdllentrydefnFirst == HDLLENTRYDEFN_Nil)
+ && (m_cbTExtEntrySize == 0)),
+ "ENTRYMGR::Read: data table not empty");
+
+ IfErrRet( pstrm->ReadUShort(&w) );
+
+ if (w != wFirstSerWord || DebErrorNow(TIPERR_InvDataRead)) {
+ return TIPERR_InvDataRead;
+ }
+
+ IfErrRet( pstrm->ReadUShort(&w) );
+
+ if (w != wCurFormat || DebErrorNow(TIPERR_UnsupFormat)) {
+ return TIPERR_UnsupFormat;
+ }
+
+ // Read in persistent ENTRYMGR members
+ IfErrRet(pstrm->Read((BYTE *)&m_hdllentrydefnFirst, cbSizeSerMem));
+
+#if HP_BIGENDIAN
+ SwapStruct(&m_hdllentrydefnFirst, ENTRYMGR_Layout);
+#endif
+
+ // Read in Entry Data block
+ IfErrRet(m_bmEntryData.Read(pstrm));
+
+
+ // Swap back the DllENTRY_DEFN(s)
+#if HP_BIGENDIAN
+ // Swap the Dll entry Defn(s)
+ SwapDllentrydefns(TRUE);
+
+#endif
+
+ // If Code page conversion is needed then walk all the Dll EntryDefns a
+ // CodePage translate the STRING(s) (i.e. DllEntry Name);
+ //
+
+
+ return TIPERR_None;
+}
+
+
+
+/***
+*PUBLIC ENTRYMGR::Write - Write ENTRYMGR to stream
+*
+*Purpose:
+* Called by containing TYPE_INFO to write ENTRYMGR instance to stream.
+*
+*Entry:
+* psstrm - pointer of stream to write to
+*
+*Exit:
+* returns TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR ENTRYMGR::Write(STREAM *pstrm)
+{
+ TIPERROR err = TIPERR_None;
+
+ DebAssert(pstrm != NULL, "ENTRYMGR::Write - invalid STREAM");
+
+ // Write out identification byte and version number
+ IfErrRet( pstrm->WriteUShort(wFirstSerWord) );
+ IfErrRet( pstrm->WriteUShort(wCurFormat) );
+
+#if HP_BIGENDIAN
+ SwapStruct(&m_hdllentrydefnFirst, ENTRYMGR_Layout);
+#endif
+
+ // Write out persistent ENTRYMGR members
+ err = pstrm->Write((BYTE *)&m_hdllentrydefnFirst, cbSizeSerMem);
+
+#if HP_BIGENDIAN
+ SwapStruct(&m_hdllentrydefnFirst, ENTRYMGR_Layout);
+#endif
+ IfErrRet(err);
+
+
+ // Write out Entry Data block
+ err = m_bmEntryData.Write(pstrm);
+
+
+ return err;
+}
+#pragma code_seg()
+
+
+#if HP_BIGENDIAN
+/***
+*PUBLIC ENTRYMGR::SwapDllentrydefns
+*Purpose:
+* Swap a DLLENTRY_DEFN(s). For OB it swaps the dllentrydefn stored in
+* Instmgr and for OLE this swaps the entrymgr stored in Entrymgr.
+*
+*Entry:
+* None;
+*
+*Exit:
+* fSwapFirst : if True then swap the DLLENTRYDEFN first before accessing
+* the m_dllentrydefnNext field.
+*
+*Errors:
+* NONE.
+*
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+VOID ENTRYMGR::SwapDllentrydefns(BOOL fSwapFirst)
+{
+ HDLLENTRY_DEFN hdllentrydefnNext;
+ DLLENTRY_DEFN *qdllentrydefn;
+
+
+
+ Lock();
+
+ // if fSwapFirst is TRUE then we need to swap the structure before accessing
+ // any datamember in the DLLENTRY_DEFN.
+ if (fSwapFirst) {
+ for (hdllentrydefnNext = m_hdllentrydefnFirst;
+ hdllentrydefnNext != HDLLENTRYDEFN_Nil;
+ qdllentrydefn = QdllentrydefnOfHdllentrydefn(hdllentrydefnNext),
+ SwapStruct(qdllentrydefn, DLLENTRY_DEFN_LAYOUT),
+ hdllentrydefnNext = qdllentrydefn->HdllentrydefnNext());
+
+ // end of FOR Loop
+ }
+ else {
+ for (hdllentrydefnNext = m_hdllentrydefnFirst;
+ hdllentrydefnNext != HDLLENTRYDEFN_Nil;
+ qdllentrydefn = QdllentrydefnOfHdllentrydefn(hdllentrydefnNext),
+ hdllentrydefnNext = qdllentrydefn->HdllentrydefnNext(),
+ SwapStruct(qdllentrydefn, DLLENTRY_DEFN_LAYOUT));
+ // end of FOR Loop
+ }
+
+
+ Unlock();
+}
+#pragma code_seg( )
+#endif //HP_BIGENDIAN
+
+
+
+
+
+
+
+#if ID_DEBUG
+
+
+/***
+*PUBLIC ENTRYMGR::DebCheckState
+*Purpose:
+* Check internal state of ENTRYMGR
+*
+*Entry:
+* uLevel
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+VOID ENTRYMGR::DebCheckState(UINT uLevel) const
+{
+}
+
+
+
+#endif //ID_DEBUG
+
+
+///////////////////////////////////////////////////////////////////////
+//
+// Below are the functions needed by EntryMgr at compile time (for OLE)
+// and is also needed by INSTMGR at RunTime. Hence they are Global functions.
+// WHY??? b'cos INSTMGR is not included in OLE. :)
+//
+//
+/***
+*ReleaseLibrary(HANDLE hLibrary)
+*Purpose:
+* Release one library.
+* Note:- On MAC this function releases the CODE RESOURCE.
+*
+*Entry:
+* hLibrary - handle to librry to release
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+// UNDONE: MPPC. Need to free CFM DLLs
+#if OE_MAC
+VOID ReleaseLibrary(Handle hLibrary)
+{
+
+// UNDONE: PPC: [jimcool]: PowerPC doesn't do DLL binding yet. (1-12-94)
+#if OE_MAC68K
+ if (hLibrary != 0) {
+#if 0
+ UnloadClass(FunctionSetID((LPSTR)hLibrary)); // UNDONE: MAC68k do these ref count correctly?
+#else //0
+ DebHalt("how'd it get set?");
+#endif //0
+ }
+#endif // OE_MAC68K
+}
+#else
+VOID ReleaseLibrary(HINSTANCE hLibrary)
+{
+ // ensure library is valid
+ if (hLibrary >= (HINSTANCE) HINSTANCE_ERROR) {
+ FreeLibrary(hLibrary);
+ } /* if */
+ return;
+}
+#endif
+
+
+/***
+*ReleaseDllEntries()
+*Purpose:
+* Releases all the loaded libraries
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+VOID ReleaseDllEntries(VOID *pv)
+{
+ ENTRYMGR* pmgr=((ENTRYMGR*)pv);
+ DLLENTRY_DEFN *qdllentrydefn;
+ HDLLENTRY_DEFN hdllentrydefn;
+
+ // iterate over list of DLLENTRY_DEFNs and release the Lib.
+ hdllentrydefn = pmgr->m_hdllentrydefnFirst;
+
+ while (hdllentrydefn != HDLLENTRYDEFN_Nil) {
+
+
+ qdllentrydefn = pmgr->QdllentrydefnOfHdllentrydefn(hdllentrydefn);
+
+ ReleaseLibrary(qdllentrydefn->HLibrary());
+
+ qdllentrydefn->SetHLibrary(0);
+ qdllentrydefn->SetLpDllEntryPoint(NULL);
+ hdllentrydefn = qdllentrydefn->HdllentrydefnNext();
+ }
+ return;
+}
+#pragma code_seg()
+
+////////////////////////////////////////////////////////////////////////
+//
+// Function common to both ENTRYMGR(for OLE) and INSTRMGR(for OB)
+//
+////////////////////////////////////////////////////////////////////////
+TIPERROR ENTRYMGR::GetAddressOfDllentry(HDLLENTRY_DEFN hdllentrydefn,VOID **ppv
+#if OE_MACPPC
+ , DLLTEMPLATECALLBLOCK *pDllBlock
+#endif // OE_MACPPC
+)
+
+{
+ DLLENTRY_DEFN *qdllentrydefn;
+ NAMMGR *pnammgr;
+ TIPERROR err = TIPERR_None;
+ XCHAR rgbuffer[MAX_NAME];
+
+
+ qdllentrydefn = QdllentrydefnOfHdllentrydefn(hdllentrydefn);
+
+
+ IfErrGoTo(m_pdtroot->GetNamMgr(&pnammgr), RaiseException);
+
+ // Get the library Name
+ IfErrGoTo(pnammgr->StrOfHlnam(qdllentrydefn->HlnamDllName(), rgbuffer,
+ sizeof(rgbuffer)), RaiseException);
+
+
+
+#if !OE_MAC
+
+ UINT uRetCode;
+ XCHAR *szFileName;
+ HFILE hfile;
+ OFSTRUCT OpenBuff;
+
+ // if the full path is specified then first try to load from that
+ // directory. If this will fail then try to load the library from the
+ // directories in the "path".
+
+ // Check if the path specified is a full path.
+ // Full Path either starts with \ or has a :
+ if ((rgbuffer[0] == '\\') || (xstrchr(rgbuffer, ':') != NULL)) {
+ // Check if we can load from from the specified directory.
+ hfile = OpenFile(rgbuffer, &OpenBuff, OF_EXIST);
+
+ // if an error occured then the file does not exist
+ if (hfile == HFILE_ERROR) {
+
+ // Change the file name, so that it does not include the path.
+ szFileName = xstrrchr (rgbuffer, '\\');
+
+ // if the name does not contain "\" then get the name of the file
+ // starting from ":"
+ if (szFileName == NULL) {
+ szFileName = xstrrchr(rgbuffer, ':');
+ }
+
+ // move up 1 character to the beginning of the file name.
+ xstrinc(szFileName);
+
+ // Copy the file name to rgbuffer
+ xstrcpy(rgbuffer, szFileName);
+ } // if
+
+ } // if
+
+
+
+
+
+ // CONSIDER : Caching the pointer to the function.
+
+ // Tell the OS, to stop displaying the FileNotFound or any error occured
+ // while loading the dll.
+ uRetCode = SetErrorMode(SEM_FAILCRITICALERRORS | SEM_NOOPENFILEERRORBOX);
+
+ // Load the library if we have not yet loaded the library
+ if (qdllentrydefn->HLibrary() < (HINSTANCE) HINSTANCE_ERROR) {
+ qdllentrydefn->SetHLibrary(LoadLibrary(rgbuffer));
+ } /* if */
+
+ DWORD dwError;
+
+ if (qdllentrydefn->HLibrary() < (HINSTANCE) HINSTANCE_ERROR) {
+ // Reset the OS's error reporting capability.
+ uRetCode = SetErrorMode(uRetCode);
+
+
+#if OE_WIN16
+ dwError = (INT)qdllentrydefn->HLibrary();
+#else // OE_WIN32
+ // On NT we need to get the specific error code by calling GetLastError.
+ dwError = GetLastError();
+#endif // OE_WIN16
+
+ goto Error;
+ }
+
+ // Reset the OS's error reporting capability.
+ uRetCode = SetErrorMode(uRetCode);
+
+
+ // get the procedures address
+ if (qdllentrydefn->HasOrdinal()) {
+ // Get Address of the Procedure
+ // CONSIDER: this may return a bogus non-'NULL value if
+ // the ordinal is invalid creating a warp into
+ // never-never land. see windows documentation
+ // for GetProcAddress()
+ // Rajivk: The document says this can happen but according to a
+ // other(semi-reliable) sources this will never happen.
+ if (!(*ppv = GetProcAddress( qdllentrydefn->HLibrary(),
+ MAKEINTRESOURCE(qdllentrydefn->UDllOrdinal())))) {
+ // GetProcAddress() failed so....
+ // set error code
+ err = TIPERR_InvalidOrdinal;
+ } /* if */
+ }
+ else {
+
+ // Get Name for Procedure
+ DllEntryNameOfHchunk(qdllentrydefn->HchunkDllEntry(), rgbuffer, MAX_NAME);
+
+ if (!(*ppv = GetProcAddress(qdllentrydefn->HLibrary(), rgbuffer))) {
+ // failed, set error code
+ //
+ err = TIPERR_InvalidDllFunctionName;
+ }
+
+ } /* if HasOrdinal else */
+
+
+ // check if an error occured
+ if (err != TIPERR_None) {
+ // free the library that was successfully loaded
+ ReleaseLibrary(qdllentrydefn->HLibrary());
+ qdllentrydefn->SetHLibrary(0);
+
+ // in case of error raise an exception for OB
+ goto RaiseException;
+ } /* if */
+
+
+
+#else //OE_MAC
+
+#if OE_MAC68K
+ if ((!xstricmp(rgbuffer, "vba"))||(!xstricmp(rgbuffer, "vba.dll"))) {
+ // RajivK: this is a work around. Since we do not have DLLs
+ // on MAC we use a table to map function name to its address.
+
+#define RTORDINAL_FIRST 512
+#define RTORDINAL_LAST 685 // rtErrObj
+
+ if (!qdllentrydefn->HasOrdinal()) {
+ err = TIPERR_InvalidDllFunctionName;
+ }
+
+ // ensure ordinal number is within the range of runtime entrypoints
+ if (qdllentrydefn->UDllOrdinal() < RTORDINAL_FIRST ||
+ qdllentrydefn->UDllOrdinal() > RTORDINAL_LAST) {
+
+ err = TIPERR_InvalidDllFunctionName;
+ goto RaiseException;
+ }
+
+ *ppv = (INT (FAR PASCAL *)()) rgMacStrdcl[qdllentrydefn->UDllOrdinal()-RTORDINAL_FIRST];
+
+ } else
+#endif //OE_MAC68K
+ {
+
+ // ASLM & Code resources do not support call by ordinal functions
+ //
+ // UNDONE: PPC: [jimcool]: PPC support these (1-11-94)
+ //
+ if (qdllentrydefn->HasOrdinal()) {
+ // CONSIDER: better error?
+ err = TIPERR_InvalidDllFunctionName;
+ goto RaiseException;
+ }
+
+#if OE_MAC68K
+ // No more ASLM DLL's -- just return an error
+ return TIPERR_DLLLoadErr;
+
+#else //!OE_MAC68K
+
+ // UNDONE: PPC: [jimcool]: PowerPC to support CFM calling. (1-11-94)
+ return TIPERR_DLLLoadErr;
+
+#if 0
+ char rgFnName[80];
+ // Handle hInstance;
+
+ ConnectionID hInstance=kNoConnectionID;
+ Ptr pfnMainEntry;
+ Str255 rgchErrBuff;
+
+
+ // See if Proc name valid:
+ if ((err = DllEntryNameOfHchunk(qdllentrydefn->HchunkDllEntry(), rgFnName, MAX_NAME))) {
+ return TIPERR_InvalidDllFunctionName;
+ }
+
+ if (!qdllentrydefn->HLibrary()) {
+ err = GetSharedLibrary(c2pstr(rgbuffer), kPowerPC, (kFindLib | kLoadLib | kUseInPlace), &hInstance, &pfnMainEntry, rgchErrBuff);
+ if (!err) {
+ qdllentrydefn->SetHLibrary(hInstance);
+
+ // get the procedures address
+ err = FindSymbol(hInstance, c2pstr(rgFnName), ppv, kCodeSym);
+ if (err) {
+ return TIPERR_InvalidDllFunctionName;
+ }
+
+ } else {
+
+ // UNDONE: PPC: [jimcool]: Temp until PPC supports 68k ASLM Calling (1-11-94)
+ return TIPERR_DLLLoadErr;
+ }
+ }
+
+
+#endif // 0
+
+#endif //!OE_MAC68K
+
+ }
+
+#endif // OE_MAC
+
+
+
+#if !OE_MAC
+
+ // if we got an error then raise exception in OB
+ goto RaiseException;
+
+Error:
+
+#if OE_WIN32
+
+#define ERROR_OUT_OF_MEMORY 0
+
+#else
+ // Define the constants
+#define ERROR_FILE_NOT_FOUND 2
+#define ERROR_PATH_NOT_FOUND 3
+#define ERROR_OUT_OF_MEMORY 8
+#endif
+
+ // LoadLibrary() failed so....
+ // add error code returned by LoadLibrary() to our error code base
+ // for LoadLibrary errors
+ if (dwError == ERROR_FILE_NOT_FOUND
+#if OE_WIN32
+ || dwError == ERROR_MOD_NOT_FOUND
+ || dwError == ERROR_PROC_NOT_FOUND
+#endif // OE_WIN32
+ ) {
+ err = TIPERR_FileNotFound;
+ } else {
+ if (dwError == ERROR_PATH_NOT_FOUND) {
+ err = TIPERR_PathNotFound;
+ } else {
+ if (dwError == ERROR_OUT_OF_MEMORY) {
+ err = TIPERR_OutOfMemory;
+ } else {
+ err = TIPERR_DLLLoadErr;
+ }
+ }
+ }
+
+#endif //!OE_MAC
+
+RaiseException:
+
+ return err;
+}
+
+
+
+
diff --git a/private/oleauto/src/typelib/entrymgr.hxx b/private/oleauto/src/typelib/entrymgr.hxx
new file mode 100644
index 000000000..e9b996573
--- /dev/null
+++ b/private/oleauto/src/typelib/entrymgr.hxx
@@ -0,0 +1,506 @@
+/***
+*EntryMgr.hxx - Entry Manager
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* One instance of this class exists for every GEN_DTINFO and
+* resides in CT segment. It manages entry point info during
+* method compilation.
+*
+* ENTRYMGR is a repository for the small subset of information
+* known to DYN_TYPEMEMBERS needed to build a TYPEFIXUPS. Its
+* reason for being is to avoid having to load a
+* DYN_TYPEMEMBERS instance every time a class is loaded for
+* execution. ENTRYMGR builds tnative, tnativeAddr.
+*
+* Using an ENTRYMGR
+* When compiling functions the following steps should be taken:
+* - NewNativeEntry() should be called for each BASIC function and
+* AllocDllEntryDefn() should be called for each DECLARE function.
+* - SetPrtmi() should be called for each BASIC function and
+* AssignDLlentrydefnHmember() should be called for each DECLARE function
+* - MakeAddressable() brings the class to a runnable state in which
+* - Decompile() should be called to bring the class out of runnable
+* state.
+* - After Decompilation NewNativeEntry(), SetPrtmi() and
+* AssignDllentrydefnHmember() must be called again, However
+* Dllentrydefns created with AllocDllEntryDefn() must be freed
+* explicitly with ReleaseDllentrydefn().
+*
+*
+*
+*CONSIDER:
+* Currently the Dll entry points are managed in a simple(slow)
+* way. Some thought should be given to managing a completly
+* free list of entry points so that calls to LoadLibrary,
+* GetProcAddress, and FreeLibrary can be kept to a minimum
+* during the edit/compile/run cycle.
+*
+* RajivK : June-05-93 :Since we have implemented late binding we call load
+* library/GetProcAddress/FreeLibrary only once.
+*
+* Also class modules are not supported. This includes virtual functions
+* and Creation of classes Copy/Assign/Construct and Destruct functions.
+* Dll support should be reviewed for non-windows platforms.
+* Building the VFT_MGR.
+*
+*
+*Revision History:
+*
+* 16-Apr-91 alanc: Created.
+* 10-Dec-91 ilanc: Override --> SetOverride
+* ClassAttr --> SetClassAttr
+* 23-Apr-92 ilanc: m_hchunkDllEntryDefn --> m_hdllentrydefn.
+* 28-May-92 stevenl: Fixed bugs in OrdinalOfDllEntryDefn and
+* DllEntryOfDllEntryDefn.
+* 07-Jul-92 w-peterh: added LoadDllEntry()
+* 23-Sep-92 rajivk: new naming convention ( P-->Q )
+* 14-Dec-92 w-peterh: made OtexOfHmember() a release function
+* 08-Dec-92 RajivK: Support for InvokeKind
+* 08-Jan-93 RajivK: Support for Code Resource on Mac
+* 08-Jan-93 RajivK: Fixed some undone(s)
+* 15-Jan-93 RajivK: Support for late binding for DLL functions
+* 30-Apr-93 w-jeffc: made DEFN data members private
+* 11-Aug-93 Rajivk: added SetPrtmi() and PrtmiOfHmember()
+* 17-Nov-93 Rajivk: added CreateNewVtableSlotData & modified DefVtableSlot
+*
+*****************************************************************************/
+
+// In later versions,
+// entry manager needs to be a protocol because there will
+// be a DLL specific implementation.
+// The GEN_DTINFO method which returns a pointer to the
+// entry manager needs to be virtual OR there needs to be
+// a GEN_DTINFO constructor which takes a pointer to
+// the ENTRYMGR.
+
+#ifndef ENTRYMGR_HXX_INCLUDED
+#define ENTRYMGR_HXX_INCLUDED
+
+#include "sheapmgr.hxx"
+#include "cltypes.hxx"
+#include "blkmgr.hxx"
+#include "defn.hxx"
+#include "gdtinfo.hxx"
+
+
+#if OE_MAC
+#include <macos\resource.h>
+#endif
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szENTRYMGR_HXX)
+#define SZ_FILE_NAME g_szENTRYMGR_HXX
+#endif
+
+class INSTMGR; // instmgr.hxx
+class STREAM; // stream.hxx
+
+#if OE_MAC
+ VOID ReleaseLibrary(Handle hCodeResource);
+#else
+ VOID ReleaseLibrary(HINSTANCE hLibrary);
+#endif
+
+
+typedef HCHUNK HVTABLESLOTDATA; // hvtsd
+typedef sHCHUNK sHVTABLESLOTDATA;
+typedef HCHUNK HVTABLEDATA; // hvtd
+typedef sHCHUNK sHVTABLEDATA;
+
+
+// global function
+UINT OffsetOfHmember(HMEMBER hmember,
+ INVOKEKIND invokekind,
+ UINT cbProcTemplateSize);
+
+
+
+
+
+
+/***
+*struct VTABLESLOTDATA - vtsd
+*Purpose:
+* Used to describe a single vtable slot. These are linked
+* in a list (not in order), with the head of the list held by
+* a VTABLEDATA. Each vtsd represents a virtual function in the VFT.
+*
+*
+***********************************************************************/
+
+struct VTABLESLOTDATA {
+ sHVTABLESLOTDATA m_hvtsdNext; // next in list.
+ INVOKEKIND m_invokekind; // invoke kind.
+ USHORT m_ovftSlot; // offset of vtable slot
+ sHMEMBER m_hmember; // member handle of function
+ BYTE m_isPublic:1; // is the event sub public.
+ BYTE m_fAddedInBrkMode:1;
+ BYTE m_UNDONE:6;
+};
+
+
+
+/***
+*struct VTABLEDATA - vtd
+*Purpose:
+* Used to describe a single vtable. These are linked
+* in a list (not in order), with the head of the list held by
+* the ENTRYMGR.
+*
+***********************************************************************/
+
+struct VTABLEDATA {
+ sHVTABLEDATA m_hvtdNext; // next in list.
+ sHVTABLESLOTDATA m_hvtsdFirst; // list of vtable slots
+ USHORT m_oPvft; // offset of the vtable ptr
+ // in the class instance.
+ USHORT m_cb; // size of the vtable
+ HIMPTYPE m_himptype; // himptype of the source.
+ MEMBERID m_memid;
+};
+
+
+
+
+// Defines the ENTRYMGR structure layout
+#define ENTRYMGR_Layout "sssss"
+
+
+/***
+*class ENTRYMGR - 'entmgr'
+*Purpose:
+* ENTRYMGR is a repository for the small subset of information
+* known to DYN_TYPEMEMBERS needed to build a TYPEFIXUPS. Its
+* reason for being is to avoid having to load a
+* DYN_TYPEMEMBERS instance every time a class is loaded for
+* execution. ENTRYMGR builds tnative, tnativeAddr,textentryaddr and VFTMGR.
+*Notes:
+* When Dll entries are being built:
+* Call AllocDllEntry() to allocate an entry in the ENTRYMGR's
+* BLK_MGR. Calling AssignDllentry() allocates a block in the
+* INSTMGR's TExtEntryAddr table. ReleaseDllentry() will create
+* an unused entry in tExtEntryAddr so both the ENTRYMGR and
+* the INSTMGR should be brought to CS_UNDECLARED state by
+* calling Decompile(CS_UNDECLARED) and re-Assigning hmembers
+* whenever ReleaseDllEntry() is called.
+* This allows MakeAddressable() to not regenerate tExtEntryAddr
+* each time it is called since if tExtEntryAddr exists when
+* it has been called then it has not been modified and can
+* simply be re-used. Again this has the consequence that
+* the tExtEntryAddr table must be completely rebuilt even
+* if a new dll entry is added, otherwise the old table will
+* be reused, without the new entry. So after any calls to
+* AllocDllEntryDefn(), ReleaseDllentrydefn(), and AssignDllentrydefnHmember()
+* both ENTRYMGR::Decompile() and INSTMGR::Decompile() must be
+* called.
+*
+*
+***********************************************************************/
+
+class ENTRYMGR
+{
+ friend VOID ReleaseDllEntries(VOID* pv); // releases the loaded library
+
+public:
+ ENTRYMGR();
+ ~ENTRYMGR();
+ nonvirt TIPERROR Init(SHEAP_MGR *psheapmgr,
+ DYN_TYPEROOT *pdtroot);
+ nonvirt VOID Decompile(COMPSTATE compstate);
+ nonvirt TIPERROR Read(STREAM *pstrm);
+ nonvirt TIPERROR Write(STREAM *pstrm);
+
+ nonvirt inline VOID Lock() { m_bmEntryData.Lock(); }
+ nonvirt inline VOID Unlock() { m_bmEntryData.Unlock(); }
+
+
+ nonvirt TIPERROR DllEntryNameOfHchunk(HCHUNK hchunk, LPSTR lpstr, UINT cch);
+ nonvirt VOID SwapDllentrydefns(BOOL fSwapFirst);
+ nonvirt TIPERROR AllocDllentrydefnByName(HLNAM hlnamDllModule,
+ LPSTR szName,
+ HDLLENTRY_DEFN *phdllentrydefn);
+ nonvirt TIPERROR AllocDllentrydefnByOrdinal(HLNAM hlnamDllModule,
+ UINT ordinal,
+ HDLLENTRY_DEFN *phdllentrydefn);
+ nonvirt VOID ReleaseDllentrydefn(HDLLENTRY_DEFN hdllentrydefn);
+
+ nonvirt DLLENTRY_DEFN *QdllentrydefnOfHdllentrydefn(HDLLENTRY_DEFN hdllentrydefn) const;
+ nonvirt BOOL HasOrdinalOfHdllentrydefn(HDLLENTRY_DEFN hdllentrydefn) const;
+ nonvirt HLNAM DllNameOfHdllentrydefn(HDLLENTRY_DEFN hdllentrydefn) const;
+ nonvirt USHORT OrdinalOfHdllentrydefn(HDLLENTRY_DEFN hdllentrydefn) const;
+ nonvirt HCHUNK DllEntryOfHdllentrydefn(HDLLENTRY_DEFN hdllentrydefn) const;
+ nonvirt TIPERROR GetAddressOfDllentry(HDLLENTRY_DEFN hdllentrydefn,
+ VOID **ppv
+#if OE_MACPPC
+ , DLLTEMPLATECALLBLOCK *pDllTemplateCallBlock
+#endif // OE_MACPPC
+ );
+
+ nonvirt BOOL IsEmpty();
+ nonvirt TIPERROR MakeAddressable();
+ nonvirt UINT GetSize();
+
+ nonvirt TIPERROR CreateNewVtableData(HIMPTYPE himptypeBase,
+ ULONG oPvft,
+ UINT cbVftBase,
+ MEMBERID memid,
+ HVTABLEDATA *phvtd);
+ nonvirt TIPERROR DefVtableSlot(HMEMBER hmember,
+ INVOKEKIND invokekind,
+ UINT ovftSlot,
+ HVTABLEDATA hvtd);
+
+ nonvirt TIPERROR DefVtableSlotInBreakMode(HMEMBER hmember,
+ INVOKEKIND invokekind,
+ UINT ovftSlot,
+ HVTABLEDATA hvtd);
+
+
+ nonvirt TIPERROR RecompileToAddressableState();
+
+
+
+ nonvirt HMEMBER HmemberBasicClassConstructor();
+ nonvirt HMEMBER HmemberBasicClassDestructor();
+ nonvirt HMEMBER HmemberBasicClassAddRef();
+ nonvirt HMEMBER HmemberBasicClassRelease();
+ nonvirt HMEMBER HmemberBasicClassQueryInt();
+
+ //NOTE: probably want to add extra methods for OB to support
+ //NOTE: per-instance data
+ //VOID PerInstConstructor(SHORT oVar, HIMPTYPE himptype);
+ //VOID SetVbaseTbl(USHORT oPvbt, USHORT cb, SHORT rgdelta[]);
+
+
+#if ID_DEBUG
+ nonvirt VOID DebCheckState(UINT uLevel) const;
+ nonvirt VOID DebShowState(UINT uLevel);
+ nonvirt VOID DebShowStateRtmi();
+ nonvirt UINT DebShowSize();
+#else //!ID_DEBUG
+ nonvirt VOID DebCheckState(UINT uLevel) const {}
+ nonvirt VOID DebShowState(UINT uLevel) {}
+ nonvirt VOID DebShowState() {}
+ nonvirt VOID DebShowSize() {}
+#endif
+
+private:
+
+
+ nonvirt TIPERROR AllocDllentrydefn(HDLLENTRY_DEFN *phdllentrydefn,
+ HLNAM hlnamDllModule,
+ BOOL fHasOrdinal);
+
+ nonvirt VOID ReleaseDllList(HDLLENTRY_DEFN hdllentrydefnStop);
+
+
+ nonvirt VTABLEDATA * QvtdOfHvtd(HVTABLEDATA hvtd) const;
+ nonvirt VTABLESLOTDATA * QvtsdOfHvtsd(HVTABLESLOTDATA hvtsd) const;
+ nonvirt TIPERROR MakeClassAddressable();
+
+ static CONSTDATA WORD wFirstSerWord; // First word of serialization
+ static CONSTDATA WORD cbSizeSerMem; // size of serialized members of ENTRYMGR
+ static CONSTDATA WORD wCurFormat; // Serialization format version number
+
+ // THESE MEMBERS ARE SERIALIZED IN THIS ORDER
+ sHDLLENTRY_DEFN m_hdllentrydefnFirst;
+
+
+
+ sHVTABLEDATA m_hvtdFirst;
+ USHORT m_cbTExtEntrySize; // bytes used in DllEntryTable
+ USHORT m_cbVftbl; // bytes used in bdVftbl
+ USHORT m_cbTNativeSize; // bytes used in TNative
+ // THESE MEMBERS ARE SERIALIZED IN THIS ORDER
+
+ USHORT m_usecfuncCount; // count of functions added in E&C.
+ BLK_MGR m_bmEntryData; // contains NATIVEENTRYDATAs
+ // for OLE it contains DLL_ENTRYDEFN also
+
+ USHORT m_cInterfaces; // Keeps the count of Interfaces.
+
+ // Start of non-serialized data members
+ DYN_TYPEROOT *m_pdtroot;
+ INSTMGR *m_pinstmgr;
+
+ // Size, location and fixup location of procedure template. These are
+ // different depending on if we're a class or a module.
+ UINT m_cbProcTemplateSize;
+ USHORT m_hProcTemplate;
+
+};
+
+
+
+/***
+*PUBLIC ENTRYMGR::XXX-OfHdllentrydefn
+*
+*Purpose:
+* Get/Set a XXX given a handle to a dllentrydefn
+*
+*Entry:
+* hdllentrydefn - handle to get
+*
+*Exit:
+* XXX
+*
+***********************************************************************/
+
+inline DLLENTRY_DEFN *ENTRYMGR::QdllentrydefnOfHdllentrydefn(HDLLENTRY_DEFN hdllentrydefn) const
+{
+ DebAssert(hdllentrydefn != HDLLENTRYDEFN_Nil,
+ "QdllentrydefnOfHdllentrydefn : bad handle");
+ return (DLLENTRY_DEFN*) m_bmEntryData.QtrOfHandle(hdllentrydefn);
+}
+
+
+inline BOOL ENTRYMGR::HasOrdinalOfHdllentrydefn(HDLLENTRY_DEFN hdllentrydefn) const
+{
+ return QdllentrydefnOfHdllentrydefn(hdllentrydefn)->HasOrdinal();
+}
+
+
+inline HLNAM ENTRYMGR::DllNameOfHdllentrydefn(HDLLENTRY_DEFN hdllentrydefn) const
+{
+ return QdllentrydefnOfHdllentrydefn(hdllentrydefn)->HlnamDllName();
+}
+
+
+inline USHORT ENTRYMGR::OrdinalOfHdllentrydefn(HDLLENTRY_DEFN hdllentrydefn) const
+{
+ DebAssert(HasOrdinalOfHdllentrydefn(hdllentrydefn),
+ "OrdinalOfHDllentrydefn : bad dllentrydefn");
+ return QdllentrydefnOfHdllentrydefn(hdllentrydefn)->UDllOrdinal();
+}
+
+
+inline HCHUNK ENTRYMGR::DllEntryOfHdllentrydefn(HDLLENTRY_DEFN hdllentrydefn) const
+{
+ DebAssert(!HasOrdinalOfHdllentrydefn(hdllentrydefn),
+ "OrdinalOfHDllentrydefn : bad dllentrydefn");
+ return QdllentrydefnOfHdllentrydefn(hdllentrydefn)->HchunkDllEntry();
+}
+
+
+/***
+*PUBLIC ENTRYMGR::AllocDllentrydefnByName
+*
+*Purpose:
+* allocate a dllentrydefn in the entrymgr
+*
+*Entry
+* hlnamDllModule - handle of dll module name
+* szName - name of the Entry (Dll Function/Code Resource/SLM Dll Function Name)
+* phdllentrydefn - address of return value
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+inline TIPERROR ENTRYMGR::AllocDllentrydefnByName(HLNAM hlnamDllModule,
+ LPSTR szName,
+ HDLLENTRY_DEFN *phdllentrydefn)
+{
+ TIPERROR err;
+ HCHUNK hchunk;
+ BYTE *qbStr;
+
+ DebAssert(hlnamDllModule != HLNAM_Nil,
+ "ENTRYMGR::AllocDllentrydefnByName - invalid handle");
+ DebAssert(szName != NULL,
+ "ENTRYMGR::AllocDllentrydefnByName - invalid handle");
+ DebAssert(phdllentrydefn != NULL,
+ "ENTRYMGR::AllocDllentrydefnByName - invalid pointer");
+
+ IfErrRet(AllocDllentrydefn(phdllentrydefn, hlnamDllModule, FALSE));
+
+ // Allocate space for the Name of the entry point.
+ IfErrRet(m_bmEntryData.AllocChunk(&hchunk, xstrblen0(szName)));
+ qbStr = m_bmEntryData.QtrOfHandle(hchunk);
+
+ // Copy the string in the memory allocated.
+ xstrcpy((XCHAR *)qbStr, szName);
+
+ QdllentrydefnOfHdllentrydefn(*phdllentrydefn)->SetHchunkDllEntry(hchunk);
+ return TIPERR_None;
+}
+
+
+/***
+*PUBLIC ENTRYMGR::AllocDllentrydefnByOrdinal
+*
+*Purpose:
+* allocate a dllentrydefn in the entrymgr
+*
+*Entry
+* hlnamDllModule - handle of dll module name
+* ordinal - ordinal of dll entry
+* phdllentrydefn - address of return value
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+inline TIPERROR ENTRYMGR::AllocDllentrydefnByOrdinal(HLNAM hlnamDllModule,
+ UINT ordinal,
+ HDLLENTRY_DEFN *phdllentrydefn)
+{
+ TIPERROR err;
+
+ DebAssert(hlnamDllModule != HLNAM_Nil,
+ "ENTRYMGR::AllocDllentrydefnByOrdinal - invalid handle");
+ DebAssert(phdllentrydefn != NULL,
+ "ENTRYMGR::AllocDllentrydefnByOrdinal - invalid pointer");
+
+ IfErrRet(AllocDllentrydefn(phdllentrydefn, hlnamDllModule, TRUE));
+ QdllentrydefnOfHdllentrydefn(*phdllentrydefn)->SetUDllOrdinal(ordinal);
+ return TIPERR_None;
+}
+
+
+/***
+*ENTRYMGR::QvtdOfHvtd, QvtsdOfHvtsd - get ptr from handle
+*Purpose:
+* Gets a pointer to a VTABLEDATA or VTABLESLOTDATA from a handle
+* thereof.
+*
+***********************************************************************/
+
+
+inline VTABLEDATA * ENTRYMGR::QvtdOfHvtd(HVTABLEDATA hvtd) const
+{
+ return (VTABLEDATA *) m_bmEntryData.QtrOfHandle(hvtd);
+}
+
+inline VTABLESLOTDATA * ENTRYMGR::QvtsdOfHvtsd(HVTABLESLOTDATA hvtsd) const
+{
+ return (VTABLESLOTDATA *) m_bmEntryData.QtrOfHandle(hvtsd);
+}
+
+
+
+/***
+*PUBLIC ENTRYMGR::IsEmpty -
+*Purpose:
+* Returns TRUE if there is nothing in the the Entry manager
+* to serialize.
+*
+*Entry:
+*
+*Exit:
+* BOOL : returns TRUE if the Entry manager is empty. Else returns FALSE.
+***********************************************************************/
+inline BOOL ENTRYMGR::IsEmpty()
+{
+ return (m_hdllentrydefnFirst == HDLLENTRYDEFN_Nil);
+}
+
+
+#endif // ! ENTRYMGR_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/errmap.cxx b/private/oleauto/src/typelib/errmap.cxx
new file mode 100644
index 000000000..e1022ed83
--- /dev/null
+++ b/private/oleauto/src/typelib/errmap.cxx
@@ -0,0 +1,161 @@
+/***
+*errmap.cxx - Error mapping utilities
+*
+* Copyright (C) 1994, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Error mapping utilities.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "silver.hxx"
+#pragma hdrstop(RTPCHNAME)
+
+#if OE_WIN16
+#include "dos.h"
+#endif // OE_WIN16
+
+#if OE_MAC
+#include "macos\errors.h"
+#endif
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+static char szErrmapCxx[] = __FILE__;
+#define SZ_FILE_NAME szErrmapCxx
+#endif
+
+
+/***
+*PUBLIC HRESULT GetErrorInfo
+*Purpose:
+* Filling the given EXCEPINFO structure from the contents of
+* the current OLE error object (if any).
+*
+*Entry:
+* pexcepinfo = pointer to caller allocated EXCEPINFO to fillin.
+*
+*Exit:
+* return value = HRESULT
+*
+*Note:
+* This routine assumes that the given EXCEPINFO does *not* contain
+* any strings that need to be freed before its contents are set.
+*
+***********************************************************************/
+HRESULT
+GetErrorInfo(EXCEPINFO *pexcepinfo)
+{
+ HRESULT hresult;
+
+ memset(pexcepinfo, 0, sizeof(*pexcepinfo));
+ IErrorInfo *perrinfo;
+ if((hresult = GetErrorInfo(0L, &perrinfo)) == NOERROR){
+ perrinfo->GetSource(&pexcepinfo->bstrSource);
+ perrinfo->GetDescription(&pexcepinfo->bstrDescription);
+ perrinfo->GetHelpFile(&pexcepinfo->bstrHelpFile);
+ perrinfo->GetHelpContext(&pexcepinfo->dwHelpContext);
+ perrinfo->Release();
+ }
+ return hresult;
+}
+
+
+#if !OE_MAC
+/***
+*TiperrOfOFErr - Maps error codes returned from OpenFile to TIPERRORs.
+***********************************************************************/
+TIPERROR TiperrOfOFErr(UINT nErrCode)
+{
+ switch (nErrCode) {
+ case 0x02: return TIPERR_FileNotFound;
+ case 0x03:
+ case 0x0f:
+ case 0x33:
+ case 0x35:
+ case 0x37:
+ case 0x40:
+ case 0x43: return TIPERR_PathNotFound;
+ case 0x04:
+ case 0x23:
+ case 0x24:
+ case 0x44:
+ case 0x45:
+ case 0x54: return TIPERR_TooManyFiles;
+ case 0x05:
+ case 0x0c:
+ case 0x13:
+ case 0x20:
+ case 0x21:
+ case 0x41:
+ case 0x42:
+ case 0x15:
+ case 0x36: return TIPERR_PermissionDenied;
+ case 0x08: return TIPERR_OutOfMemory;
+ case 0x19: return TIPERR_SeekErr;
+ case 0x1d:
+ case 0x58: return TIPERR_WriteFault;
+ case 0x1e: return TIPERR_ReadFault;
+ case 0x34:
+ case 0x50: return TIPERR_FileAlreadyExists;
+ default: return TIPERR_IOError;
+ }
+}
+
+#else // !OE_MAC
+
+/***
+*TIPERROR TiperrOfOSErr
+*Purpose:
+* Return the TIPERROR that corresponds to the given
+* Mac system error (OSErr).
+*
+*Entry:
+* oserr = the Mac OSErr to mac.
+*
+*Exit:
+* return value = TIPERROR
+*
+*Note:
+* This list isn't necessarrily complete. It was
+* created to handle errors resulting from file open
+* when loading a typelib, so if you have other uses,
+* go ahead and add aditional errors as needed.
+*
+***********************************************************************/
+TIPERROR
+TiperrOfOSErr(OSErr oserr)
+{
+static struct {
+ OSErr oserr;
+ TIPERROR tiperr;
+} rgerrmap[] = {
+ { fnfErr, TIPERR_FileNotFound }
+ , { bdNamErr, TIPERR_FileNotFound }
+ , { tmfoErr, TIPERR_TooManyFiles }
+ , { dirFulErr, TIPERR_TooManyFiles }
+ , { writErr, TIPERR_IOError }
+ , { readErr, TIPERR_IOError }
+ , { ioErr, TIPERR_IOError }
+ , { dskFulErr, TIPERR_DiskFull }
+ , { opWrErr, TIPERR_PermissionDenied }
+ , { wPrErr, TIPERR_PermissionDenied }
+ , { permErr, TIPERR_PermissionDenied }
+ , { dupFNErr, TIPERR_PermissionDenied }
+ , { dirNFErr, TIPERR_PathNotFound }
+};
+
+ for(int i = 0; i < DIM(rgerrmap); ++i){
+ if(oserr == rgerrmap[i].oserr){
+ return rgerrmap[i].tiperr;
+ }
+ }
+
+
+ DebAssert(0/*UNREACHED*/, "");
+ return TIPERR_OutOfMemory; // an unmapped error
+};
+#endif // !OE_MAC
diff --git a/private/oleauto/src/typelib/errmap.hxx b/private/oleauto/src/typelib/errmap.hxx
new file mode 100644
index 000000000..eefdd58cb
--- /dev/null
+++ b/private/oleauto/src/typelib/errmap.hxx
@@ -0,0 +1,31 @@
+/***
+*errmap.hxx - Error mapping utilities
+*
+* Copyright (C) 1994, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Error mapping utilities.
+*
+*Implementation Notes:
+* These utilities are all built into both OB and OLE.
+*
+*****************************************************************************/
+
+#ifndef ERRMAP_HXX_INCLUDED
+#define ERRMAP_HXX_INCLUDED
+
+
+#if OE_MAC
+TIPERROR TiperrOfOSErr(OSErr err);
+#else // !OE_MAC
+TIPERROR TiperrOfOFErr(UINT nErrCode);
+#endif
+
+HRESULT GetErrorInfo(EXCEPINFO *pexcepinfo);
+HRESULT SetErrorInfo(EXCEPINFO *pexcepinfo);
+
+#define TiperrOfHresult(s) (s)
+#define HresultOfTiperr(s) (s)
+
+#endif // ! ERRMAP_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/exbind.hxx b/private/oleauto/src/typelib/exbind.hxx
new file mode 100644
index 000000000..c10b6a2d5
--- /dev/null
+++ b/private/oleauto/src/typelib/exbind.hxx
@@ -0,0 +1,167 @@
+/***
+*exbind.hxx - excode binding interface
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+*
+*Revision History:
+*
+* [01] 04-Aug-92 ilanc/davebra
+*
+*Design: see exmgr.doc
+*Implementation Notes:
+* See exmgr.cxx.
+*
+*
+*****************************************************************************/
+
+#ifndef EXBIND_HXX_INCLUDED
+#define EXBIND_HXX_INCLUDED
+
+#include "defn.hxx"
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szEXBIND_HXX)
+#define SZ_FILE_NAME g_szEXBIND_HXX
+#endif
+
+class EXBIND
+{
+private:
+ BIND_KIND m_bkind; // typetag essentially
+ ITypeInfoA *m_ptinfo; // ITypeInfo of defining type.
+ union {
+ // NOTE: For now we cache the
+ // ITypeInfo of the defining type -- this is in particular
+ // important for the REAL ITypeInfo from the providing
+ // ITypeLib as opposed to the mockup (proxy) instance
+ // of GEN_DTINFO used for the exmgr.
+ // Note that probably as we abstract EXBIND more and more
+ // we will introduce a DESCKIND and BINDPTR as well, and
+ // probably not be able to unionize any longer (????)
+ //
+ struct {
+ TYPE_DATA *m_ptdata; // TYPE_DATA that contains DEFN.
+ SHORT m_ofs; // for vars: offset within instance
+ // of "introducing" base. In SI == 0.
+ // for funcs: offset of pointer to vft
+ // from THIS. In SI == 0.
+ sHDEFN m_hdefn; // for vars: hdefn of VAR_DEFN
+ // for Funcs: hdefn of FUNC_DEFN
+ } m_AccessMember;
+ struct {
+ DEFN_TYPEBIND *m_pdfntbind; // DEFN_TYPEBIND for types/projects.
+ } m_AccessType;
+ }; // end of union
+
+ BOOL m_isDispatch; // Used to support dispinterfaces
+ // that are defined in terms of
+ // a pseudo-base interface.
+ // In this case, m_ptinfo is that of
+ // the defining "pseudo-base" interface
+ // and m_isDispatch indicates that
+ // the "derived" class was a
+ // dispinterface.
+
+public:
+ // ctor
+ EXBIND() {
+ m_bkind = BKIND_NoMatch;
+ m_ptinfo = NULL;
+ m_AccessMember.m_ptdata = NULL; // m_ptbind = NULL
+ m_AccessMember.m_ofs = 0;
+ m_AccessMember.m_hdefn = HDEFN_Nil;
+ m_isDispatch = FALSE;
+ }
+
+ // accessors
+ BIND_KIND BindKind() const { return m_bkind; }
+ BOOL IsError() const { return m_bkind == BKIND_Error; }
+ BOOL IsNoMatch() const { return m_bkind == BKIND_NoMatch; }
+ BOOL IsOneVarMatch() const { return m_bkind == BKIND_OneVarMatch; }
+ BOOL IsFuncMatch() const { return m_bkind == BKIND_FuncMatch; }
+ BOOL IsDynTypeBindMatch() const { return m_bkind == BKIND_DynTypeBindMatch; }
+ BOOL IsProjTypeBindMatch() const { return m_bkind == BKIND_ProjTypeBindMatch; }
+ BOOL IsNestedTypeBindMatch() const { return m_bkind == BKIND_NestedTypeBindMatch; }
+ BOOL IsWrongArity() const { return m_bkind == BKIND_WrongArity; }
+ BOOL IsTypeInfoMatch() const { return m_bkind == BKIND_TypeInfoMatch; }
+ BOOL IsImplicitAppobjMatch() const {
+ return m_bkind == BKIND_ImplicitAppobjMatch;
+ }
+
+ INT OIntroducingBase() const {
+ DebAssert(IsOneVarMatch(), "must be var.");
+ return m_AccessMember.m_ofs;
+ }
+ INT OPvft() const {
+ DebAssert(IsFuncMatch(), "must be func.");
+ return m_AccessMember.m_ofs;
+ }
+ HDEFN Hdefn() const {
+ DebAssert(IsImplicitAppobjMatch() || IsOneVarMatch() || IsFuncMatch(),
+ "must be func or var or appobj.");
+ return (HDEFN)m_AccessMember.m_hdefn;
+ }
+ HVAR_DEFN Hvdefn() const {
+ DebAssert(IsImplicitAppobjMatch() || IsOneVarMatch(),
+ "must be var or implicit appobj.");
+ return (HVAR_DEFN)Hdefn();
+ }
+ HFUNC_DEFN Hfdefn() const {
+ DebAssert(IsFuncMatch(), "must be func.");
+ return (HFUNC_DEFN)Hdefn();
+ }
+ DEFN_TYPEBIND *Pdfntbind() const {
+ DebAssert(IsDynTypeBindMatch() ||
+ IsProjTypeBindMatch() ||
+ IsNestedTypeBindMatch(), "must be type or proj match.");
+ return m_AccessType.m_pdfntbind;
+ }
+ TYPE_DATA *Ptdata() const {
+ DebAssert(IsOneVarMatch() || IsFuncMatch() || IsImplicitAppobjMatch(),
+ "must be var or func or appobj match.");
+ return m_AccessMember.m_ptdata;
+ }
+
+ ITypeInfoA *Ptinfo() const {
+ return m_ptinfo;
+ }
+
+ BOOL IsDispatch() const {
+ return m_isDispatch;
+ }
+
+ // mutators
+ VOID SetBindKind(BIND_KIND bkind) { m_bkind = bkind; }
+ VOID SetOfs(INT ofs) { m_AccessMember.m_ofs = (SHORT)ofs; }
+ VOID SetHdefn(HDEFN hdefn) { m_AccessMember.m_hdefn = (sHDEFN)hdefn; }
+ VOID SetPtdata(TYPE_DATA *ptdata) { m_AccessMember.m_ptdata = ptdata; }
+ VOID SetPdfntbind(DEFN_TYPEBIND *pdfntbind) { m_AccessType.m_pdfntbind = pdfntbind; }
+ VOID SetPtinfo(ITypeInfoA *ptinfo) { m_ptinfo = ptinfo; }
+ VOID SetIsDispatch(BOOL isDispatch) {
+ m_isDispatch = isDispatch;
+ }
+ VOID AdjustOfs(INT db) {m_AccessMember.m_ofs += db;}
+
+ // Non-virtual functions
+ nonvirt TIPERROR GetOrdinalHparamdefnOfHlnam(NAMMGR *pnammgr,
+ HLNAM hlnamParam,
+ USHORT *pusOrdinal,
+ sHPARAM_DEFN *phparamdefn);
+ nonvirt BOOL IsBasicFunction() const;
+
+#if ID_DEBUG
+ nonvirt VOID DebCheckState(UINT uLevel) const;
+ nonvirt VOID DebShowState(UINT uLevel) const;
+#else //!ID_DEBUG
+ nonvirt VOID DebCheckState(UINT uLevel) const {}
+ nonvirt VOID DebShowState(UINT uLevel) const {}
+#endif //!ID_DEBUG
+};
+
+
+#endif // EXBIND_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/fstream.cxx b/private/oleauto/src/typelib/fstream.cxx
new file mode 100644
index 000000000..dfe40e764
--- /dev/null
+++ b/private/oleauto/src/typelib/fstream.cxx
@@ -0,0 +1,364 @@
+/***
+*fstream.cxx - Simple stream based on CFile.
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Defines FILE_STREAM implementation.
+*
+*Revision History:
+*
+* [00] 06-Jun-91 alanc: Created.
+* [01] 03-Mar-93 rajivk : Added SwapStructArray()
+*
+*Implementation Notes:
+* All data must be written in Intel byte ordering, so that files
+* are compatible between platforms. This requires byte-swapping;
+* it is done automatically by the WriteUShort, WriteULong functions,
+* if useing Write, the user should swap bytes before writing.
+*
+*****************************************************************************/
+
+#define STREAM_VTABLE
+#define FILE_STREAM_VTABLE
+#define SEEKSTREAM_VTABLE
+
+#include "silver.hxx"
+#include "typelib.hxx"
+
+#include <stdlib.h> // for errno
+
+#if OE_MAC
+ #include <macos\Files.h>
+#endif
+
+#include "xstring.h"
+#include "stream.hxx"
+#include "tiperr.h"
+#include "mem.hxx"
+#include "sheapmgr.hxx" // for min macro
+#include "clutil.hxx"
+
+#pragma hdrstop(RTPCHNAME)
+
+#if OE_MAC
+ #include <macos\Errors.h>
+#endif
+
+#include <sys\types.h>
+#include <sys\stat.h>
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+char szOleFstreamCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleFstreamCxx
+#else
+static char szFstreamCxx[] = __FILE__;
+#define SZ_FILE_NAME szFstreamCxx
+#endif
+#endif
+
+
+//
+// Implementation of STREAM abstract class non-inline methods
+//
+
+
+
+/***
+*PUBLIC STREAM::ReadSz - read LPOLESTR from the stream
+*Purpose:
+* Read an LPOLESTR from a stream. Will not modify psz unless the
+* string is successfully read in.
+*
+*Entry:
+* pointer to LPOLESTR
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR STREAM::ReadSz(LPOLESTR *psz)
+{
+ USHORT cbLen;
+ TIPERROR tiperr;
+ XSZ xszLocal;
+
+ if (tiperr = ReadUShort(&cbLen)) // read in length of serialized string
+ return tiperr;
+
+ xszLocal = (SZ)MemAlloc(cbLen + sizeof(XCHAR));
+
+ if (xszLocal == NULL)
+ return TIPERR_OutOfMemory;
+
+ if (tiperr = Read(xszLocal, cbLen)) {
+ MemFree(xszLocal);
+ return tiperr;
+ }
+
+ xszLocal[cbLen] = 0; //null terminate string
+
+#if OE_WIN32
+ // Convert from Ansi to Unicode and free up Ansi copy
+ tiperr = TiperrOfHresult(ConvertStringToW(xszLocal, psz));
+ MemFree(xszLocal);
+ return tiperr;
+#else //OE_WIN32
+ *psz = xszLocal;
+ return TIPERR_None;
+#endif //OE_WIN32
+}
+
+
+/***
+*Read - read data from the stream.
+*Purpose:
+* These functions read data from the stream. Either a byte, word,
+* long.
+*
+*Exit:
+* Returns number of bytes written, which is always the
+* same as the numberof bytes requested.
+*
+***********************************************************************/
+
+TIPERROR STREAM::ReadByte(BYTE *pb)
+{
+ return Read(pb, sizeof(BYTE));
+}
+
+
+#pragma code_seg(CS_INIT)
+TIPERROR STREAM::ReadUShort(USHORT *pus)
+{
+#if HP_BIGENDIAN
+ USHORT us;
+ TIPERROR err;
+
+ IfErrRet(Read(&us, sizeof(USHORT)));
+ // Swap bytes to read in Intel byte ordering.
+ *pus = ((us & 0xFF) << 8) | (us >> 8);
+ return TIPERR_None;
+#else //!HP_BIGENDIAN
+ return Read(pus, sizeof(USHORT));
+#endif //!HP_BIGENDIAN
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_INIT)
+TIPERROR STREAM::ReadULong(ULONG * pul)
+{
+#if HP_BIGENDIAN
+ ULONG ul;
+ TIPERROR err;
+
+ IfErrRet(Read(&ul, sizeof(ULONG)));
+ // Swap bytes to read in Intel byte ordering.
+ *pul = ((ul & 0x000000FF) << 24) |
+ ((ul & 0x0000FF00) << 8) |
+ ((ul & 0x00FF0000) >> 8) |
+ (ul >> 24);
+ return TIPERR_None;
+#else //!HP_BIGENDIAN
+ return Read(pul, sizeof(ULONG));
+#endif //!HP_BIGENDIAN
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC STREAM::Write - write data to the stream
+*Purpose:
+* These function write data to the stream. Bytes, words, longs.
+*
+* CONDIDER: Should below functions be . I think it's slightly
+* CONSIDER: worse to be based on code size, but haven't
+* CONSIDER: tested it. Might be made up by optimizer.
+*Exit:
+* Returns number of bytes written, which is always the number of
+* bytes requested.
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR STREAM::WriteByte(BYTE b)
+{
+ return Write(&b, sizeof(BYTE));
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+TIPERROR STREAM::WriteUShort(USHORT us)
+{
+#if HP_BIGENDIAN
+ // Swap bytes to write in Intel byte ordering.
+ us = ((us & 0xFF) << 8) | (us >> 8);
+#endif //!HP_BIGENDIAN
+ return Write(&us, sizeof(USHORT));
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+TIPERROR STREAM::WriteULong(ULONG ul)
+{
+#if HP_BIGENDIAN
+ // Swap bytes to write in Intel byte ordering.
+ ul = ((ul & 0x000000FF) << 24) |
+ ((ul & 0x0000FF00) << 8) |
+ ((ul & 0x00FF0000) >> 8) |
+ (ul >> 24);
+#endif //HP_BIGENDIAN
+
+ return Write(&ul, sizeof(ULONG));
+}
+#pragma code_seg()
+
+
+#if HP_BIGENDIAN
+/***
+*SwapShortArray - byte swap an array of shorts.
+*Purpose:
+* This function byte swaps an array of shorts in place.
+*
+*Entry:
+* pvArray - pointer to array
+* cShorts - number of shorts in the array.
+*
+*Exit:
+* None.
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+void SwapShortArray(void * pvArray, UINT cShorts)
+{
+ // The run-time function _swab is used here; it should be
+ // better optimized.
+ _swab((char *)pvArray, (char *)pvArray, cShorts * 2);
+}
+#pragma code_seg()
+
+/***
+*SwapLongArray - byte swap an array of longs.
+*Purpose:
+* This function byte swaps an array of longs in place.
+*
+*Entry:
+* pvArray - pointer to array
+* cLongs - number of shorts in the array.
+*
+*Exit:
+* None.
+***********************************************************************/
+
+void SwapLongArray(void * pvArray, UINT cLongs)
+{
+ ULONG * plArray = (ULONG *)pvArray;
+
+ while (cLongs--) {
+ *plArray = ((*plArray & 0x000000FF) << 24) |
+ ((*plArray & 0x0000FF00) << 8) |
+ ((*plArray & 0x00FF0000) >> 8) |
+ (*plArray >> 24);
+ ++plArray;
+ }
+}
+
+
+/***
+*SwapStruct - swap a structure.
+*Purpose:
+* Byte swaps a struct in place. The layout of the structure is
+* described by a character string, which has a character for each
+* member of the string, which is one of:
+* 'b': BYTE/CHAR
+* 's': SHORT/USHORT
+* 'l': LONG/ULONG
+*
+*Entry:
+* pvStruct - points to struct
+* szFormat - formatting string (NOTE: NOT AN XSZ -- NEVER UNICODE!)
+*
+*Exit:
+* UINT : size of the structure that was passed in (in bytes)
+* None.
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+UINT SwapStruct(void * pvArray, SZ szFormat)
+{
+ USHORT us;
+ ULONG ul;
+ UINT uSize = 0;
+
+ for (;;) {
+ switch (*szFormat++) {
+ case '\0':
+ // End of string.
+ return uSize;
+
+ case 'b':
+ // Nothing to swap - a byte.
+ pvArray = (BYTE *) pvArray + 1;
+ // Increment the size
+ uSize++;
+ break;
+
+ case 's':
+ us = *(USHORT *)pvArray;
+ *(USHORT *)pvArray = ((us & 0xFF) << 8) |
+ (us >> 8);
+ pvArray = (USHORT *) pvArray + 1;
+ // Increment the size
+ uSize += 2;
+ break;
+
+ case 'l':
+ ul = *(ULONG *)pvArray;
+ *(ULONG *)pvArray = ((ul & 0x000000FF) << 24) |
+ ((ul & 0x0000FF00) << 8) |
+ ((ul & 0x00FF0000) >> 8) |
+ (ul >> 24);
+
+ pvArray = (ULONG *) pvArray + 1;
+ // Increment the size
+ uSize += 4;
+ break;
+
+ default:
+ DebHalt("SwapStruct: Bad format string");
+ }
+ }
+ return uSize;
+}
+#pragma code_seg()
+
+
+/***
+*SwapStructArray - swaps an array of structures.
+*Purpose: For each structure in the array
+* Byte swaps the structs in place. Differs to SwapStruct to swap a struct.
+*
+*Entry:
+* pvStruct - points to struct
+* sStructs - count of structures in the array
+* szFormat - formatting string (NOTE: NOT AN XSZ -- NEVER UNICODE!)
+*
+*Exit:
+* None.
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+void SwapStructArray(void * pvArray, UINT cStructs, SZ szFormat)
+{
+ UINT i;
+ UINT uSize = 0;
+
+ for (i=0; i< cStructs ; i++)
+ uSize = SwapStruct((VOID *)((BYTE *)pvArray + i*uSize), szFormat);
+
+}
+#pragma code_seg()
+#endif //HP_BIGENDIAN
diff --git a/private/oleauto/src/typelib/gbindtbl.cxx b/private/oleauto/src/typelib/gbindtbl.cxx
new file mode 100644
index 000000000..3a1c86499
--- /dev/null
+++ b/private/oleauto/src/typelib/gbindtbl.cxx
@@ -0,0 +1,1377 @@
+/***
+*gbindtbl.cxx - GENPROJ_BINDNAME_TABLE class implementation
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Class for name binding table.
+*
+*Revision History:
+*
+* 17-Jun-92 ilanc: Created (from bindtbl.cxx)
+* 02-Jul-92 w-peterh: added support for serializing pointers to typebinds
+* 30-Jul-92 w-peterh: removed function overloading
+* 01-Mar-93 w-peterh: use OLE interface to get module names
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "silver.hxx"
+
+#define GENPROJ_BINDNAME_TABLE_VTABLE
+#include "gbindtbl.hxx"
+#include "gptbind.hxx"
+#include "gdtinfo.hxx"
+#include "dtmbrs.hxx"
+#include "nammgr.hxx"
+#include "clutil.hxx" // for HashOfHgnam()
+#include <limits.h> // for INT_MAX
+#include "xstring.h" // for memset
+
+
+#pragma hdrstop(RTPCHNAME)
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+static char szGpbindtblCxx[] = __FILE__;
+#define SZ_FILE_NAME szGpbindtblCxx
+#endif
+
+/***
+*PUBLIC GENPROJ_BINDNAME_TABLE::Constructor - Construct an instance.
+*Purpose:
+* Constructs a GENPROJ_BINDNAME_TABLE instance.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+GENPROJ_BINDNAME_TABLE::GENPROJ_BINDNAME_TABLE()
+{
+ m_indexFirstGlobal = BIND_INVALID_INDEX; // listhead
+ m_hchunkRqpdtbind = HCHUNK_Nil; // array of DYN_TYPEBIND
+
+ m_hchunkBucketTbl = HCHUNK_Nil;
+ m_cBuckets = (UINT)BIND_INVALID_INDEX;
+ m_pnammgr = NULL;
+}
+#pragma code_seg()
+
+// Dtor:
+// Implementation Notes:
+// Free caches and binding table.
+//
+#pragma code_seg(CS_INIT) // called during initialization ?
+GENPROJ_BINDNAME_TABLE::~GENPROJ_BINDNAME_TABLE()
+{
+ ReleaseTable(); // will free caches as well.
+}
+#pragma code_seg()
+
+
+/***
+*PROTECTED GENPROJ_BINDNAME_TBL::Pgptbind
+*Purpose:
+* Gets pointer to containing project-level typebind.
+*
+*Implementation Notes:
+* NOTE: defined inline here and not in the header becuase
+* of mutual dependency between gtlibole and gptbind.
+*
+* Subtracts from this pointer the offset of this
+* embedded instance in container. Offset is obtained
+* from a GENPROJ_TYPEBIND static member const.
+*
+*Entry:
+*
+*Exit:
+* GENPROJ_TYPEBIND *
+*
+***********************************************************************/
+
+inline GENPROJ_TYPEBIND *GENPROJ_BINDNAME_TABLE::Pgptbind() const
+{
+ return (GENPROJ_TYPEBIND *)((BYTE *)this - GENPROJ_TYPEBIND::oGbindnametbl);
+}
+
+
+/***
+*PUBLIC GENPROJ_BINDNAME_TABLE::Initializer - initialize an instance.
+*Purpose:
+* initializes a GENPROJ_BINDNAME_TABLE instance.
+*
+*Implementation Notes:
+*
+*Entry:
+* psheapmgr SHEAP_MGR to manage binding table and caches.
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR GENPROJ_BINDNAME_TABLE::Init(SHEAP_MGR *psheapmgr, NAMMGR *pnammgr)
+{
+ TIPERROR err;
+
+ DebAssert(psheapmgr != NULL, "GENPROJ_BINDNAME_TABLE: bad params.");
+ DebAssert(pnammgr != NULL, "BINDNAME_TABLE: pnammgr uninitialized.");
+
+ // Cache name manager member
+ m_pnammgr = pnammgr;
+
+ // Set cache size
+ m_cBuckets = 0;
+
+ IfErrRet(m_bmBindTable.Init(psheapmgr));
+ IfErrGo(m_bmArrayCache.Init(psheapmgr));
+ return err;
+
+Error:
+ m_bmBindTable.Free();
+ return err;
+}
+#pragma code_seg()
+
+
+/***
+*PROTECTED GENPROJ_BINDNAME_TABLE::GetBucketOfHlnam
+*Purpose:
+* Gets the bucket of an hlnam, based on its hash value.
+*
+*Implementation Notes:
+*
+*Entry:
+* hlnam - name to get the bucket of.
+*
+*Exit:
+* Returns a pointer to the gpbinddesc.
+*
+***********************************************************************/
+
+inline UINT GENPROJ_BINDNAME_TABLE::GetBucketOfHlnam(HLNAM hlnam) const
+{
+ DebAssert(hlnam != HCHUNK_Nil, "Invalid hlnam.");
+
+ if (m_cBuckets == 0) {
+ return (UINT)BIND_INVALID_INDEX;
+ }
+
+ return (UINT)(((USHORT)m_pnammgr->HashOfHlnam(hlnam)) % m_cBuckets);
+}
+
+
+/***
+*PROTECTED GENPROJ_BINDNAME_TABLE::IndexOfHlnam
+*Purpose:
+* Find the instance of the hlnam.
+*
+*Implementation Notes:
+*
+*Entry:
+* hlnam - The name to find.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+UINT GENPROJ_BINDNAME_TABLE::IndexOfHlnam(HLNAM hlnam) const
+{
+ GENPROJ_BIND_DESC *rqbinddesc;
+ UINT iBucket, iStartBucket;
+
+ // If the table is not valid, just return INVALID
+ if (m_cBuckets == 0) {
+ return (UINT)BIND_INVALID_INDEX;
+ }
+
+ // Dereference the hdefn so we can get the hlnam
+ rqbinddesc = Rqgpbinddesc();
+ iStartBucket = GetBucketOfHlnam(hlnam);
+
+ // Loop through the table, starting at the given
+ // index.
+ //
+ BOOL fDone = FALSE;
+ for (iBucket = iStartBucket;
+ !fDone;
+ fDone = (iBucket = (iBucket + 1) % m_cBuckets) == iStartBucket) {
+
+ // If the bucket is empty, our linear probe failed
+ if (rqbinddesc[iBucket].Hlnam() == (HLNAM)HCHUNK_Nil) {
+ return (UINT)BIND_INVALID_INDEX;
+ }
+
+ // Check to see if the names are the same
+ if (rqbinddesc[iBucket].Hlnam() == hlnam) {
+ return iBucket;
+ }
+ }
+
+ DebHalt("should never reach here since table should never be full.");
+
+ // We should never reach this, but the compiler will
+ // complain if it isn't there.
+ //
+ return (UINT)BIND_INVALID_INDEX;
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC GENPROJ_BINDNAME_TABLE::Read - read table
+*Purpose:
+* read a GENPROJ_BINDNAME_TABLE instance and caches.
+*
+*Implementation Notes:
+*
+*Entry:
+* pstrm - stream to read from
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR GENPROJ_BINDNAME_TABLE::Read(STREAM *pstrm)
+{
+ USHORT ctyp, cRefLibs=0;
+ USHORT ushort;
+ TIPERROR err;
+
+ IfErrRet(m_bmBindTable.Read(pstrm));
+ IfErrRet(pstrm->ReadUShort(&ctyp)); // # of types in this lib
+
+ IfErrRet(pstrm->ReadUShort(&ushort));
+ m_indexFirstGlobal = (UINT)ushort;
+
+ IfErrRet(pstrm->ReadUShort(&ushort));
+ m_cBuckets = (UINT)ushort;
+
+ IfErrRet(pstrm->ReadUShort(&ushort));
+ m_hchunkBucketTbl = (HCHUNK)ushort;
+
+#if HP_BIGENDIAN
+ // now that the above data members are read, we can swap the BIND_DESCs
+ SwapBindDescs();
+#endif //HP_BIGENDIAN
+
+ // Build the new array caches: note that upon deserialization
+ // they have to be reinited anyway since we don't serialize pointers.
+ //
+ IfErrRet(AllocCaches(ctyp, cRefLibs));
+
+ DebCheckState(1); // blkmgrs will be checked.
+
+ return TIPERR_None;
+}
+
+
+/***
+*PUBLIC GENPROJ_BINDNAME_TABLE::Write - write table
+*Purpose:
+* write a GENPROJ_BINDNAME_TABLE instance.
+*
+*Implementation Notes:
+* layout:
+* bindtable
+* cache arrays (ptrs nullified on reload).
+* hchunk of module cache
+* hchunk of ref'ed proj cache
+*
+*Entry:
+* pstrm - stream to write to
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR GENPROJ_BINDNAME_TABLE::Write(STREAM *pstrm)
+{
+ TIPERROR err;
+
+ DebCheckState(1); // blkmgrs will be checked.
+
+#if HP_BIGENDIAN
+ SwapBindDescs();
+#endif // HP_BIGENDIAN
+
+ IfErrRet(m_bmBindTable.Write(pstrm));
+
+#if HP_BIGENDIAN
+ SwapBindDescs();
+#endif // HP_BIGENDIAN
+
+ // Write out the number of types in this proj/typelib.
+ IfErrRet(pstrm->WriteUShort((USHORT)(m_hchunkRqpdtbind != HCHUNK_Nil ?
+ (ULONG)Rqpdtbind()[0] :
+ HCHUNK_Nil)));
+
+
+ IfErrRet(pstrm->WriteUShort((USHORT)m_indexFirstGlobal));
+ IfErrRet(pstrm->WriteUShort((USHORT)m_cBuckets));
+ IfErrRet(pstrm->WriteUShort((USHORT)m_hchunkBucketTbl));
+
+ // To verify everything is un-swapped correctly
+ DebCheckState(0);
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+#if HP_BIGENDIAN
+/***
+*PUBLIC GENPROJ_BINDNAME_TABLE::SwapBindDescs
+*Purpose:
+* Swap the entries in the given binddesc for serialization
+*
+*Entry:
+* hbinddesc - the binddesc to swap
+*
+*Exit:
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+void GENPROJ_BINDNAME_TABLE::SwapBindDescs() const
+{
+ UINT iBucket;
+ GENPROJ_BIND_DESC *rqbinddesc;
+
+ if (m_hchunkBucketTbl != HCHUNK_Nil) {
+ rqbinddesc = Rqgpbinddesc();
+
+ for (iBucket = 0; iBucket < m_cBuckets; iBucket++) {
+ SwapStruct((VOID *)&rqbinddesc[iBucket], GENPROJ_BIND_DESC_LAYOUT);
+ }
+ }
+}
+#pragma code_seg( )
+#endif // HP_BIGENDIAN
+
+
+
+/***
+*PRIVATE GENPROJ_BINDNAME_TABLE::AddNameToTable
+*Purpose:
+* Adds a module or project name to project's binding table.
+*
+*Implementation Notes:
+* Allocs a binddesc and adds it to table.
+*
+*Entry:
+* hlnam name handle to add.
+* uOrdinal Ordinal of module/project: note: 0xFFFF reserved for curproj.
+* isTypeInfo TRUE if describes a typeinfo
+* isTypeGlobal TRUE if describes type that exposes global names (IN).
+*
+*Exit:
+*
+*Errors:
+* TIPERROR (OOM if can't alloc binddesc).
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR GENPROJ_BINDNAME_TABLE::AddNameToTable(HLNAM hlnam,
+ UINT uOrdinal,
+ BOOL isTypeInfo,
+ BOOL isGlobal)
+{
+ UINT ctyp = 0, cRefLibs = 0, ctypAdd, cRefLibsAdd=0;
+ GENPROJ_BIND_DESC gpbinddesc;
+ TIPERROR err;
+
+ // Add the information to the new entry
+ gpbinddesc.m_fTypeInfoIndex = isTypeInfo;
+ gpbinddesc.m_hlnam = (sHLNAM)hlnam >> 1;
+ gpbinddesc.m_uOrdinal = (USHORT)uOrdinal;
+
+ // We figure out whether this name is global or not by the contents of
+ // m_iNextGlobal. (BIND_INVALID_INDEX means not global)
+ // So set m_iNextGlobal accordingly.
+ //
+ if (isGlobal && isTypeInfo) {
+ gpbinddesc.m_iNextGlobal = 0; // anything besides Invalid
+ }
+ else {
+ gpbinddesc.m_iNextGlobal = BIND_INVALID_INDEX;
+ }
+
+ // Adjust the size of the project cache, depending on what
+ // we have added..
+ //
+ if (m_hchunkRqpdtbind != HCHUNK_Nil) {
+ ctyp = (UINT)(ULONG)(Rqpdtbind()[0]);
+ }
+
+ ctypAdd = ctyp + (UINT)(isTypeInfo ? 1 : 0);
+
+
+ // We must change the size of the project caches to reflect the
+ // new number of TypeInfos in the current project. At the end
+ // of each compile, the contents of the caches are released but
+ // the caches themselves are not. Thus we must first release
+ // the current caches before we allocate the new caches (of the
+ // new size).
+ //
+ FreeCaches();
+
+ // Note that in EI_OLE, cRefLibsAdd isn't initialized
+ // BUT IT DOESN'T MATTER since there aren't any reflibs in OLE.
+ // (yes, there are cleaner ways to do this... VBA2).
+ //
+ IfErrGo(AllocCaches(ctypAdd, cRefLibsAdd));
+
+ // Readjust the size of the table.
+ // SetTableSize will automaticly copy the contents of the
+ // table into the new, larger table, and will properly set
+ // up the Global list.
+ //
+ IfErrGo(SetTableSize(m_cBuckets / BIND_SIZE_FACTOR + 1));
+
+
+ // Add it to the name cache
+ AddQgpbinddesc(&gpbinddesc);
+
+ return TIPERR_None;
+
+Error:
+ // We failed to reset the table size, so we must reset
+ // the project-level caches to their previous value. We know
+ // this will succeed because FreeCaches will free up more
+ // memory than we are going to allocate. In any event, we must
+ // ignore any error returned by AllocCaches because we are
+ // already handling an error.
+ //
+ FreeCaches();
+
+ DebSuspendError();
+
+ (VOID)AllocCaches(ctyp, cRefLibs);
+
+ DebResumeError();
+
+ return err;
+}
+#pragma code_seg( )
+
+
+/***
+*PRIVATE GENPROJ_BINDNAME_TABLE::AddQgpbinddesc
+*Purpose:
+* Adds a GENPROJ_BIND_DESC to project's binding table.
+*
+*Implementation Notes:
+* Adds a given binddesc to the table.
+*
+*Entry:
+* gpbinddesc - the gpbinddesc to add
+*
+*Exit:
+*
+*Errors:
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+VOID GENPROJ_BINDNAME_TABLE::AddQgpbinddesc(GENPROJ_BIND_DESC *pgpbinddesc)
+{
+ UINT iBucket, iStartBucket;
+ GENPROJ_BIND_DESC *rqbinddesc;
+
+ DebAssert(m_cBuckets != 0, "Invalid table");
+
+ // Dereference the table
+ rqbinddesc = Rqgpbinddesc();
+
+ // Assert that this gpbinddesc is valid. We must
+ // strip off the lowest-order bit of the HCHUNK_Nil below
+ // because it lowest order bit of the hlnam is lost
+ // while it is stored in the gpbinddesc.
+ //
+ DebAssert(pgpbinddesc->Hlnam() != (HLNAM)HCHUNK_Nil,
+ "Invalid gpbinddesc.");
+
+ iStartBucket = GetBucketOfHlnam(pgpbinddesc->Hlnam());
+
+ // Determine where we are going to put this.
+ BOOL fDone = FALSE;
+ for (iBucket = iStartBucket;
+ !fDone;
+ fDone = (iBucket = (iBucket + 1) % m_cBuckets) == iStartBucket) {
+
+ // If the bucket is empty, add
+ if (rqbinddesc[iBucket].Hlnam() == (HLNAM)HCHUNK_Nil) {
+
+ // Just do a shallow copy
+ rqbinddesc[iBucket] = *pgpbinddesc;
+
+ // If this is a global typeinfo (m_iNextGlobal != BIND_INVALID_INDEX),
+ // add it to the front of the global list.
+ //
+ if (rqbinddesc[iBucket].m_iNextGlobal != BIND_INVALID_INDEX) {
+ // The last entry of the list points to itself
+ if ((USHORT)m_indexFirstGlobal == BIND_INVALID_INDEX) {
+ rqbinddesc[iBucket].m_iNextGlobal = (USHORT)iBucket;
+ m_indexFirstGlobal = iBucket;
+ }
+ else {
+ rqbinddesc[iBucket].m_iNextGlobal = (USHORT)m_indexFirstGlobal;
+ m_indexFirstGlobal = iBucket;
+ }
+ }
+
+ return;
+ }
+ }
+
+ DebHalt("Table full.");
+}
+#pragma code_seg( )
+
+
+/***
+*PRIVATE GENPROJ_BINDNAME_TABLE::RemoveNameFromTableOfIBucket
+*Purpose:
+* Removes a module or project name from project's binding table.
+* Called by both RemoveNameFromTableOf{Hlnam | Ordinal}
+*Entry:
+* Ibucket bucket entry to remove.
+*
+*Exit:
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR GENPROJ_BINDNAME_TABLE::RemoveNameFromTableOfIbucket(UINT iBucket)
+{
+ BOOL isTypeInfo;
+ UINT ctyp = 0, cRefLibs = 0;
+ GENPROJ_BIND_DESC *rqbinddesc;
+ GENPROJ_BIND_DESC binddescSave;
+ TIPERROR err;
+
+ // Make sure it's in here
+ DebAssert((USHORT)iBucket != BIND_INVALID_INDEX, "bad index.");
+
+ rqbinddesc = Rqgpbinddesc();
+
+ // Determine if this is a typeinfo.
+ isTypeInfo = rqbinddesc[iBucket].IsTypeInfo();
+
+ // Save the entry so that we can restore in the error case.
+ binddescSave = rqbinddesc[iBucket];
+
+ // Clear this entry
+ rqbinddesc[iBucket].m_fTypeInfoIndex = TRUE;
+ rqbinddesc[iBucket].m_hlnam = (USHORT)(HLNAM_Nil >> 1);
+ rqbinddesc[iBucket].m_uOrdinal = (USHORT)~0;
+ rqbinddesc[iBucket].m_iNextGlobal = BIND_INVALID_INDEX;
+
+ // Allocate the new array, shrinking it by 1.
+ IfErrGo(SetTableSize(m_cBuckets / BIND_SIZE_FACTOR - 1));
+
+ // Adjust the size of the project cache, depending on what
+ // we have removed...
+ //
+ if (m_hchunkRqpdtbind != HCHUNK_Nil) {
+ ctyp = (UINT)(ULONG)(Rqpdtbind()[0]);
+ }
+
+ ctyp -= (UINT)(isTypeInfo ? 1 : 0);
+
+ if (ctyp == 0) {
+ ctyp = (UINT)HCHUNK_Nil;
+ }
+
+
+ // We must change the size of the project caches to reflect the
+ // new number of TypeInfos in the current project. At the end
+ // of each compile, the contents of the caches are released but
+ // the caches themselves are not. Thus we must first release
+ // the current caches before we allocate the new caches (of the
+ // new size).
+ //
+ // The call to AllocCaches will NOT fail because we are
+ // shrinking the size of the caches.
+ //
+ FreeCaches();
+
+ DebSuspendError();
+
+ err = AllocCaches(ctyp, cRefLibs);
+ DebAssert(err == TIPERR_None, "AllocCaches failed.");
+
+ DebResumeError();
+
+
+ return TIPERR_None;
+
+Error:
+ // Restore the saved entry.
+ rqbinddesc[iBucket] = binddescSave;
+
+ return err;
+}
+
+
+/***
+*PRIVATE GENPROJ_BINDNAME_TABLE::RemoveNameFromTableOfHlnam
+*Purpose:
+* Removes a module or project name from project's binding table.
+*
+*Entry:
+* hlnam name handle to remove.
+*
+*Exit:
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR GENPROJ_BINDNAME_TABLE::RemoveNameFromTableOfHlnam(HLNAM hlnam)
+{
+ UINT iBucket;
+
+ // If the table is empty, then there is nothing
+ // to remove.
+ //
+ if (m_cBuckets == 0) {
+ return TIPERR_None;
+ }
+
+ iBucket = IndexOfHlnam(hlnam);
+
+ // Make sure it's in here
+ if ((USHORT)iBucket == BIND_INVALID_INDEX) {
+ return TIPERR_None;
+ }
+
+ return RemoveNameFromTableOfIbucket(iBucket);
+}
+
+
+#if 0 //Dead Code
+/***
+*PRIVATE GENPROJ_BINDNAME_TABLE::RemoveNameFromTableOfOrdinal
+*Purpose:
+* Removes a module or project name from project's binding table
+* by ordinal.
+*
+*Entry:
+* ordinal ordinal of typeinfo/ref'ed typelib to remove.
+* isTypeInfo TRUE if ordinal is of typeinfo, otherwise of ref'ed typelib.
+*
+*Exit:
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR GENPROJ_BINDNAME_TABLE::RemoveNameFromTableOfOrdinal(UINT uOrdinal,
+ BOOL isTypeInfo)
+{
+ UINT iBucket;
+ GENPROJ_BIND_DESC *rqbinddesc;
+
+ // If the table is empty, then there is nothing
+ // to remove.
+ //
+ if (m_cBuckets == 0) {
+ return TIPERR_None;
+ }
+
+ rqbinddesc = Rqgpbinddesc();
+ // Loop through the array, looking for the ordinal we want,
+ // if we find it, remove it by iBucket.
+ //
+ for (iBucket = 0; iBucket < m_cBuckets; iBucket++) {
+ if ((isTypeInfo && rqbinddesc[iBucket].IsTypeInfo()) ||
+ (!isTypeInfo && !rqbinddesc[iBucket].IsTypeInfo())) {
+ if (rqbinddesc[iBucket].Ordinal() == uOrdinal) {
+ return RemoveNameFromTableOfIbucket(iBucket);
+ }
+ }
+ } // for
+ return TIPERR_None;
+}
+#endif //0
+
+/***
+*PUBLIC GENPROJ_BINDNAME_TABLE::VerifyNameOfOrdinal
+*Purpose:
+* Check the given name against the given ordinal (and type/proj) to
+* see if our table is current. If not, change it.
+*
+*Entry:
+* hlnam hlnam to verify
+* ordinal ordinal of typeinfo/ref'ed typelib to verify.
+* isTypeInfo TRUE if ordinal is of typeinfo, otherwise of ref'ed typelib.
+*
+*Exit:
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR GENPROJ_BINDNAME_TABLE::VerifyNameOfOrdinal(HLNAM hlnam,
+ UINT uOrdinal,
+ BOOL isTypeInfo)
+{
+ GENPROJ_BIND_DESC *qbinddesc, *rqbinddescTable, binddescSave;
+ UINT iBucket;
+ TIPERROR err;
+
+ // If the table is empty, just return.
+ if (m_cBuckets == 0) {
+ return TIPERR_None;
+ }
+
+ rqbinddescTable = Rqgpbinddesc();
+
+ // To avoid having to iterate over the table each time we are
+ // called, look up the name and compare.
+ //
+ iBucket = IndexOfHlnam(hlnam);
+
+ // Compare the name we found to the information we have.
+ if (iBucket != BIND_INVALID_INDEX) {
+ qbinddesc = &rqbinddescTable[iBucket];
+
+ if ( ( (qbinddesc->IsTypeInfo() && isTypeInfo) ||
+ (!qbinddesc->IsTypeInfo() && !isTypeInfo) ) &&
+ (qbinddesc->Ordinal() == uOrdinal) ) {
+ // The information in the table is valid, return
+ return TIPERR_None;
+ }
+ }
+
+ // The table is not correct, so we must update this entry by
+ // ordinal. So search the table for an entry with the same
+ // ordinal and isTypeInfo.
+ // This loop produces an ordinal: iBucket
+ //
+ for (iBucket = 0; iBucket < m_cBuckets; iBucket++) {
+ qbinddesc = &rqbinddescTable[iBucket];
+ // if there's a valid typeinfo entry then...
+ if (qbinddesc->Hlnam() != (HLNAM)HCHUNK_Nil) {
+ if ((isTypeInfo && qbinddesc->IsTypeInfo()) ||
+ (!isTypeInfo && !qbinddesc->IsTypeInfo())) {
+ // if it's got the ordinal we want, then map it and break.
+ if (qbinddesc->Ordinal() == uOrdinal) {
+ break;
+ } // if
+ } // if
+ } // if
+ } // for
+
+ DebAssert(iBucket < m_cBuckets, "should have found ordinal.");
+
+ // Save the old bind desc for error recovery.
+ binddescSave = *qbinddesc;
+
+ // Update the hlnam of the TypeInfo
+ qbinddesc->m_hlnam = hlnam >> 1;
+
+ // We need to rebuild the binding table because changing this
+ // entries HLNAM corrupts the hashing w/linear probing. Calling
+ // SetTableSize with the current size does this.
+ //
+ IfErrGo(SetTableSize(m_cBuckets / BIND_SIZE_FACTOR));
+
+ return TIPERR_None;
+
+Error:
+ // Reset the entry we changed to keep the binding table valid.
+ *qbinddesc = binddescSave;
+
+ return err;
+}
+
+/***
+*PRIVATE GENPROJ_BINDNAME_TABLE::FreeCaches
+*Purpose:
+* Frees arrays for caches.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+*Errors:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+VOID GENPROJ_BINDNAME_TABLE::FreeCaches()
+{
+ UINT ctyp;
+ UINT cbSizeRqpdtbind;
+#if ID_DEBUG
+ UINT ityp;
+#endif // ID_DEBUG
+
+
+
+ // We need to release resources explicitly here since
+ // there could be callers that FreeCaches directly w/o
+ // releasing resources themselves.
+ //
+ ReleaseResources();
+
+
+ if (m_hchunkRqpdtbind != HCHUNK_Nil) {
+ // Get array cardinality -- stored at offset 0 of array.
+ ctyp = (UINT)(ULONG)Rqpdtbind()[0];
+ cbSizeRqpdtbind = (ctyp+1) * sizeof(DYN_TYPEBIND *);
+
+#if ID_DEBUG
+ for (ityp = 1; ityp <= ctyp; ityp++) {
+ DebAssert(Rqpdtbind()[ityp] == NULL, "unreleased ref.");
+ }
+#endif // ID_DEBUG
+
+ // Free array of DYN_TYPEBIND*.
+ m_bmArrayCache.FreeChunk(m_hchunkRqpdtbind, cbSizeRqpdtbind);
+ m_hchunkRqpdtbind = HCHUNK_Nil;
+ }
+}
+#pragma code_seg()
+
+
+/***
+*PRIVATE GENPROJ_BINDNAME_TABLE::AllocCaches
+*Purpose:
+* Allocates arrays for caches.
+*
+*Implementation Notes:
+* Allocates array of size ctyp for module typebinds
+* and array of size cRefLibs for ref'ed proj typebinds.
+*
+*Entry:
+* ctyp
+* cRefLibs
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR GENPROJ_BINDNAME_TABLE::AllocCaches(UINT ctyp, UINT cRefLibs)
+{
+ HCHUNK hchunkRqpdtbind = HCHUNK_Nil;
+ UINT cbSizeRqpdtbind;
+ TIPERROR err;
+
+ if (ctyp != (USHORT)HCHUNK_Nil) {
+ // Allocate array of DYN_TYPEBIND* for modules indexed by ordinal,
+ // store array cardinality at offset 0.
+ //
+ cbSizeRqpdtbind = (ctyp+1) * sizeof(DYN_TYPEBIND *);
+ IfErrRet(m_bmArrayCache.AllocChunk(&hchunkRqpdtbind, cbSizeRqpdtbind));
+ m_hchunkRqpdtbind = (sHCHUNK)hchunkRqpdtbind;
+
+ // initialize entries to NULL
+ memset(m_bmArrayCache.QtrOfHandle(hchunkRqpdtbind),
+ (int)NULL,
+ cbSizeRqpdtbind);
+
+ // store array cardinality at offset 0.
+ DebAssert(sizeof(ULONG) >= sizeof(DYN_TYPEBIND *), "bad ptr size.");
+ Rqpdtbind()[0] = (DYN_TYPEBIND *)ctyp;
+ }
+ else {
+ m_hchunkRqpdtbind = HCHUNK_Nil;
+ }
+
+
+ return TIPERR_None;
+
+}
+#pragma code_seg( )
+
+
+
+/***
+*PUBLIC GENPROJ_BINDNAME_TABLE::ReleaseTable
+*Purpose:
+* Release hashtable and associated typebind arrays.
+*
+*Implementation Notes:
+* Defers to base class to free table and frees
+* (proj-level only) typebind arrays.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+VOID GENPROJ_BINDNAME_TABLE::ReleaseTable()
+{
+ UINT cbSizeTable;
+
+ FreeCaches();
+
+ // free the table
+ if (m_hchunkBucketTbl != HCHUNK_Nil) {
+ DebAssert(m_cBuckets != BIND_INVALID_INDEX, "bad bindtable.");
+
+ cbSizeTable = m_cBuckets * sizeof(GENPROJ_BIND_DESC);
+ m_bmBindTable.FreeChunk(m_hchunkBucketTbl, cbSizeTable);
+ m_hchunkBucketTbl = HCHUNK_Nil;
+ m_cBuckets = 0;
+ } // end of if
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GENPROJ_BINDNAME_TABLE::ReleaseResources
+*Purpose:
+* Release resources owned by binding table.
+*
+*Implementation Notes:
+* Iterates over each non-NIL entry in array of ref'ed proj
+* typebinds and module typebinds.
+* Note that module-level typebinds maintain *internal*
+* refcounts and proj-level typebinds have *external* refcounts,
+* thus they are released accordingly.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+VOID GENPROJ_BINDNAME_TABLE::ReleaseResources()
+{
+ UINT ctyp, ityp;
+
+ if (m_hchunkRqpdtbind != HCHUNK_Nil) {
+ // Release internal references to module typebinds.
+ ctyp = (UINT)(ULONG)Rqpdtbind()[0];
+ for (ityp = 1; ityp <= ctyp; ityp++) {
+ if (Rqpdtbind()[ityp] != NULL) {
+ Rqpdtbind()[ityp]->RelInternalRef();
+ Rqpdtbind()[ityp]=NULL;
+ }
+ }
+ }
+
+
+
+}
+#pragma code_seg()
+
+
+/***
+*GENPROJ_BINDNAME_TABLE::SetTableSize
+*Purpose:
+* Set and allocate the bindname table.
+*
+*Implementation Notes:
+* Copy all of the elements from the existing table into a newly
+* allocated table.
+* Note: we save the old table in dynalloced memory, the free old table,
+* create a new table
+* and then copy back the save table to the new.
+* Finally, we free the dynalloced memory.
+*
+*Entry:
+* cEntries - The number of entries into this table.
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR GENPROJ_BINDNAME_TABLE::SetTableSize(UINT cEntries)
+{
+ UINT iBucket, cBucketOld, cBucketNew;
+ GENPROJ_BIND_DESC *rqbinddesc, *rqbinddescTableOld;
+ HCHUNK hchunkBucketTblNew, hchunkBucketTblOld;
+ BYTE *pbTableCopy = NULL;
+ UINT indexFirstGlobalOld;
+ TIPERROR err = TIPERR_None, err2;
+
+ // VBA2: Rewrite the table to use a BLK_DESC instead of a
+ // BLK_MGR so that we can just Realloc the table instead
+ // of going through the BS below.
+ //
+ // Also, we should be able to reorganize the table in place
+ // instead of copying it to a separate block of memory by
+ // utilizing the iNextGlobal field to store any information
+ // we might require.
+
+ // Cache and save the old table, if it exists
+ hchunkBucketTblOld = m_hchunkBucketTbl;
+ if (hchunkBucketTblOld != HCHUNK_Nil) {
+ cBucketOld = m_cBuckets;
+ indexFirstGlobalOld = m_indexFirstGlobal;
+ IfNullRet(pbTableCopy =
+ (BYTE *)MemAlloc(cBucketOld * sizeof(GENPROJ_BIND_DESC)));
+ rqbinddescTableOld = Rqgpbinddesc();
+ // save the old table
+ memcpy(pbTableCopy,
+ (BYTE *)rqbinddescTableOld,
+ cBucketOld * sizeof(GENPROJ_BIND_DESC));
+ // Free the old array
+ m_bmBindTable.Free();
+
+ // The following should never fail because we just freed up
+ // a bunch of memory.
+ //
+ DebSuspendError();
+
+ // need to reinit with sheapmgr -- but gosh how hard it is to get.
+ err = m_bmBindTable.Init(Pgptbind()->Pgtlibole()->Psheapmgr());
+ DebAssert(err == TIPERR_None, "Can't fail.");
+
+ DebResumeError();
+ }
+
+ // Clear the existing table
+ m_indexFirstGlobal = (UINT)BIND_INVALID_INDEX;
+
+ // Set the new table size
+ // CONSIDER: 27-Aug-93 andrewso
+ // Set the # of buckets to the nearest power of two. Would
+ // require saving cEntries for AddHbindescIncTable and
+ // RemoveHlnam, but should considerable speed up the mods.
+ //
+ cBucketNew = cEntries * BIND_SIZE_FACTOR;
+ hchunkBucketTblNew = HCHUNK_Nil;
+
+ // Allocate a new table.
+ IfErrGoTo(m_bmBindTable.AllocChunk(&hchunkBucketTblNew,
+ cBucketNew * sizeof(GENPROJ_BIND_DESC)),
+ Error2);
+
+ // Store the new table size and handle.
+ m_cBuckets = (USHORT)cBucketNew;
+ m_hchunkBucketTbl = (sHCHUNK)hchunkBucketTblNew;
+
+ // Initialize all entries with HCHUNK_Nil
+ rqbinddesc = Rqgpbinddesc();
+
+ for (iBucket = 0; iBucket < m_cBuckets; iBucket++) {
+ new (&rqbinddesc[iBucket]) GENPROJ_BIND_DESC;
+ }
+
+ // If we have a saved copy of the old table we need to transfer
+ // it to the new table.
+ //
+ if (hchunkBucketTblOld != HCHUNK_Nil) {
+ rqbinddescTableOld = (GENPROJ_BIND_DESC *)pbTableCopy;
+
+ // Loop through the old array, adding all entries to the new array.
+ for (iBucket = 0; iBucket < cBucketOld; iBucket++) {
+ // if there's a valid entry then add to new table.
+ if (rqbinddescTableOld[iBucket].Hlnam() != (HLNAM)HCHUNK_Nil) {
+ AddQgpbinddesc(&rqbinddescTableOld[iBucket]);
+ }
+ } // for
+ } // if
+ goto Error;
+
+Error2:
+ // We want to restore the old table so that error recovery can
+ // continue correctly.
+ // Note that we MUST be able to allocate a chunk sufficient
+ // for the old block since we just freed it.
+ //
+ if (hchunkBucketTblOld != HCHUNK_Nil) {
+ m_cBuckets = cBucketOld;
+ m_indexFirstGlobal = indexFirstGlobalOld;
+
+ // Allocate a chunk for the old table.
+ //
+ // Since we freed a chunk the same size as this above, the
+ // below should never fail.
+ //
+ DebSuspendError();
+
+ err2 = m_bmBindTable.AllocChunk(&hchunkBucketTblOld,
+ m_cBuckets * sizeof(GENPROJ_BIND_DESC));
+ DebAssert(err2 == TIPERR_None, "must be able to go back to old table.");
+
+ DebResumeError();
+
+ // Restore it.
+ m_hchunkBucketTbl = (sHCHUNK)hchunkBucketTblOld;
+ memcpy((BYTE *)Rqgpbinddesc(),
+ pbTableCopy,
+ cBucketOld * sizeof(GENPROJ_BIND_DESC));
+
+ }
+ // fall through...
+
+Error:
+ MEMFREE(pbTableCopy);
+ return err;
+}
+#pragma code_seg( )
+
+
+#if 0 //Dead Code
+/***
+*GENPROJ_BINDNAME_TABLE::NotifyNewOrdinalOfOldOrdinal
+*Purpose:
+* Used by clients to notify binder that the ordinal of typeinfo
+* has been changed (probably cos of a deleted module).
+*
+*Implementation Notes:
+* Searches proj-level binding table and replaces the old ordinal
+* with the new ordinal.
+* Asserts if old ordinal not found -- client bug.
+*
+*Entry:
+* uOrdinalOld
+* uOrdinalNew
+* isTypeInfo
+*
+*Exit:
+* None
+*
+***********************************************************************/
+
+VOID GENPROJ_BINDNAME_TABLE::NotifyNewOrdinalOfOldOrdinal(UINT uOrdinalNew,
+ UINT uOrdinalOld,
+ BOOL isTypeInfo)
+{
+ UINT iBucket;
+ GENPROJ_BIND_DESC *rqbinddescTable;
+ GENPROJ_BIND_DESC *qbinddesc;
+#if ID_DEBUG
+ BOOL fFound = FALSE; // be pessimistic
+#endif // ID_DEBUG
+
+ // If the table is empty, there is nothing for us to do.
+ if (m_cBuckets == 0) {
+ return;
+ }
+
+ // get binding table.
+ rqbinddescTable = Rqgpbinddesc();
+
+ // Loop through the array, searching for uOrdinalOld.
+ for (iBucket = 0; iBucket < m_cBuckets; iBucket++) {
+ qbinddesc = &rqbinddescTable[iBucket];
+ // if there's a valid typeinfo entry then...
+ if (qbinddesc->Hlnam() != (HLNAM)HCHUNK_Nil) {
+ if ((isTypeInfo && qbinddesc->IsTypeInfo()) ||
+ (!isTypeInfo && !qbinddesc->IsTypeInfo())) {
+ // if it's got the ordinal we want, then map it and break.
+ if (qbinddesc->Ordinal() == uOrdinalOld) {
+ qbinddesc->m_uOrdinal = (USHORT)uOrdinalNew;
+#if ID_DEBUG
+ fFound = TRUE;
+#endif // ID_DEBUG
+ break;
+ } // if
+ } // if
+ } // if
+ } // for
+ DebAssert(fFound, "should have found old ordinal.");
+ return;
+}
+#endif
+
+
+#if ID_DEBUG
+
+/***
+*GENPROJ_BINDNAME_TABLE::DebCheckState
+*Purpose:
+* Verify that the information in the binding table is valid.
+*
+*Entry:
+* uLevel - unused
+*
+*Exit:
+* None
+*
+***********************************************************************/
+
+VOID GENPROJ_BINDNAME_TABLE::DebCheckState(UINT uLevel) const
+{
+ USHORT cTypeInfo;
+ UINT iBucket, cTable;
+ GenericTypeLibOLE *pgtlibole;
+ GENPROJ_BIND_DESC *rqbinddescTable;
+ BYTE *rgFound;
+
+
+ // Check state of embedded blkmgrs.
+ m_bmBindTable.DebCheckState(uLevel);
+ m_bmArrayCache.DebCheckState(uLevel);
+
+ DebSuspendError();
+
+ pgtlibole = m_pnammgr->Pgtlibole();
+
+ // Get the number of TypeInfos and RefLibs in this TypeLib
+ cTypeInfo = pgtlibole->GetTypeInfoCount();
+
+
+ // (1) Check the size of the table
+ //
+ DebAssert((UINT)(cTypeInfo * BIND_SIZE_FACTOR) == m_cBuckets,
+ "Invalid table size.");
+
+ // If the table is empty, we must leave before we try to
+ // dereference the binding table.
+ //
+ if (m_cBuckets == 0) {
+ DebResumeError();
+
+ return;
+ }
+
+ // (2) Check the TypeInfos in the table
+ // Verify that:
+ // A) The number of TypeInfos in the table agrees
+ // with the number in the TypeLib.
+ // B) The ordinals of the TypeInfos are valid.
+ // and
+ // C) The are no duplicate ordinals
+ //
+ // get binding table.
+ rqbinddescTable = Rqgpbinddesc();
+
+ // We set the nth field of this array when we find an entry
+ // with an ordinal of n.
+ //
+ // This could be done with bits.
+ //
+ if (!(rgFound = (BYTE *)MemZalloc(cTypeInfo))) {
+ DebResumeError();
+
+ return;
+ }
+
+ for (iBucket = 0, cTable = 0; iBucket < m_cBuckets; iBucket++) {
+ if (rqbinddescTable[iBucket].IsTypeInfo() &&
+ rqbinddescTable[iBucket].Ordinal() != BIND_INVALID_INDEX) {
+
+ cTable++;
+
+ // The ordinal should be less than the total number
+ // of TypeInfos in the TypeLib.
+ //
+ DebAssert(rqbinddescTable[iBucket].Ordinal() < cTypeInfo,
+ "Invalid GENPROJ_BIND_DESC ordinal.");
+
+ // Check the nth entry in the Found array, where n is the ordinal
+ // in this binddesc.
+ //
+ DebAssert(rgFound[rqbinddescTable[iBucket].Ordinal()]++ == 0,
+ "Duplicate ordinal.");
+ }
+ }
+
+ MemFree(rgFound);
+
+ // Assert that the number of TypeInfos we found in the table
+ // matches the number in the TypeLib.
+ //
+ DebAssert(cTable == cTypeInfo, "Invalid binding table");
+
+ // (3) Check the global list, making sure there is no invalid
+ // links or loops.
+ //
+ cTable = 0; // Counts the number of entries we've visited
+
+ iBucket = IndexFirstGlobal();
+
+ while(iBucket != BIND_INVALID_INDEX) {
+
+ // Is a valid index
+ DebAssert(iBucket < m_cBuckets, "Invalid bucket");
+
+ // Points to a valid GENPROJ_BIND_DESC
+ DebAssert(rqbinddescTable[iBucket].IsTypeInfo(),
+ "Global list points to a RefLib.");
+
+ // Points to a global typeinfo entry
+ DebAssert(rqbinddescTable[iBucket].IndexNextGlobal() != BIND_INVALID_INDEX,
+ "Global list points to a non-global TypeInfo.");
+
+ // This is valid!
+ cTable++;
+
+ // If we've found more entries than are in the table, there
+ // must be a loop somewhere.
+ //
+ DebAssert(cTable <= cTypeInfo, "Loop in global list.");
+
+ // Get the next entry in the list. If it is the same as the
+ // current entry, we are at the end of the list and should
+ // exit.
+ //
+ if (iBucket == rqbinddescTable[iBucket].IndexNextGlobal()) {
+ iBucket = BIND_INVALID_INDEX;
+ }
+ else {
+ iBucket = rqbinddescTable[iBucket].IndexNextGlobal();
+ }
+ }
+
+
+ DebResumeError();
+}
+
+
+VOID GENPROJ_BINDNAME_TABLE::DebShowState(UINT uLevel) const
+{
+ UINT iBucket;
+ GENPROJ_BIND_DESC *rqbinddesc;
+
+ DebPrintf("*** GENPROJ_BINDNAME_TABLE ***\n");
+ DebPrintf("buckets: %u\n", m_cBuckets);
+
+ if (uLevel > 0 && m_cBuckets != 0) {
+ rqbinddesc = Rqgpbinddesc();
+
+ for (iBucket = 0; iBucket < m_cBuckets; iBucket++) {
+ DebPrintf(" hlnam: %X\n", rqbinddesc[iBucket].Hlnam());
+ }
+ }
+}
+
+#endif // ID_DEBUG
diff --git a/private/oleauto/src/typelib/gbindtbl.hxx b/private/oleauto/src/typelib/gbindtbl.hxx
new file mode 100644
index 000000000..4734d7ec7
--- /dev/null
+++ b/private/oleauto/src/typelib/gbindtbl.hxx
@@ -0,0 +1,415 @@
+/***
+*gbindtbl.hxx - GENPROJ_BINDNAME_TABLE header file
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Manages hashtable of names for binding.
+* Project-level specific implementation.
+*
+*Revision History:
+*
+* 02-Mar-92 ilanc: created.
+* 02-Jul-92 w-peterh: added serializing pointers to typebinds
+* 30-Jul-92 w-peterh: removed function overloading
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#ifndef GENPROJ_BINDNAME_TABLE_HXX_INCLUDED
+#define GENPROJ_BINDNAME_TABLE_HXX_INCLUDED
+
+#include "stream.hxx"
+#if OE_MAC
+#include "silver.hxx"
+#endif
+
+
+class DYN_TYPEBIND;
+class DEFN_TYPEBIND;
+class GENPROJ_TYPEBIND;
+#define STAT_TYPELIB GEN_PROJECT
+class GEN_PROJECT;
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szGBINDTBL_HXX)
+#define SZ_FILE_NAME g_szGBINDTBL_HXX
+#endif
+
+class GenericTypeLibOLE;
+
+#define BIND_INVALID_INDEX ((USHORT)~0)
+#define BIND_SIZE_FACTOR 2
+
+/***
+*struct GENPROJ_BIND_DESC - 'pbinddesc'
+*Purpose:
+* Holds the information stored in the project-level binding table
+*
+***********************************************************************/
+struct GENPROJ_BIND_DESC
+{
+ // Data members
+
+ // m_fTypeInfoIndex determins whether m_uOrdinal reflects
+ // the index to a TypeInfo or the index to a referenced library.
+ // It can be stored in the same word as the HLNAM because the
+ // lowest bit of an HLNAM is always zero.
+ //
+ USHORT m_fTypeInfoIndex:1;
+ USHORT m_hlnam:15;
+
+ USHORT m_uOrdinal;
+ USHORT m_iNextGlobal;
+
+ // ctor
+ GENPROJ_BIND_DESC() {
+ m_fTypeInfoIndex = TRUE;
+ m_hlnam = HLNAM_Nil >> 1;
+ m_uOrdinal = (USHORT)~0;
+ m_iNextGlobal = BIND_INVALID_INDEX;
+ }
+
+ // accessors
+ BOOL IsTypeInfo() {
+ return m_fTypeInfoIndex;
+ }
+
+ HLNAM Hlnam() {
+ // We must check to see if hlnam contains
+ // an HCHUNK_Nil, and, if so, return an
+ // HCHUNK_Nil.
+ //
+ if (m_hlnam == ((USHORT)HCHUNK_Nil >> 1)) {
+ return HCHUNK_Nil;
+ }
+ else {
+ return (HLNAM)(m_hlnam << 1);
+ }
+ }
+
+ UINT Ordinal() {
+ return m_uOrdinal;
+ }
+
+ UINT IndexNextGlobal() {
+ return m_iNextGlobal;
+ }
+};
+
+// The layout string must be kept updated with the
+// structure of the struct above.
+//
+#define GENPROJ_BIND_DESC_LAYOUT "sss"
+
+// Private struct for cross-typelib binding: needed to distinguish
+// between OB projects and non-OB typelibs.
+//
+
+// Tagfield enumeration
+enum BINDINFOKIND
+{
+ BINDINFOKIND_Empty,
+ BINDINFOKIND_OB,
+ BINDINFOKIND_NonOB,
+ BINDINFOKIND_CountRefLib,
+};
+
+struct BINDINFO
+{
+ BINDINFOKIND m_bindinfokind;
+ union {
+ ULONG m_cRefLibs; // only ever in first elem of array.
+ DEFN_TYPEBIND *m_pdfntbind;
+ ITypeCompA *m_ptcomp;
+ };
+
+ // paramless ctor
+ BINDINFO() {
+ m_bindinfokind = BINDINFOKIND_Empty;
+ m_ptcomp = NULL; // m_pdfnbind == NULL
+ }
+
+ // accessors
+ BINDINFOKIND BindInfoKind() { return m_bindinfokind; }
+
+ ULONG CRefLibs() {
+ DebAssert(m_bindinfokind == BINDINFOKIND_CountRefLib, "whoops!");
+ return m_cRefLibs;
+ }
+
+ DEFN_TYPEBIND *Pdfntbind() {
+ DebAssert(m_bindinfokind == BINDINFOKIND_OB, "whoops!");
+ return m_pdfntbind;
+ }
+
+ ITypeCompA *Ptcomp() {
+ DebAssert(m_bindinfokind == BINDINFOKIND_NonOB, "whoops!");
+ return m_ptcomp;
+ }
+
+ BOOL IsEmpty() {
+ return (BOOL)(m_bindinfokind == BINDINFOKIND_Empty);
+ }
+};
+
+
+/***
+*class GENPROJ_BINDNAME_TABLE - 'gbindtbl': BindNameTable implementation.
+*Purpose:
+* BindNameTable impl. Project-level specific.
+*
+***********************************************************************/
+
+class GENPROJ_BINDNAME_TABLE
+{
+ // We let the project-level binder be a friend so that
+ // it can walk our binding table. For the sake of
+ // efficiency this is sometimes useful, i.e. avoids
+ // iterating over the typeinfo's in the lib in some cases
+ // and lets the binder modify fields in the BIND_DESC's.
+ //
+ friend class GENPROJ_TYPEBIND;
+
+public:
+ GENPROJ_BINDNAME_TABLE();
+ nonvirt ~GENPROJ_BINDNAME_TABLE();
+
+ nonvirt TIPERROR Init(SHEAP_MGR *psheapmgr, NAMMGR *pnammgr);
+
+ nonvirt TIPERROR AddNameToTable(HLNAM hlnam,
+ UINT uOrdinal,
+ BOOL isTypeInfo,
+ BOOL isGlobal=FALSE);
+ nonvirt TIPERROR RemoveNameFromTableOfHlnam(HLNAM hlnam);
+#if 0
+ nonvirt TIPERROR RemoveNameFromTableOfOrdinal(UINT uOrdinal,
+ BOOL isTypeInfo);
+#endif
+
+ nonvirt TIPERROR VerifyNameOfOrdinal(HLNAM hlnam,
+ UINT uOrdinal,
+ BOOL isTypeInfo);
+
+ nonvirt UINT IndexOfHlnam(HLNAM hlnam) const;
+ nonvirt UINT IndexFirstGlobal() const;
+
+
+ nonvirt GENPROJ_BIND_DESC *QgpbinddescOfIndex(UINT index) const;
+
+ nonvirt TIPERROR Read(STREAM *pstrm);
+ nonvirt TIPERROR Write(STREAM *pstrm);
+#if HP_BIGENDIAN
+ nonvirt VOID SwapBindDescs() const;
+#endif
+
+ // introduced methods: Cache methods
+
+ nonvirt VOID ReleaseResources();
+ nonvirt VOID ReleaseTable();
+
+ nonvirt DYN_TYPEBIND *PdtbindOfOrdinal(UINT uOrdinal) const;
+ nonvirt VOID SetPdtbindOfOrdinal(UINT uOrdinal, DYN_TYPEBIND *);
+#if 0
+ nonvirt VOID NotifyNewOrdinalOfOldOrdinal(UINT uOrdinalNew,
+ UINT uOrdinalOld,
+ BOOL isTypeInfo);
+#endif //0
+
+#if ID_DEBUG
+ nonvirt VOID DebCheckState(UINT uLevel) const;
+ nonvirt VOID DebShowState(UINT uLevel) const;
+#else //!ID_DEBUG
+ nonvirt VOID DebCheckState(UINT uLevel) const {}
+ nonvirt VOID DebShowState(UINT uLevel) const {}
+#endif //!ID_DEBUG
+
+protected:
+ TIPERROR RemoveNameFromTableOfIbucket(UINT Ibucket);
+
+ UINT GetBucketOfHlnam(HLNAM hlnam) const;
+ VOID AddQgpbinddesc(GENPROJ_BIND_DESC *gpbinddesc);
+
+ TIPERROR SetTableSize(UINT cEntries);
+
+ GENPROJ_BIND_DESC *Rqgpbinddesc() const;
+
+ // Typeinfo cache methods.
+ nonvirt TIPERROR AllocCaches(UINT ctyp, UINT cRefLibs);
+ nonvirt VOID FreeCaches();
+
+ GENPROJ_TYPEBIND *Pgptbind() const;
+
+ DYN_TYPEBIND **Rqpdtbind() const;
+
+ // data members
+ UINT m_indexFirstGlobal; // listhead of first binddesc
+ // of type that exposes global
+ // names.
+
+ BLK_MGR m_bmBindTable; // Contains proj-level binding table.
+ HCHUNK m_hchunkBucketTbl; // hchunk of the bucket table:
+
+ UINT m_cBuckets; // The number of "entries" that are
+ // currently in this table.
+
+ // below is not serialized
+
+ NAMMGR *m_pnammgr; // cached NAMMGR
+
+ BLK_MGR m_bmArrayCache; // manages typebind array caches
+ // for ref'ed projs and
+ // contained modules.
+
+ HCHUNK m_hchunkRqpdtbind; // hchunk of array of
+ // module typebinds.
+ // Nil if not valid.
+
+
+#ifdef GENPROJ_BINDNAME_TABLE_VTABLE
+#pragma VTABLE_EXPORT
+#endif
+};
+
+
+/***
+*Rqpdtbind() - Get pointer module-level typebind array.
+*Purpose:
+* Returns a pointer to array of module-level typebinds.
+*
+*Entry:
+* None.
+*
+*Exit:
+* Returns a pointer to array. Only valid
+* for a short time.
+*
+***********************************************************************/
+
+inline DYN_TYPEBIND **GENPROJ_BINDNAME_TABLE::Rqpdtbind() const
+{
+ return (DYN_TYPEBIND **)m_bmArrayCache.QtrOfHandle(m_hchunkRqpdtbind);
+}
+
+
+
+
+
+
+/***
+*PdtbindOfOrdinal()
+*Purpose:
+* Get GENPROJ_TYPEBIND* given ordinal (of ref'ed proj).
+* Since array cardinality is stored at offset 0, the input
+* param is incremented and then derefed.
+*
+*Entry:
+* None.
+*
+*Exit:
+* Returns a GENPROJ_TYPEBIND* or NULL.
+*
+***********************************************************************/
+
+inline DYN_TYPEBIND *GENPROJ_BINDNAME_TABLE::PdtbindOfOrdinal(UINT uOrdinal) const
+{
+#if ID_DEBUG
+ ULONG ctyp;
+
+ ctyp = (ULONG)(Rqpdtbind()[0]);
+ DebAssert((ULONG)uOrdinal < ctyp, "bad subscript.");
+#endif
+ return Rqpdtbind()[uOrdinal+1];
+}
+
+
+
+/***
+*SetPdtbindOfOrdinal()
+*Purpose:
+* Set DYN_TYPEBIND* given ordinal (of ref'ed proj).
+* Since array cardinality is stored at offset 0, the input
+* param is incremented and then derefed.
+*
+*Entry:
+* None.
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID GENPROJ_BINDNAME_TABLE::SetPdtbindOfOrdinal(
+ UINT uOrdinal,
+ DYN_TYPEBIND *pdtbind)
+{
+#if ID_DEBUG
+ ULONG ctyp;
+
+ ctyp = (ULONG)(Rqpdtbind()[0]);
+ DebAssert((ULONG)uOrdinal < ctyp, "bad subscript.");
+#endif
+ Rqpdtbind()[uOrdinal+1] = pdtbind;
+}
+
+
+/***
+*PUBLIC GENPROJ_BINDNAME_TABLE::IndexFirstGlobal
+*Purpose:
+* Returns the index of the first global.
+*
+*Entry:
+* None.
+*
+*Exit:
+*
+***********************************************************************/
+
+inline UINT GENPROJ_BINDNAME_TABLE::IndexFirstGlobal() const
+{
+ return m_indexFirstGlobal;
+}
+
+
+/***
+*PUBLIC GENPROJ_BINDNAME_TABLE::QgpbinddescOfIndex
+*Purpose:
+* Returns the GENPROJ_BIND_DESC of the given index
+*
+*Entry:
+* index - which gpbinddesc to return
+*
+*Exit:
+*
+***********************************************************************/
+
+inline GENPROJ_BIND_DESC *GENPROJ_BINDNAME_TABLE::QgpbinddescOfIndex(UINT index) const
+{
+ DebAssert(index < m_cBuckets, "Invalid index.");
+
+ return &(Rqgpbinddesc()[index]);
+}
+
+
+/***
+*PUBLIC GENPROJ_BINDNAME_TABLE::Rqgpbinddesc
+*Purpose:
+* Returns a pointer to the gpbinddesc array.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+inline GENPROJ_BIND_DESC *GENPROJ_BINDNAME_TABLE::Rqgpbinddesc() const
+{
+ DebAssert(m_hchunkBucketTbl != HCHUNK_Nil, "Bad table.");
+
+ return (GENPROJ_BIND_DESC *)m_bmBindTable.QtrOfHandle(m_hchunkBucketTbl);
+}
+
+
+#endif // ! GENPROJ_BINDNAME_TABLE_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/gdtinfo.cxx b/private/oleauto/src/typelib/gdtinfo.cxx
new file mode 100644
index 000000000..ef6e87db3
--- /dev/null
+++ b/private/oleauto/src/typelib/gdtinfo.cxx
@@ -0,0 +1,4981 @@
+/***
+*gdtinfo.cxx - GEN_DTINFO definition
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* GEN_DTINFO is inherited by BASIC_TYPEINFO and used directly
+* by clients such as COMPOSER.
+*
+*Owner:
+* AlanC
+*
+*Revision History:
+*
+* 01-Mar-91 alanc: Created.
+* [01] 20-Mar-91 ilanc: include ctseg.hxx (COMPILETIME_SEG)
+* [02] 04-Apr-91 ilanc: init private universe member in constructor.
+* [03] 13-Nov-91 ilanc: rm TYPEKIND param from Init of DYN_TYPEMEMBERS.
+* [04] 05-Mar-92 ilanc: Added m_isBasic attr to DYN_TYPEROOT::Init().
+* [05] 12-Apr-92 ilanc: Check for NULL m_pdtmbrs in DebCheckState();
+* [06] 05-May-92 ilanc: Added CS_SEMIDECLARED stuff.
+* [07] 02-Jul-92 w-peterh: add OrdinalOfRectbind() and PrtbindOfOrdinal()
+* [08] 10-Jul-92 w-peterh: set TypeInfo's of imptype in CreateRecTinfos
+* [09] 01-Sep-92 rajivk: Functions for bringing all needed class to runnable state.
+* [10] 17-Sep-92 rajivk: implementing "edit and continue" support.
+* [11] 17-Nov-92 rajivk: Added CanProjChange() stuff.
+* [11] 12-Nov-92 w-peterh: added immediate/watch functions
+* [12] 21-Nov-92 rajivk : call User Defined Reset() when reseting a module
+* [13] 02-Dec-92 rajivk : Lock sheapmgr when the module is in runnable state
+* [14] 02-Dec-92 rajivk :DecompileToCompiledState()
+* [15] 08-Jan-93 RajivK: Support for Code Resource on Mac
+* [16] 08-Jan-93 RajivK: Fixed some undone(s)
+* [17] 18-Jan-93 w-peterh: implemented AddFuncDesc and AddVarDesc
+* [18] 26-Jan-93 w-peterh: added doc and help functions
+* [19] 02-Feb-93 w-peterh: added IndexOfFuncName
+* [20] 10-Feb-93 rajivk: added DefineFuncAsDllEntry() & AddressOfMember()
+* [21] 12-Feb-93 w-peterh: added RefTypeInfo, ImplTypeInfo, TypeDescAlias etc.
+* [22] 23-Feb-93 rajivk : add CreateInstance support
+* [23] 01-Mar-93 w-peterh: used new dispatch.h names
+* [24] 02-Mar-93 w-peterh: move m_guid to DYN_TYPEROOT check that enum size is ok
+* [25] 19-Mar-93 w-jeffc: added GetDocumentationOfFuncName
+* [26] 26-Mar-93 mikewo: move m_guid back to gtlibole's TYPE_ENTRY
+* [27] 30-Apr-93 w-jeffc: made DEFN data members private
+* [28] 07-Sep-93 w-jeffc: enabled TYPE_DATA compaction
+*
+*****************************************************************************/
+
+#include "silver.hxx"
+#include "macros.hxx"
+#include "typelib.hxx"
+#include <new.h>
+#include <stdlib.h>
+
+#define GEN_DTINFO_VTABLE // export GEN_DTINFO vtable
+#define DYN_TYPEROOT_VTABLE // export DYN_TYPEROOT vtable
+
+#include "string.h"
+#include "gdtinfo.hxx"
+#include "ctseg.hxx"
+#include "sheapmgr.hxx"
+#include "dtbind.hxx"
+#include "mem.hxx"
+#include "dfntcomp.hxx"
+#include "clutil.hxx"
+#include "exbind.hxx"
+
+
+
+#pragma hdrstop(RTPCHNAME)
+
+OLECHAR FAR * g_szGuidStdole = WIDE("{00020430-0000-0000-C000-000000000046}");
+
+// Define static class constants
+//
+CONSTDATA LPOLESTR GEN_DTINFO::szProtocolName = WIDE("*D\0");
+
+// Serialization format version numbers
+CONSTDATA BYTE DYN_TYPEROOT::bCurVersion = 5; // DO NOT CHANGE!
+
+CONSTDATA BYTE DYN_TYPEROOT::bFirstSerByte = LOBYTE('D' * 4 + 'T' * 2 + 'I');
+ // offsetof(Firstmemberafterlastserializedmember) -
+ // offsetof(firstserializedmember)
+CONSTDATA WORD DYN_TYPEROOT::cbSizeDir =
+ offsetof(DYN_TYPEROOT, m_unused1) + 3 * sizeof(USHORT) -
+ offsetof(DYN_TYPEROOT, m_lImpMgr);
+
+
+
+// typedefs for calling basic functions
+//
+typedef void (FAR PASCAL *CALL_SUB) (void);
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+char szOleGDTInfoCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleGDTInfoCxx
+#else
+static char szGDTInfoCxx[] = __FILE__;
+#define SZ_FILE_NAME szGDTInfoCxx
+#endif
+#endif //ID_DEBUG
+
+
+// Global useful functions...
+//
+// Works out if a given GEN_DTINFO is funky dispinterface,
+// i.e. a dispinterface defined in terms of an interface.
+//
+#define HREFTYPE_FUNKY_DISPATCH (HREFTYPE)0
+#define HREFTYPE_FUNKY_SIGNAL_DISPATCH (HREFTYPE)-2
+#define HREFTYPE_FUNKY_SIGNAL_PARTNER (HREFTYPE)-4
+
+TIPERROR IsFunkyDispinterface(GEN_DTINFO *pgdtinfo,
+ BOOL *pisFunkyDispinterface)
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+
+ DebAssert(pisFunkyDispinterface, "bad param.");
+ IfErrRet(pgdtinfo->Pdtroot()->GetDtmbrs(&pdtmbrs));
+
+ // Work out if we're a dispinterface defined in terms of an interface...
+ *pisFunkyDispinterface = (pgdtinfo->GetTypeKind() == TKIND_DISPATCH) &&
+ (pdtmbrs->Ptdata()->CBase() > 1);
+ return TIPERR_None;
+}
+
+
+// Helper function to munge an interface funcdesc into a dispinterface funcdesc
+void InterfaceFuncdescToDispatch(FUNCDESC * pfuncdesc)
+{
+ DebAssert(pfuncdesc->funckind != FUNC_DISPATCH,
+ "should have been set to something other than disp.");
+ pfuncdesc->funckind = FUNC_DISPATCH;
+
+ // If necessary, nuke the lcid & retval parms, and convert return value
+ WORD cParams;
+ ELEMDESC * pelemdesc;
+
+ cParams = pfuncdesc->cParams;
+ pelemdesc = pfuncdesc->lprgelemdescParam;
+ while (cParams > 0) {
+
+ // loop through the parameters, looking for the 'lcid' and 'retval' parms
+ // retval should be the last one, 'lcid' should be the last one before
+ // retval
+
+ cParams--;
+
+ if (pelemdesc->idldesc.wIDLFlags & IDLFLAG_FLCID) {
+ // nuke the LCID param if it was specified
+ ClearElemDesc(pelemdesc);
+ pfuncdesc->cParams -= 1; // pretend one less param
+
+ // If the next parameter is NOT a retval parameter, copy it down
+ // into the LCID parameter's spot and quit. We can do this
+ // without worrying about freeing any resources becuase the lcid
+ // parameter is always a simple type.
+ // This case will happen for a property put function with an LCID
+ // parameter.
+ //
+ if (cParams > 0
+ && !((pelemdesc + 1)->idldesc.wIDLFlags & IDLFLAG_FRETVAL)) {
+
+ DebAssert(cParams == 1, "Can only have 1 param after LCID");
+ *pelemdesc = *(pelemdesc + 1);
+ break;
+ }
+ }
+ else if (pelemdesc->idldesc.wIDLFlags & IDLFLAG_FRETVAL) {
+ TYPEDESC * ptdesc;
+ // handle the RETVAL param if it was specified
+ // first free the return value elemdesc
+ DebAssert(pfuncdesc->elemdescFunc.tdesc.vt == VT_HRESULT, "");
+ ClearElemDesc(&pfuncdesc->elemdescFunc);
+ pfuncdesc->cParams -= 1; // pretend one less param
+ // copy the retval param's type to the return value, removing one
+ // level of "VT_PTR" indirection.
+ pfuncdesc->elemdescFunc = *pelemdesc;
+ DebAssert(pfuncdesc->elemdescFunc.tdesc.vt == VT_PTR, "");
+ ptdesc = pfuncdesc->elemdescFunc.tdesc.lptdesc;
+ pfuncdesc->elemdescFunc.tdesc = *ptdesc;
+ MemFree(ptdesc); // free the old tdesc's memory
+
+ // the must be the last param, so we don't have to worry about
+ // copying params down
+ DebAssert(cParams == 0, "shouldn't be any parms left");
+ goto NoHresultCheck; // last parm -- we're done
+ }
+
+ pelemdesc += 1; // point to next param
+ }
+
+ // if we have a HRESULT-returning function with no 'retval' parm, then
+ // it should look like a SUB.
+ if (pfuncdesc->elemdescFunc.tdesc.vt == VT_HRESULT) {
+ pfuncdesc->elemdescFunc.tdesc.vt = VT_VOID; // pretend it's a SUB
+ }
+
+NoHresultCheck:
+ ;
+}
+
+
+
+// Gets a base typeinfo given an impltype ordinal.
+//
+HRESULT GetTypeInfoOfImplType(GEN_DTINFO *pgdtinfo,
+ UINT uImplType,
+ ITypeInfoA **pptinfo)
+{
+ HREFTYPE hreftype;
+ IMPMGR *pimpmgr;
+ DYN_TYPEMEMBERS *pdtmbrs;
+ BOOL fGetInterface;
+ ITypeInfoA *ptinfoDisp = NULL;
+
+ TIPERROR err;
+
+ IfErrGo(pgdtinfo->Pdtroot()->GetDtmbrs(&pdtmbrs));
+ IfErrGo(pdtmbrs->Ptdata()->GetRefTypeOfImplType(uImplType, &hreftype));
+
+ fGetInterface = (BOOL)(hreftype & 0x00000001);
+ hreftype &= ~0x00000001;
+
+ IfErrGo(pgdtinfo->Pdtroot()->GetImpMgr(&pimpmgr));
+ IfErrGo(pimpmgr->GetTypeInfo(pgdtinfo->Pdtroot()
+ ->HimptypeOfHreftype(hreftype),
+ DEP_None,
+ pptinfo));
+
+ // Check to see if we should load the interface of the
+ // just gotten dual interface.
+ //
+ if (fGetInterface) {
+ TYPEATTR *ptypeattr;
+ TYPEKIND tkind;
+
+ ptinfoDisp = *pptinfo;
+
+ IfErrGo(TiperrOfHresult(ptinfoDisp->GetTypeAttr(&ptypeattr)));
+ tkind = ptypeattr->typekind;
+ DebAssert(ptypeattr->wTypeFlags & TYPEFLAG_FDUAL, "Not a dual");
+ ptinfoDisp->ReleaseTypeAttr(ptypeattr);
+
+ if (tkind == TKIND_DISPATCH) {
+ // Get the other interface.
+ IfErrGo(TiperrOfHresult(ptinfoDisp->GetRefTypeOfImplType((UINT)-1,
+ &hreftype)));
+ err = TiperrOfHresult(ptinfoDisp->GetRefTypeInfo(hreftype,
+ pptinfo));
+ }
+ else {
+ ptinfoDisp = NULL;
+ }
+ }
+
+Error:
+ RELEASE(ptinfoDisp);
+ return HresultOfTiperr(err);
+}
+
+
+
+// Determines if given interface is supported in V1.
+// I.e. it and its bases must recursively been created by typelib.dll
+
+HRESULT IsInterfaceSupported(ITypeInfoA *ptinfo,
+ BOOL *pisInterfaceSupported)
+{
+ GEN_DTINFO *pgdtinfo;
+ ITypeInfoA *ptinfoBase;
+ DYN_TYPEMEMBERS *pdtmbrs;
+ HRESULT hresult;
+ TIPERROR err;
+
+ *pisInterfaceSupported = TRUE; // be optimistic
+ hresult = ptinfo->QueryInterface(IID_TYPELIB_GEN_DTINFO,
+ (LPVOID *)&pgdtinfo);
+ if (hresult != NOERROR) {
+ *pisInterfaceSupported = FALSE;
+ return NOERROR;
+ }
+
+ IfErrGo(pgdtinfo->Pdtroot()->GetDtmbrs(&pdtmbrs));
+
+ // do we have yet another base?
+ if (pdtmbrs->Ptdata()->CBase() > 0) {
+ // Now check if base interface is supported...
+ hresult = GetTypeInfoOfImplType(pgdtinfo, 0, &ptinfoBase);
+ pgdtinfo->Release();
+ if (hresult == NOERROR) {
+ hresult = IsInterfaceSupported(ptinfoBase, pisInterfaceSupported);
+ ptinfoBase->Release();
+ }
+ return hresult;
+ }
+ // fall through...
+
+Error:
+ pgdtinfo->Release();
+ return HresultOfTiperr(err);
+}
+
+
+ // Class methods
+//#if OE_MAC
+//class MY_GDTINFO : public GEN_DTINFO {};
+//MY_GDTINFO gendtinfo;
+//#endif
+
+
+/***
+*PROTECTED GEN_DTINFO::GEN_DTINFO()
+*
+*Purpose:
+*
+*
+*Entry:
+* None.
+*
+*Exit:
+* TIPERROR
+***********************************************************************/
+#pragma code_seg( CS_CORE2 )
+GEN_DTINFO::GEN_DTINFO()
+{
+ m_pdtroot = NULL;
+ m_pvResetFunc = NULL;
+
+}
+#pragma code_seg( )
+
+
+/***
+*PROTECTED GEN_DTINFO::~GEN_DTINFO()
+*
+*Purpose:
+*
+*
+*Entry:
+* None.
+*
+*Exit:
+***********************************************************************/
+#pragma code_seg( CS_CORE )
+GEN_DTINFO::~GEN_DTINFO()
+{
+
+ delete m_pdtroot;
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC GEN_DTINFO::ReleasePublicResources()
+*
+*Purpose:
+* Releases any resources we don't want to keep around after
+* the public refcount goes to zero.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+***********************************************************************/
+
+VOID GEN_DTINFO::ReleasePublicResources()
+{
+#if OE_WIN32
+#if _X86_
+ if (!g_fWin32s)
+#endif // _X86_
+ {
+ if (Pdtroot()->m_htinfo != HTINFO_Nil) {
+ g_AppObjectTable.RemoveTypeInfo(Pdtroot()->m_htinfo);
+ Pdtroot()->m_htinfo = HTINFO_Nil;
+ }
+ }
+#if _X86_
+ else if (m_pdtroot->m_punk != NULL) {
+ m_pdtroot->m_punk->Release();
+ m_pdtroot->m_punk = NULL;
+ }
+#endif _X86_
+#else // !OE_WIN32
+ if (m_pdtroot->m_punk != NULL) {
+ m_pdtroot->m_punk->Release();
+ m_pdtroot->m_punk = NULL;
+ }
+#endif // !OE_WIN32
+}
+
+
+
+
+
+/***
+*PUBLIC GEN_DTINFO::Create
+*
+*Purpose:
+* Static function for creation of a GEN_DTINFO.
+*
+*Entry:
+* ppgdtinfo - set to point to produced GEN_DTINFO
+* accessModule - Indicates visibility of module wrt other projects (IN).
+* syskind (OLE) - syskind of the containing typelib
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR GEN_DTINFO::Create(GEN_DTINFO **ppgdtinfo,
+ TYPEKIND tkind,
+ BOOL isBasic,
+ ACCESS accessModule
+ , SYSKIND syskind
+ )
+{
+ GEN_DTINFO *pgdtinfo;
+ DYN_TYPEROOT *pdtroot;
+ SHEAP_MGR *psheapmgr;
+ TIPERROR err;
+
+ pgdtinfo = MemNew(GEN_DTINFO);
+
+ if (pgdtinfo == NULL)
+ return(TIPERR_OutOfMemory);
+
+ ::new (pgdtinfo) GEN_DTINFO;
+
+ // Construct the DYN_TYPEROOT.
+ // Note that the reason that the Create method constructs the DYN_TYPEROOT
+ // instead of the Init method is because the Init method is called
+ // by classes that derive from GEN_DTINFO and they need to
+ // construct their own derivative of TYPEROOT.
+
+ err = SHEAP_MGR::Create((SHEAP_MGR **)&psheapmgr,
+ sizeof(SHEAP_MGR) + sizeof(DYN_TYPEROOT));
+
+ if (err != TIPERR_None) {
+ goto Error;
+ }
+
+ // Construct the dtroot immediately following the sheapmgr.
+ pdtroot = ::new (psheapmgr+1) DYN_TYPEROOT;
+
+ if (err = pdtroot->Init(pgdtinfo,
+ sizeof(DYN_TYPEROOT),
+ sizeof(COMPILETIME_SEG),
+ isBasic,
+ accessModule,
+ tkind
+ , syskind
+ )) {
+ delete pdtroot;
+ goto Error;
+ }
+
+ // initialize the datamember
+ pgdtinfo->m_pdtroot = pdtroot;
+
+ *ppgdtinfo = pgdtinfo;
+ return TIPERR_None;
+
+Error:
+ pgdtinfo->GEN_DTINFO::~GEN_DTINFO();
+ MemFree(pgdtinfo);
+ return err;
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::RemoveInternalRefs()
+*Purpose:
+* Remove internal references from a module to other modules in
+* the same project. This is called before destructor is called.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+***********************************************************************/
+
+#pragma code_seg( CS_CORE )
+VOID GEN_DTINFO::RemoveInternalRefs()
+{
+ IMPMGR *pimpmgr;
+
+ // If this fails, assume there is nothing to remove.
+ if (!m_pdtroot->GetImpMgr( &pimpmgr )) {
+ pimpmgr->RemoveInternalRefs();
+ }
+}
+#pragma code_seg( )
+
+
+
+/***
+*PUBLIC GEN_DTINFO::QueryInterface
+*Purpose:
+* Implementation of QueryInterface method. Supports casting to GEN_DTINFO.
+*
+*Entry:
+* riid - Interface GUID
+* ppvObj - LPVOID * that receives the requested protocol.
+*
+*Exit:
+* Return NOERROR or ReportResult(0, E_NOINTERFACE, 0, 0)
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+HRESULT GEN_DTINFO::QueryInterface(REFIID riid, LPVOID FAR* ppvObj)
+{
+ if (IIDEQ(riid, IID_TYPELIB_GEN_DTINFO)) {
+ *ppvObj = (LPVOID) (GEN_DTINFO *) this;
+ AddRef();
+ return NOERROR;
+ }
+ return this->STL_TYPEINFO::QueryInterface(riid, ppvObj);
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC GEN_DTINFO::GetDynTypeMembers - return DynTypeMembers of the Type
+*Purpose:
+* Retrieve the DYN_TYPEMEMBERS of the TYPEINFO
+*
+*Implementation Notes:
+* Defers to GetDtmbrs() which does NOT add a ref, hence
+* explicitly adds a reference. Clients must eventually release.
+*
+*Entry:
+* None.
+*
+*Exit:
+* returns DynTypeMembers instance or Null if one can not be produced
+*
+***********************************************************************/
+
+TIPERROR GEN_DTINFO::GetDynTypeMembers(DYN_TYPEMEMBERS **ppdtmbrs)
+{
+ TIPERROR err;
+
+ IfErrRet(m_pdtroot->GetDtmbrs(ppdtmbrs));
+
+ // Add reference
+ m_pdtroot->AddRefDtmbrs();
+
+ // Invalidate
+ // ilanc: 19-Nov-92: No need to decompile anymore -- since
+ // we're replacing the typemembers interface and implementation
+ // we cross our fingers and hope that no client of GetTypeMembers
+ // will attempt to edit the class definition... that is
+ // if its state isn't undeclared.
+ //
+ return TIPERR_None;
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::GetDefnTypeBind - return DefnTypeBind of the Type
+*Purpose:
+* TYPEMEMBERS must be laid out, if not, will attempt to layout.
+* NOTE: bumps refcount -- by deferring to
+* DYN_TYPEMEMBES::GetDefnTypeBind) -- hence client must Release().
+*
+*Entry:
+* None.
+*
+*Exit:
+* returns TypeBind instance or Null if one can not be produced
+*
+***********************************************************************/
+
+TIPERROR GEN_DTINFO::GetDefnTypeBind(DEFN_TYPEBIND **ppdfntbind)
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err = TIPERR_None;
+
+ IfErrRet( EnsureInDeclaredState() );
+
+ IfErrRet(m_pdtroot->GetDtmbrs(&pdtmbrs));
+
+ DebAssert(pdtmbrs != NULL, "whoops! null dtmbrs.");
+
+ return pdtmbrs->GetDefnTypeBind(ppdfntbind);
+
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::CreateInstance - return new instance of class
+*
+*Purpose: It returns a pointer to the active object for predeclared ID and
+* if the FAPPOBJECT flag is set. Otherwise call CoCreateInstance()
+* to get a pointer to the object.
+*
+*Entry:
+* iid : Guid of the object
+*
+*Exit:
+* lplpObj : Pointer to the object whose GUID is passed int.
+* HRESULT : if an error is returned then lplpObj is not modified.
+*
+***********************************************************************/
+
+
+// The Ole version of CreateInstance
+HRESULT GEN_DTINFO::CreateInstance(
+ IUnknown FAR* punkOuter,
+ REFIID riid,
+ LPLPVOID lplpObj)
+{
+ GUID guid;
+ HRESULT hresult;
+ IUnknown FAR* punk;
+
+ if (lplpObj == NULL) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+ *lplpObj = NULL;
+
+ // Create Instance can only be called for CoClasses
+ if(GetTypeKind() != TKIND_COCLASS)
+ return HresultOfTiperr(TIPERR_BadModuleKind);
+
+ // UNDONE: Bug #4849. I am certain that the following check is wrong
+ // for at least the CoCreateInstance class below -bradlo.
+
+ // we require that punkOuter be NULL in this version?
+ if (punkOuter != NULL)
+ return HresultOfScode(CLASS_E_NOAGGREGATION);
+
+ // Can't create instances if type hasn't been laid yet...
+ if (m_pdtroot->CompState() < CS_DECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ PgtlibOleContaining()->GetTypeGuid(GetIndex(), &guid);
+
+ // for predeclared Id we return the Active Object if there is one
+ if ((lplpObj == (LPLPVOID) &(m_pdtroot->m_punk)) &&
+ (m_pdtroot->m_uTypeFlags & TYPEFLAG_FAPPOBJECT)) {
+
+ hresult = GetActiveObject(guid, NULL, &punk);
+
+ // if the above call to GetActiveObject succeeded then return
+ // else fall through and try CoCreateInstance.
+ if (hresult == NOERROR) {
+ hresult = punk->QueryInterface(riid, lplpObj);
+ // if the QueryInterface fails for some reason we still want to
+ // release the object returned by GetActiveObject then return
+ // the error to the caller
+ punk->Release();
+ return hresult;
+ }
+ }
+
+ // create an instance of the object specified by guid
+ hresult = CoCreateInstance(guid,
+ NULL,
+ CLSCTX_SERVER,
+ riid,
+ lplpObj);
+ return hresult;
+}
+
+
+
+/***
+*PUBLIC GEN_DTINFO::GetMemberName
+* Not implemented.
+*
+*Purpose:
+* Returns name of a specified member
+*
+*Entry:
+* hmember - handle of the member whose name is to be returned
+* plstrName - returns lstr containing name
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR GEN_DTINFO::GetMemberName(HMEMBER hmember, BSTRA *plstrName)
+{
+ DebAssert(0, "GetMemberName -- not implemented");
+ return TIPERR_None;
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::CommitChanges
+* This function commits all the changes made in the module.
+*
+*Purpose:
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+TIPERROR GEN_DTINFO::CommitChanges()
+{
+return TIPERR_None;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GEN_DTINFO::SzTypeIdOfTypeInfo
+*Purpose:
+* Returns the TypeId of the TypeInfo instance
+*Entry:
+* None.
+*Exit:
+* TypeId of the TypeInfo instance
+***********************************************************************/
+
+LPOLESTR GEN_DTINFO::SzTypeIdofTypeInfo()
+{
+ return szProtocolName;
+}
+
+
+
+/***
+*PUBLIC GEN_DTINFO::Reset - Reset the global runtime state of this TYPEINFO.
+*Purpose:
+* This method resets the global runtime state of this GEN_DTINFO.
+*
+*Entry:
+* None.
+*
+*Exit:
+* TIPERROR
+***********************************************************************/
+
+#pragma code_seg( CS_CORE )
+TIPERROR GEN_DTINFO::ResetPrePass()
+{
+ TIPERROR err = TIPERR_None;
+ return TIPERR_None;
+}
+
+
+
+
+/***
+*PUBLIC GEN_DTINFO::Reset - Reset the global runtime state of this TYPEINFO.
+*Purpose:
+* This method resets the global runtime state of this GEN_DTINFO.
+*
+*Entry:
+* None.
+*
+*Exit:
+* TIPERROR
+***********************************************************************/
+
+#pragma code_seg( CS_CORE )
+TIPERROR GEN_DTINFO::Reset()
+{
+ TIPERROR err = TIPERR_None;
+
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+
+
+
+
+
+
+
+
+
+
+/***
+*GEN_DTINFO::MakeDual
+*Purpose:
+* Creates a dual typeinfo out of the current typeinfo.
+*
+*Entry:
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR GEN_DTINFO::MakeDual()
+{
+ GEN_DTINFO *pgdtinfoNew, *pgdtinfoInterface, *pgdtinfoDispatch;
+ UINT cRefsThis, cRefsNew;
+
+ TIPERROR err;
+
+ DebAssert(PgdtinfoPartner() == NULL, "Already have a partner.");
+
+ // Create the new partner typeinfo.
+ IfErrRet(Create(&pgdtinfoNew,
+ GetTypeKind() == TKIND_INTERFACE
+ ? TKIND_DISPATCH
+ : TKIND_INTERFACE,
+ FALSE, // !Basic
+ ACCESS_Public,
+ PgtlibOleContaining()->GetSyskind()));
+
+ // Determine which typeinfo is which.
+ pgdtinfoInterface = GetTypeKind() == TKIND_INTERFACE
+ ? this
+ : pgdtinfoNew;
+
+ pgdtinfoDispatch = GetTypeKind() == TKIND_DISPATCH
+ ? this
+ : pgdtinfoNew;
+
+ // Copy the attributes from us to the new typeinfo.
+ pgdtinfoNew->SetContainingTypeLib(PgtlibOleContaining());
+ pgdtinfoNew->SetHTEntry(GetIndex());
+
+ pgdtinfoNew->Pdtroot()->m_uTypeFlags = Pdtroot()->m_uTypeFlags
+ & (TYPEFLAG_FHIDDEN
+ | TYPEFLAG_FDUAL
+ | TYPEFLAG_FNONEXTENSIBLE);
+
+ pgdtinfoNew->Pdtroot()->m_wMajorVerNum = Pdtroot()->m_wMajorVerNum;
+ pgdtinfoNew->Pdtroot()->m_wMinorVerNum = Pdtroot()->m_wMinorVerNum;
+
+#if ID_DEBUG
+ // Copy the debug string info.
+ strcpy(pgdtinfoNew->m_szDebName, m_szDebName);
+#endif // ID_DEBUG
+
+ // Link them together.
+ SetPstltiPartner(pgdtinfoNew);
+ pgdtinfoNew->SetPstltiPartner(this);
+
+ // Sync their refcounts. We can do this because we are a
+ // friend of STL_TYPEINFO.
+ //
+ cRefsThis = (UINT)m_cRefs + (UINT)m_cInternalRefs;
+ cRefsNew = (UINT)pgdtinfoNew->m_cRefs + (UINT)pgdtinfoNew->m_cInternalRefs;
+
+ for (; cRefsThis > 0; cRefsThis--) {
+ AddPartnerRef();
+ }
+ for (; cRefsNew > 0; cRefsNew--) {
+ pgdtinfoNew->AddPartnerRef();
+ }
+
+ // If we're the interface, then we must change the ptinfo stored
+ // in the type_entry for the typeinfo to point to the
+ // dispinterface.
+ //
+ if (GetTypeKind() == TKIND_INTERFACE) {
+ TYPE_ENTRY *qte;
+
+ // If we're currently laid out, we must lay out the new
+ // typeinfo we just created.
+ //
+ if (Pdtroot()->CompState() > CS_UNDECLARED) {
+ IfErrGoTo(TiperrOfHresult(pgdtinfoNew->LayOut()), Error2);
+ }
+
+ // Update the information in the type entry.
+ qte = PgtlibOleContaining()->Qte(GetIndex());
+
+ qte->m_ste.m_typekind = TKIND_DISPATCH;
+ qte->m_pstltinfo = pgdtinfoDispatch;
+ }
+
+ SetIsDual(TRUE);
+ pgdtinfoNew->SetIsDual(TRUE);
+
+ goto Error;
+
+Error2:
+ SetPstltiPartner(NULL);
+
+Error:
+ RELEASE(pgdtinfoNew);
+
+ return err;
+}
+
+
+/***
+*DYN_TYPEROOT::MakeHimptypeLevels
+*Purpose:
+* Make sure LHrefOffset is set.
+*
+*Entry:
+* None.
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR DYN_TYPEROOT::MakeHimptypeLevels()
+{
+ ITypeInfo *ptinfo;
+ GEN_DTINFO *pgdtinfoBase;
+ IMPMGR *pimpmgr;
+ BOOL fGetInterface = FALSE;
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TYPE_DATA *ptdata;
+
+ TIPERROR err;
+
+ // We don't need to do anything if:
+ // - we've read or already calculated the offset
+ // - we're not a TKIND_INTERFACE
+ // - we're not laid out yet.
+ //
+ if (FUseHrefOffset()
+ || Pgdtinfo()->GetTypeKind() != TKIND_INTERFACE
+ || CompState() == CS_UNDECLARED) {
+
+ return TIPERR_None;
+ }
+
+ IfErrRet(GetDtmbrs(&pdtmbrs));
+ ptdata = pdtmbrs->Ptdata();
+
+ // Make sure our impmgr/dependencies are read.
+
+ // If we don't have a base class, set the offset to zero.
+ if (ptdata->CBase() == 0) {
+ SetLHrefOffset(0);
+ return TIPERR_None;
+ }
+
+ // Get our base class.
+ IfErrRet(ptdata->GetTypeInfoOfHvdefn(ptdata->HvdefnFirstBase(),
+ &ptinfo,
+ NULL));
+
+ if (ptinfo->QueryInterface(IID_TYPELIB_GEN_DTINFO,(LPVOID *)&pgdtinfoBase)
+ != NOERROR) {
+
+ ptinfo->Release();
+ return TIPERR_NotYetImplemented; // CONSIDER: better error?
+ }
+
+ // Make sure the base class has its HimptypeLevels set.
+ IfErrGo(pgdtinfoBase->Pdtroot()->MakeHimptypeLevels());
+ IfErrGo(pgdtinfoBase->Pdtroot()->GetImpMgr(&pimpmgr));
+
+ DebAssert(pgdtinfoBase->Pdtroot()->FUseHrefOffset(), "Must be set");
+
+ // Calculate the offset.
+ SetLHrefOffset(pgdtinfoBase->Pdtroot()->LHrefOffset()
+ + pimpmgr->GetImpTypeSize());
+
+Error:
+ pgdtinfoBase->Release();
+ ptinfo->Release();
+
+ return err;
+}
+
+
+#if ID_DEBUG
+
+/***
+*PUBLIC GEN_DTINFO::DebCheckState
+*Purpose:
+* Check internal state of GEN_DTINFO and its parts.
+* Delegates to DYN_TYPEROOT::DebCheckState
+*
+*Entry:
+* uLevel
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+VOID GEN_DTINFO::DebCheckState(UINT uLevel) const
+{
+ m_pdtroot->DebCheckState(uLevel);
+}
+
+
+
+
+#endif //ID_DEBUG
+
+//CONSIDER: The following new and delete operations can be used if a
+//CONSIDER: GEN_DTINFO instance is to be a member of a DYN_TYPEROOT,
+//CONSIDER: i.e. if for locality of reference the GEN_DTINFO resides
+//CONSIDER: in the DYN_TYPEROOT segment.
+//***
+//*PUBLIC GEN_DTINFO::operator new - allocates space for a GEN_DTINFO
+//*Purpose:
+//*
+//*Implementation Notes:
+//* Allocate a SHEAP_MGR segment and return a pointer to immediately
+//* following the sheap_mgr instance so the GEN_DTINFO
+//* will be constructed there
+//*
+//*Entry:
+//* size - always sizeof(GEN_DTINFO)
+//*
+//*Exit:
+//* None.
+//***********************************************************************/
+//
+//VOID *GEN_DTINFO::operator new(size_t size)
+//{
+// SHEAP_MGR *psheap_mgr = new SHEAP_MGR;
+//
+// DebAssert(psheap_mgr != 0, "Couldn't allocate sheap_mgr");
+// psheap_mgr->Init(sizeof(DYN_TYPEROOT));
+// return(psheap_mgr+1);
+//}
+//
+//
+///***
+//*PUBLIC GEN_DTINFO::operator delete - releases memory of GEN_DTINFO
+//*Purpose:
+//*
+//*Implementation Notes:
+//* Deletes the SHEAP_MGR segment
+//*
+//*Entry:
+//* pv - Pointer to where the GEN_DTINFO instance used to
+//* be within its SHEAP_MGR segment.
+//*
+//*Exit:
+//* None.
+//***********************************************************************/
+//
+//VOID GEN_DTINFO::operator delete(VOID *pv)
+//{
+// SHEAP_MGR *psheapmgr = (SHEAP_MGR *)pv;
+//
+// delete (SHEAP_MGR *)OOB_MAKEP(OOB_SELECTOROF(pv),0);
+//}
+
+
+/***
+*PUBLIC GEN_DTINFO::GetTypeAttr()
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+HRESULT GEN_DTINFO::GetTypeAttr(TYPEATTR FAR* FAR*pptypeattr)
+{
+ TYPEATTR *ptypeattr;
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TYPE_DATA *ptdata;
+ DYN_TYPEBIND *pdtbind;
+
+ USHORT cbSizeVft = 0;
+
+ TIPERROR err = TIPERR_None;
+ HRESULT hresult;
+
+ if (pptypeattr == NULL) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+
+ if (m_pdtroot->m_ptypeattrCache == NULL) {
+
+ // Can't get attributes unless been laid...
+ if (m_pdtroot->CompState() < CS_DECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ // use one allocation to get both ptypeattrCache and ptypeattrOut
+ ptypeattr = (TYPEATTR FAR*)MemZalloc(2*sizeof(TYPEATTR));
+ if (!ptypeattr) {
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+
+ // no need to zero these ase they are already zero from the MemZalloc
+ // idldesc
+ //ptypeattr->idldescType.wIDLFlags = 0;
+ //ptypeattr->idldescType.bstrIDLInfo = NULL;
+
+ //ptypeattr->lpstrSchema = NULL; // not used
+
+ ptypeattr->typekind = GetTypeKind();
+ ptypeattr->wTypeFlags = m_pdtroot->GetTypeFlags();
+
+ ptypeattr->wMajorVerNum = m_pdtroot->m_wMajorVerNum;
+ ptypeattr->wMinorVerNum = m_pdtroot->m_wMinorVerNum;
+
+ IfErrGo(GetLcid(&(ptypeattr->lcid)));
+ IfErrGo(m_pdtroot->GetDtmbrs(&pdtmbrs));
+
+ ptdata = pdtmbrs->Ptdata();
+
+ // Work out if we're a dispinterface defined in terms of an interface...
+ BOOL isFunkyDispinterface; // for the lack of a better name...
+ ITypeInfoA FAR* ptinfoBase;
+ TYPEATTR *ptypeattrBase;
+
+ IfErrGo(IsFunkyDispinterface(this, &isFunkyDispinterface));
+ if (isFunkyDispinterface) {
+ // HACK: Get the 2nd base class's vft size, and conclude that the
+ // func count in the "derived" dispinterface is just the
+ // the number of funcs in the interface's vft.
+ // The "right" way to do this is to recurse on the 2nd impltype.
+ // NOTE: we can't call GetImplTypeOfRefType for the 2nd base
+ // of a funky dispinterface because it will deny all knowledge
+ // of having one! So we delve into the gory internals...
+ //
+ // pseudo-base
+ //
+ IfOleErrGoTo(GetTypeInfoOfImplType(this, 1, &ptinfoBase),
+ Error1);
+ hresult = ptinfoBase->GetTypeAttr(&ptypeattrBase);
+ if (hresult != NOERROR) {
+ ptinfoBase->Release();
+ goto Error1;
+ }
+
+ ptypeattr->cFuncs = ptypeattrBase->cbSizeVft / sizeof(VOID *);
+
+ ptypeattr->cVars = 0; // can't have datamembers
+ ptypeattr->cImplTypes = 1; // only one true base: IDispatch
+ ptinfoBase->ReleaseTypeAttr(ptypeattrBase);
+ ptinfoBase->Release();
+ }
+ else
+ {
+ ptypeattr->cFuncs = ptdata->CAvailMeth();
+ ptypeattr->cVars = ptdata->CDataMember();
+ ptypeattr->cImplTypes = ptdata->CBase();
+ }
+
+ PgtlibOleContaining()->GetTypeGuid(GetIndex(), &ptypeattr->guid);
+
+ pdtbind = pdtmbrs->Pdtbind();
+
+ ptypeattr->cbAlignment = pdtbind->GetAlignment();
+ ptypeattr->cbSizeInstance = pdtbind->GetCbSize();
+ ptypeattr->cbSizeVft = pdtbind->GetCbSizeVft();
+
+ ptypeattr->memidConstructor = MEMBERID_NIL;
+ ptypeattr->memidDestructor = MEMBERID_NIL;
+
+ InitTypeDesc(&(ptypeattr->tdescAlias));
+
+ m_pdtroot->m_ptypeattrCache = ptypeattr;
+ m_pdtroot->m_ptypeattrOut = ptypeattr+1; // both typeattrs are allocated at once
+ m_pdtroot->m_ftypeattrOutUsed = FALSE;
+
+ } else {
+ ptdata = NULL; // in case we're an alias
+ } //if
+
+ if (m_pdtroot->m_ftypeattrOutUsed) {
+ // ptypeattrOut has been given out, so allocate memory to make a copy
+ // of the cached type attr
+ ptypeattr = (TYPEATTR FAR*)MemZalloc(sizeof(TYPEATTR));
+ if (!ptypeattr) {
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+ } else {
+ // use the pre-allocated ptypeattr pointer
+ ptypeattr = m_pdtroot->m_ptypeattrOut;
+ m_pdtroot->m_ftypeattrOutUsed = TRUE;
+ }
+
+ // copy
+ memcpy(ptypeattr, m_pdtroot->m_ptypeattrCache, sizeof(TYPEATTR));
+
+
+ if (GetTypeKind() == TKIND_ALIAS) {
+ if (ptdata == NULL) {
+ // if we're getting it from the cached typeattr, must set up this stuff
+ IfErrGo(m_pdtroot->GetDtmbrs(&pdtmbrs));
+ ptdata = pdtmbrs->Ptdata();
+ }
+ // get the type desc from the type data
+ IfErrGo(ptdata->AllocTypeDescOfTypeDefn(ptdata->HtdefnAlias(),
+ ptdata->IsSimpleTypeAlias(),
+ &(ptypeattr->tdescAlias)));
+ }
+
+ *pptypeattr = ptypeattr;
+ return NOERROR;
+
+Error:
+ hresult = HresultOfTiperr(err);
+ // fall through...
+Error1:
+ ReleaseTypeAttr(ptypeattr); // can pass in NULL.
+ return hresult;
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::ReleaseFuncDesc(FUNCDESC FAR*pFuncDesc)
+*Purpose: Free this data structure and anything it points to
+* directly or indirectly
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+VOID GEN_DTINFO::ReleaseFuncDesc(FUNCDESC FAR*pFuncDesc)
+{
+ FreeFuncDesc(pFuncDesc);
+}
+
+/***
+*PUBLIC GEN_DTINFO::ReleaseVarDesc(VARDESC FAR*pVarDesc)
+*Purpose: Free this data structure and anything it points to
+* directly or indirectly
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+VOID GEN_DTINFO::ReleaseVarDesc(VARDESCA FAR*pVarDesc)
+{
+ FreeVarDesc(pVarDesc);
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::ReleaseTypeAttr(TYPEATTR FAR*ptypeattr)
+*Purpose: Free this data structure and anything it points to
+* directly or indirectly
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+VOID GEN_DTINFO::ReleaseTypeAttr(TYPEATTR FAR*ptypeattr)
+{
+ if (ptypeattr != NULL) {
+ ClearTypeDesc(&(ptypeattr->tdescAlias));
+ if (ptypeattr == m_pdtroot->m_ptypeattrOut) {
+ DebAssert(m_pdtroot->m_ftypeattrOutUsed, "Cached typeattr released twice");
+ m_pdtroot->m_ftypeattrOutUsed = FALSE;
+ } else
+ MemFree(ptypeattr);
+ }
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::GetTypeComp(ITypeCompA FAR* FAR*)
+*Purpose:
+*
+*Entry:
+* pptcomp OUT
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+HRESULT GEN_DTINFO::GetTypeComp(ITypeCompA FAR* FAR* pptcomp)
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ DYN_TYPEBIND *pdtbind;
+ CDefnTypeComp *pdfntcomp;
+ TIPERROR err = TIPERR_None;
+
+ if (pptcomp == NULL) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+ // Can't get an ITypeCompA if type hasn't been laid yet...
+ if (m_pdtroot->CompState() < CS_DECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ IfErrGo(m_pdtroot->GetDtmbrs(&pdtmbrs));
+
+ DebAssert(pdtmbrs != NULL, "whoops! null dtmbrs.");
+
+ // Note no need to bump refcount here since the CDefnTypeComp
+ // instance that we create will do so.
+ //
+ pdtbind = pdtmbrs->Pdtbind();
+
+ // Create a CDefnTypeComp to return to the user who must
+ // must release it eventually...
+ //
+ IfErrGo(CDefnTypeComp::Create(&pdfntcomp, pdtbind));
+ *pptcomp = pdfntcomp;
+
+Error:
+ return HresultOfTiperr(err);
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::GetNames()
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+HRESULT GEN_DTINFO::GetNames(MEMBERID memid,
+ BSTR FAR* rgbstrNames,
+ UINT cNameMax,
+ UINT FAR* lpcName)
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+ ITypeInfoA FAR* ptinfo;
+ HRESULT hresult;
+
+ if (rgbstrNames == NULL || lpcName == NULL) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+ // Can't get attributes if type hasn't been laid yet...
+ if (m_pdtroot->CompState() < CS_DECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ if ((err = m_pdtroot->GetDtmbrs(&pdtmbrs)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+ // only works with things that can have members
+ if (GetTypeKind() == TKIND_ALIAS) {
+ err = TIPERR_BadModuleKind;
+ }
+ else {
+ BOOL isFunkyDispinterface;
+ IfErrGo(IsFunkyDispinterface(this, &isFunkyDispinterface));
+ if (isFunkyDispinterface) {
+ GEN_DTINFO *pgdtinfo;
+ USHORT cNamCount;
+
+ //CONSIDER: share code with code below
+ IfOleErrRet(GetTypeInfoOfImplType(this, 1, &ptinfo)); // pseudo-base
+ hresult = ptinfo->GetNames(memid, rgbstrNames, cNameMax, lpcName);
+
+ // Determine if the funcdesc for this memid has a retval parameter.
+ if (hresult == NOERROR) {
+ hresult = ptinfo->QueryInterface(IID_TYPELIB_GEN_DTINFO, (VOID **)&pgdtinfo);
+ DebAssert(hresult == NOERROR, "Must be typeinfo GDTINFO!");
+
+ // If we have a retval/lcid, remove the last names.
+ if (pgdtinfo->Pdtroot()->IsIdMungable(memid, &cNamCount)
+ && cNameMax >= cNamCount) {
+
+ for (;*lpcName > cNamCount;) {
+ *lpcName -= 1;
+ FreeBstr(rgbstrNames[*lpcName]);
+ rgbstrNames[*lpcName] = NULL;
+ }
+ }
+
+ pgdtinfo->Release();
+ }
+
+ ptinfo->Release();
+ return hresult;
+ }
+ err = pdtmbrs->Ptdata()->GetNames(memid, rgbstrNames, cNameMax, lpcName);
+ if (err == TIPERR_ElementNotFound && pdtmbrs->Ptdata()->CBase() > 0) {
+ // if not found locally, try recursing on base class, if any
+ // Note we only recurse on the FIRST base class (except for COCLASS's).
+ //
+
+ UINT index = 0;
+ INT impltypeflags;
+ if (GetTypeKind() == TKIND_COCLASS) {
+ for (;;index++) {
+ IfOleErrRet(GetImplTypeFlags(index, &impltypeflags))
+ // if no 'default' base interface, this will return
+ // TIPERR_ElementNotFound (mapped to a HRESULT), which is exactly
+ // what we want.
+ if (impltypeflags == IMPLTYPEFLAG_FDEFAULT) {
+ break; // found it
+ }
+ }
+ }
+
+ IfOleErrRet(GetTypeInfoOfImplType(this, index, &ptinfo));
+ hresult = ptinfo->GetNames(memid, rgbstrNames, cNameMax, lpcName);
+ ptinfo->Release();
+ return hresult;
+ }
+ }
+
+Error:
+ return HresultOfTiperr(err);
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::GetRefTypeInfoOfImplType(UINT, HREFTYPE FAR*)
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+HRESULT GEN_DTINFO::GetRefTypeOfImplType(UINT index,
+ HREFTYPE FAR* phreftype)
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+
+ if (phreftype == NULL) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+
+ // Can't get base list if construct member lists hasn't run
+ if (m_pdtroot->CompState() < CS_SEMIDECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ if ((err = m_pdtroot->GetDtmbrs(&pdtmbrs)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+
+
+ // Can't get at our partner unless we're flagged as a
+ // dual interface and the passed in index is -1.
+ //
+ if (Pdtroot()->GetTypeFlags() & TYPEFLAG_FDUAL
+ && index == (UINT)-1) {
+
+ DebAssert(PgdtinfoPartner() != NULL, "Bad dual");
+
+ *phreftype = HREFTYPE_FUNKY_SIGNAL_PARTNER;
+
+ return NOERROR;
+ }
+
+ // only works for classes
+ switch (GetTypeKind()) {
+ case TKIND_DISPATCH:
+ BOOL isFunkyDispinterface;
+ IfErrGo(IsFunkyDispinterface(this, &isFunkyDispinterface));
+ if (isFunkyDispinterface) {
+ if (index > 0) {
+ err = TIPERR_ElementNotFound;
+ goto Error;
+ }
+
+ // If we're trying to get the first base class of the
+ // funky dispinterface, return HREFTYPE_FUNKY_SIGNAL.
+ //
+#if ID_DEBUG
+ err = pdtmbrs->Ptdata()->GetRefTypeOfImplType(index, phreftype);
+
+ // Parallel code in GetRefTypeInfo assumes it can convert
+ // HREFTYPE_FUNKY_SIGNAL_DISPATCH to HREFTYPE_FUNKY_DISPATCH.
+ //
+ DebAssert (err != TIPERR_None || *phreftype == HREFTYPE_FUNKY_DISPATCH,
+ "IDispatch must be first");
+#endif //ID_DEBUG
+
+ *phreftype = HREFTYPE_FUNKY_SIGNAL_DISPATCH; // signal funky dispinterface
+
+ break;
+ } // isFunkyDispinterface
+
+ // fall through...
+
+ case TKIND_COCLASS :
+
+ case TKIND_INTERFACE :
+ err = pdtmbrs->Ptdata()->GetRefTypeOfImplType(index, phreftype);
+ break;
+ default :
+ err = TIPERR_BadModuleKind;
+ break;
+ } // switch
+
+Error:
+ return HresultOfTiperr(err);
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::GetImplTypeFlags(UINT, INT FAR*)
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+HRESULT GEN_DTINFO::GetImplTypeFlags(UINT index,
+ INT FAR* pimpltypeflags)
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+
+ if (pimpltypeflags == NULL) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+ if ((err = m_pdtroot->GetDtmbrs(&pdtmbrs)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+
+ err = pdtmbrs->Ptdata()->GetImplTypeFlags(index, pimpltypeflags);
+
+ return HresultOfTiperr(err);
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::GetDocumentation(ID, BSTR FAR*, BSTR FAR*, DWORD FAR*, BSTR FAR *)
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg( CS_CORE2 )
+HRESULT GEN_DTINFO::GetDocumentation(MEMBERID memid,
+ BSTR FAR*lpbstrName,
+ BSTR FAR*lpbstrDocString,
+ DWORD FAR*lpdwHelpContext,
+ BSTR FAR *lpbstrHelpFile)
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ HRESULT hresult;
+ TIPERROR err;
+ ITypeInfoA FAR* ptinfo;
+
+ if (memid == MEMBERID_NIL) {
+ // get module documentation from typelib
+ return PgtlibOleContaining()->GetDocumentation(
+ GetIndex(),
+ lpbstrName,
+ lpbstrDocString,
+ lpdwHelpContext,
+ lpbstrHelpFile);
+ }
+
+ if ((err = m_pdtroot->GetDtmbrs(&pdtmbrs)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+
+ BOOL isFunkyDispinterface;
+ IfOleErrRet(HresultOfTiperr(IsFunkyDispinterface(
+ this,
+ &isFunkyDispinterface)));
+ if (isFunkyDispinterface) {
+ //CONSIDER: share code with code below
+ IfOleErrRet(GetTypeInfoOfImplType(
+ this,
+ 1,
+ &ptinfo)); // pseudo-base
+ hresult = ptinfo->GetDocumentation(memid,
+ lpbstrName,
+ lpbstrDocString,
+ lpdwHelpContext,
+ lpbstrHelpFile);
+ ptinfo->Release();
+ return hresult;
+ }
+ err = pdtmbrs->Ptdata()->GetDocumentation(memid,
+ lpbstrName,
+ lpbstrDocString,
+ lpdwHelpContext);
+ if (err == TIPERR_ElementNotFound && pdtmbrs->Ptdata()->CBase() > 0) {
+ // if not found locally, try recursing on base class, if any
+ // Note we only recurse on FIRST base class (except for COCLASS's)
+ //
+ UINT index = 0;
+ INT impltypeflags;
+ if (GetTypeKind() == TKIND_COCLASS) {
+ for (;;index++) {
+ IfOleErrRet(GetImplTypeFlags(index, &impltypeflags))
+ // if no 'default' base interface, this will return
+ // TIPERR_ElementNotFound (mapped to a HRESULT), which is exactly
+ // what we want.
+ if (impltypeflags == IMPLTYPEFLAG_FDEFAULT) {
+ break; // found it
+ }
+ }
+ }
+
+ IfOleErrRet(GetTypeInfoOfImplType(this, index, &ptinfo));
+ hresult = ptinfo->GetDocumentation(memid,
+ lpbstrName,
+ lpbstrDocString,
+ lpdwHelpContext,
+ lpbstrHelpFile);
+ ptinfo->Release();
+ return hresult;
+ }
+
+ if (err != TIPERR_None)
+ return HresultOfTiperr(err);
+
+ // get help file from typelib, if requested
+
+ // Though we could do without the following check, I've added it as a
+ // speed optimization, as the Layout code calls this function.
+ if (lpbstrHelpFile == NULL) {
+ return NOERROR;
+ }
+
+ hresult = PgtlibOleContaining()->GetDocumentation(-1,
+ NULL,
+ NULL,
+ NULL,
+ lpbstrHelpFile);
+ if (hresult != NOERROR) {
+ // free any alloced strings
+ if (lpbstrName) {
+ SysFreeString(*lpbstrName);
+ *lpbstrName = NULL;
+ }
+ if (lpbstrDocString) {
+ SysFreeString(*lpbstrDocString);
+ *lpbstrDocString = NULL;
+ }
+ }
+
+ return hresult;
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC GEN_DTINFO::GetRefTypeInfo(UINT, ITypeInfoA FAR* FAR*)
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+HRESULT GEN_DTINFO::GetRefTypeInfo(HREFTYPE hreftype,
+ ITypeInfoA FAR* FAR* pptinfo)
+{
+ IMPMGR *pimpmgr;
+ TIPERROR err = TIPERR_None;
+
+ // CONSIDER: (dougf) how to validate hreftype?
+ if (pptinfo == NULL) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+ BOOL isFunkyDispinterface;
+ ITypeInfoA FAR* ptinfoBase, *ptinfoDisp = NULL;
+ HRESULT hresult;
+ GEN_DTINFO *pgdtinfoBase = NULL;
+ BOOL fGetInterface;
+
+ // If the low bit of the hreftype is set, we want to get this
+ // type's interface (assuming its a dual).
+ //
+ fGetInterface = (BOOL)(hreftype & 0x00000001);
+ hreftype &= ~0x00000001;
+
+ if (hreftype == HREFTYPE_FUNKY_SIGNAL_PARTNER) {
+ // They want our partner...so give it to them.
+ DebAssert(PgdtinfoPartner() != NULL, "Not a dual");
+
+ *pptinfo = PgdtinfoPartner();
+ (*pptinfo)->AddRef();
+
+ goto Error;
+ }
+
+ IfErrGo(IsFunkyDispinterface(this, &isFunkyDispinterface));
+ if (isFunkyDispinterface) {
+ // defer to pseudo-base UNLESS this hreftype came from
+ // GetRefTypeInfoOfImplType where the hreftype for the base of a
+ // Funky dispinterface is being returned. In that case, we've got a
+ // special value HREFTYPE_FUNKY_SIGNAL, which means that we're just
+ // supposed to return the typeinfo for the first base (HREFTYPE_FUNKY).
+
+ if (hreftype == HREFTYPE_FUNKY_SIGNAL_DISPATCH) {
+ hreftype = HREFTYPE_FUNKY_DISPATCH;
+ }
+ else {
+ // get the first interface in the inheritance heirarchy
+ IfOleErrRet(GetTypeInfoOfImplType(this, 1, &ptinfoBase));
+
+ // Must ensure this is one of "our" typeinfo's in order to do the cast
+ hresult = ptinfoBase->QueryInterface(IID_TYPELIB_GEN_DTINFO,
+ (LPVOID *)&pgdtinfoBase);
+ ptinfoBase->Release();
+ if (hresult != NOERROR) {
+ return HresultOfScode(E_NOTIMPL); // CONSIDER: better error?
+ }
+
+ while (!pgdtinfoBase->Pdtroot()->FUseHrefOffset()
+ || !pgdtinfoBase->Pdtroot()->IsHimptypeLevel(hreftype)) {
+ // recurse on first base (assumes no multiple-inheritance)
+ // We could use our internal gory implementation details here...
+ // but we don't, cos it would be a bloody mess.
+ // Note: only support single inheritance here...
+ //
+ hresult = GetTypeInfoOfImplType(pgdtinfoBase, 0, &ptinfoBase);
+ pgdtinfoBase->Release();
+ if (hresult != NOERROR) {
+ return hresult;
+ }
+ // Must ensure this is one of "our" typeinfo's in order to do the cast
+ hresult = ptinfoBase->QueryInterface(IID_TYPELIB_GEN_DTINFO,
+ (LPVOID *)&pgdtinfoBase);
+ ptinfoBase->Release();
+ if (hresult != NOERROR) {
+ return HresultOfScode(E_NOTIMPL); // CONSIDER: better error?
+ }
+ }
+
+ IfErrGo(pgdtinfoBase->Pdtroot()->GetImpMgr(&pimpmgr));
+ err = pimpmgr->GetTypeInfo(pgdtinfoBase->Pdtroot()
+ ->HimptypeOfHreftype(hreftype),
+ DEP_None, pptinfo);
+
+ goto GetInterface;
+ }
+ // fall into original code
+ }
+
+ IfErrGo(Pdtroot()->GetImpMgr(&pimpmgr));
+ IfErrGo(pimpmgr->GetTypeInfo(Pdtroot()->HimptypeOfHreftype(hreftype),
+ DEP_None,
+ pptinfo));
+ // fall through...
+
+GetInterface:
+
+ // Check to see if we should load the interface of the
+ // just gotten dual interface.
+ //
+ if (fGetInterface) {
+ TYPEATTR *ptypeattr;
+ TYPEKIND tkind;
+
+ ptinfoDisp = *pptinfo;
+
+ IfErrGo(TiperrOfHresult(ptinfoDisp->GetTypeAttr(&ptypeattr)));
+ tkind = ptypeattr->typekind;
+ DebAssert(ptypeattr->wTypeFlags & TYPEFLAG_FDUAL, "Not a dual");
+ ptinfoDisp->ReleaseTypeAttr(ptypeattr);
+
+ if (tkind == TKIND_DISPATCH) {
+ // Get the other interface.
+ IfErrGo(TiperrOfHresult(ptinfoDisp->GetRefTypeOfImplType((UINT)-1,
+ &hreftype)));
+ IfErrGo(TiperrOfHresult(ptinfoDisp->GetRefTypeInfo(hreftype,
+ pptinfo)));
+ }
+ else {
+ ptinfoDisp = NULL;
+ }
+ }
+
+Error:
+ RELEASE(ptinfoDisp);
+ RELEASE(pgdtinfoBase);
+ return HresultOfTiperr(err);
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::GetDllEntry(MEMBERID, INVOKEKIND, BSTR FAR*, BSTR FAR*, WORD FAR*)
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+* CONSIDER: this code looks a lot like AddressOfMember() below.
+* CONSIDER: maybe some of it could be shared?
+***********************************************************************/
+HRESULT GEN_DTINFO::GetDllEntry(MEMBERID memid,
+ INVOKEKIND invokekind,
+ BSTR FAR* lpbstrDllName,
+ BSTR FAR* lpbstrName,
+ WORD FAR* lpwOrdinal)
+{
+ TIPERROR err;
+ HFUNC_DEFN hfdefn;
+ FUNC_DEFN *qfdefn;
+ DYN_TYPEMEMBERS *pdtmbrs;
+ HDLLENTRY_DEFN hdllentrydefn;
+ ENTRYMGR *pentrymgr;
+ NAMMGR *pnammgr;
+ HLNAM hlnam;
+ XCHAR rgBuffer[255];
+ DLLENTRY_DEFN *qdllentrydefn;
+
+
+ if (memid == MEMBERID_NIL) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+ if ((invokekind & (INVOKE_FUNC | INVOKE_PROPERTYGET | INVOKE_PROPERTYPUT | INVOKE_PROPERTYPUTREF)) == 0) { // one of the bits must be set
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+ // Can't get attributes if type hasn't been laid yet...
+ if (m_pdtroot->CompState() < CS_DECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ // Get the DYN_TYPEMEMBERS
+ if ((err = m_pdtroot->GetDtmbrs(&pdtmbrs)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+
+ // Get the ENTRYMGR
+ if ((err = m_pdtroot->GetEntMgr(&pentrymgr)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+
+ // Get the NAMMGR
+ if ((err = m_pdtroot->GetNamMgr(&pnammgr)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+
+ // check if the member whose address is requested is a function.
+ // If it is not a function then return error.
+ //
+ hfdefn = pdtmbrs->Ptdata()->HfdefnOfHmember((HMEMBER) memid, invokekind);
+ if (hfdefn == HFUNCDEFN_Nil) {
+ return HresultOfTiperr(TIPERR_ElementNotFound);
+ }
+
+ // Get the address of the FUNC_DEFN
+ qfdefn = pdtmbrs->Ptdata()->QfdefnOfHfdefn(hfdefn);
+
+ // Is it a DLL function ?
+ if ((GetTypeKind() != TKIND_MODULE) ||
+ (hdllentrydefn = qfdefn->Hdllentrydefn()) == HDLLENTRYDEFN_Nil) {
+ return HresultOfTiperr(TIPERR_BadModuleKind);
+ }
+
+ if (lpbstrDllName) {
+ hlnam = pentrymgr->DllNameOfHdllentrydefn(hdllentrydefn);
+ if ((err = pnammgr->BstrWOfHlnam(hlnam, lpbstrDllName)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+ }
+
+ if (pentrymgr->HasOrdinalOfHdllentrydefn(hdllentrydefn)) {
+ // call-by-ordinal
+ if (lpwOrdinal) {
+ *lpwOrdinal = pentrymgr->OrdinalOfHdllentrydefn(hdllentrydefn);
+ }
+ if (lpbstrName) {
+ *lpbstrName = NULL; // no name
+ }
+ }
+ else {
+ // call by name
+ if (lpwOrdinal) {
+ *lpwOrdinal = 0; // no ordinal
+ }
+
+ if (lpbstrName) {
+
+ // Get the entry name from the entry manager.
+ qdllentrydefn = pentrymgr->QdllentrydefnOfHdllentrydefn(hdllentrydefn);
+
+ err = pentrymgr->DllEntryNameOfHchunk(qdllentrydefn->HchunkDllEntry(),
+ rgBuffer,
+ sizeof(rgBuffer));
+
+ if (err == TIPERR_None) {
+#if OE_WIN32
+ int cchUnicode, cbBuffer;
+
+ cbBuffer = xstrblen0(rgBuffer);
+ cchUnicode = MultiByteToWideChar(CP_ACP, 0, rgBuffer, cbBuffer, NULL, 0);
+ if (cchUnicode == 0)
+ err = TIPERR_OutOfMemory;
+ else {
+ if ((*lpbstrName = AllocBstrLen(NULL, cchUnicode)) == NULL)
+ err = TIPERR_OutOfMemory;
+ else
+ NoAssertRetail(MultiByteToWideChar(CP_ACP, 0, rgBuffer, cbBuffer, *lpbstrName, cchUnicode), "");
+ }
+#else
+ if ((*lpbstrName = AllocBstr(rgBuffer)) == NULL) {
+ err = TIPERR_OutOfMemory;
+ }
+#endif
+ }
+
+ if (err != TIPERR_None) {
+ if (lpbstrDllName) {
+ SysFreeString(*lpbstrDllName);
+ }
+ return HresultOfTiperr(err);
+ }
+ }
+ }
+
+ return NOERROR;
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::AddressOfMember(ID, INVOKEKIND, VOID FAR* FAR*)
+*Purpose: Returns the addess of the member identified by ID.
+*
+*Entry:
+* ID : identifies the member.
+* INOKEKIND : specifies the invoke kind (GET, LET or SET)
+*
+*Exit:
+* VOID FAR* FAR* : address of the member.
+* HRESULT : error
+* None.
+*
+***********************************************************************/
+HRESULT GEN_DTINFO::AddressOfMember(MEMBERID memid,
+ INVOKEKIND invokekind,
+ VOID FAR* FAR* ppv)
+{
+ TIPERROR err = TIPERR_None;
+ HFUNC_DEFN hfdefn;
+ FUNC_DEFN *qfdefn;
+ DYN_TYPEMEMBERS *pdtmbrs;
+ HDLLENTRY_DEFN hdllentrydefn;
+ ENTRYMGR *pentrymgr;
+
+
+ // Can't get address if type hasn't been laid yet...
+ if (m_pdtroot->CompState() < CS_DECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ if (memid == MEMBERID_NIL || ppv == NULL) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+ if ((invokekind & (INVOKE_FUNC | INVOKE_PROPERTYGET | INVOKE_PROPERTYPUT | INVOKE_PROPERTYPUTREF)) == 0) { // one of the bits must be set
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+ // if memid represents the PREDECLARED identifier then return the
+ // pointer to the ModuleInstance.
+ if (memid == ID_DEFAULTINST) {
+ if (!((m_pdtroot->m_typekind == TKIND_COCLASS
+ )
+ && m_pdtroot->GetTypeFlags()
+ & (TYPEFLAG_FAPPOBJECT | TYPEFLAG_FPREDECLID))) {
+
+ return HresultOfTiperr(TIPERR_ElementNotFound);
+ }
+
+#if OE_WIN32
+#if _X86_
+ if (g_fWin32s) {
+ *ppv = &(m_pdtroot->m_punk);
+ }
+ else
+#endif //_X86_
+ {
+ if (Pdtroot()->m_htinfo == HTINFO_Nil) {
+ GUID guid;
+
+ PgtlibOleContaining()->GetTypeGuid(GetIndex(), &guid);
+
+ IfErrRet(g_AppObjectTable.AddTypeInfo(&guid,
+ &Pdtroot()->m_htinfo));
+ }
+
+ g_AppObjectTable.AddressOfAppObject(Pdtroot()->m_htinfo,
+ ppv);
+ }
+#else // !OE_WIN32
+ *ppv = &(m_pdtroot->m_punk);
+#endif // !OE_WIN32
+
+ return NOERROR;
+ }
+
+ // UNDONE :: VBA3 Before returning the address we need to ensure that
+ // the class/module is in ADDRESSABLE state.
+
+ // Get the DYN_TYPEMEMBERS
+ if ((err = m_pdtroot->GetDtmbrs(&pdtmbrs)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+
+ // Get the ENTRYMGR
+ if ((err = m_pdtroot->GetEntMgr(&pentrymgr)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+
+ // check if the member whose address is requested is a function.
+ // If it is not a function then return error.
+ //
+ hfdefn = pdtmbrs->Ptdata()->HfdefnOfHmember((HMEMBER) memid, invokekind);
+ if (hfdefn == HFUNCDEFN_Nil) {
+ return HresultOfTiperr(TIPERR_ElementNotFound);
+ }
+
+ // Get the address of the FUNC_DEFN
+ qfdefn = pdtmbrs->Ptdata()->QfdefnOfHfdefn(hfdefn);
+
+ // Is it a DLL function ?
+ if ((GetTypeKind() != TKIND_MODULE) ||
+ (hdllentrydefn = qfdefn->Hdllentrydefn()) == HDLLENTRYDEFN_Nil) {
+ return HresultOfTiperr(TIPERR_BadModuleKind);
+ }
+
+ // Get the address of the the function.
+#if OE_MACPPC
+ if ( err = pentrymgr->GetAddressOfDllentry(hdllentrydefn, ppv, NULL)) {
+#else // OE_MACPPC
+ if ( err = pentrymgr->GetAddressOfDllentry(hdllentrydefn, ppv)) {
+#endif // OE_MACPPC
+ return HresultOfTiperr(err);
+ }
+
+ return HresultOfTiperr(err);
+}
+
+#pragma code_seg(CS_RARE)
+/***
+*PUBLIC GEN_DTINFO::GetMops(MEMBERID, BSTR FAR*)
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+HRESULT GEN_DTINFO::GetMops(MEMBERID memid, BSTR FAR* lpbstrMops)
+{
+ if (lpbstrMops == NULL) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+ // Can't get attributes if type hasn't been laid yet...
+ if (m_pdtroot->CompState() < CS_DECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ // Return a Null string
+ *lpbstrMops = NULL;
+
+ return NOERROR;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GEN_DTINFO::SetGuid(REFGUID)
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+HRESULT GEN_DTINFO::SetGuid(REFGUID guid)
+{
+ // Can't modify type unless still in undeclared.
+ if (m_pdtroot->CompState() > CS_UNDECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ PgtlibOleContaining()->SetTypeGuid(GetIndex(), guid);
+ return NOERROR;
+}
+#pragma code_seg()
+
+/***
+*PUBLIC GEN_DTINFO::SetDocString(LPOLESTR)
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+HRESULT GEN_DTINFO::SetDocString(LPOLESTR lpstrDoc)
+{
+ HRESULT hresult;
+
+ // Can't modify type unless still in undeclared.
+ if (m_pdtroot->CompState() > CS_UNDECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ hresult = HresultOfTiperr(PgtlibOleContaining()->SetTypeDocString(GetIndex(), lpstrDoc));
+
+ return hresult;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GEN_DTINFO::SetHelpContext(DWORD)
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+HRESULT GEN_DTINFO::SetHelpContext(DWORD dwHelpContext)
+{
+ // Can't modify type unless still in undeclared.
+ if (m_pdtroot->CompState() > CS_UNDECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ return HresultOfTiperr(PgtlibOleContaining()->SetTypeHelpContext(GetIndex(), dwHelpContext));
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GEN_DTINFO::SetVersion(WORD, WORD)
+*Purpose:
+*
+*Entry:
+* wMajorVerNum - Major version number for the type
+* wMinorVerNum - Minor version number for the type
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+HRESULT GEN_DTINFO::SetVersion(WORD wMajorVerNum, WORD wMinorVerNum)
+{
+ // Can't modify type unless still in undeclared.
+ if (m_pdtroot->CompState() > CS_UNDECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ m_pdtroot->m_wMajorVerNum = wMajorVerNum;
+ m_pdtroot->m_wMinorVerNum = wMinorVerNum;
+
+ // If this is a dual interface, we must update out partner.
+ if (IsDual()) {
+ PgdtinfoPartner()->Pdtroot()->m_wMajorVerNum = wMajorVerNum;
+ PgdtinfoPartner()->Pdtroot()->m_wMinorVerNum = wMinorVerNum;
+ }
+
+ return NOERROR;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GEN_DTINFO::SetTypeFlags(UINT uTypeFlags)
+*Purpose:
+*
+*Entry:
+* uTypeFlags - type flags to set.
+*
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+HRESULT GEN_DTINFO::SetTypeFlags(UINT uTypeFlags)
+{
+ TYPEKIND tkind;
+ HRESULT hresult = NOERROR;
+
+ // Can't modify type unless still in undeclared.
+ if (m_pdtroot->CompState() > CS_UNDECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ DebAssert( ((uTypeFlags & ~(TYPEFLAG_FAPPOBJECT
+ | TYPEFLAG_FCANCREATE
+ | TYPEFLAG_FLICENSED
+ | TYPEFLAG_FPREDECLID
+ | TYPEFLAG_FHIDDEN
+ | TYPEFLAG_FCONTROL
+ | TYPEFLAG_FDUAL
+ | TYPEFLAG_FNONEXTENSIBLE
+ | TYPEFLAG_FOLEAUTOMATION
+ )) == 0),
+ " SetTypeFlags passed invalid flags " );
+
+ tkind = GetTypeKind();
+ switch (tkind) {
+ case TKIND_COCLASS:
+ if (uTypeFlags & ~(TYPEFLAG_FAPPOBJECT
+ | TYPEFLAG_FCANCREATE
+ | TYPEFLAG_FLICENSED
+ | TYPEFLAG_FPREDECLID
+ | TYPEFLAG_FHIDDEN
+ | TYPEFLAG_FCONTROL)) {
+ return HresultOfScode(TYPE_E_BADMODULEKIND);
+ }
+ break;
+ case TKIND_INTERFACE:
+ if (uTypeFlags & ~(TYPEFLAG_FHIDDEN
+ | TYPEFLAG_FDUAL
+ | TYPEFLAG_FNONEXTENSIBLE
+ | TYPEFLAG_FOLEAUTOMATION)) {
+ return HresultOfScode(TYPE_E_BADMODULEKIND);
+ }
+ break;
+ case TKIND_DISPATCH:
+ if (uTypeFlags & ~(TYPEFLAG_FHIDDEN
+ | TYPEFLAG_FDUAL
+ | TYPEFLAG_FNONEXTENSIBLE)) {
+ return HresultOfScode(TYPE_E_BADMODULEKIND);
+ }
+ break;
+
+ case TKIND_ALIAS:
+ case TKIND_MODULE:
+ case TKIND_ENUM:
+ case TKIND_RECORD:
+ case TKIND_UNION:
+ if ((uTypeFlags & ~(TYPEFLAG_FHIDDEN))) {
+ return HresultOfScode(TYPE_E_BADMODULEKIND);
+ }
+ break;
+
+ default:
+ DebHalt("bad TKIND");
+ }
+
+ // WARNING -- this is a bit field -- if you add support for new bits,
+ // you must expand the definition of m_uTypeFlags.
+ m_pdtroot->m_uTypeFlags = uTypeFlags;
+
+ // If we're already a dual interface, copy the new typeflags
+ // to our partner.
+ //
+ if (IsDual()) {
+ PgdtinfoPartner()->Pdtroot()->m_uTypeFlags = uTypeFlags;
+ }
+
+ // If we're setting the FDUAL bit, turn this interface into
+ // a dual interface.
+ //
+ if (uTypeFlags & TYPEFLAG_FDUAL && !IsDual()) {
+ PgtlibOleContaining()->SetDualTypeLib();
+ IfOleErrRet(HresultOfTiperr(MakeDual()));
+ }
+
+ // If we change this to an appobject, we must update it in the
+ // project-level binding table. The easiest way to do this is to
+ // remove it from the table then readd it.
+ //
+ if (tkind == TKIND_COCLASS &&
+ uTypeFlags & TYPEFLAG_FAPPOBJECT) {
+
+ BSTR bstrName = NULL;
+ GENPROJ_TYPEBIND *pgptbind;
+#if OE_WIN32
+ LPSTR lpstr = NULL;
+#endif
+
+ pgptbind = PgtlibOleContaining()->Pgptbind();
+
+ IfOleErrRet(GetDocumentation(-1, &bstrName, NULL, NULL, NULL));
+
+ IfOleErrGo(HresultOfTiperr(pgptbind->RemoveNameFromTable(bstrName)));
+#if OE_WIN32
+ IfOleErrGo(ConvertStringToA(bstrName, &lpstr));
+ IfOleErrGo(HresultOfTiperr(pgptbind->AddNameToTable(lpstr,
+ GetIndex(),
+ TRUE)))
+ ConvertStringFree(lpstr);
+#else //OE_WIN32
+ IfOleErrGo(HresultOfTiperr(pgptbind->AddNameToTable(bstrName,
+ GetIndex(),
+ TRUE)));
+#endif
+
+Error:
+ FreeBstr(bstrName);
+ }
+
+ return hresult;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GEN_DTINFO::AddRefTypeInfo(ITypeInfoA FAR*, UINT FAR*)
+*Purpose:
+* Creates an impmgr entry for imported typeinfo.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_LAYOUT)
+HRESULT GEN_DTINFO::AddRefTypeInfo(ITypeInfoA FAR* ptinfo,
+ HREFTYPE FAR* phreftype)
+{
+ IMPMGR *pimpmgr;
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+ sHIMPTYPE himptype;
+
+ // Can't modify type unless still in undeclared.
+ if (m_pdtroot->CompState() > CS_UNDECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ DebAssert(ptinfo && phreftype, "invalid arguments");
+
+ IfErrGo(Pdtroot()->GetImpMgr(&pimpmgr));
+ IfErrGo(Pdtroot()->GetDtmbrs(&pdtmbrs));
+ IfErrGo(Pdtroot()->MakeHimptypeLevels());
+
+ IfErrGo(pimpmgr->GetHimptype(ptinfo, DEP_None, &himptype));
+
+ *phreftype = Pdtroot()->HreftypeOfHimptype(himptype);
+
+ // fall through...
+
+Error:
+ return HresultOfTiperr(err);
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_LAYOUT)
+/***
+*PUBLIC GEN_DTINFO::AddImplType(UINT, UINT)
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+HRESULT GEN_DTINFO::AddImplType(UINT index, HREFTYPE hreftype)
+{
+ IMPMGR *pimpmgr;
+ ITypeInfoA *ptinfoImplType = NULL, *ptinfoImplTypeCur = NULL;
+ TYPEATTR *ptypeattrImplType = NULL, *ptypeattrImplTypeCur = NULL;
+ HRESULT hresult;
+ TYPEKIND tkindImplType;
+#if 0
+ HREFTYPE hreftypeImplTypeCur;
+ BOOL isDispatch;
+ UINT iImplType;
+#endif //0
+ BOOL isInterfaceSupported;
+ TYPEKIND tkind;
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+
+ // Can't modify type unless still in undeclared.
+ if (m_pdtroot->CompState() > CS_UNDECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ IfErrRetHresult(m_pdtroot->GetDtmbrs(&pdtmbrs));
+
+ tkind = GetTypeKind();
+
+ // only works for classes
+ switch (tkind) {
+ case TKIND_COCLASS:
+ case TKIND_DISPATCH:
+ case TKIND_INTERFACE:
+ // check that typekind of impltype is ok
+
+ // get typekind of impltype requested
+ IfErrRetHresult(m_pdtroot->GetImpMgr(&pimpmgr));
+ IfErrRetHresult(pimpmgr->GetTypeInfo(m_pdtroot
+ ->HimptypeOfHreftype(hreftype),
+ DEP_None,
+ (TYPEINFO**)&ptinfoImplType));
+
+ IfOleErrGo(ptinfoImplType->GetTypeAttr(&ptypeattrImplType));
+ tkindImplType = ptypeattrImplType->typekind;
+
+ // Record that this is a dual interface in the hreftype
+ // so we know to dereference it later when we get the
+ // interface back. Don't want to get the Interface typeinfo if
+ // this is a CoClass's impltype.
+ //
+ if (tkind != TKIND_COCLASS && (ptypeattrImplType->wTypeFlags & TYPEFLAG_FDUAL)) {
+ hreftype |= 0x00000001;
+ }
+
+ if (tkindImplType != TKIND_INTERFACE) {
+ // Everybody can derive from an interface
+ switch (tkind) {
+ case TKIND_COCLASS:
+ if (tkindImplType == TKIND_DISPATCH) {
+#if 0
+ // coclass. We can't check here anymore (because flags aren't
+ // set yet. So we rely on mktyplib to do this checking..
+ for (iImplType = 0;
+ iImplType < pdtmbrs->Ptdata()->CBase();
+ iImplType++) {
+ // Note: can't use ITypeInfo::GetRefTypeOfImplType interface
+ // method here
+ // yet cos not laid out... so use TYPE_DATA stuff.
+ //
+ IfErrGo(pdtmbrs->Ptdata()->GetRefTypeOfImplType(
+ iImplType,
+ &hreftypeImplTypeCur));
+ // However can use GetRefTypeInfo...
+ IfOleErrGo(GetRefTypeInfo(hreftypeImplTypeCur,
+ &ptinfoImplTypeCur));
+ IfOleErrGo(ptinfoImplTypeCur->GetTypeAttr(
+ &ptypeattrImplTypeCur));
+ isDispatch =
+ (ptypeattrImplTypeCur->typekind == TKIND_DISPATCH);
+ ptinfoImplTypeCur->ReleaseTypeAttr(ptypeattrImplTypeCur);
+ ptypeattrImplTypeCur = NULL;
+ RELEASE(ptinfoImplTypeCur);
+ if (isDispatch) {
+ err = TIPERR_BadModuleKind;
+ break;
+ }
+ } // for each impltype
+#endif //0
+ break;
+ }
+ // fall into code to give error
+
+ default:
+ err = TIPERR_WrongTypeKind;
+ break;
+ } // switch
+ } // if !TKIND_INTERFACE
+ else {
+ // We want to derive from an interface,
+ // well ok, but if we're a dispinterface then
+ // the interface had better be from typelib.dll.
+ //
+ if (tkind == TKIND_DISPATCH) {
+ IfOleErrRet(IsInterfaceSupported(
+ ptinfoImplType,
+ &isInterfaceSupported));
+ if (!isInterfaceSupported) {
+ err = TIPERR_BadModuleKind;
+ break;
+ }
+ } // if TKIND_DISPATCH
+ }
+
+ ptinfoImplType->ReleaseTypeAttr(ptypeattrImplType);
+ ptypeattrImplType = NULL;
+ RELEASE(ptinfoImplType);
+ // return error, if any
+ IfErrRetHresult(err);
+
+ err = pdtmbrs->Ptdata()->AddImplType(index, hreftype);
+
+ break;
+
+ default :
+ err = TIPERR_BadModuleKind;
+ break;
+ } // switch
+
+ return HresultOfTiperr(err);
+
+Error:
+ if (ptypeattrImplType)
+ ptinfoImplType->ReleaseTypeAttr(ptypeattrImplType);
+ if (ptinfoImplTypeCur && ptypeattrImplTypeCur)
+ ptinfoImplType->ReleaseTypeAttr(ptypeattrImplTypeCur);
+ RELEASE(ptinfoImplType);
+ RELEASE(ptinfoImplTypeCur);
+ return hresult;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GEN_DTINFO::SetFuncAndParamNames()
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+HRESULT GEN_DTINFO::SetFuncAndParamNames(UINT index,
+ LPOLESTR FAR *rgszNames,
+ UINT cNames)
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+
+ // Can't modify type unless still in undeclared.
+ if (m_pdtroot->CompState() > CS_UNDECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ if ((err = m_pdtroot->GetDtmbrs(&pdtmbrs)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+ return HresultOfTiperr(pdtmbrs->Ptdata()->SetFuncAndParamNames(index,
+ rgszNames,
+ cNames));
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GEN_DTINFO::SetVarName()
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+HRESULT GEN_DTINFO::SetVarName(UINT index, LPOLESTR szName)
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+ HRESULT hresult;
+#if OE_WIN32
+ LPSTR szNameA;
+#else //OE_WIN32
+ #define szNameA szName
+#endif //OE_WIN32
+
+ // Can't modify type unless still in undeclared.
+ if (m_pdtroot->CompState() > CS_UNDECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ if ((err = m_pdtroot->GetDtmbrs(&pdtmbrs)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+
+#if OE_WIN32
+ IfOleErrRet(ConvertStringToA(szName, &szNameA));
+#endif //OE_WIN32
+
+ hresult = HresultOfTiperr(pdtmbrs->Ptdata()->SetVarName(index, szNameA));
+#if OE_WIN32
+ ConvertStringFree(szNameA);
+#endif //OE_WIN32
+ return hresult;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GEN_DTINFO::SetTypeDescAlias(TYPEDESC FAR*)
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+HRESULT GEN_DTINFO::SetTypeDescAlias(TYPEDESC FAR* ptdesc)
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+
+ // Can't modify type unless still in undeclared.
+ if (m_pdtroot->CompState() > CS_UNDECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ if (GetTypeKind() != TKIND_ALIAS) {
+ return HresultOfTiperr(TIPERR_BadModuleKind);
+ }
+
+ if ((err = m_pdtroot->GetDtmbrs(&pdtmbrs)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+ return HresultOfTiperr(pdtmbrs->Ptdata()->SetTypeDefnAlias(ptdesc));
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GEN_DTINFO::SetFuncDocString(UINT, LPOLESTR)
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+HRESULT GEN_DTINFO::SetFuncDocString(UINT index, LPOLESTR szDoc)
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+#if OE_WIN32
+ HRESULT hresult;
+ LPSTR szDocA;
+#else //OE_WIN32
+ #define szDocA szDoc
+#endif //OE_WIN32
+
+ // Can't modify type unless still in undeclared.
+ if (m_pdtroot->CompState() > CS_UNDECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+#if OE_WIN32
+ IfOleErrRet(ConvertStringToA(szDoc, &szDocA));
+#endif //OE_WIN32
+
+ IfErrGo(m_pdtroot->GetDtmbrs(&pdtmbrs));
+ IfErrGo(pdtmbrs->Ptdata()->SetFuncDocString(index, szDocA));
+
+ SetModified(TRUE);
+ // fall through (with err == TIPERR_None)
+
+Error:
+#if OE_WIN32
+ ConvertStringFree(szDocA);
+#endif //OE_WIN32
+ return HresultOfTiperr(err);
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GEN_DTINFO::DefineFuncAsDllEntry
+*Purpose:
+*
+*Entry:
+* UINT : index of the function
+* LPSTR : Name Of the DLL containing the entry point
+* DWORD : Specifies the entrypoint : If the high word of lpProcName is
+* 0 then the low word contains the ordinal of the entrypoint.
+* Otherwise lpProcName is a pointer to the NULL terminated name.
+*
+*
+*Exit:
+* retruns HRESULT :
+* TIPERR_ElementNotFound : if the index is has bad value.
+* TIPERR_OutOfMemory
+*
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+HRESULT GEN_DTINFO::DefineFuncAsDllEntry(UINT index,
+ LPOLESTR szDllName,
+ LPOLESTR szProcName)
+{
+ TIPERROR err = TIPERR_None;
+ HLNAM hlnamDll;
+ NAMMGR *pnammgr;
+ ENTRYMGR *pentrymgr;
+ HDLLENTRY_DEFN hdllentrydefn;
+ DYN_TYPEMEMBERS *pdtmbrs;
+
+ // Can't modify type unless still in undeclared.
+ if (m_pdtroot->CompState() > CS_UNDECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ // Get the NAMMGR
+ if (err = m_pdtroot->GetNamMgr(&pnammgr))
+ return HresultOfTiperr(err);
+
+ // Get the ENTRYMGR
+ if (err = m_pdtroot->GetEntMgr(&pentrymgr))
+ return HresultOfTiperr(err);
+
+
+ // Get the hlnam for the szDllName;
+ if (err = pnammgr->HlnamOfStrW(szDllName, &hlnamDll, FALSE, NULL))
+ return HresultOfTiperr(err);
+
+
+ // is szProcName a pointer to the name of the function
+ if (((DWORD) szProcName) & 0xffff0000) {
+ // The uppper word is non NULL. So we have a pointer to the name
+ // of the DLL entry point
+
+ // Call the entrymgr to allocate a DLLENTRY_DEFN for the Dll entry
+ // by Name.
+#if OE_WIN32
+ // Convert from UNICODE to ANSI
+ LPSTR szAnsiProcName;
+ HRESULT hResult = ConvertStringToA(szProcName, &szAnsiProcName);
+
+ if (hResult)
+ return hResult;
+
+ err = pentrymgr->AllocDllentrydefnByName(hlnamDll,
+ szAnsiProcName,
+ &hdllentrydefn);
+ ConvertStringFree(szAnsiProcName);
+#else
+ err = pentrymgr->AllocDllentrydefnByName(hlnamDll,
+ szProcName,
+ &hdllentrydefn);
+#endif
+ if (err != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+
+ }
+ else {
+ // ordinal of the entrypoint is specified
+
+ // call the entrymgr to allcate a DLL_ENTRYDEFN for the DLL entry point
+ if (err = pentrymgr->AllocDllentrydefnByOrdinal(hlnamDll,
+ (UINT) (ULONG)szProcName,
+ &hdllentrydefn)) {
+ return HresultOfTiperr(err);
+ }
+ }
+
+ // Get the DYN_TYPE_MEMBER
+ if ((err = m_pdtroot->GetDtmbrs(&pdtmbrs)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+
+ // Save the hdllentrydefn in FUNC_DEFN (of TYPEDATA)
+ if (err = pdtmbrs->Ptdata()->SetDllEntryDefn(index, hdllentrydefn)) {
+ return HresultOfTiperr(err);
+ }
+
+ return HresultOfTiperr(err);
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GEN_DTINFO::SetVarDocString(UINT, LPSTR)
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+HRESULT GEN_DTINFO::SetVarDocString(UINT index, LPOLESTR szDoc)
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+#if OE_WIN32
+ CHAR FAR* szDocA;
+#else //OE_WIN32
+ #define szDocA szDoc
+#endif //OE_WIN32
+ HRESULT hresult;
+
+ // Can't modify type unless still in undeclared.
+ if (m_pdtroot->CompState() > CS_UNDECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ if ((err = m_pdtroot->GetDtmbrs(&pdtmbrs)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+#if OE_WIN32
+ IfOleErrRet(ConvertStringToA(szDoc, &szDocA));
+#endif //OE_WIN32
+
+ hresult = HresultOfTiperr(pdtmbrs->Ptdata()->SetVarDocString(index, szDocA));
+
+#if OE_WIN32
+ ConvertStringFree(szDocA);
+#endif //OE_WIN32
+ return hresult;
+}
+#pragma code_seg()
+
+/***
+*PUBLIC GEN_DTINFO::SetFuncHelpContext(UINT, DWORD)
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+HRESULT GEN_DTINFO::SetFuncHelpContext(UINT index, DWORD dwHelpContext)
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+
+ // Can't modify type unless still in undeclared.
+ if (m_pdtroot->CompState() > CS_UNDECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ if ((err = m_pdtroot->GetDtmbrs(&pdtmbrs)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+ return HresultOfTiperr(pdtmbrs->Ptdata()->SetFuncHelpContext(index,
+ dwHelpContext));
+}
+#pragma code_seg()
+
+/***
+*PUBLIC GEN_DTINFO::SetVarHelpContext(UINT, DWORD)
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+HRESULT GEN_DTINFO::SetVarHelpContext(UINT index, DWORD dwHelpContext)
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+
+ // Can't modify type unless still in undeclared.
+ if (m_pdtroot->CompState() > CS_UNDECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ if ((err = m_pdtroot->GetDtmbrs(&pdtmbrs)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+ return HresultOfTiperr(pdtmbrs->Ptdata()->SetVarHelpContext(index,
+ dwHelpContext));
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_RARE)
+/***
+*PUBLIC GEN_DTINFO::SetMops(UINT, BSTR)
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+HRESULT GEN_DTINFO::SetMops(UINT index, BSTR bstrMops)
+{
+ return HresultOfScode(E_NOTIMPL);
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_RARE)
+/***
+*PUBLIC GEN_DTINFO::SetTypeIdldesc(IDLDESC FAR*)
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+HRESULT GEN_DTINFO::SetTypeIdldesc(IDLDESC FAR* lpidldesc)
+{
+ return HresultOfScode(E_NOTIMPL);
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GEN_DTINFO::LayOut()
+*Purpose:
+* Lays out the class
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_LAYOUT)
+HRESULT GEN_DTINFO::LayOut()
+{
+ GEN_DTINFO *pgdtinfoDisp, *pgdtinfoInt;
+ ITypeInfoA *ptinfo = NULL, *ptinfoNext;
+ TYPEATTR *ptypeattr;
+ HREFTYPE hreftype;
+
+
+ TIPERROR err = TIPERR_None; // assume no error
+ HRESULT hresult;
+
+ // Determine if we are a dual interface and which interface
+ // is which.
+ //
+ if (GetTypeKind() == TKIND_DISPATCH) {
+ pgdtinfoDisp = this;
+ pgdtinfoInt = PgdtinfoPartner();
+ }
+ else {
+ DebAssert(!IsDual() || GetTypeKind() == TKIND_INTERFACE,
+ "Dual interfaces can only have INTERFACe or DISP");
+
+ pgdtinfoDisp = PgdtinfoPartner();
+ pgdtinfoInt = this;
+ }
+
+ // Make sure that an interface is laid out before we start to
+ // process it.
+ //
+ if (pgdtinfoInt != NULL
+ && pgdtinfoInt->Pdtroot()->CompState() < CS_DECLARED) {
+
+ IfErrGoTo(pgdtinfoInt->EnsureInDeclaredState(), Error2);
+ IfErrGoTo(pgdtinfoInt->Pdtroot()->MakeHimptypeLevels(), Error2);
+ }
+
+ // Once the interface is laid out, we must add IDispatch
+ // and the interface as base classes of the dispinterface.
+ //
+ // Try to get IDispatch from a registered STDOLE, it not,
+ // get it from the base class of the interface typeinfo.
+ // We may have to iterate down the base class list.
+ //
+ // NOTE: Only do this for dual interfaces.
+ //
+ if (pgdtinfoInt != NULL && pgdtinfoDisp != NULL) {
+ ITypeLibA *ptlib;
+
+ if (LoadRegTypeLibOfSzGuid(g_szGuidStdole,
+ STDOLE_MAJORVERNUM,
+ STDOLE_MINORVERNUM,
+ STDOLE_LCID,
+ &ptlib) == NOERROR) {
+
+ // Load IDispatch.
+ err = TiperrOfHresult(ptlib->GetTypeInfoOfGuid(IID_IDispatch,
+ &ptinfo));
+
+ ptlib->Release();
+
+ if (err != TIPERR_None) {
+ goto Error;
+ }
+ }
+
+ // Didn't find it, so get it from the base class of the interface.
+ else {
+
+ for (ptinfo = (ITypeInfoA *)pgdtinfoInt, ptinfo->AddRef();;) {
+ IfOleErrGo(ptinfo->GetTypeAttr(&ptypeattr));
+
+ if (ptypeattr->guid == IID_IDispatch) {
+ ptinfo->ReleaseTypeAttr(ptypeattr);
+ break;
+ }
+
+ // We've run out of base classes and haven't found
+ // IDispatch, so return an error.
+ //
+ if (ptypeattr->cImplTypes == 0) {
+ err = TIPERR_ElementNotFound;
+ }
+
+ ptinfo->ReleaseTypeAttr(ptypeattr);
+
+ IfErrGoTo(err, Error2);
+
+ IfOleErrGo(ptinfo->GetRefTypeOfImplType(0, &hreftype));
+ IfOleErrGo(ptinfo->GetRefTypeInfo(hreftype, &ptinfoNext));
+ ptinfo->Release();
+ ptinfo = ptinfoNext;
+ }
+ }
+
+ // Add it as the first base class of the dispinterface.
+ IfOleErrGo(pgdtinfoDisp->AddRefTypeInfo(ptinfo, &hreftype));
+ IfOleErrGo(pgdtinfoDisp->AddImplType(0, hreftype));
+
+ // Add the interface as the pseudo-base of the dispinterface.
+ IfOleErrGo(pgdtinfoDisp->AddRefTypeInfo(pgdtinfoInt, &hreftype));
+
+ DebAssert(pgdtinfoDisp->Pdtroot()->Pdtmbrs() != NULL,
+ "Should have been loaded.");
+
+ IfErrGoTo(pgdtinfoDisp->Pdtroot()->Pdtmbrs()
+ ->Ptdata()->AddImplType(1, hreftype),
+ Error2);
+ }
+
+ // If we're the interface portion of a dual interface,
+ // make sure the dispinterface is laid out before we leave.
+ //
+ if (pgdtinfoDisp != NULL) {
+ err = pgdtinfoDisp->EnsureInDeclaredState();
+ }
+
+Error2:
+ hresult = HresultOfTiperr(err);
+
+Error:
+ RELEASE(ptinfo);
+ return hresult;
+}
+#pragma code_seg()
+
+
+//
+//DYN_TYPEROOT method definitions
+//
+//
+
+
+/***
+*PUBLIC DYN_TYPEROOT constructor
+*Purpose:
+* Initializes the members of DYN_TYPEROOT which are pointers to
+* subparts to NULL so that if the destructor is called before
+* initialization is complete then it will not try to free uninitialized
+* pointers.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+DYN_TYPEROOT::DYN_TYPEROOT()
+{
+ m_pctseg = NULL;
+ m_pdtmbrs = NULL;
+ m_pimpmgr = NULL;
+ m_pentmgr = NULL;
+ m_pbModuleInstance = NULL;
+ m_ptypeattrCache = NULL;
+
+
+ m_cRefsDtmbrs = 0;
+
+ m_fNotDual = TRUE;
+ m_lHrefOffset = (ULONG)OHREF_INVALID;
+
+#if OE_WIN32
+ m_htinfo = HTINFO_Nil;
+#endif // OE_WIN32
+}
+#pragma code_seg( )
+
+
+/***
+*PROTECTED DYN_TYPEROOT operator delete
+*Purpose:
+* Deletes the sheap.
+*
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+VOID DYN_TYPEROOT::operator delete(VOID *pv)
+{
+ // This deletes the sheapmgr within which we are embedded.
+ delete (SHEAP_MGR *)((BYTE *)pv - sizeof(SHEAP_MGR));
+}
+#pragma code_seg( )
+
+
+
+
+/***
+*PUBLIC DYN_TYPEROOT::Init
+*Purpose:
+* Initializes the members of DYN_TYPEROOT.
+* Initializes all block_desc's in the DYN_TYPEROOT segment.
+* Does not allocate the compile time segment since it may not be needed.
+*
+*Entry:
+* pdti - pointer to GEN_DTINFO instance
+* cbRootReserve - number of bytes reserved in runtime seg for Root instance
+* cbCtSegReserve - number of bytes reserved in ct seg for fixed structs
+* isBasic - TRUE if basic module.
+* accessModule - access attribute of this mod wrt other projs.
+* syskind (OLE) - syskind of the containing typelib
+* (this has to be provided explicitly since the GEN_DTINFO
+* hasn't been added to the typelib yet)
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR DYN_TYPEROOT::Init(GEN_DTINFO *pdti,
+ UINT cbRootReserve,
+ UINT cbCtSegReserve,
+ BOOL isBasic,
+ ACCESS accessModule,
+ TYPEKIND tkind
+ , SYSKIND syskind
+ )
+{
+ TIPERROR err;
+
+ m_pgdti = pdti;
+ m_hasDiskImage = FALSE;
+ m_lImpMgr = -1;
+ m_lEntryMgr = -1;
+ m_lDtmbrs = -1;
+ m_lTdata = -1;
+ m_hasWriteAccess = FALSE;
+ m_wasInRunnableState = FALSE;
+ m_willDecompile = FALSE;
+ m_isWatchModule = FALSE;
+ m_isImmediateModule = FALSE;
+
+ m_canDecompile = FALSE;
+ m_cbCtSegReserve = (USHORT)cbCtSegReserve;
+ m_compstate = CS_UNDECLARED;
+ m_isBasic = isBasic;
+ m_accessModule = (USHORT)accessModule;
+ m_fBadTypelib = 0; // good typelib -- initializes it's data
+ m_unused2 = 0x3FFF; // unused bits. All bits are set in both
+ // old & new typelibs
+ m_unused1 = 0; // unused word -- 0 in new typelibs, corrected
+ // to 0 when loading old, bad typelibs
+ m_typekind = tkind;
+ m_uTypeFlags = 0;
+ m_unused3 = 0; // unused bits -- 0 in new typlibs, corrected
+ // to 0 when loading old, bad typelibs
+ m_wMajorVerNum = 0;
+ m_wMinorVerNum = 0;
+
+ // Initialize the instance manager
+ //We don't need to be concerned with undoing the side-affects of
+ // these allocation since the DYN_TYPEROOT will be discarded if
+ // Init fails
+
+ IfErrRet(m_bdTimptype.Init(Psheapmgr(), 0));
+ IfErrRet(m_bdTimpaddr.Init(Psheapmgr(), 0));
+
+ // Initialize the data members in typeinfo needed for MakeRunnable
+ pdti->InitializeIteration();
+
+
+
+
+// If this is OLE, this value is set based on the SysKind of the
+// containing typelib. (only a 'best guess' since this won't work
+// for the risc platforms) It really should be set with
+// ICreateTypeInfo::SetAlignment anyway.
+// For OB, set this value according to the platform we're building on.
+//
+ switch (syskind) {
+ case SYS_WIN16:
+ m_cbAlignMax = 1;
+ break;
+ case SYS_MAC:
+ m_cbAlignMax = 2;
+ break;
+ case SYS_WIN32:
+ m_cbAlignMax = 4;
+ break;
+ default:
+ DebHalt("bad SYSKIND");
+ }
+
+
+ return TIPERR_None;
+}
+#pragma code_seg( )
+
+
+
+/***
+*PUBLIC DYN_TYPEROOT destructor
+*Purpose:
+* Deletes those parts of the GEN_DTINFO implementation which are
+* referenced by the DYN_TYPEROOT. Specifically this includes all
+* objects created in the compile time segment.
+* Essentially restores the DYN_TYPEROOT to an uninitialized state
+* then deletes it.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE )
+DYN_TYPEROOT::~DYN_TYPEROOT()
+{
+
+#if ID_DEBUG
+ // if the module is in runnable state then remove the debug lock before
+ // destructing.
+ // Note : For Std. basic modules the lock is removed in ~BASIC_TYPEROOT
+ if ((CompState() == CS_RUNNABLE) && Psheapmgr()->DebIsLocked() ) {
+ Psheapmgr()->DebUnlock();
+ }
+#endif
+
+ // if the module is in runnable state and the sheapmgr is locked then
+ // unlock it before decompiling.
+ // Note : For Std. basic modules the lock is removed in ~BASIC_TYPEROOT
+ if (CompState() == CS_RUNNABLE) {
+ // Here compstate is being used as a flag to indicate that
+ // the lock has been removed. Since we do this in the destructor we
+ // are safe.
+ SetCompState(CS_ADDRESSABLE);
+ DebAssert(Psheapmgr()->IsLocked(), " Should be locked " );
+ Psheapmgr()->Unlock();
+ }
+
+ if (m_pentmgr != NULL)
+ m_pentmgr->ENTRYMGR::~ENTRYMGR();
+ if (m_pdtmbrs != NULL)
+ m_pdtmbrs->DYN_TYPEMEMBERS::~DYN_TYPEMEMBERS();
+ if (m_pimpmgr != NULL)
+ m_pimpmgr->IMPMGR::~IMPMGR();
+
+
+ if (m_punk != NULL) {
+ // in this case m_punk points to a appobject.
+ // Just release the object
+ m_punk->Release();
+ }
+
+ // Release the typeattribute
+ Pgdtinfo()->ReleaseTypeAttr(m_ptypeattrCache);
+
+#if OE_WIN32
+ // Release the appdata (if needed)
+ if (m_htinfo != HTINFO_Nil) {
+ g_AppObjectTable.RemoveTypeInfo(m_htinfo);
+ }
+#endif // OE_WIN32
+
+ delete (SHEAP_MGR *)m_pctseg;
+}
+#pragma code_seg( )
+
+
+
+
+
+/***
+*PUBLIC DYN_TYPEROOT::GetNamMgr - return pointer to the NAMMGR
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+*Exceptions:
+* May generate exceptions reading NAMMGR from GEN_DTINFO image.
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR DYN_TYPEROOT::GetNamMgr(NAMMGR **ppnammgr)
+{
+ // delegate to containing typelib
+ return m_pgdti->PgtlibOleContaining()->GetNamMgr(ppnammgr);
+}
+#pragma code_seg( )
+
+
+
+/***
+*PUBLIC DYN_TYPEROOT::GetImpMgr - return pointer to the IMPMGR
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+*Exceptions:
+* May generate exceptions reading IMPMGR from GEN_DTINFO image.
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR DYN_TYPEROOT::GetImpMgr(IMPMGR **ppimpmgr)
+{
+ STREAM *pstrm = NULL;
+ TIPERROR err = 0;
+
+ if (m_pimpmgr == NULL) {
+ // Ensure that the COMPILETIME_SEG is created
+ if (m_pctseg == NULL)
+ IfErrRet( SHEAP_MGR::Create((SHEAP_MGR **)&m_pctseg, m_cbCtSegReserve));
+
+ // Create the ImpMgr within the ctseg
+ m_pimpmgr = ::new (&m_pctseg->m_impmgr) IMPMGR;
+ if (err = m_pimpmgr->Init(&m_pctseg->m_sheapmgr,
+ &m_bdTimptype,
+ &m_bdTimpaddr,
+ this)) {
+ m_pimpmgr->IMPMGR::~IMPMGR();
+ m_pimpmgr = NULL;
+ return err;
+ }
+
+ // If DTI has a disk image then read in the name manager
+ if (m_hasDiskImage && (m_lImpMgr != -1) ) {
+
+ // Open stream for reading import manager
+ if (err = m_pgdti->OpenStream(&pstrm, SOM_Read)) {
+ m_pimpmgr->IMPMGR::~IMPMGR();
+ m_pimpmgr = NULL;
+ return err;
+ }
+
+ if ((err = pstrm->SetPos(m_lImpMgr)) ||
+ (err = m_pctseg->m_impmgr.Read(pstrm))) {
+ pstrm->Release();
+ m_pimpmgr->IMPMGR::~IMPMGR();
+ m_pimpmgr = NULL;
+ return err;
+ };
+
+ pstrm->Release();
+
+ }
+ }
+ *ppimpmgr = m_pimpmgr;
+ return TIPERR_None;
+
+}
+#pragma code_seg( )
+
+
+
+/***
+*PUBLIC DYN_TYPEROOT::GetEntMgr - return pointer to the ENTRYMGR
+*Purpose:
+* Returns pointer to entry manager associated with the DYN_TYPEROOT.
+* If there is no entry manager then a new one is created and if there
+* is an associated disk image then its contents is read in.
+*
+*Entry:
+* ppentmgr - for returning pointer to import manager
+*
+*Exit:
+* TIPERROR
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR DYN_TYPEROOT::GetEntMgr(ENTRYMGR **ppentmgr)
+{
+ STREAM *pstrm = NULL;
+ TIPERROR err = 0;
+
+ if (m_pentmgr == NULL) {
+ // Ensure that the COMPILETIME_SEG is created
+ if (m_pctseg == NULL)
+ IfErrRet( SHEAP_MGR::Create((SHEAP_MGR **)&m_pctseg, m_cbCtSegReserve));
+
+ // Create the EntryMgr within the ctseg
+ m_pentmgr = ::new (&m_pctseg->m_entmgr) ENTRYMGR;
+ if (err = m_pentmgr->Init(&m_pctseg->m_sheapmgr, this)) {
+ m_pentmgr->ENTRYMGR::~ENTRYMGR();
+ m_pentmgr = NULL;
+ return err;
+ }
+
+ // If DTI has a disk image then read in the name manager
+ if (m_hasDiskImage && (m_lEntryMgr != -1)) {
+
+ // Open stream for reading import manager
+ if (err = m_pgdti->OpenStream(&pstrm, SOM_Read)) {
+ m_pentmgr->ENTRYMGR::~ENTRYMGR();
+ m_pentmgr = NULL;
+ return err;
+ }
+
+ if ((err = pstrm->SetPos(m_lEntryMgr)) ||
+ (err = m_pctseg->m_entmgr.Read(pstrm))) {
+ pstrm->Release();
+ m_pentmgr->ENTRYMGR::~ENTRYMGR();
+ m_pentmgr = NULL;
+ return err;
+ };
+
+ pstrm->Release();
+
+ } // if
+ } // if
+
+ *ppentmgr = m_pentmgr;
+ return TIPERR_None;
+
+}
+#pragma code_seg( )
+
+
+
+
+/***
+*PUBLIC DYN_TYPEROOT::GetDtmbrs - return pointer to DYN_TYPEMEMBERS
+*Purpose:
+*
+*Implementation Notes:
+* Does NOT add a reference, hence clients should not Release.
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR DYN_TYPEROOT::GetDtmbrs(DYN_TYPEMEMBERS **ppdtmbrs)
+{
+ STREAM *pstrm = NULL;
+ TIPERROR err= TIPERR_None;
+
+ if (m_pdtmbrs == NULL) {
+ // Open for all to use
+ if (m_hasDiskImage) {
+ IfErrRet(m_pgdti->OpenStream(&pstrm, SOM_Read));
+ }
+
+ // Ensure that the COMPILETIME_SEG is created
+ if (m_pctseg == NULL) {
+ IfErrGo( SHEAP_MGR::Create((SHEAP_MGR **)&m_pctseg, m_cbCtSegReserve));
+ }
+
+ // Create the DYN_TYPEMEMBERS within the ctseg
+ m_pdtmbrs = ::new (&m_pctseg->m_dtmbrs) DYN_TYPEMEMBERS;
+ IfErrGoTo(m_pdtmbrs->Init(&m_pctseg->m_sheapmgr, this), Error1);
+
+ // If DTI has a disk image then read in the name manager
+ if (m_hasDiskImage) {
+ if (m_lDtmbrs != -1) {
+ IfErrGoTo(pstrm->SetPos(m_lDtmbrs), Error1);
+ IfErrGoTo(m_pctseg->m_dtmbrs.Read(pstrm), Error1);
+ }
+ pstrm->Release();
+ }
+ }
+
+ *ppdtmbrs = m_pdtmbrs;
+
+ return TIPERR_None;
+
+Error1:
+ m_pdtmbrs->DYN_TYPEMEMBERS::~DYN_TYPEMEMBERS();
+ m_pdtmbrs = NULL;
+
+ // Fall through
+
+Error:
+ if (m_hasDiskImage) {
+ pstrm->Release();
+ }
+
+ return err;
+}
+#pragma code_seg( )
+
+
+
+
+
+
+/***
+*PUBLIC GEN_DTINFO::EnsurePartsRead
+*Purpose:
+* Ensure that all parts of the GEN_DTINFO have been read in.
+* NOTE: wrapper on the *VIRTUAL* (as of 15-Dec-92) typeroot method.
+* Each derived implementation has to override this appropriately.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR GEN_DTINFO::EnsurePartsRead()
+{
+ return m_pdtroot->EnsurePartsRead();
+}
+#pragma code_seg( )
+
+
+
+
+
+/***
+*PUBLIC DYN_TYPEROOT::ReleaseDtmbrs - Release DYN_TYPEMEMBERS member.
+*Purpose:
+* Method used by DYN_TYPEMEMBERS member to notify that
+* a client has released.
+* Decrements private ref count of dtmbrs and
+* defers to GEN_DTINFO::Release() -- which could result
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+VOID DYN_TYPEROOT::ReleaseDtmbrs()
+{
+ DebAssert(m_cRefsDtmbrs > 0, "underflow.");
+ m_cRefsDtmbrs--;
+ Pgdtinfo()->Release();
+}
+
+
+/***
+*PUBLIC DYN_TYPEROOT::AddRefDtmbrs - Add a ref DYN_TYPEMEMBERS member.
+*Purpose:
+* Method used by DYN_TYPEMEMBERS member to notify that
+* a client has added a ref.
+* Bumps private ref count of dtmbrs and defers to GEN_DTINFO::AddRef().
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+VOID DYN_TYPEROOT::AddRefDtmbrs()
+{
+ m_cRefsDtmbrs++;
+ Pgdtinfo()->AddRef();
+}
+
+
+/***
+*PUBLIC DYN_TYPEROOT::Read - read in DYN_TYPEROOT
+*Purpose:
+* Read in DYN_TYPEROOT using associated FileLoc
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+TIPERROR DYN_TYPEROOT::Read()
+{
+ STREAM * pstrm;
+ BYTE bVersion, b;
+ TIPERROR err;
+
+ DebAssert(!m_hasDiskImage &&
+ m_pctseg == NULL,
+ "DYN_TYPEROOT::Read subparts exist");
+
+ IfErrRet( m_pgdti->OpenStream(&pstrm, SOM_Read) );
+
+ IfErrGo( pstrm->ReadByte(&b) );
+
+ if (b != bFirstSerByte || DebErrorNow(TIPERR_InvDataRead)) {
+ err = TIPERR_InvDataRead;
+ goto Error;
+ }
+
+ IfErrGo( pstrm->ReadByte(&bVersion) );
+
+ if (bVersion != bCurVersion || DebErrorNow(TIPERR_UnsupFormat)) {
+ err = TIPERR_UnsupFormat;
+ goto Error;
+ }
+
+
+ IfErrGo( ReadFixed(pstrm) );
+
+ if (m_fBadTypelib) {
+ // initialize data that was indeterminate in old typelibs
+ m_unused1 = 0;
+ m_uTypeFlags &= (WORD)(TYPEFLAG_FCANCREATE | TYPEFLAG_FAPPOBJECT);
+ m_unused3 = 0;
+ }
+
+ m_hasDiskImage = TRUE;
+ IfErrGo(m_pgdti->SetModified(FALSE));
+
+Error:
+ // Close the stream
+ pstrm->Release(); // ignore errors from closing read stream
+
+
+ if (Pgdtinfo()->IsDual()) {
+ err = Pgdtinfo()->MakeDual();
+ }
+
+ DebCheckState(1); // Arg=1 will will force blkmgrs to be checked.
+ return err;
+}
+
+
+/***
+*PUBLIC DYN_TYPEROOT::ReadFixed
+*Purpose:
+* Read in the fixed sized part of the DYN_TYPEROOT
+*
+*Entry:
+* pstrm - stream to read from
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR DYN_TYPEROOT::ReadFixed(STREAM *pstrm)
+{
+ BYTE byte;
+ TIPERROR err;
+
+
+
+ IfErrRet(pstrm->Read((void *)&m_lImpMgr, cbSizeDir));
+
+#if HP_BIGENDIAN
+ SwapStruct(&m_lImpMgr, DYN_TYPEROOT_Layout);
+#endif
+
+ // Read the ENUMS
+ IfErrRet(pstrm->ReadByte(&byte));
+ m_compstate = (COMPSTATE) byte;
+
+ IfErrRet(pstrm->ReadByte(&byte));
+ m_typekind = (TYPEKIND) byte;
+
+ // Load the hrefoffset last so modified V1 typelibs can read this
+ // typeinfo without having to worry about changing their
+ // file formats.
+ //
+ if (Pgdtinfo()->PgtlibOleContaining()->GetVersion() > 2) {
+ ULONG lHrefOffset;
+
+ IfErrRet(pstrm->ReadULong(&lHrefOffset));
+ SetLHrefOffset(lHrefOffset);
+ }
+
+ return TIPERR_None;
+
+}
+
+
+
+/***
+*PUBLIC DYN_TYPEROOT::EnsurePartsRead
+*Purpose:
+* Ensure that all parts of the DYN_TYPEROOT have been read in.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR DYN_TYPEROOT::EnsurePartsRead()
+{
+ NAMMGR *pnammgr;
+ IMPMGR *pimpmgr;
+ ENTRYMGR *pentmgr;
+ DYN_TYPEMEMBERS *pdtmbrs;
+ DEPEND_KIND dependkind;
+ TIPERROR err;
+
+ IfErrRet( GetNamMgr(&pnammgr) );
+
+ // Fix for OB bug# 5793
+ // Dtmbrs should be read before the import manager is read so
+ // that all rectinfos are read in before the impmgr attempts
+ // to reference any of them.
+ //
+ IfErrRet( GetDtmbrs(&pdtmbrs) );
+
+ IfErrRet( GetImpMgr(&pimpmgr) );
+
+ IfErrRet( pimpmgr->CheckRemainingDep(&dependkind) );
+
+ DebAssert(dependkind == DEP_None, "For OLE it is always DEP_None");
+
+ IfErrRet( GetEntMgr(&pentmgr) );
+
+ m_hasDiskImage = FALSE;
+ return TIPERR_None;
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC DYN_TYPEROOT::EnsureInDeclaredState
+*Purpose:
+* Bring the state of the module to CS_DECLARED
+*
+*Entry:
+* None.
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_LAYOUT)
+TIPERROR DYN_TYPEROOT::EnsureInDeclaredState()
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+
+ DebAssert((m_compstate != CS_QUASIUNDECLARED) &&
+ (m_compstate != CS_QUASIDECLARED),
+ " This module did not get decompiled ");
+
+
+ // Note:- We unconditionally bring the module to Semideclared state because
+ // we need to read the layout dependencies even if we are already in SEMI_DECLARED
+ // state.
+ //
+ IfErrRet(EnsureInSemiDeclaredState());
+
+ if (m_compstate < CS_DECLARED) {
+ DebAssert(m_compstate == CS_SEMIDECLARED, " We should be in semideclared state here ");
+
+
+ // Update the type ID. Note that if we get an error after we
+ // successfully update the TypeId then it doesn't really matter.
+ //
+ IfErrRet(
+ m_pgdti->PgtlibOleContaining()->UpdateTypeId(m_pgdti->GetIndex()));
+
+
+ IfErrRet( GetDtmbrs(&pdtmbrs) );
+ IfErrRet( pdtmbrs->MakeLaidOut() );
+ IfErrRet(m_pgdti->SetModified(TRUE));
+ m_compstate = CS_DECLARED;
+ }
+ return TIPERR_None;
+
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC DYN_TYPEROOT::EnsureInSemiDeclaredState
+*Purpose:
+* Bring the state of the module to CS_SEMIDECLARED
+*
+*Entry:
+* None.
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_LAYOUT)
+TIPERROR DYN_TYPEROOT::EnsureInSemiDeclaredState()
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+
+ DebAssert((m_compstate != CS_QUASIUNDECLARED) &&
+ (m_compstate != CS_QUASIDECLARED),
+ " This module did not get decompiled ");
+
+ if (m_compstate < CS_SEMIDECLARED) {
+ IfErrRet(GetDtmbrs(&pdtmbrs) );
+ IfErrRet(pdtmbrs->BuildBindNameTable() );
+ IfErrRet(m_pgdti->SetModified(TRUE));
+ m_compstate = CS_SEMIDECLARED;
+
+ }
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC DYN_TYPEROOT::Write - write out DYN_TYPEROOT to default stream
+*Purpose:
+* Write out DYN_TYPEROOT using associated FileLoc
+* Format currenty is:
+* MagicNumber
+* Directory
+* Name
+* Import Manager
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg(CS_LAYOUT)
+TIPERROR DYN_TYPEROOT::Write()
+{
+ STREAM * pstrm;
+ TIPERROR err, err2;
+
+ // If we're the dispinterface protion of a dual interface,
+ // save the interface portion instead.
+ //
+ if (Pgdtinfo()->IsDualDispinterface()) {
+ return Pgdtinfo()->PgdtinfoPartner()->Write();
+ }
+
+ // Before openning up the stream for writing make sure all parts
+ // are loaded
+ IfErrRet( EnsurePartsRead() );
+
+ // Check state before writing
+ DebCheckState(1); // Arg=1 will will force blkmgrs to be checked.
+
+ // Open the stream.
+ IfErrRet( m_pgdti->OpenStream(&pstrm, SOM_Write) );
+
+ // Write everything to it.
+ err = WriteToStream(pstrm);
+
+ // Close the stream.
+ err2 = pstrm->Release();
+
+ if (err == TIPERR_None)
+ err = err2;
+
+ if (err == TIPERR_None) {
+ m_hasDiskImage = TRUE;
+
+ // Clear the dirty flag.
+ // WARNING WARNING !!! SetModified(FALSE) will release the TYPEINFO
+ // if there are no references to the TYPEINFO
+ IfErrRet(m_pgdti->SetModified(FALSE));
+ }
+
+ return err;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC DYN_TYPEROOT::WriteToStream - write out DYN_TYPEROOT to a stream
+*Purpose:
+* Write out DYN_TYPEROOT using specified stream.
+* Format currenty is:
+* MagicNumber
+* Directory
+* Name
+* Import Manager
+*
+*Entry:
+* pstrm - The stream to which the write should occur.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR DYN_TYPEROOT::WriteToStream(STREAM *pstrm)
+{
+ TIPERROR err;
+ LONG lDirPostn;
+ ENTRYMGR *pentrymgr;
+
+ IfErrRet(GetEntMgr(&pentrymgr));
+
+#if HP_BIGENDIAN
+ // Swap the Dll entry Defn(s)
+ pentrymgr->SwapDllentrydefns(FALSE);
+#endif
+
+ // Write out identification byte and version number
+ IfErrGo( pstrm->Write(&bFirstSerByte, sizeof(bFirstSerByte)) );
+ IfErrGo( pstrm->Write(&bCurVersion, sizeof(bCurVersion)) );
+
+
+ // Get the position of where the directory is stored in the stream
+ // so we can return to this position and write out the directory
+ IfErrGo( pstrm->GetPos(&lDirPostn) );
+
+ // DO NOT serialize any datamember here.
+
+ // Write out current contents of directory -- must be rewritten later
+ IfErrGo( WriteFixed(pstrm) );
+
+ // WARNING: DON'T SERIALIZE ANY INFORMATION HERE; SERIALIZE IT IN
+ // WARNING: WriteFixed; OTHERWISE, THE INFORMATION IS NOT SERIALIZED
+ // WARNING: FOR DERIVATIVES OF GEN_DTINFO
+
+ IfErrGo( WriteParts(pstrm) );
+
+ // Seek to position of directory and rewrite it
+ IfErrGo( pstrm->SetPos(lDirPostn) );
+ err = WriteFixed(pstrm);
+
+Error:
+#if HP_BIGENDIAN
+ // Swap the Dll entry Defn(s)
+ pentrymgr->SwapDllentrydefns(TRUE);
+#endif
+
+ return err;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC DYN_TYPEROOT::WriteFixed
+*Purpose:
+* Write out the fixed sized part of the DYN_TYPEROOT
+*
+*Entry:
+* pstrm - stream to write to
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR DYN_TYPEROOT::WriteFixed(STREAM *pstrm)
+{
+ TIPERROR err;
+ COMPSTATE compstateOld;
+ BYTE byte;
+
+
+ compstateOld = m_compstate;
+
+ // If compstate greater than COMPILED then just write out COMPILED.
+ m_compstate = (m_compstate > CS_COMPILED) ?
+ (COMPSTATE) CS_COMPILED :
+ m_compstate;
+
+
+#if HP_BIGENDIAN
+ SwapStruct(&m_lImpMgr, DYN_TYPEROOT_Layout);
+#endif
+ err = pstrm->Write((void *)&m_lImpMgr, cbSizeDir);
+
+#if HP_BIGENDIAN
+ SwapStruct(&m_lImpMgr, DYN_TYPEROOT_Layout);
+#endif
+
+ // Check for error
+ IfErrGo(err);
+
+ // Save the ENUMS
+ byte = (BYTE) m_compstate;
+ IfErrGo(pstrm->WriteByte(byte));
+
+ byte = (BYTE) m_typekind;
+ IfErrGo(pstrm->WriteByte(byte));
+
+ // Save this last for backwards compatibility.
+ IfErrGo(pstrm->WriteULong(LHrefOffset()));
+
+Error:
+ // restore saved compstate
+ m_compstate = compstateOld;
+ return err;
+
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC DYN_TYPEROOT::WriteParts
+*Purpose:
+* Write out the variable sized parts of the DYN_TYPEROOT
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR DYN_TYPEROOT::WriteParts(STREAM *pstrm)
+{
+ TIPERROR err;
+ IMPMGR *pimpmgr;
+ ENTRYMGR *pentmgr;
+ DYN_TYPEMEMBERS *pdtmbrs;
+
+ // Write out import manager if it is not empty
+ IfErrRet(GetImpMgr(&pimpmgr));
+ // in OLE we serialize the impmgr only if it is not empty.
+ if (!pimpmgr->IsEmpty()) {
+ IfErrRet(pstrm->GetPos(&m_lImpMgr));
+ IfErrRet(pimpmgr->Write(pstrm));
+ }
+
+
+ // Write out DYN_TYPEMEMBERS
+ IfErrRet(pstrm->GetPos(&m_lDtmbrs));
+ IfErrRet(GetDtmbrs(&pdtmbrs));
+ IfErrRet(pdtmbrs->Write(pstrm));
+
+ // Write out entry manager
+ IfErrRet(GetEntMgr(&pentmgr));
+ // in OLE we serialize the entrymgr only if it is not empty.
+ if (!pentmgr->IsEmpty()) {
+ IfErrRet(pstrm->GetPos(&m_lEntryMgr));
+ IfErrRet(pentmgr->Write(pstrm));
+ }
+
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_RARE)
+/***
+*PUBLIC DYN_TYPEINFO::GetEmbeddedTypeInfo()
+*Purpose:
+* This TYPEINFO impl doesn't support embedded typeinfos.
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+TIPERROR GEN_DTINFO::GetEmbeddedTypeInfo(LPOLESTR, LPLPTYPEINFO)
+{
+ DebAssert(0, "GEN_DTINFO::GetEmbeddedTypeInfo not Implemented ");
+
+ return TIPERR_NotYetImplemented;
+
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GEN_DTINFO::Init
+*Purpose:
+* Initializes the data members ( required for bringing all dependent
+* class to runnable state.
+*
+*Entry:
+*
+*
+*Exit:
+* void
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR GEN_DTINFO::InitializeIteration()
+{
+ m_pptinode = NULL;
+ m_himptypeNextDep = HIMPTYPE_Nil;
+
+ return TIPERR_None;
+
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC GEN_DTINFO::BeginDepIteration()
+*Purpose:
+* Marks the beginnning of the iteration over all the modules this calls
+* depends on. This also checks if this calls is in the process of
+* bringing itself to runnable state. In case this class is in the meddle
+* of bringing it self to runnalble state, then it sets ppptinodeCycleMax to
+* pptinode of the first invocation ( the one that stared the process of bringing
+* this class to runnable state). This is done by caching pptinode in m_pptinode;
+*
+*Entry:
+* ptinode : pointer to TINODE
+*
+*
+*Exit:
+* TIPERROR.
+*
+* ppptinodeCylcleMax : returns the contents of pptinode if cycle is detected.
+* If the m_pptinode is not NULL then it means that this
+* type info is in the process is bringing it self to runnalble
+* state. Otherwise this caches pptinode and brings the class to
+* addressable state.
+*
+****************************************************************************/
+#pragma code_seg(CS_CREATE)
+TIPERROR GEN_DTINFO::BeginDepIteration( TINODE **pptinode, TINODE ***ppptinodeCycleMax)
+{
+ TIPERROR err = TIPERR_None;
+
+
+ return err;
+
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GEN_DTINFO::GetNextDepTypeInfo(GEN_DTINFO **)
+*Purpose:
+* Returns the next typeinfo on which this module is dependent on
+* if none is left it returns NULL;
+*
+*Entry:
+*
+*
+*
+*Exit:
+* TIPERROR.
+*
+* ppdtiNext : used for return value. To return the next typeinfo
+* on which this class depends on.
+*
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+TIPERROR GEN_DTINFO::GetNextDepTypeInfo(DYNTYPEINFO **ppdtiNext)
+{
+ TIPERROR err = TIPERR_None;
+ IMPMGR *pimpmgr;
+ ITypeInfoA *ptinfo;
+
+ IfErrGo(m_pdtroot->GetImpMgr(&pimpmgr));
+
+ // the the typeinfo associated with the m_himptypeNextDep
+ // It is first initialized in BeginDepItertion.
+ if (m_himptypeNextDep == HIMPTYPE_Nil) {
+ ptinfo = NULL;
+ }
+ else {
+ // Yes, this bumps the reference count, but we release it after we have
+ // completed the processing (i.e after the CheckAllDep call for this typeinfo.
+ IfErrGo(pimpmgr->GetTypeInfo(m_himptypeNextDep, DEP_None, &ptinfo));
+ }
+
+ *ppdtiNext = (DYNTYPEINFO *) ptinfo;
+
+ if (*ppdtiNext != NULL) {
+ // cache the next himptype for next invocation.
+ m_himptypeNextDep = pimpmgr->HimptypeNext(m_himptypeNextDep);
+ }
+
+ return TIPERR_None;
+
+Error:
+ EndDepIteration();
+ return err;
+
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_RARE)
+/***
+*PUBLIC GEN_DTINFO::GetTypeFixups - return TypeFixups of the Type
+*Purpose:
+* Retrieve the TYPEFIXUPS of the TYPEINFO
+*
+*Entry:
+* None.
+*
+*Exit:
+* returns TypeFixups instance or Null if one can not be produced
+*
+***********************************************************************/
+
+TIPERROR GEN_DTINFO::GetTypeFixups(TYPEFIXUPS **pptfixups)
+{
+ DebAssert(0, " TypeFixup will die. ");
+
+#if 0
+#endif
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+
+/***
+*PUBLIC GEN_DTINFO::AllDepReady()
+*Purpose:
+* Causes the class to be totally ready. binds the import addresses and
+* marks the class to be in runnable state. This call brings the typeinfo
+* runnable state. This is called after bringing all the dependent typeinfos
+* to runnable state.
+* Caches a pointer to the User Defined RESET function (if defined).
+*
+*
+*Entry: None;
+*
+*
+*
+*Exit:
+* TIPERROR.
+*
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+TIPERROR GEN_DTINFO::AllDepReady()
+{
+ TIPERROR err = TIPERR_None;
+
+
+ return err;
+
+}
+#pragma code_seg()
+
+
+
+
+
+/***
+*PUBLIC GEN_DTINFO::NotReady()
+*Purpose:
+*
+*Entry:
+*
+*
+*
+*Exit:
+* TIPERROR.
+*
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+TIPERROR GEN_DTINFO::NotReady()
+{
+
+ DebAssert( m_pdtroot->CompState() == CS_RUNNABLE, "GEN_DTINFO::NotReady failed ");
+
+ // Unlock the segment since we lock it when we go to Runnable state.
+ //
+ m_pdtroot->Psheapmgr()->Unlock();
+ m_pdtroot->Psheapmgr()->DebUnlock();
+
+ m_pdtroot->SetCompState(CS_ADDRESSABLE);
+
+
+ // Set the pointer to reset function to NULL
+ m_pvResetFunc = NULL;
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC DYN_TYPEROOT::PdfntbindSemiDeclared - Get a semi-decled DEFN_TYPEBIND.
+*Purpose:
+* Get a DEFN_TYPEBIND that is at least in CS_SEMIDECLARED.
+* Does not increment DYN_TYPEMEMBERS external or internal refcount -- hence
+* client must not eventually release the internal ref.
+*
+*Entry:
+* ppdfntbind Pointer to callee-allocated DEFN_TYPEBIND (OUT).
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+***********************************************************************/
+
+TIPERROR DYN_TYPEROOT::PdfntbindSemiDeclared(DEFN_TYPEBIND **ppdfntbind)
+{
+
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+
+ DebAssert(ppdfntbind != NULL, "bad param.");
+
+ IfErrRet(m_pgdti->EnsureInSemiDeclaredState());
+ IfErrRet(GetDtmbrs(&pdtmbrs));
+
+ DebAssert(pdtmbrs != NULL, "bad DYN_TYPEMEMBERS.");
+
+ *ppdfntbind = pdtmbrs->Pdtbind();
+
+ DebAssert(pdtmbrs->Pdtbind()->Pdbindnametbl()->IsValid(),
+ "no binding table yet.");
+
+ return TIPERR_None;
+}
+
+
+
+
+
+
+/***
+*PUBLIC DYN_TYPEROOT::IsIdMungable
+*Purpose:
+* See if the given function has a retval parameter.
+*
+*Entry:
+* memid - the function to get
+*
+*Exit:
+* returns TRUE if func has a retval parameter.
+***********************************************************************/
+
+BOOL DYN_TYPEROOT::IsIdMungable(HMEMBER memid, USHORT *usNamCount)
+{
+ TYPE_DATA *ptdata;
+ HFUNC_DEFN hfdefn;
+ TYPE_DEFN *qtdefn;
+
+ HRESULT hresult;
+
+ ptdata = Pdtmbrs()->Ptdata();
+
+ // Get the funcdesc for the property get function. If it
+ // doesn't exist, get the first one we find.
+ //
+ hfdefn = ptdata->HfdefnOfHmember(memid, INVOKE_PROPERTYGET);
+ if (hfdefn == HFUNCDEFN_Nil) {
+ hfdefn = ptdata->HfdefnOfHmember(memid);
+ }
+
+ if (hfdefn == HFUNCDEFN_Nil) {
+ GEN_DTINFO *pgdtinfo;
+ BOOL fRet = FALSE;
+
+ // Recurse on our base class, if we have one.
+ hresult = GetTypeInfoOfImplType(Pgdtinfo(), 0, (ITypeInfo **)&pgdtinfo);
+
+ if (hresult == NOERROR) {
+ fRet = pgdtinfo->Pdtroot()->IsIdMungable(memid, usNamCount);
+ }
+
+ pgdtinfo->Release();
+
+ return fRet;
+ }
+
+ // Get the max # of names.
+ *usNamCount = ptdata->QfdefnOfHfdefn(hfdefn)->CArgsUnmunged() + 1;
+
+ // Return whether it has a retval parameter or not.
+ if (ptdata->QfdefnOfHfdefn(hfdefn)->m_ftdefn.HtdefnResult()
+ == HTYPEDEFN_Nil) {
+
+ return FALSE;
+ }
+
+ // If this has an lcid/retval paramter, adjust the
+ // count of parameters.
+ //
+ qtdefn = ptdata->QtdefnResultOfHfdefn(hfdefn);
+
+ if (qtdefn->IsLCID()) {
+ (*usNamCount)--;
+ }
+
+ if (qtdefn->IsRetval()) {
+ (*usNamCount)--;
+ }
+
+ return qtdefn->IsLCID() || qtdefn->IsRetval();
+}
+
+
+
+
+
+
+
+#if ID_DEBUG
+
+/***
+*PUBLIC DYN_TYPEROOT::DebCheckState
+*Purpose:
+* Check internal state of GEN_DTINFO and its parts.
+* Delegates to DYN_TYPEROOT::DebCheckState
+*
+*Entry:
+* uLevel
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+VOID DYN_TYPEROOT::DebCheckState(UINT uLevel) const
+{
+ // if this module is going to decompile then we do not want to do
+ // the state checking.
+ if (m_willDecompile)
+ return;
+
+ if (m_pimpmgr != NULL) {
+ m_pimpmgr->DebCheckState(uLevel);
+ }
+
+ if (m_pdtmbrs != NULL) {
+ m_pdtmbrs->DebCheckState(uLevel);
+ }
+
+ if (m_pentmgr != NULL) {
+ m_pentmgr->DebCheckState(uLevel);
+ }
+
+}
+
+
+#endif //ID_DEBUG
+
+
+//CONSIDER: May want to change the way that a COMPILETIME_SEG to be the
+//CONSIDER: as how a DYN_TYPEROOT is built so that its constructor is called.
+//CONSIDER: If this is done then the statements which explicitly create
+//CONSIDER: instances of the members of COMPILETIME_SEG above must be deleted.
+//CONSIDER: A disadvantage of this is that we would need to construct all the
+//CONSIDER: elements of the COMPILETIME_SEG to load the class which is
+//CONSIDER: unnecessary.
+//
+///*
+///***
+//*PUBLIC COMPILETIME_SEG::operator new - allocates space for a COMPILETIME_SEG
+//*Purpose:
+//*
+//*Implementation Notes:
+//* Allocate a SHEAP_MGR segment and return a pointer to immediately
+//* following the sheap_mgr instance so the GEN_DTINFO
+//* will be constructed there
+//*
+//*Entry:
+//* size - always sizeof(COMPILETIME_SEG)
+//*
+//*Exit:
+//* None.
+//*
+//***********************************************************************
+//
+//VOID *COMPILETIME_SEG::operator new(size_t size)
+//{
+// return SHEAP_MGR::operator new(size);
+//}
+//
+//
+///***
+//*PUBLIC COMPILETIME_SEG::operator delete - releases memory of COMPILETIME_SEG
+//*Purpose:
+//* Releases memory allocated by COMPILETIME_SEG::new
+//*
+//*Entry:
+//* pv - Pointer to COMPILETIME_SEG to delete.
+//*
+//*Exit:
+//* None.
+//*
+//***********************************************************************/
+//
+//VOID COMPILETIME_SEG::operator delete(VOID *pv)
+//{
+// SHEAP_MGR::operator delete(pv);
+//}
+
+
+
+/***
+*PUBLIC GEN_DTINFO::GetVarDesc
+*Purpose:
+* Get a var desc given an index
+*
+*Implementation Notes:
+*
+*Entry:
+* index - index of var to get
+*
+*Exit:
+* Returns HRESULT
+* *ppvardesc - pointer to vardesc returned
+***********************************************************************/
+
+HRESULT GEN_DTINFO::GetVarDesc(UINT index, VARDESCA **ppvardesc)
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+
+ if (ppvardesc == NULL) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+ // Can't get attributes unless been laid...
+ if (m_pdtroot->CompState() < CS_DECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ if ((err = m_pdtroot->GetDtmbrs(&pdtmbrs)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+
+ return HresultOfTiperr(pdtmbrs->Ptdata()->GetVarDesc(index, ppvardesc));
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::AddVarDesc
+*Purpose:
+* Add a var desc
+*
+*Implementation Notes:
+*
+*Entry:
+* index - index of var to add
+* pvardesc - var desc to add
+*
+*Exit:
+* Returns HRESULT
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+HRESULT GEN_DTINFO::AddVarDesc(UINT index, VARDESCA *pvardesc)
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+
+ DebAssert(pvardesc != NULL, "NULL param.");
+
+ // Can't modify type unless still in undeclared.
+ if (m_pdtroot->CompState() > CS_UNDECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ switch (GetTypeKind()) {
+ case TKIND_RECORD :
+ case TKIND_UNION :
+ if (pvardesc->varkind != VAR_PERINSTANCE) {
+ return HresultOfTiperr(TIPERR_BadModuleKind);
+ }
+ break;
+ case TKIND_ENUM :
+ if (pvardesc->varkind != VAR_CONST) {
+ return HresultOfTiperr(TIPERR_BadModuleKind);
+ }
+#if ID_DEBUG
+ // check that enum size is correct
+ DebAssert(pvardesc->lpvarValue, "variant const val isn't set");
+
+ switch (PgtlibOleContaining()->GetSyskind())
+ {
+ case SYS_WIN16:
+ DebAssert(pvardesc->lpvarValue->vt == VT_I2,
+ "expected two byte constant");
+ break;
+
+ case SYS_WIN32:
+ case SYS_MAC:
+ DebAssert(pvardesc->lpvarValue->vt == VT_I4,
+ "expected four byte constant");
+ break;
+
+ default:
+ DebHalt("Invalid SYSKIND");
+ } // switch
+#endif // ID_DEBUG
+ break;
+ case TKIND_MODULE :
+ if (pvardesc->varkind != VAR_CONST && pvardesc->varkind != VAR_STATIC) {
+ return HresultOfTiperr(TIPERR_BadModuleKind);
+ }
+ break;
+ case TKIND_DISPATCH :
+ if (pvardesc->varkind != VAR_DISPATCH) {
+ return HresultOfTiperr(TIPERR_BadModuleKind);
+ }
+ break;
+#if 0
+ case TKIND_Class :
+ if (pvardesc->varkind == VAR_DISPATCH) {
+ return HresultOfTiperr(TIPERR_BadModuleKind);
+ }
+ break;
+#endif //VBA2
+ case TKIND_INTERFACE :
+ case TKIND_ALIAS :
+ case TKIND_COCLASS :
+ return HresultOfTiperr(TIPERR_BadModuleKind);
+ break;
+ default:
+ DebHalt("Unrecognzed typekind");
+ } // switch
+
+ if ((err = m_pdtroot->GetDtmbrs(&pdtmbrs)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+ return HresultOfTiperr(pdtmbrs->Ptdata()->AddVarDesc(index, pvardesc));
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GEN_DTINFO::GetFuncDesc
+*Purpose:
+* Get a func desc given an index
+*
+*Implementation Notes:
+*
+*Entry:
+* index - index of function to get
+*
+*Exit:
+* Returns HRESULT
+* *ppfuncdesc - pointer to funcdesc returned
+***********************************************************************/
+
+HRESULT GEN_DTINFO::GetFuncDesc(UINT index, FUNCDESC **ppfuncdesc)
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+
+ if (ppfuncdesc == NULL) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+ // Can't get attributes unless been laid...
+ if (m_pdtroot->CompState() < CS_DECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ if ((err = m_pdtroot->GetDtmbrs(&pdtmbrs)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+
+ BOOL isFunkyDispinterface;
+ TYPEATTR *ptypeattrBase;
+ ITypeInfoA *ptinfoBase, *ptinfo;
+ UINT cFuncs, cFuncsLeft, cImplTypes;
+ HREFTYPE hreftype;
+ HRESULT hresult;
+
+ // Work out if we're a dispinterface defined in terms of an interface...
+ // If so, our life becomes somewhat harder since we've effectively
+ // flattened the inheritance hierarchy of the pseudo-base interface
+ // and now we have to work out which base the function was really
+ // introduced in.
+ //
+ IfErrGo(IsFunkyDispinterface(this, &isFunkyDispinterface));
+ if (isFunkyDispinterface) {
+ // Work out how many funcs in the flattened hierarchy...
+ // Need the typeattr for this...
+ //
+ IfOleErrRet(GetTypeInfoOfImplType(
+ this,
+ 1, // pseudo-base
+ &ptinfoBase));
+ IfOleErrGoTo(ptinfoBase->GetTypeAttr(&ptypeattrBase), Error2);
+ DebAssert(ptypeattrBase->typekind == TKIND_INTERFACE, "bad base.");
+ cFuncs = ptypeattrBase->cbSizeVft / sizeof(VOID *);
+
+ // index is 0-based
+ // Note: cFuncsLeft is used to count the total number of funcs
+ // inherited from all base interfaces.
+ //
+ for (;;) {
+ cFuncsLeft = cFuncs - ptypeattrBase->cFuncs;
+ cImplTypes = ptypeattrBase->cImplTypes;
+ ptinfoBase->ReleaseTypeAttr(ptypeattrBase);
+ if (cFuncsLeft <= index) {
+ hresult = ptinfoBase->GetFuncDesc(index - cFuncsLeft, ppfuncdesc);
+ if (hresult == NOERROR) {
+ // Eureka! now pretend the function is a FUNC_DISPATCH
+ // and not some esoteric virtual thingy...
+ //
+ InterfaceFuncdescToDispatch(*ppfuncdesc);
+ }
+ goto Error2;
+ }
+ cFuncs = cFuncsLeft;
+ if (cImplTypes > 0) {
+ // set up for next iteration
+ // Note: we only look at the first base (no MI here).
+ //
+ IfOleErrGoTo(ptinfoBase->GetRefTypeOfImplType(0, &hreftype),
+ Error2);
+ IfOleErrGoTo(ptinfoBase->GetRefTypeInfo(hreftype, &ptinfo),
+ Error2);
+ ptinfoBase->Release();
+ ptinfoBase = ptinfo;
+ IfOleErrGoTo(ptinfoBase->GetTypeAttr(&ptypeattrBase), Error2);
+ }
+ else {
+ err = TIPERR_ElementNotFound; // not found means that our index
+ ptinfoBase->Release(); // is out of bounds
+ goto Error;
+ }
+ } // while
+ } // if funky disp
+
+ return HresultOfTiperr(pdtmbrs->Ptdata()->GetFuncDesc(index, ppfuncdesc));
+
+Error2:
+ ptinfoBase->Release();
+ return hresult;
+
+Error:
+ return HresultOfTiperr(err);
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::AddFuncDesc
+*Purpose:
+* Add a func desc
+*
+*Implementation Notes:
+*
+*Entry:
+* index - index of function to add
+* pfuncdesc - func desc to add
+*
+*Exit:
+* Returns HRESULT
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+HRESULT GEN_DTINFO::AddFuncDesc(UINT index, FUNCDESC *pfuncdesc)
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+
+ DebAssert(pfuncdesc != NULL, "NULL param.");
+
+ // Can't modify type unless still in undeclared.
+ if (m_pdtroot->CompState() > CS_UNDECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ switch (GetTypeKind()) {
+ case TKIND_RECORD :
+ case TKIND_UNION :
+ case TKIND_ENUM :
+ case TKIND_ALIAS :
+ case TKIND_COCLASS :
+ return HresultOfTiperr(TIPERR_BadModuleKind);
+ break;
+ case TKIND_MODULE :
+ if (pfuncdesc->funckind != FUNC_STATIC) {
+ return HresultOfTiperr(TIPERR_BadModuleKind);
+ }
+ break;
+ case TKIND_DISPATCH :
+ if (pfuncdesc->funckind != FUNC_DISPATCH) {
+ return HresultOfTiperr(TIPERR_BadModuleKind);
+ }
+ break;
+#if 0
+ case TKIND_Class :
+ if (pfuncdesc->funckind == FUNC_DISPATCH) {
+ return HresultOfTiperr(TIPERR_BadModuleKind);
+ }
+ break;
+#endif //VBA2
+ case TKIND_INTERFACE :
+ if (pfuncdesc->funckind != FUNC_PUREVIRTUAL) {
+ return HresultOfTiperr(TIPERR_BadModuleKind);
+ }
+ break;
+ default:
+ DebHalt("Unrecognzed typekind");
+ } // switch
+ if ((err = m_pdtroot->GetDtmbrs(&pdtmbrs)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+ return HresultOfTiperr(pdtmbrs->Ptdata()->AddFuncDesc(index, pfuncdesc));
+}
+#pragma code_seg()
+
+
+/***
+*GEN_DTINFO::PrepareForDestructio
+*Purpose:
+* NO OP
+*Entry:
+* None
+*Exit:
+* None
+***********************************************************************/
+#pragma code_seg( CS_CORE )
+VOID GEN_DTINFO::PrepareForDestruction()
+{
+ // No op
+}
+#pragma code_seg( )
+
+
+
+
+
+
+
+
+
+/***
+*PUBLIC GEN_DTINFO::SetImplTypeFlags
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+HRESULT GEN_DTINFO::SetImplTypeFlags(UINT index,
+ INT impltypeflags)
+{
+ DYN_TYPEMEMBERS *pdtmbrs;
+ TIPERROR err;
+
+ // no flags are valid for non-coclass's
+ if (GetTypeKind() != TKIND_COCLASS) {
+ return HresultOfScode(TYPE_E_BADMODULEKIND);
+ }
+
+ if ((err = m_pdtroot->GetDtmbrs(&pdtmbrs)) != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+
+ err = pdtmbrs->Ptdata()->SetImplTypeFlags(index, impltypeflags);
+ return HresultOfTiperr(err);
+}
+#pragma code_seg()
+
+/***
+*PUBLIC GEN_DTINFO::SetAlignment
+*Purpose:
+* Set maximum alignment value for this type info. Members will be
+* naturally aligned, not exceeding this value.
+*
+*Entry:
+* cbAlignment - maximum alignment value
+*
+*Exit:
+* No errors possible.
+*
+*Implementation notes:
+* caches the alignment value in DYN_TYPEROOT
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+HRESULT GEN_DTINFO::SetAlignment(WORD cbAlignment)
+{
+ Pdtroot()->SetAlignment(cbAlignment);
+ return NOERROR;
+
+
+}
+#pragma code_seg()
+
+/***
+*PUBLIC GEN_DTINFO::SetSchema
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg(CS_RARE)
+HRESULT GEN_DTINFO::SetSchema(LPOLESTR lpstrSchema)
+{
+ return ResultFromScode(E_NOTIMPL); // NYI (used by Cairo)
+}
+#pragma code_seg()
+
+
+#if ID_DEBUG
+
+
+#endif //ID_DEBUG
diff --git a/private/oleauto/src/typelib/gdtinfo.hxx b/private/oleauto/src/typelib/gdtinfo.hxx
new file mode 100644
index 000000000..b6862e717
--- /dev/null
+++ b/private/oleauto/src/typelib/gdtinfo.hxx
@@ -0,0 +1,1323 @@
+/***
+*gdtinfo.hxx - GEN_DTINFO header file
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* GEN_DTINFO is inherited by BASIC_TYPEINFO and used directly
+* by clients such as COMPOSER.
+*
+*
+*Revision History:
+*
+* 26-Feb-91 alanc: Created.
+* [01] 11-Mar-91 ilanc: Added constructor decl.
+* [02] 20-Mar-91 ilanc: Move COMPILETIME_SEG out and forward decl
+* it and DYN_TYPEMEMBERS instead of including.
+* [03] 04-Apr-91 ilanc: Added universe member to DYN_TYPEROOT.
+* [04] 14-May-91 ilanc: Added ID_TEST wrapper around friends.
+* [05] 05-Mar-92 ilanc: Added isBasic flag.
+* [06] 16-Mar-92 ilanc: Added DYN_TYPEROOT::CanChange()
+* [07] 18-Jun-92 w-peterh: add rectypeinfo stuff
+* [08] 02-Jul-92 w-peterh: OrdinalOfRectbind() and PrtbindOfOrdinal()
+* [09] 18-Aug-92 w-peterh: added ImpAddrOfHImpAddr()
+* [10] 25-Aug-92 rajivk: support for bringing all needed class to runnable state
+* [11] 17-Sep-92 rajivk: Edit & Continue support ( CanOtherChange ).
+* [12] 17-Sep-92 rajivk: Suport for saving all the edits. ( CommitChanges).
+* [13] 12-Nov-92 w-peterh: added watch/immediate support
+* [14] 21-Nov-92 rajivk : call User Defined Reset() when reseting a module
+* [15] 09-Dec-92 rajivk : PContainingProject();
+* [16] 08-Jan-93 RajivK: Support for Code Resource on Mac
+* [17] 08-Jan-93 RajivK: Fixed some undone(s)
+* [18] 18-Jan-93 w-peterh: moved Clear funcs to itdesc.hxx, moved GetFunctions to cxx
+* [19] 02-Feb-93 w-peterh: added IndexOfFuncName
+* [20] 23-Feb-93 rajivk : add CreateInstance support
+*
+*****************************************************************************/
+
+#ifndef GDTInfo_HXX_INCLUDED
+#define GDTInfo_HXX_INCLUDED
+
+
+#include "sheapmgr.hxx" //Note that this include should come first
+ // to avoid overly deep nesting of includes
+#include "cltypes.hxx"
+#include "stltinfo.hxx"
+#include "mem.hxx"
+#include "macros.hxx"
+#include "dtmbrs.hxx"
+
+#if OE_WIN32
+#include "oautil.h"
+#endif // OE_WIN32
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szGDTINFO_HXX)
+#define SZ_FILE_NAME g_szGDTINFO_HXX
+#endif
+
+class IMPMGR;
+class ENTRYMGR;
+class NAMMGR;
+class COMPILETIME_SEG;
+class DYN_TYPEROOT;
+class BASIC_TYPESRC;
+class DYN_CLASSLIB;
+class DEFN_TYPEBIND;
+#define STAT_TYPELIB GEN_PROJECT
+class GEN_PROJECT;
+
+extern OLECHAR FAR *g_szGuidStdole; // string version of STDOLE's GUID
+
+// Layout of DYN_TYPEROOT serialized data members except for GUID and enums
+#define DYN_TYPEROOT_Layout "llllsssss"
+
+#define CCCONSTANT_INCREMENT 16
+
+#define OHREF_INVALID (~(0L))
+
+/***
+*class GEN_DTINFO - 'dti': DYNAMIC TYPEINFO implementation
+*Purpose:
+* GEN_DTINFO is inherited by BASIC_TYPEINFO and used directly
+* by clients such as COMPOSER.
+*
+***********************************************************************/
+class GEN_DTINFO : public STL_TYPEINFO
+{
+friend class STL_TYPEINFO;
+friend class GenericTypeLibOLE;
+public:
+
+ // Inherited methods
+// OLE2 ITypeInfo methods
+
+ STDMETHOD(GetTypeAttr)(THIS_ TYPEATTR FAR* FAR* lplptypeattr);
+ STDMETHOD(GetTypeComp)(THIS_ ITypeCompA FAR* FAR* lplptcomp);
+ STDMETHOD(GetFuncDesc)(THIS_ UINT index,
+ FUNCDESC FAR* FAR* lplpfuncdesc);
+ STDMETHOD(GetVarDesc)(THIS_ UINT index,
+ VARDESCA FAR* FAR* lplpvardesc);
+ STDMETHOD(GetNames)(THIS_ MEMBERID memid,
+ BSTR FAR* rgbstrNames,
+ UINT cMaxNames,
+ UINT FAR* lpcNames);
+ STDMETHOD(GetRefTypeOfImplType)(THIS_ UINT index,
+ HREFTYPE FAR* phreftype);
+ STDMETHOD(GetImplTypeFlags)(THIS_ UINT index,
+ INT FAR* pimpltypeflags);
+ STDMETHOD(GetIDsOfNames)(THIS_ OLECHAR FAR* FAR* rgszNames,
+ UINT cNames,
+ MEMBERID FAR* rgmemid);
+ STDMETHOD(Invoke)(THIS_ VOID FAR* lpvInstance,
+ MEMBERID memid,
+ WORD wFlags,
+ DISPPARAMSA FAR *lpdispparams,
+ VARIANTA FAR *lpvarResult,
+ EXCEPINFOA FAR *lpexcepinfo,
+ UINT FAR *lpuArgErr);
+ STDMETHOD(GetDocumentation)(THIS_ MEMBERID memid,
+ BSTR FAR* lpbstrName,
+ BSTR FAR* lpbstrDocString,
+ DWORD FAR* lpdwHelpContext,
+ BSTR FAR* lpbstrHelpFile);
+ STDMETHOD(GetDllEntry)(THIS_
+ MEMBERID memid,
+ INVOKEKIND invkind,
+ BSTR FAR* lpbstrDllName,
+ BSTR FAR* lpbstrName,
+ WORD FAR* lpwOrdinal);
+ STDMETHOD(GetRefTypeInfo)(THIS_ HREFTYPE hreftype,
+ ITypeInfoA FAR* FAR* lplptinfo);
+ STDMETHOD(AddressOfMember)(THIS_ MEMBERID memid,
+ INVOKEKIND invkind,
+ VOID FAR* FAR* lplpv);
+ STDMETHOD(CreateInstance)(THIS_
+ IUnknown FAR* punkOuter,
+ REFIID iid,
+ VOID FAR* FAR* lplpvObject);
+ STDMETHOD(GetMops)(THIS_ MEMBERID memid,
+ BSTR FAR* lpbstrMops);
+ STDMETHOD_(void, ReleaseTypeAttr)(THIS_ TYPEATTR FAR* lptypeattr);
+ STDMETHOD_(void, ReleaseFuncDesc)(THIS_ FUNCDESC FAR* lpfuncdesc);
+ STDMETHOD_(void, ReleaseVarDesc)(THIS_ VARDESCA FAR* lpvardesc);
+
+// OLE2 ICreateTypeInfo methods
+ STDMETHOD(SetGuid)(THIS_ REFGUID guid);
+ STDMETHOD(SetTypeFlags)(THIS_ UINT uTypeFlags);
+ STDMETHOD(SetDocString)(THIS_ LPOLESTR lpstrDoc);
+ STDMETHOD(SetHelpContext)(THIS_ DWORD dwHelpContext);
+ STDMETHOD(SetVersion)(THIS_ WORD wMajorVerNum,
+ WORD wMinorVerNum);
+ STDMETHOD(AddRefTypeInfo)(THIS_ ITypeInfoA FAR* ptinfo,
+ HREFTYPE FAR* lphreftype);
+ STDMETHOD(AddFuncDesc)(THIS_ UINT index,
+ FUNCDESC FAR* lpfuncdesc);
+ STDMETHOD(AddImplType)(THIS_ UINT index,
+ HREFTYPE hreftype);
+ STDMETHOD(SetImplTypeFlags)(THIS_ UINT index,
+ INT impltypeflags);
+ STDMETHOD(SetAlignment)(THIS_ WORD cbAlignment);
+
+ STDMETHOD(SetSchema)(THIS_ LPOLESTR lpstrSchema);
+
+ STDMETHOD(AddVarDesc)(THIS_ UINT index,
+ VARDESCA FAR* lpvardesc);
+ STDMETHOD(SetFuncAndParamNames)(THIS_ UINT index,
+ LPOLESTR FAR* rgszNames,
+ UINT cNames);
+ STDMETHOD(SetVarName)(THIS_ UINT index,
+ LPOLESTR szName);
+ STDMETHOD(SetTypeDescAlias)(THIS_ TYPEDESC FAR* lptdescAlias);
+ STDMETHOD(DefineFuncAsDllEntry)(THIS_ UINT index,
+ LPOLESTR szDllName,
+ LPOLESTR szProcName);
+ STDMETHOD(SetFuncDocString)(THIS_ UINT index,
+ LPOLESTR szDocString);
+ STDMETHOD(SetVarDocString)(THIS_ UINT index,
+ LPOLESTR szDocString);
+ STDMETHOD(SetFuncHelpContext)(THIS_ UINT index,
+ DWORD dwHelpContext);
+ STDMETHOD(SetVarHelpContext)(THIS_ UINT index,
+ DWORD dwHelpContext);
+ STDMETHOD(SetMops)(THIS_
+ UINT index, BSTR bstrMops);
+ STDMETHOD(SetTypeIdldesc)(THIS_
+ IDLDESC FAR* lpidldesc);
+ STDMETHOD(LayOut)(THIS);
+
+ STDMETHOD(QueryInterface) (THIS_ REFIID riid, LPVOID FAR* ppvObj);
+
+#if 0
+ virtual TIPERROR CreateInst(LPLPVOID lplpObj);
+#endif
+ virtual TIPERROR GetDynTypeMembers(LPLPDYNTYPEMEMBERS lplpDynTypeMembers);
+ virtual TIPERROR GetDefnTypeBind(DEFN_TYPEBIND **pdfntbind);
+ virtual TIPERROR GetTypeFixups(LPLPTYPEFIXUPS lplpTypeFixups);
+ nonvirt TYPEKIND GetTypeKind();
+ virtual TIPERROR Read();
+ virtual TIPERROR Write();
+ virtual TIPERROR WriteToStream(STREAM *pstrm);
+ virtual TIPERROR GetMemberName(HMEMBER hmember, BSTRA *plstrName);
+ virtual LPOLESTR SzTypeIdofTypeInfo();
+ virtual TIPERROR Reset();
+ virtual TIPERROR ResetPrePass();
+ virtual TIPERROR EnsurePartsRead();
+ virtual TIPERROR GetEmbeddedTypeInfo(LPOLESTR szTypeId,
+ LPLPTYPEINFO pptinfo);
+ virtual VOID ReleasePublicResources();
+
+ // Introduced methods
+ static TIPERROR Create(GEN_DTINFO **ppgdtinfo);
+ static TIPERROR Create(GEN_DTINFO **ppgdtinfo,
+ TYPEKIND typekind,
+ BOOL isBasic,
+ ACCESS access,
+ SYSKIND syskind
+ );
+
+ nonvirt TIPERROR GetDefnTypeBindSemiDeclared(DEFN_TYPEBIND **ppdfntbind);
+ nonvirt TIPERROR EnsureInDeclaredState();
+ nonvirt TIPERROR EnsureInSemiDeclaredState();
+ nonvirt TIPERROR Pdfntbind(DEFN_TYPEBIND **ppdfntbind);
+ nonvirt TIPERROR PdfntbindSemiDeclared(DEFN_TYPEBIND **ppdfntbind);
+
+ nonvirt TIPERROR GetDocumentationOfFuncName(LPOLESTR szFuncName,
+ BSTR FAR *lpbstrDocString,
+ DWORD FAR *lpdwHelpContext,
+ UINT *puIndex);
+
+ // Methods for Watch/Immediate support
+ nonvirt TIPERROR GetLpfnOfHfdefn(HFUNC_DEFN hfdefn, VOID **lplpfn);
+ nonvirt TIPERROR GetHfdefnOfFunctionName(LPSTR szFuncName,
+ INVOKEKIND invokekind,
+ HFUNC_DEFN *phfdefn);
+ nonvirt TIPERROR GetFunctionNameOfHfdefn(HFUNC_DEFN hfdefn,
+ BSTRA *pbstrName,
+ INVOKEKIND *pinvokekind);
+ nonvirt TIPERROR GetFunctionCount(ACCESS access,
+ UINT *pcFunctions);
+ nonvirt TIPERROR GetNextFunctionName(HFUNC_DEFN *phfdefn,
+ ACCESS access,
+ BSTRA *pbstrName,
+ INVOKEKIND *pinvokekind);
+ nonvirt TIPERROR CreateImmediateImplicitVar(XSZ xszName,
+ TYPEDESCKIND tdesckind);
+
+ // Method to remove cycle problem within a project.
+ virtual VOID RemoveInternalRefs();
+
+ // inherited methods for bringing needed modules to runnable state.
+ virtual TIPERROR BeginDepIteration(TINODE **pptinode, TINODE ***ppptinodeCycleMax);
+ virtual VOID EndDepIteration();
+ virtual TIPERROR GetNextDepTypeInfo(DYNTYPEINFO **ppdtiNext);
+ virtual BOOL IsReady();
+ virtual TIPERROR AllDepReady();
+ virtual TIPERROR NotReady();
+ virtual TIPERROR CommitChanges();
+ nonvirt DYN_TYPEROOT* Pdtroot();
+ virtual BOOL IterationNotInProgress();
+ virtual TIPERROR InitializeIteration();
+
+
+ // methods for adding a funcdesc/vardescs and getting hdefns back
+ nonvirt TIPERROR AddFuncDesc(UINT index,
+ FUNCDESC *pfuncdesc,
+ HFUNC_DEFN *phfdefn);
+ nonvirt TIPERROR AddVarDesc(UINT index,
+ VARDESCA *pvardesc,
+ HVAR_DEFN *phvdefn);
+ virtual VOID PrepareForDestruction();
+
+
+ // the following are related to the implementation of ITypeInfo::Invoke().
+ struct INVOKEARGS{
+ UINT cArgs;
+ VARTYPE FAR* rgvt;
+ VARIANTARGA FAR* FAR* rgpvarg;
+ VARIANTARGA FAR* rgvarg;
+ VARIANTARGA FAR* rgvarg2;
+ VARIANTARGA FAR* FAR* rgpvargByref;
+ BYTE FAR* rgbVarMustBeFreed; // array of BYTEs which flag for each
+ // argument as to whether GDTINFO owns the
+ // memory and should free it or not
+ // (vba2 #3279)
+ SAFEARRAYA FAR* psa; // for the vararg case
+ };
+
+ nonvirt HRESULT NEARCODE IndexOfParam(DISPPARAMSA FAR* pdispparams,
+ UINT uPos,
+ UINT FAR* puIndex);
+ nonvirt HRESULT NEARCODE VariantVtOfTypedesc(TYPEDESC FAR* lptdesc,
+ USHORT *pfGotObjGuid,
+ GUID *pGuid,
+ VARTYPE FAR* pvt);
+ nonvirt HRESULT NEARCODE VariantVtOfHtdefn(HTYPE_DEFN htdefn,
+ TYPE_DATA * ptdata,
+ BOOL fSimpleType,
+ USHORT *pfGotObjGuid,
+ GUID *pGuid,
+ VARTYPE FAR* pvt);
+ nonvirt HRESULT NEARCODE AllocInvokeArgs(UINT cArgs, UINT cArgsVarArg, INVOKEARGS FAR* FAR* ppinvargs);
+ nonvirt void NEARCODE ReleaseInvokeArgs(INVOKEARGS FAR* pinvargs);
+ nonvirt HRESULT NEARCODE CoerceArg(VARIANTARGA FAR* pvargSrc,
+ VARTYPE vt,
+ USHORT fGotObjGuid,
+ GUID FAR* pGuid,
+ INVOKEARGS FAR* pinvargs,
+ UINT u);
+ nonvirt HRESULT NEARCODE GetInvokeArgs(HFUNC_DEFN hfdefn,
+ TYPE_DATA * ptdata,
+ WORD wFlags,
+ DISPPARAMSA FAR* pdispparams,
+ VARIANTA ** ppvarRetval,
+ void * pbufRetval,
+ INVOKEARGS FAR* FAR* ppinvargsOut,
+ UINT FAR* puArgErr,
+ BOOL fPropParamSplit);
+
+ nonvirt BOOL IsPropGet(WORD wFlags);
+ nonvirt BOOL IsPropPut(WORD wFlags);
+ nonvirt BOOL IsLegalInvokeFlags(WORD wFlags);
+ nonvirt HRESULT NEARCODE CopyBackByrefArgs(INVOKEARGS FAR* pinvargs);
+
+ // Dual functions.
+ nonvirt BOOL IsDual();
+ nonvirt BOOL IsDualInterface();
+ nonvirt BOOL IsDualDispinterface();
+
+ nonvirt VOID SetIsDual(BOOL fParam);
+
+ nonvirt GEN_DTINFO *PgdtinfoPartner();
+
+ nonvirt TIPERROR MakeDual();
+
+ // Versioning functions.
+ nonvirt UINT GetVersion();
+
+ // Public data members
+ static CONSTDATA LPOLESTR szProtocolName;
+
+#if ID_DEBUG
+ nonvirt VOID DebCheckState(UINT uLevel) const;
+ nonvirt VOID DebShowState(UINT uLevel) const;
+ nonvirt UINT DebShowSize();
+#else // !ID_DEBUG
+ nonvirt VOID DebCheckState(UINT uLevel) const {}
+ nonvirt VOID DebShowState(UINT uLevel) const {}
+ nonvirt VOID DebShowSize() {}
+#endif // ID_DEBUG
+
+
+protected:
+ GEN_DTINFO();
+ ~GEN_DTINFO();
+
+ DYN_TYPEROOT *m_pdtroot;
+
+ //CONSIDER: new and delete operations needed if GEN_DTINFO allocated
+ //CONSIDER: within the DYN_TYPEROOT segment
+ // nonvirt VOID *operator new(size_t cbSize);
+ //
+ //
+ // now have to redefine operator new that is inherited from COBJECT because
+ // the preceeding declaration shadows it
+ // VOID * operator new(size_t, VOID *p) { return p; }
+ //
+ // nonvirt VOID operator delete(VOID *pv); should this be virtual?
+
+ // these data memebers are required for bringing all dependent class to
+ // runnable state.
+ TINODE **m_pptinode;
+ HIMPTYPE m_himptypeNextDep;
+ // cache a pointer to the RESET function
+ VOID *m_pvResetFunc;
+
+#ifdef GEN_DTINFO_VTABLE
+#pragma VTABLE_EXPORT
+#endif
+};
+
+
+
+
+/***
+*class DYN_TYPEROOT - 'dtroot':
+*Purpose:
+* Each GEN_DTINFO has a DYN_TYPEROOT which serves as an interface
+* between the GEN_DTINFO and its subparts.
+*
+***********************************************************************/
+
+class DYN_TYPEROOT
+{
+
+friend class GEN_DTINFO;
+friend class ENTRYMGR; // for m_pbModuleInstance;
+friend class INSTMGR; // ditto
+#if ID_TEST
+ friend TIPERROR GetSheapSize(UINT argc, BSTRA *rglstr);
+#endif
+
+public:
+ // No Create method is defined since GEN_DTINFO is only client
+ TIPERROR Init(GEN_DTINFO *pgdti,
+ UINT cbRootReserve,
+ UINT cbSegReserve,
+ BOOL isBasic,
+ ACCESS accessModule,
+ TYPEKIND tkind
+ , SYSKIND syskind
+ );
+ nonvirt TIPERROR Release();
+ VOID operator delete(VOID *pv);
+
+ nonvirt TIPERROR GetNamMgr(NAMMGR **ppnammgr);
+ nonvirt TIPERROR GetImpMgr(IMPMGR **ppimpmgr);
+ nonvirt TIPERROR GetEntMgr(ENTRYMGR **ppentmgr);
+ virtual TIPERROR GetDtmbrs(DYN_TYPEMEMBERS **pdtmbrs);
+ nonvirt GEN_DTINFO *Pgdtinfo();
+ nonvirt DYN_TYPEMEMBERS * Pdtmbrs();
+ nonvirt COMPSTATE CompState() const;
+ nonvirt TIPERROR SetCompState( COMPSTATE compstate);
+
+ nonvirt TIPERROR Pdfntbind(DEFN_TYPEBIND **ppdfntbind);
+ nonvirt TIPERROR PdfntbindSemiDeclared(DEFN_TYPEBIND **ppdfntbind);
+
+ nonvirt TIPERROR EnsureInSemiDeclaredState();
+ nonvirt TIPERROR EnsureInDeclaredState();
+
+ nonvirt SHEAP_MGR *Psheapmgr();
+
+
+ nonvirt VOID ReleaseDtmbrs();
+ nonvirt VOID AddRefDtmbrs();
+
+ nonvirt BOOL IsBasic() const;
+ nonvirt IMPADDR ImpAddrOfHImpAddr(HIMPADDR himpaddr);
+ nonvirt TIPERROR GetWriteAccess();
+ nonvirt ACCESS Access() const;
+ nonvirt VOID SetAccess(ACCESS access);
+ nonvirt UINT GetTypeFlags() const;
+ nonvirt TIPERROR CreateInstance(HIMPTYPE himptype, LPLPVOID lplpObj);
+ nonvirt BOOL IsIdMungable(HMEMBER memid, USHORT *usNamCount);
+
+ nonvirt VOID SetAlignment(USHORT cbAlign) { m_cbAlignMax = cbAlign; }
+ nonvirt USHORT GetAlignment() { return m_cbAlignMax; }
+
+ nonvirt BYTE *PbModuleInstance();
+
+ // HREFTYPE functions.
+ ULONG LHrefOffset();
+ VOID SetLHrefOffset(ULONG lOffset);
+ BOOL FUseHrefOffset();
+ TIPERROR MakeHimptypeLevels();
+
+ HREFTYPE HreftypeOfHimptype(HIMPTYPE himptype);
+ HIMPTYPE HimptypeOfHreftype(HREFTYPE hreftype);
+ BOOL IsHimptypeLevel(HREFTYPE hreftype);
+
+#if ID_DEBUG
+ nonvirt VOID DebCheckState(UINT uLevel) const;
+ nonvirt VOID DebShowState(UINT uLevel) const;
+ nonvirt VOID DebShowStateAndSize(UINT uLevel);
+ nonvirt UINT DebShowSize();
+#else //!ID_DEBUG
+ nonvirt VOID DebCheckState(UINT uLevel) const {}
+ nonvirt VOID DebShowState(UINT uLevel) const {}
+ nonvirt VOID DebShowStateAndSize(UINT uLevel) {};
+ nonvirt VOID DebShowSize() {}
+#endif //!ID_DEBUG
+
+protected:
+ DYN_TYPEROOT();
+ ~DYN_TYPEROOT();
+
+ // client should call SHEAP_MGR::Create() and use placement
+ // new.
+ //
+ VOID *operator new(size_t cbSize);
+ virtual TIPERROR Read(); //invoked by GEN_DTINFO::Read
+ virtual TIPERROR Write(); //invoked by GEN_DTINFO::Write
+ virtual TIPERROR WriteToStream(STREAM *pstrm); //invoked by GEN_DTINFO::WriteToStream
+ virtual TIPERROR WriteParts(STREAM *pstrm);
+ virtual TIPERROR ReadFixed(STREAM *pstrm);
+ virtual TIPERROR EnsurePartsRead();
+ virtual TIPERROR WriteFixed(STREAM *pstrm);
+
+
+
+ static CONSTDATA BYTE bCurVersion; // Serialization format version number
+ static CONSTDATA BYTE bFirstSerByte; // First byte of serialization
+ static CONSTDATA WORD cbSizeDir; // Size of directory
+
+
+ GEN_DTINFO *m_pgdti;
+ COMPILETIME_SEG *m_pctseg;
+ BLK_DESC m_bdTimpaddr;
+ BLK_DESC m_bdTimptype;
+
+ USHORT m_cbCtSegReserve;
+
+ // non-serialized flag word
+ USHORT m_hasDiskImage:1;
+ USHORT m_hasWriteAccess:1;
+ USHORT m_wasInRunnableState:1;
+ USHORT m_willDecompile:1; // module will get decompiled
+ USHORT m_isWatchModule:1; // is this a watch module
+ USHORT m_isImmediateModule:1; // is this an immed module
+ USHORT m_isImmedImplicitMod:1; // is this the immediate implicit mod
+ USHORT m_canDecompile:1; // is set if the module can decompile
+ USHORT undone:8; // extra bits
+
+ // These are serialized by passing pointer to m_lImpMgr
+ // and serializing cbSizeDir bytes.
+
+ // If you add a new data member please update DYN_TYPEROOT_Layout
+ // FIRST serialized member.
+ LONG m_lImpMgr;
+ LONG m_lEntryMgr;
+ LONG m_lDtmbrs;
+ LONG m_lTdata;
+ WORD m_wMajorVerNum;
+ WORD m_wMinorVerNum;
+ USHORT m_unused1; // WARNING: this is unused/uninitialized in V1
+ // typelibs (0 in new typelibs). This is
+ // corrected in DYN_TYPEROOT::ReadFixed().
+ USHORT m_fBadTypelib:1; // set ==> bad V1 typelib (with uninitialized
+ // data items)
+ // clear ==> new typelib with initialized data.
+
+ USHORT m_fNotDual:1; // This typeinfo is not part of a dual
+ // interface.
+
+ USHORT m_unused2:14; // these bits are all unused at present. They
+ // are all set in both old and new typelibs
+
+ // serialized flag word (LAST serialized member)
+ USHORT m_isBasic:1; // is this an Object Basic class?
+ USHORT m_accessModule:2; // type wannabe ACCESS
+ USHORT m_uTypeFlags:9; // TypeInfo TypeFlags
+ // possible bits are:
+ // TYPEFLAG_FCANCREATE 0x0001
+ // TYPEFLAG_FAPPOBJECT 0x0002
+ // TYPEFLAG_FLICENSED 0x0004
+ // TYPEFLAG_FPREDECLID 0x0008
+ // TYPEFLAG_FHIDDEN 0x0010
+ // TYPEFLAG_FCONTROL 0x0020
+ // TYPEFLAG_FDUAL 0x0040
+ // TYPEFLAG_FNONEXTENSIBLE 0x0080
+ // TYPEFLAG_FOLEAUTOMATION 0x0100
+ // WARNING: all but FCANCREATE and FAPPOBJECT
+ // were uninitialized in V1 typelibs. This is
+ // corrected in DYN_TYPEROOT::ReadFixed().
+ USHORT m_unused3:4; // extra bits
+ // WARNING: these bits were uninitialized in V1
+ // typelibs. This is corrected in
+ // DYN_TYPEROOT::ReadFixed().
+
+ IMPMGR *m_pimpmgr; // Must follow last serialized members.
+
+ // This must be serialized separately to support the PPC
+ // hybrid-V1/V2 typelib.
+ //
+ ULONG m_lHrefOffset;
+
+ // NOTE: must be serialized separately
+ // since hxxtoinc needs its offset.
+ //
+ // RajivK : for portability reasons enumerated data types are serialized
+ // separately.
+ // CONSIDER: (dougf) for size on disk (and in-memory) considerations,
+ // CONSIDER: could move these enums into the unused bits above
+ // CONSIDER: (at the expense of speed of accessing them).
+ COMPSTATE m_compstate; ENUMPAD(m_compstate) // Must follow bit flags.
+ TYPEKIND m_typekind; ENUMPAD(m_typekind)
+
+ ENTRYMGR *m_pentmgr;
+ DYN_TYPEMEMBERS *m_pdtmbrs;
+
+
+ // The dual partner of this interface, if it exists.
+ GEN_DTINFO *m_pgdtinfoDualPartner;
+
+ TYPEATTR *m_ptypeattrCache; // "template" typeattr to be copied
+ TYPEATTR *m_ptypeattrOut; // typeattr to be passed out, to save MemAlloc calls
+ BOOL m_ftypeattrOutUsed; // TRUE if ptypeattrOutUsed has been returned to a caller
+
+ // m_pbModuleInstance should not be under EI_OB switch as we are
+ // overloading this pointer to use it as the predeclared Identifier.
+
+ union {
+ BYTE *m_pbModuleInstance; // pointer to instance for standard module
+ IUnknown *m_punk; // pointer to the object instance (for predeclared id)
+ };
+
+
+ //CONSIDER: following is needed if GEN_DTINFO allocated within DYN_TYPEROOT
+ //GEN_DTINFO m_dti;
+
+ // DYN_TYPEMEMBERS reference count - 25-Jun-92 ilanc
+ USHORT m_cRefsDtmbrs;
+
+ // Max alignment value - used with DYN_TYPEMEMBERS::AlignmentTdesckind
+ // and set by GEN_DTINFO::SetAlignment
+ USHORT m_cbAlignMax;
+
+#if OE_WIN32
+ HTINFO m_htinfo;
+#endif // OE_WIN32
+
+#ifdef DYN_TYPEROOT_VTABLE
+#pragma VTABLE_EXPORT
+#endif
+};
+
+
+
+/***
+*PUBLIC DYN_TYPEROOT::Psheapmgr()
+*Purpose:
+* returns pointer to the containing SHEAP_MGR
+*Exit:
+* returns pointer to the SHEAP_MGR.
+*
+***********************************************************************/
+inline SHEAP_MGR *DYN_TYPEROOT::Psheapmgr()
+{
+ return (SHEAP_MGR *)((BYTE *)this - sizeof(SHEAP_MGR));
+}
+
+
+
+
+
+/***
+*PUBLIC DYN_TYPEROOT::PbModuleInstance()
+*Purpose:
+* returns module instance
+*Exit:
+* returns module instance
+*
+***********************************************************************/
+inline BYTE *DYN_TYPEROOT::PbModuleInstance() {
+ DebAssert (m_typekind == TKIND_MODULE, "need module in order to call PbModuleInstance");
+ return m_pbModuleInstance;
+}
+
+
+
+
+/***
+*PUBLIC DYN_TYPEROOT::CompState()
+*Purpose:
+* Accessor: Returns class's compilation state.
+*
+*Entry:
+*
+*Exit:
+* COMPSTATE
+*
+***********************************************************************/
+inline COMPSTATE DYN_TYPEROOT::CompState() const
+{
+ return (COMPSTATE)m_compstate;
+}
+
+
+/***
+*PUBLIC DYN_TYPEROOT::SetCompState(COMPSTATE)
+*Purpose:
+* set the m_compstate to the COMPSTATE passed to it.
+*
+*Entry:
+* COMPSTATE
+*
+*Exit:
+* COMPSTATE
+*
+***********************************************************************/
+inline TIPERROR DYN_TYPEROOT::SetCompState(COMPSTATE compstate)
+{
+ m_compstate = compstate;
+ return TIPERR_None;
+}
+
+
+/***
+*PUBLIC DYN_TYPEROOT::IsBasic - is this a Basic class?
+*Purpose:
+* Tests whether this is a class defined in Basic.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* BOOL
+*
+***********************************************************************/
+
+inline BOOL DYN_TYPEROOT::IsBasic() const
+{
+ return (BOOL)m_isBasic;
+}
+
+
+/***
+*PUBLIC DYN_TYPEROOT::Access - get access attribute.
+*Purpose:
+* Gets the access/visibility attribute of this module.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* ACCESS
+*
+***********************************************************************/
+
+inline ACCESS DYN_TYPEROOT::Access() const
+{
+ return (ACCESS)m_accessModule;
+}
+
+inline VOID DYN_TYPEROOT::SetAccess(ACCESS access)
+{
+ m_accessModule = access;
+}
+
+/***
+*PUBLIC DYN_TYPEROOT::GetTypeFlags - get access attribute.
+*Purpose:
+* Gets the access/visibility attribute of this module.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* ACCESS
+*
+***********************************************************************/
+
+inline UINT DYN_TYPEROOT::GetTypeFlags() const
+{
+ return (UINT)m_uTypeFlags;
+}
+
+
+/***
+*PUBLIC DYN_TYPEROOT::Pgdtinfo
+*Purpose:
+* Return a pointer to the GEN_DTINFO of the DYN_TYPEROOT
+*
+*Entry:
+* None.
+*
+*Exit:
+* Return a pointer to the GEN_DTINFO of the DYN_TYPEROOT
+*
+***********************************************************************/
+
+inline GEN_DTINFO *DYN_TYPEROOT::Pgdtinfo()
+{
+ return m_pgdti;
+}
+
+
+/***
+*PUBLIC DYN_TYPEROOT::Pdtmbrs()
+*Purpose:
+* returns pointer to the dtmbrs
+*Exit:
+* returns pointer to the dtmbrs
+*
+***********************************************************************/
+inline DYN_TYPEMEMBERS *DYN_TYPEROOT::Pdtmbrs() {
+ return m_pdtmbrs;
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::IterationNotInProgress()
+*Purpose:
+* To check if iteraion is in progress or not.
+*
+*Entry:
+*
+*Exit:
+* True if iteration is not in progress.
+*
+***********************************************************************/
+inline BOOL GEN_DTINFO::IterationNotInProgress() {
+ return ( m_pptinode == NULL );
+}
+
+/***
+*PUBLIC GEN_DTINFO::EnsureInDeclaredState
+*Purpose:
+* Bring the state of the module to CS_DECLARED
+* Defer to DYN_TYPEROOT.
+*
+*Entry:
+* None.
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+inline TIPERROR GEN_DTINFO::EnsureInDeclaredState()
+{
+ return m_pdtroot->EnsureInDeclaredState();
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::EnsureInSemiDeclaredState
+*Purpose:
+* Bring the state of the module to CS_SEMIDDECLARED
+* Defer to DYN_TYPEROOT.
+*
+*Entry:
+* None.
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+inline TIPERROR GEN_DTINFO::EnsureInSemiDeclaredState()
+{
+ return m_pdtroot->EnsureInSemiDeclaredState();
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::Pdtroot
+*Purpose:
+* Returns the pointer to the DYN_TYPEROOT of this typeinfo.
+*Entry:
+* None.
+*
+*Exit:
+* pointer to dyn type root.
+*
+***********************************************************************/
+
+inline DYN_TYPEROOT* GEN_DTINFO::Pdtroot()
+{
+ return m_pdtroot;
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::Read - read in GEN_DTINFO
+*Purpose:
+* Defer to DYN_TYPEROOT Read method
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+inline TIPERROR GEN_DTINFO::Read()
+{
+ return m_pdtroot->Read();
+}
+
+
+
+/***
+*PUBLIC GEN_DTINFO::Write - write out GEN_DTINFO
+*Purpose:
+* Defer to DYN_TYPEROOT Write method
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+inline TIPERROR GEN_DTINFO::Write()
+{
+ return m_pdtroot->Write();
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::WriteToStream - write GEN_DTINFO to a specified stream
+*Purpose:
+* Defer to DYN_TYPEROOT Write method
+*
+***********************************************************************/
+
+inline TIPERROR GEN_DTINFO::WriteToStream(STREAM *pstrm)
+{
+ return m_pdtroot->WriteToStream(pstrm);
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::Create
+*
+*Purpose:
+* Static function for creation of a GEN_DTINFO.
+*
+*Entry:
+* ppdtinfo -- set to point to produced GEN_DTINFO
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+inline TIPERROR GEN_DTINFO::Create(GEN_DTINFO **ppdtinfo)
+{
+ // Create a new public Basic module.
+ return Create(ppdtinfo,
+ TKIND_MODULE,
+ TRUE,
+ ACCESS_Public
+ // this function is used only in typelib creation, so
+ // it doesn't matter what the syskind value is
+ , SYSKIND_CURRENT
+ );
+}
+
+
+
+
+/***
+*PUBLIC GEN_DTINFO::Pdfntbind - Get a decled DEFN_TYPEBIND.
+*Purpose:
+* Get a DEFN_TYPEBIND that is at least in CS_DECLARED.
+* Does not increment DYN_TYPEMEMBERS refcount -- hence
+* client must not release produced pointer (and can
+* cache it).
+*
+*Entry:
+* ppdfntbind Pointer to callee-allocated DEFN_TYPEBIND (OUT).
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+***********************************************************************/
+
+inline TIPERROR GEN_DTINFO::Pdfntbind(DEFN_TYPEBIND **ppdfntbind)
+{
+ return m_pdtroot->Pdfntbind(ppdfntbind);
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::PdfntbindSemiDeclared - Get a decled DEFN_TYPEBIND.
+*Purpose:
+* Get a DEFN_TYPEBIND that is at least in CS_DECLARED.
+* Does not increment DYN_TYPEMEMBERS refcount -- hence
+* client must not release produced pointer (and can
+* cache it).
+*
+*Entry:
+* ppdfntbind Pointer to callee-allocated DEFN_TYPEBIND (OUT).
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+***********************************************************************/
+
+inline TIPERROR GEN_DTINFO::PdfntbindSemiDeclared(DEFN_TYPEBIND **ppdfntbind)
+{
+ return m_pdtroot->PdfntbindSemiDeclared(ppdfntbind);
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::EndDepIteration
+*Purpose:
+* This marks the end of the iteration over all the dependent
+* modules.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+*Errors:
+* None.
+***********************************************************************/
+
+inline VOID GEN_DTINFO::EndDepIteration()
+{
+ m_pptinode = NULL;
+ m_himptypeNextDep = HIMPTYPE_Nil;
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::IsReady
+*Purpose:
+* Is this class in runnable state.
+*
+*Entry:
+* None.
+*
+*Exit:
+* Boolean : true if the module is in CS_RUNNABLE state else false.
+*
+*Errors:
+* None.
+***********************************************************************/
+
+inline BOOL GEN_DTINFO::IsReady()
+{
+ return (m_pdtroot->CompState() == CS_RUNNABLE);
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::IsDual
+*Purpose:
+* Returns TRUE if this interface is part of a dual interface.
+*
+* NOTE: The bit used to store this value defaults to TRUE,
+* so we store the opposite of what we truely want.
+*
+*Entry:
+* None.
+*
+*Exit:
+* BOOLEAN
+*
+*Errors:
+* None.
+***********************************************************************/
+
+inline BOOL GEN_DTINFO::IsDual()
+{
+ return !m_pdtroot->m_fNotDual;
+}
+
+/***
+*PUBLIC GEN_DTINFO::GetTypeKind - return TypeKind of Type
+*Purpose:
+* Retrieve the TYPEKIND of the TYPEINFO
+*
+*Entry:
+* None.
+*
+*Exit:
+* returns TypeKind of described Type
+*
+***********************************************************************/
+
+inline TYPEKIND GEN_DTINFO::GetTypeKind()
+{
+ return m_pdtroot->m_typekind;
+}
+
+/***
+*PUBLIC GEN_DTINFO::IsDualInterface
+*Purpose:
+* Returns TRUE if this is the interface portion of a dual interface.
+*
+*Entry:
+* None.
+*
+*Exit:
+* BOOLEAN
+*
+*Errors:
+* None.
+***********************************************************************/
+
+inline BOOL GEN_DTINFO::IsDualInterface()
+{
+ return IsDual() && GetTypeKind() == TKIND_INTERFACE;
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::IsDualDispinterface.
+*Purpose:
+* Returns TRUE if this member is the dispinterface protion of a
+* dual interface.
+*
+*Entry:
+* None.
+*
+*Exit:
+* BOOLEAN
+*
+*Errors:
+* None.
+***********************************************************************/
+
+inline BOOL GEN_DTINFO::IsDualDispinterface()
+{
+ return IsDual() && GetTypeKind() == TKIND_DISPATCH;
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::SetIsDual
+*Purpose:
+* Sets whether we are a dual interface.
+*
+* NOTE: The bit used to store this value defaults to TRUE,
+* so we store the opposite of what we truely want.
+*
+*Entry:
+* None.
+*
+*Exit:
+* BOOLEAN
+*
+*Errors:
+* None.
+***********************************************************************/
+
+inline VOID GEN_DTINFO::SetIsDual(BOOL fParam)
+{
+ m_pdtroot->m_fNotDual = !fParam;
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::PgdtinfoPartner
+*Purpose:
+* Returns this typeinfo's partner, if its part of a dual pair.
+*
+*Entry:
+* None.
+*
+*Exit:
+* GEN_DTINFO * of the parnter.
+*
+*Errors:
+* None.
+***********************************************************************/
+
+inline GEN_DTINFO *GEN_DTINFO::PgdtinfoPartner()
+{
+ return (GEN_DTINFO *)PstltiPartner();
+}
+
+
+/***
+*PUBLIC GEN_DTINFO::GetVersion
+*Purpose:
+* Returns the typeinfo's version
+*
+*Entry:
+* None.
+*
+*Errors:
+* None.
+***********************************************************************/
+
+inline UINT GEN_DTINFO::GetVersion()
+{
+ return PgtlibOleContaining()->GetVersion();
+}
+
+
+/***
+*PUBLIC DYN_TYPEROOT::LHrefOffset
+*Purpose:
+* Accessors for m_wHrefOffset.
+*
+*Entry:
+* None.
+*
+*Errors:
+* None.
+***********************************************************************/
+
+inline ULONG DYN_TYPEROOT::LHrefOffset()
+{
+ return m_lHrefOffset;
+}
+
+inline VOID DYN_TYPEROOT::SetLHrefOffset(ULONG lOffset)
+{
+ m_lHrefOffset = lOffset;
+}
+
+
+/***
+*PUBLIC DYN_TYPEROOT::FUseHrefOffset
+*Purpose:
+* Returns TRUE if we need to adjust our hreftypes.
+*
+*Errors:
+* None.
+***********************************************************************/
+
+inline BOOL DYN_TYPEROOT::FUseHrefOffset()
+{
+ return LHrefOffset() != OHREF_INVALID;
+}
+
+
+/***
+*PUBLIC DYN_TYPEROOT::IsHimptypeLevel
+*Purpose:
+* Returns TRUE if this is the correct level in the inheritence
+* heirarchy to dereference this hreftype at.
+*
+*Entry:
+* hreftype
+*
+*Exit:
+* BOOL
+*
+*Errors:
+* None.
+***********************************************************************/
+
+inline BOOL DYN_TYPEROOT::IsHimptypeLevel(HREFTYPE hreftype)
+{
+ return FUseHrefOffset() ? ((LONG)hreftype - (LONG)LHrefOffset()) >= 0
+ : TRUE;
+}
+
+
+/***
+*PUBLIC DYN_TYPEROOT::HreftypeOfHimptype
+*Purpose:
+* Calculate an hreftype given an himptype.
+*
+*Entry:
+* himptype
+*
+*Exit:
+* hreftype
+*
+*Errors:
+* None.
+***********************************************************************/
+
+inline HREFTYPE DYN_TYPEROOT::HreftypeOfHimptype(HIMPTYPE himptype)
+{
+ if (!FUseHrefOffset()) {
+ DebAssert(Pgdtinfo()->GetTypeKind() != TKIND_INTERFACE
+ || CompState() == CS_UNDECLARED,
+ "Levels must be set for interfaces.");
+
+ return (HREFTYPE)himptype;
+ }
+
+ return (HREFTYPE)(himptype + LHrefOffset());
+}
+
+
+/***
+*PUBLIC DYN_TYPEROOT::HimptypeOfHreftype
+*Purpose:
+* Calculate an himptype given an hreftype.
+*
+*Entry:
+* hreftype
+*
+*Exit:
+* himptype
+*
+*Errors:
+* None.
+***********************************************************************/
+
+inline HIMPTYPE DYN_TYPEROOT::HimptypeOfHreftype(HREFTYPE hreftype)
+{
+ if (!FUseHrefOffset()) {
+ DebAssert(Pgdtinfo()->GetTypeKind() != TKIND_INTERFACE
+ || CompState() == CS_UNDECLARED,
+ "Levels must be set for interfaces.");
+
+ return (HIMPTYPE)hreftype;
+ }
+
+ DebAssert(IsHimptypeLevel(hreftype), "Not proper level!");
+
+ return (HIMPTYPE)(hreftype - LHrefOffset());
+}
+
+
+/***
+*PUBLIC DYN_TYPEROOT::ImpAddrOfHImpAddr
+*Purpose:
+* Dereference a HIMPADDR
+*Entry:
+* HimpAddr to be dereferenced
+*
+*Exit:
+* IMPADDR
+***********************************************************************/
+
+inline IMPADDR DYN_TYPEROOT::ImpAddrOfHImpAddr(HIMPADDR himpaddr)
+{
+ DebAssert(m_bdTimpaddr.CbSize() > himpaddr, "invalid handle");
+ return *(IMPADDR *)((BYTE*)m_bdTimpaddr.QtrOfBlock() + himpaddr);
+}
+
+
+
+void InterfaceFuncdescToDispatch(FUNCDESC * pfuncdesc);
+
+
+#endif // ! GDTInfo_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/gdtrt.cxx b/private/oleauto/src/typelib/gdtrt.cxx
new file mode 100644
index 000000000..13653dce4
--- /dev/null
+++ b/private/oleauto/src/typelib/gdtrt.cxx
@@ -0,0 +1,2576 @@
+/***
+*gdtrt.cxx - definition of GEN_DTINFO runtime (rt) members
+*
+* Copyright (C) 1991-93, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* GEN_DTINFO is inherited by BASIC_TYPEINFO and used directly
+* by clients such as COMPOSER.
+*
+*Owner:
+* AlanC
+*
+*Revision History:
+*
+* [00] 05-Apr-93 bradlo: split off from gdtinfo.cxx
+* [01] 30-Apr-93 w-jeffc: made DEFN data members private
+*
+*****************************************************************************/
+
+#include "silver.hxx"
+#include "macros.hxx"
+#include "typelib.hxx"
+#include <new.h>
+#include <stdlib.h>
+
+#include "gdtinfo.hxx"
+#include "ctseg.hxx"
+#include "dtbind.hxx"
+#include "mem.hxx"
+#include "exbind.hxx"
+
+#if VBA3 && !EI_VBARUN && OE_WIN32
+#include "rtdispmod.hxx"
+#endif
+
+#pragma hdrstop(RTPCHNAME)
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if EI_OLE && OE_MAC
+char szOleGDTRTCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleGDTRTCxx
+#else
+static char szGDTRTCxx[] = __FILE__;
+#define SZ_FILE_NAME szGDTRTCxx
+#endif
+#endif //ID_DEBUG
+
+#if EI_OLE
+// Defined in gdtinfo.cxx
+extern TIPERROR IsFunkyDispinterface(GEN_DTINFO *pgdtinfo,
+ BOOL *pisFunkyDispinterface);
+#endif //EI_OLE
+
+extern HRESULT GetTypeInfoOfImplType(GEN_DTINFO *pgdtinfo,
+ UINT uImplType,
+ ITypeInfo **pptinfo);
+
+// InvokeFlags helpers
+//
+inline BOOL
+GEN_DTINFO::IsPropGet(WORD wFlags)
+{
+ return ((wFlags & DISPATCH_PROPERTYGET) != 0);
+}
+
+inline BOOL
+GEN_DTINFO::IsPropPut(WORD wFlags)
+{
+ return ((wFlags & (DISPATCH_PROPERTYPUT | DISPATCH_PROPERTYPUTREF)) != 0);
+}
+
+#if EI_OLE || ID_DEBUG
+inline BOOL
+GEN_DTINFO::IsLegalInvokeFlags(WORD wFlags)
+{ // one (or more) of the bits must be set
+ return (wFlags && ((wFlags & ~(DISPATCH_METHOD | DISPATCH_PROPERTYGET | DISPATCH_PROPERTYPUT | DISPATCH_PROPERTYPUTREF)) == 0));
+}
+#endif //EI_OLE || ID_DEBUG
+
+/***
+*PUBLIC GEN_DTINFO::GetIDsOfNames(OLECHAR FAR* FAR*, UINT, ID FAR*)
+*Purpose:
+* This routine maps an array of names into a corresponding
+* array of MEMBERIDs.
+*
+*Entry:
+* rgszNames = the array of names to map
+* cNames = count of names in the array
+*
+*Exit:
+* return value = HRESULT
+*
+* rgmemid = array of MEMBERIDs corresponding to the given array of names
+*
+***********************************************************************/
+HRESULT GEN_DTINFO::GetIDsOfNames(OLECHAR FAR* FAR* rgszNames,
+ UINT cNames,
+ MEMBERID FAR* rgmemid)
+{
+ UINT u;
+ HLNAM hlnam;
+ TIPERROR err;
+ EXBIND exbind;
+ NAMMGR *pnammgr;
+ HRESULT hresult;
+ TYPE_DATA *ptdata;
+ FUNC_DEFN *qfdefn;
+ VAR_DEFN *qvdefn;
+ HFUNC_DEFN hfdefn;
+ HVAR_DEFN hvdefn;
+ DYN_TYPEMEMBERS *pdtmbrs;
+ PARAM_DEFN *qparamdefn;
+ HPARAM_DEFN hparamdefn;
+#if EI_OB
+ HPARAM_DEFN hparamdefnFirst;
+#endif // EI_OB
+ DYN_TYPEBIND *pdtbind;
+ UINT cArgs, i, iArg;
+ HGNAM hgnam;
+
+ hresult = NOERROR;
+
+ // CONSIDER: do we really want to error cNames == 0?
+ if (rgszNames == NULL || rgmemid == NULL || cNames == 0)
+ return HresultOfScode(E_INVALIDARG);
+
+#if ID_DEBUG // param validation
+#if OE_WIN16
+ if (IsBadReadPtr(rgszNames, cNames * sizeof(char FAR*)))
+ return HresultOfScode(E_INVALIDARG);
+ for (u = 0; u < cNames; ++u) {
+ if (IsBadStringPtr(rgszNames[u], -1))
+ return HresultOfScode(E_INVALIDARG);
+ }
+ if (IsBadWritePtr(rgmemid, cNames * sizeof(MEMBERID)))
+ return HresultOfScode(E_INVALIDARG);
+#endif
+#endif
+
+ // Can't get attributes if type hasn't been laid yet...
+ if (m_pdtroot->CompState() < CS_DECLARED) {
+ return HresultOfScode(TYPE_E_INVALIDSTATE);
+ }
+
+ // assume the worst for simplicity
+ for (u = 0; u < cNames; ++u)
+ rgmemid[u] = DISPID_UNKNOWN;
+
+ IfErrRetHresult(m_pdtroot->GetDtmbrs(&pdtmbrs));
+
+ // NOTE: we really want to match the first thing with the given name,
+ // regardless of invokekind, so we pass in 0 for the invokekind
+ pdtbind = pdtmbrs->Pdtbind();
+
+ ptdata = pdtmbrs->Ptdata();
+
+ // Convert the first string into an HGNAM.
+ IfErrRetHresult(m_pdtroot->GetNamMgr(&pnammgr));
+
+#if OE_WIN32
+ LPSTR lpszName0;
+ int cbName0, cchUnicode;
+
+ cchUnicode = wcslen(rgszNames[0])+1;
+ cbName0 = WideCharToMultiByte(CP_ACP, 0, rgszNames[0], cchUnicode, NULL, 0, NULL, NULL);
+ if (cbName0 == 0)
+ return E_OUTOFMEMORY;
+ lpszName0 = (LPSTR)MemAlloc(cbName0);
+ if (lpszName0 == NULL)
+ return E_OUTOFMEMORY;
+ WideCharToMultiByte(CP_ACP, 0, rgszNames[0], cchUnicode, lpszName0, cbName0, NULL, NULL);
+
+ hlnam = pnammgr->HlnamOfStrIfExist(lpszName0);
+
+ MemFree(lpszName0);
+#else
+ hlnam = pnammgr->HlnamOfStrIfExist(rgszNames[0]);
+#endif
+
+ // If the name isn't in this TypeLib, then don't even bother
+ // going futher.
+ //
+ if (hlnam == HLNAM_Nil) {
+ return HresultOfScode(DISP_E_UNKNOWNNAME);
+ }
+
+ // See if the name is in this TypeInfo.
+ IfErrRetHresult(pnammgr->HgnamOfHlnam(hlnam, &hgnam));
+
+ IfErrRetHresult(pdtmbrs->Pdtbind()->BindDefnCur(FALSE,
+ hgnam,
+ 0,
+ ACCESS_Public,
+ &exbind));
+
+ // NOTE: all code paths after this point must release the exbind's ptinfo
+
+ switch (exbind.BindKind()) {
+ case BKIND_FuncMatch:
+ hfdefn = exbind.Hfdefn();
+ ptdata = exbind.Ptdata();
+ qfdefn = ptdata->QfdefnOfHfdefn(hfdefn);
+ rgmemid[0] = qfdefn->Hmember(); // for the function itself
+
+ // Now let's get its parameter names.
+ if (cNames > 1) {
+ hparamdefn = (HPARAM_DEFN)qfdefn->m_ftdefn.m_hdefnFormalFirst;
+#if EI_OB
+ hparamdefnFirst = hparamdefn;
+#endif // EI_OB
+
+ IfOleErrGo(HresultOfTiperr(m_pdtroot->GetNamMgr(&pnammgr)));
+ cArgs = qfdefn->CArgs(); // don't count LCID & RETVAL parms
+
+ IfErrRetHresult(m_pdtroot->GetNamMgr(&pnammgr));
+
+ // Note: since the input array of names is not necessarily
+ // sorted by parameter position, we have a nested loop to
+ // search for a given param name in the formal list.
+ //
+ // We always search through the list starting from the last
+ // parameter we matched, as people are likely to use the
+ // named parameters in the order they were defined.
+ //
+ for (u = 1, iArg = 0; u < cNames; ++u) {
+ IfOleErrGo(HresultOfTiperr(pnammgr->HlnamOfStrW(rgszNames[u],
+ &hlnam,
+ FALSE,
+ NULL)));
+ for (i=0; i < cArgs; i++, iArg++) {
+ // If we're trying to get past the last argument, start over
+ // with the first.
+ //
+ if (iArg == cArgs) {
+ iArg = 0;
+#if EI_OB
+ hparamdefn = hparamdefnFirst;
+#endif // EI_OB
+ }
+
+ // Check, which param defn (name) matches u'th name stored in the
+ // passed in array of names.
+ //
+#if EI_OB
+ DebAssert(hparamdefn != HPARAMDEFN_Nil,
+ "number vs actual dont match");
+
+ // In OB we walk the linked list of PARAM_DEFN(s).
+ qparamdefn = ptdata->QparamdefnOfHparamdefn(hparamdefn);
+
+ // Get the next param defn.
+ hparamdefn = qparamdefn->HparamdefnNext();
+#else //EI_OB
+ qparamdefn = ptdata->QparamdefnOfIndex(hparamdefn, iArg);
+#endif //EI_OB
+
+ if (qparamdefn->Hlnam() == hlnam) {
+ // NOTE: this memid can't be used as input to GetNames
+ // but only by Invoke.
+ // The memid for a parameter is just its ordinal.
+ //
+ rgmemid[u] = iArg;
+ break;
+ }
+ } // for
+ // If we reach here with i==cArgs, then we didn't find the name
+ // thus the error.
+ //
+ if (i == cArgs) {
+ hresult = HresultOfScode(DISP_E_UNKNOWNNAME);
+ break;
+ }
+
+ // Start the next search with the parameter after this one.
+ iArg++;
+ } // for
+ } // if
+ goto Done;
+ break;
+
+ case BKIND_OneVarMatch:
+ hvdefn = exbind.Hvdefn();
+ qvdefn = exbind.Ptdata()->QvdefnOfHvdefn(hvdefn);
+ // NOTE: extra casting here to appease the mac compiler.
+ DebAssert(qvdefn->IsMemberVarDefn(), "Bad defn");
+ rgmemid[0] = (MEMBERID)((MBR_VAR_DEFN *)qvdefn)->Hmember();
+ goto Done;
+ break;
+
+ case BKIND_NoMatch:
+ // The name wasn't found in our current TypeInfo, so check out
+ // our base class(es).
+ //
+#if EI_OB
+ TYPE_DEFN *qtdefn;
+ HIMPTYPE himptype;
+ ITypeInfo *ptinfo;
+
+ // Get HIMPTYPE of the base class.
+ if (ptdata->CBase() > 0) {
+ qtdefn = ptdata->QtdefnOfHvdefn(ptdata->HvdefnFirstBase());
+ DebAssert(qtdefn->IsUserDefined(), "Bad base class.");
+
+ himptype = qtdefn->Himptype();
+
+ // Try to load the TYPEINFO.
+ IfErrRetHresult(ptdata->Pimpmgr()->GetTypeInfo(himptype,
+ DEP_None,
+ &ptinfo));
+
+ hresult = ptinfo->GetIDsOfNames(rgszNames, cNames, rgmemid);
+
+ ptinfo->Release();
+ }
+
+ break;
+#else // !EI_OB
+ TYPEKIND tkind;
+ HVAR_DEFN hvdefnBaseCur, hvdefnBaseFirst, hvdefnBaseNext;
+ VAR_DEFN *qvdefnBase;
+ TYPE_DEFN *qtdefnBase;
+ HIMPTYPE himptype;
+ ITypeInfo *ptinfo;
+
+ // The following is weird but...
+ // For dispinterfaces, we first check the
+ // 2nd class and only then to the first "true" base.
+ //
+ tkind = GetTypeKind();
+ hvdefnBaseCur = hvdefnBaseFirst = ptdata->HvdefnFirstBase();
+ if (tkind == TKIND_COCLASS) {
+ // For coclasses, we attempt to bind to the DEFAULT
+ // dispinterface which isn't necessarily the first base
+ //
+ while (hvdefnBaseCur != HDEFN_Nil) {
+ qvdefnBase = ptdata->QvdefnOfHvdefn(hvdefnBaseCur);
+ hvdefnBaseNext = qvdefnBase->HdefnNext();
+ // Is this the DEFAULT dispinterface?
+ if (qvdefnBase->GetImplTypeFlags() == IMPLTYPEFLAG_FDEFAULT) {
+ break;
+ }
+ hvdefnBaseCur = hvdefnBaseNext;
+ }
+ }
+ else if (tkind == TKIND_DISPATCH) {
+ // for dispinterfaces we do the funky "start to bind at
+ // the 2nd base" thing of which there can only be one.
+ // In VBA1 we only support a single "embedded" interface.
+ // We ultimately bind to the 1st base.
+ //
+ DebAssert(hvdefnBaseCur != HDEFN_Nil,
+ "dispinterfaces must have a base class.");
+ hvdefnBaseCur = ptdata->QvdefnOfHvdefn(hvdefnBaseCur)->HdefnNext();
+ }
+
+ if (hvdefnBaseCur != HDEFN_Nil) {
+ qvdefnBase = ptdata->QvdefnOfHvdefn(hvdefnBaseCur);
+
+ qtdefnBase = ptdata->QtdefnOfHtdefn(qvdefnBase->Htdefn());
+ DebAssert(qtdefnBase->IsUserDefined(), "Bad base class.");
+
+ himptype = qtdefnBase->Himptype();
+
+ // Try to load the TYPEINFO.
+ IfErrRetHresult(ptdata->Pimpmgr()->GetTypeInfo(himptype,
+ DEP_None,
+ &ptinfo));
+
+ hresult = ptinfo->GetIDsOfNames(rgszNames, cNames, rgmemid);
+
+ ptinfo->Release();
+ }else{
+ hresult = HresultOfScode(DISP_E_UNKNOWNNAME);
+ }
+
+ // If dispinterface then
+ // if no match yet, then
+ // then finally check the first base.
+ //
+ if (tkind == TKIND_DISPATCH
+ && hresult == HresultOfScode(DISP_E_UNKNOWNNAME)) {
+
+ DebAssert(hvdefnBaseFirst != HDEFN_Nil,
+ "dispinterface must have base.");
+ qvdefnBase = ptdata->QvdefnOfHvdefn(hvdefnBaseFirst);
+
+ qtdefnBase = ptdata->QtdefnOfHtdefn(qvdefnBase->Htdefn());
+ DebAssert(qtdefnBase->IsUserDefined(), "Bad base class.");
+
+ himptype = qtdefnBase->Himptype();
+
+ // Try to load the TYPEINFO.
+ IfErrRetHresult(ptdata->Pimpmgr()->GetTypeInfo(himptype,
+ DEP_None,
+ &ptinfo));
+
+ hresult = ptinfo->GetIDsOfNames(rgszNames, cNames, rgmemid);
+
+ ptinfo->Release();
+ } // if dispinterface
+
+ break;
+#endif //EI_OLE
+
+ default:
+ // Undefined name
+ hresult = HresultOfScode(DISP_E_UNKNOWNNAME);
+ break;
+
+ } // switch
+
+ // fall through...
+Done:
+Error:
+ if (exbind.Ptinfo() != NULL) {
+ exbind.Ptinfo()->Release();
+ }
+ return hresult;
+}
+
+/***
+*PRIVATE GEN_DTINFO::IndexOfParam
+*Purpose:
+* Return the index in the given dispparams->rgvarg array of the
+* param identified by the given position.
+*
+* This is a helper for implementations of ITypeInfo::Invoke()
+*
+*Entry:
+* pdispparams = the dispparams struct to lookup in
+* uPos = the position of the param
+*
+*Exit:
+* return value = HRESULT
+*
+* *puIndex = the index in the rgvarg array of the param
+*
+***********************************************************************/
+HRESULT NEARCODE
+GEN_DTINFO::IndexOfParam(DISPPARAMS *pdispparams, UINT uPos, UINT *puIndex)
+{
+ int i;
+
+ // try for named parameter first (if there are any)
+
+ for (i = 0; i < (int)pdispparams->cNamedArgs; ++i)
+ if (pdispparams->rgdispidNamedArgs[i] == (DISPID)((int)uPos))
+ goto LGotIt;
+
+ // otherwise the param was passed positionally
+
+ i = pdispparams->cArgs - (int)uPos - 1;
+
+ if (i < (int)pdispparams->cNamedArgs)
+ return HresultOfScode(DISP_E_PARAMNOTFOUND);
+
+ DebAssert(i >= (int)pdispparams->cNamedArgs
+ && i < (int)pdispparams->cArgs, "");
+
+LGotIt:;
+ *puIndex = (UINT)i;
+
+ return NOERROR;
+}
+
+
+/***
+*PRIVATE HRESULT NEARCODE GEN_DTINFO::VariantVtOfTypedesc
+*Purpose:
+* Convert the given typeinfo TYPEDESC into a VARTYPE that can be represented
+* in a VARIANT. For some this is a 1:1 mapping, for others we convert to a
+* (possibly machine dependent, eg VT_INT->VT_I2) base type, and
+* others we cant represent in a VARIANT.
+*
+* This is a helper for implementatinos of ITypeInfo::Invoke()
+* and makes some assumptions about how the low level invocation
+* support routines expect to see things represented (void is
+* represented as VT_EMPTY for example).
+*
+*Entry:
+* lptdesc = * to the typedesc to convert
+* *pGuid -- NULL if caller doesn't care about this return value
+*
+*Exit:
+* return value = HRESULT
+*
+* *pvt = a VARTYPE that may be stored in a VARIANT.
+* *pGuid = a guid for a INTERFACE/DISPINTERFACE typeinfo (see below)
+*
+* *pfGotObjGuid = 0 no cached guid in *pGuid
+* *pfGotObjGuid = 1 Seen 'MyInterface' -- *pGuid contains MyInterface's guid
+* *pfGotObjGuid = 2 Seen 'MyInterface *' -- *pGuid contains the guid
+* NOTE: Not sufficient to check *pfGotObjGuid without
+* also checking *pvt, since the VT_BYREF and/or VT_ARRAY
+* bits could be or'ed in with VT_DISPATCH/VT_UNKNOWN
+*
+*
+***********************************************************************/
+HRESULT NEARCODE
+GEN_DTINFO::VariantVtOfTypedesc(TYPEDESC FAR* lptdesc,
+ USHORT * pfGotObjGuid,
+ GUID * pGuid,
+ VARTYPE FAR* pvt)
+{
+ HRESULT hresult = NOERROR;
+ ITypeInfo FAR * lptinfo;
+ LPTYPEATTR ptypeattr;
+ VARTYPE vt;
+
+ *pfGotObjGuid = 0; // haven't got a interface/dispinterface guid
+
+ if (lptdesc->vt <= VT_UNKNOWN || lptdesc->vt == VT_HRESULT || lptdesc->vt == VT_UI1)
+ {
+ // all types from VT_EMPTY (0) up to & including VT_UNKNOWN
+ *pvt = lptdesc->vt; // are dispatchable
+ }
+ else {
+
+ // Accept a limited set of non-simple types (like int's, alias's, and
+ // enum's) that we can easily handle.
+
+ switch (lptdesc->vt) {
+ case VT_INT:
+ // don't switch on the typelib's syskind, because at this point,
+ // we can/must assume that our syskind matches the syskind of
+ // the routine we are invoking.
+#if HP_16BIT
+ *pvt = VT_I2;
+#else
+ *pvt = VT_I4;
+#endif
+ break;
+
+ case VT_VOID:
+ *pvt = VT_EMPTY; // this is how DoInvoke() represents void
+ break;
+
+ case VT_USERDEFINED:
+ hresult = GetRefTypeInfo(lptdesc->hreftype, &lptinfo);
+ if (hresult == NOERROR) {
+ hresult = lptinfo->GetTypeAttr(&ptypeattr);
+ if (hresult == NOERROR) {
+ switch (ptypeattr->typekind) {
+ case TKIND_ENUM:
+ // don't switch on the typelib's syskind, because at this point,
+ // we can/must assume that our syskind matches the syskind of
+ // the routine we are invoking.
+#if HP_16BIT
+ *pvt = VT_I2;
+#else
+ *pvt = VT_I4;
+#endif
+ break;
+ case TKIND_ALIAS:
+ hresult = VariantVtOfTypedesc(&(ptypeattr->tdescAlias),
+ pfGotObjGuid,
+ pGuid,
+ pvt);
+ break;
+ case TKIND_COCLASS:
+ *pvt = VT_DISPATCH;
+ if(pGuid){
+ ITypeInfo *ptinfoDef;
+ TYPEATTR *ptypeattrDef;
+ INT impltypeflags;
+ UINT iImplType, cImplTypes = ptypeattr->cImplTypes;
+ HREFTYPE hreftype;
+
+ for(iImplType = 0; iImplType < cImplTypes; ++iImplType) {
+ IfOleErrGo(lptinfo->GetImplTypeFlags(iImplType,
+ &impltypeflags));
+
+ if (IMPLTYPEFLAG_FDEFAULT
+ == (impltypeflags
+ & (IMPLTYPEFLAG_FDEFAULT
+ | IMPLTYPEFLAG_FSOURCE))) {
+
+ // Found It!
+ IfOleErrGo(lptinfo->GetRefTypeOfImplType(iImplType,
+ &hreftype));
+
+ IfOleErrGo(lptinfo->GetRefTypeInfo(hreftype,
+ &ptinfoDef));
+ break;
+ } // if
+ } // for
+
+ DebAssert(iImplType != cImplTypes, "No default base.");
+
+ hresult = ptinfoDef->GetTypeAttr(&ptypeattrDef);
+
+ if (hresult == NOERROR) {
+ *pGuid = ptypeattrDef->guid;
+ ptinfoDef->ReleaseTypeAttr(ptypeattrDef);
+ }
+
+ ptinfoDef->Release();
+ }
+ (*pfGotObjGuid)++; // set flag to 1
+ break;
+ case TKIND_INTERFACE:
+ *pvt = VT_UNKNOWN;
+ goto StuffGuid;
+#if EI_OB
+ case TKIND_CLASS:
+#endif // EI_OB
+ case TKIND_DISPATCH:
+ *pvt = VT_DISPATCH;
+StuffGuid:
+ if (pGuid) { // only if we care about this info
+ *pGuid = ptypeattr->guid;
+ }
+ (*pfGotObjGuid)++; // set flag to 1
+ break;
+ default:
+ hresult = HresultOfScode(DISP_E_BADVARTYPE);
+ } // switch
+Error:
+ lptinfo->ReleaseTypeAttr(ptypeattr);
+ }
+ lptinfo->Release();
+ }
+ break;
+
+ case VT_PTR:
+ hresult = VariantVtOfTypedesc(lptdesc->lptdesc,
+ pfGotObjGuid,
+ pGuid,
+ &vt);
+ if (hresult == NOERROR) {
+ if (*pfGotObjGuid == 1) {
+ DebAssert(vt == VT_DISPATCH || vt == VT_UNKNOWN, "");
+ *pvt = vt; // don't OR in VT_BYREF here
+ (*pfGotObjGuid)++; // set flag to 2
+ } else
+ if (vt & VT_BYREF) {
+ // error if nested pointer type
+ hresult = HresultOfScode(DISP_E_BADVARTYPE);
+ } else {
+ *pvt = (vt | VT_BYREF);
+ }
+ }
+ break;
+
+ case VT_SAFEARRAY:
+ hresult = VariantVtOfTypedesc(lptdesc->lptdesc,
+ pfGotObjGuid,
+ pGuid,
+ &vt);
+ if (hresult == NOERROR) {
+ if (vt & (VT_BYREF | VT_ARRAY)) {
+ // error if nested array or array of pointers
+ hresult = HresultOfScode(DISP_E_BADVARTYPE);
+ } else {
+ *pvt = (vt | VT_ARRAY);
+ }
+ }
+ break;
+
+ default:
+ // don't know how to handle other non-simple VT_xxx types.
+ hresult = HresultOfScode(DISP_E_BADVARTYPE);
+ } // switch
+ } // if
+
+ return hresult;
+}
+
+/***
+*PRIVATE HRESULT NEARCODE GEN_DTINFO::VariantVtOfHtdefn
+*Purpose:
+* Obtain an Variant-compatible vt type for the given htdefn, or
+* return an error if this is not possible.
+*
+*Entry:
+* htdefn = the htdefn to look at
+* ptdata = the tdata
+* fSimpleType = is this htdefn a simple type or not
+* pVt = where to put the resulting VARTYPE
+*
+*Exit:
+* return value = HRESULT
+*
+* *pvt = a VARTYPE that may be stored in a VARIANT.
+*
+***********************************************************************/
+HRESULT NEARCODE
+GEN_DTINFO::VariantVtOfHtdefn(HTYPE_DEFN htdefn,
+ TYPE_DATA * ptdata,
+ BOOL fSimpleType,
+ USHORT * pfGotObjGuid,
+ GUID * pGuid,
+ VARTYPE FAR * pVt)
+{
+ HRESULT hresult;
+ TYPEDESC typedesc;
+ TIPERROR err;
+
+ IfErrRetHresult(ptdata->AllocTypeDescOfTypeDefn(htdefn,
+ fSimpleType,
+ &typedesc));
+ hresult = VariantVtOfTypedesc(&typedesc,
+ pfGotObjGuid,
+ pGuid,
+ pVt);
+
+ // don't need the typedesc anymore
+ ClearTypeDesc(&typedesc);
+ return hresult;
+
+}
+
+#if OE_MAC && !OE_DLL || OE_MACPPC // mac static lib version can't do this
+#define DoInvoke(a,b,c,d,e,f,g,h) HresultOfScode(E_NOTIMPL);
+#else //OE_MAC && !OE_DLL
+
+#if EI_OB
+// OB must have it's own low-level dispatch helper. It cannot use the OLE
+// version because the DoInvokeMethod API exposed by ole2disp.dll is private
+// and can only be used by typelib.dll.
+STDAPI
+DoInvoke(
+ void FAR* pvInstance,
+ unsigned int oVft,
+ CALLCONV cc,
+ VARTYPE vtReturn,
+ unsigned int cActuals,
+ VARTYPE FAR* rgvt,
+ VARIANTARG FAR* FAR* rgpvarg,
+ VARIANT FAR* pvarResult);
+#else //EI_OB
+STDAPI
+DoInvokeMethod(
+ void FAR* pvInstance,
+ unsigned int oVft,
+ CALLCONV cc,
+ VARTYPE vtReturn,
+ unsigned int cActuals,
+ VARTYPE FAR* rgvt,
+ VARIANTARG FAR* FAR* rgpvarg,
+ VARIANT FAR* pvarResult);
+
+#define DoInvoke DoInvokeMethod
+#endif //EI_OB
+#endif //OE_MAC && !OE_DLL
+
+#if VBA3 && !EI_VBARUN && OE_WIN32 // helper function for invoking functions in standard module
+STDAPI
+DoInvokeFunction(
+// void FAR* pvInstance, // must pass NULL
+ VOID * pvTemplate,
+ CALLCONV cc,
+ VARTYPE vtReturn,
+ unsigned int cActuals,
+ VARTYPE FAR* rgvt,
+ VARIANTARGA FAR* FAR* rgpvarg,
+ VARIANTA FAR* pvarResult,
+ EXCEPINFO FAR* pexcepinfo);
+#endif
+
+
+
+/***
+*PUBLIC GEN_DTINFO(VOID FAR*, INVOKEDESC FAR*)
+*Purpose:
+* Invoke the method identified by the given memid and wFlags,
+* using the parameters in the given dispparams struct on the
+* given instance.
+*::Invoke
+*Entry:
+* pvInstance = the instance to invoke on or NULL if this is a standard module's gtdinfo
+* memid = the MEMBERID of the method to invoke
+* wFlags = the 'kind' of the invocation
+* pdispparams = the arguments to the method
+*
+*Exit:
+* return value = HRESULT
+*
+* *pvarResult = the return value from the method
+* *pexcepinfo = a structure of extended error (exception) info
+* if the return value was DISP_E_EXCEPTION
+* *puArgErr = the index of the offending argument if a
+* typemismatch occured
+*
+*
+*Change made on Oct 20,94 for supporting UDF: (meichint)
+*Note:
+*
+*Implementation note:
+* (1) Return value issues:(for OB)
+* * If the memid is a function, the return value can be disgarded. Local variable
+* varResult is used to temporarily hold the return value when invoking either
+* DoInvoke or DoInvokeFunction.
+* * If the memid is a subroutine, the design is that an error of Type_Mismatch
+* will be generated when invoked with nonNULL pvarResult.
+*
+* (2) In the case of TKIND_MODULE
+* * If GetTypeKind()==TKIND_MODULE, vtable doesn't exist. Therefore,
+* we invoke with the native entry point of the memid through DoInvokeFunction
+* * AddressOfMember is used to retrieve native entry point
+* * In the case of OB, pvarResult must be of NULL value if the method
+* to be invoked is a subroutine rather than a function.(This is by
+* design so that we can catch this compiler error at runtime.)
+***********************************************************************/
+HRESULT GEN_DTINFO::Invoke(VOID FAR* pvInstance,
+ MEMBERID memid,
+ WORD wFlags,
+ DISPPARAMS FAR *pdispparams,
+ VARIANT FAR *pvarResult,
+ EXCEPINFO FAR *pexcepinfo,
+ UINT FAR *puArgErr)
+{
+ TIPERROR err;
+ HRESULT hresult;
+ UINT uArgErr;
+ VARTYPE vtReturn;
+ VARTYPE vtReturnTypeinfo;
+ VARIANT varResult; // temporary result holder if pvarResult==NULL
+ VARIANT *pvarRetval = NULL;
+ VARIANT bufRetval; // big enough to hold a variant
+ TYPE_DATA *ptdata;
+ FUNC_DEFN *qfdefn;
+ HFUNC_DEFN hfdefn;
+ INVOKEARGS *pinvargs;
+ DYN_TYPEMEMBERS *pdtmbrs;
+ LCID lcid;
+ ITypeInfo FAR* ptinfo;
+ USHORT fGotObjGuid;
+ CALLINGCONVENTION cc;
+#if EI_OB
+ BOOL fClean;
+ BOOL fIsSub;
+#endif // EI_OB
+ BOOL fPropParamSplit = FALSE; // TRUE if we're splitting the parameter
+ // list on a collection lookup.
+ // (vba3 bug #4481)
+#if VBA3 && !EI_VBARUN && OE_WIN32
+ BOOL isModule = 0; // TRUE if we're invoking a method of a standard module
+ LPVOID pvTemplate; // native entry point
+ INVOKEKIND invkind; // type casting for wFlags
+
+ invkind = (INVOKEKIND) wFlags;
+#endif
+
+ DebAssert(m_pdtroot->CompState() >= CS_DECLARED, "");
+
+ switch(GetTypeKind()) {
+#if EI_OB
+ // pretend this is an interface, its supposed to have all
+ // of the necessarry info, in all of the correct places.
+ case TKIND_CLASS:
+#endif
+ case TKIND_INTERFACE:
+ break;
+
+ case TKIND_DISPATCH:
+#if EI_OLE
+ // If this is a funky dispinterface, i.e. defined in terms
+ // of an interface, then recursively call invoke on the
+ // second base member (the "pseudo-base" interface).
+ // Note that this is the ONLY way currently (v1) to invoke
+ // a method on a dispinterface.
+ //
+ BOOL isFunkyDispinterface;
+
+ IfOleErrRet(HresultOfTiperr(
+ IsFunkyDispinterface(this, &isFunkyDispinterface)));
+ if (isFunkyDispinterface) {
+ // "pseudo-base"
+ IfOleErrRet(GetTypeInfoOfImplType(this, 1, &ptinfo));
+ hresult = ptinfo->Invoke(pvInstance,
+ memid,
+ wFlags,
+ pdispparams,
+ pvarResult,
+ pexcepinfo,
+ puArgErr);
+ ptinfo->Release();
+ return hresult;
+ }
+#endif // EI_OLE
+
+ return HresultOfScode(DISP_E_MEMBERNOTFOUND);
+
+ case TKIND_COCLASS:
+#if 0 //CONSIDER: activate for V2. don't want to pay the testing
+ //CONSIDER: cost for V1
+ { // recursively call invoke on the first member of CoClass
+ // NOTE: this assumes that the first implemented interface is what we
+ // want to invoke on. This may be incorrect.
+
+ // CONSIDER: the following is implemented using the public TypeInfo
+ // interface - there may be a more efficient internal way to do this.
+
+ HREFTYPE hreftype;
+
+ if ((hresult = GetRefTypeOfImplType(0, &hreftype)) != NOERROR)
+ return hresult;
+ if ((hresult = GetRefTypeInfo(hreftype, &ptinfo)) != NOERROR)
+ return hresult;
+
+ hresult = ptinfo->Invoke(pvInstance,
+ memid,
+ wFlags,
+ pdispparams,
+ pvarResult,
+ pexcepinfo,
+ puArgErr);
+ ptinfo->Release();
+
+ return hresult;
+ }
+#endif //0
+
+#if VBA3 && !EI_VBARUN && OE_WIN32
+ return HresultOfScode(E_NOTIMPL);
+#endif
+
+ case TKIND_MODULE: //CONSIDER: maybe implement for V2
+#if VBA3 && !EI_VBARUN && OE_WIN32 // TKIND_MODULE is implemented for mercury
+ isModule = 1;
+ break;
+#else
+ return HresultOfScode(E_NOTIMPL);
+#endif
+
+ default:
+ // cant invoke on anything else.
+ return HresultOfScode(E_INVALIDARG);
+ } // end switch
+
+#if EI_OLE // simple parm validation
+ if (pvInstance == NULL || pdispparams == NULL) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+#endif //EI_OLE
+
+ // design issue :
+ // When invoking a function, the return value can be disgarded.
+ // Thus varResult is disposable placeholder for the return value if the caller is not
+ // expecting a return value.
+ if (puArgErr == NULL)
+ puArgErr = &uArgErr;
+ if (pvarResult == NULL) {
+ varResult.vt = VT_EMPTY;
+ pvarResult = &varResult;
+ }
+
+#if ID_DEBUG // param validation
+#if OE_WIN16
+ if (IsBadReadPtr(pvInstance, sizeof(void FAR*)))
+ return HresultOfScode(E_INVALIDARG);
+ // CONSIDER: need a debug routine to check the contents of the following
+ if (IsBadReadPtr(pdispparams, sizeof(*pdispparams)))
+ return HresultOfScode(E_INVALIDARG);
+ if (IsBadWritePtr(pvarResult, sizeof(*pvarResult)))
+ return HresultOfScode(E_INVALIDARG);
+ if (IsBadWritePtr(puArgErr, sizeof(*puArgErr)))
+ return HresultOfScode(E_INVALIDARG);
+#endif
+#endif
+
+#if EI_OLE
+ // make sure no illegal wFlags are set
+ if (!IsLegalInvokeFlags(wFlags))
+ return HresultOfScode(E_INVALIDARG);
+#else //EI_OLE
+ DebAssert(IsLegalInvokeFlags(wFlags), "bogus flags");
+#endif //EI_OLE
+
+ IfErrRetHresult(m_pdtroot->GetDtmbrs(&pdtmbrs));
+ ptdata = pdtmbrs->Ptdata();
+
+ // 1. lookup the hdefn corresponding to the given memid & wFlags
+
+#if EI_OB
+ err = ptdata->HfdefnOfAnyHmember(memid,
+ wFlags,
+ &hfdefn,
+ &fClean);
+
+ if (err == TIPERR_FuncArityMismatch) {
+ return HresultOfScode(DISP_E_BADPARAMCOUNT);
+ }
+ else if (err != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+
+ if (hfdefn != HFUNCDEFN_Nil) {
+#else // !EI_OB
+ if ((hfdefn = ptdata->HfdefnOfHmember(memid, wFlags)) != HFUNCDEFN_Nil) {
+#endif // !EI_OB
+
+#if VBA3 && !EI_VBARUN && OE_WIN32
+ if (isModule)
+ IfFailGoTo(AddressOfMember( memid,
+ invkind,
+ &pvTemplate),
+ Error);
+#endif
+
+ // validate the arg count
+ qfdefn = ptdata->QfdefnOfHfdefn(hfdefn);
+
+ UINT cArgsMax = qfdefn->CArgs(); // don't count LCID & RETVAL parms
+ UINT cArgsOpt = qfdefn->CArgsOpt();
+ UINT cArgsReq;
+
+ if (cArgsOpt == -1) { // vararg case
+ cArgsReq = cArgsMax - 1; // don't include SAFEARRAY in min # of args
+ cArgsMax = (UINT)~0; // no upper limit on # of args
+ if (pdispparams->cNamedArgs != 0) {
+ // named args aren't allowed in a vararg function
+ hresult = HresultOfScode(DISP_E_NONAMEDARGS);
+ goto Error;
+ }
+ }
+ else {
+ cArgsReq = cArgsMax - cArgsOpt;
+ }
+
+ if (pdispparams->cArgs <= cArgsMax) {
+ if (pdispparams->cArgs >= cArgsReq) {
+ // legal parameter counts
+ goto LInvokeStandard;
+ }
+ }
+ else { // more args than the maximum
+
+ // handle possible indexed collection property access
+ // We allow property get with 0 args, and property put/putref
+ // where the matching property get function takes 0 args
+ //
+ // We also allow a property put/putref where the matching
+ // property get function takes all but the RHS parameter.
+ // (vba2 bug #4481).
+ //
+ if (IsPropGet(wFlags)) {
+ if (cArgsMax == 0)
+ goto LCollectionProperty;
+ }
+ else if (IsPropPut(wFlags)) {
+#if EI_OB
+ if (fClean) {
+ ptdata->FreeFuncDefn(hfdefn);
+ }
+ err = ptdata->HfdefnOfAnyHmember(memid,
+ (INVOKEKIND) DISPATCH_PROPERTYGET,
+ &hfdefn,
+ &fClean);
+
+ if (err == TIPERR_FuncArityMismatch) {
+ return HresultOfScode(DISP_E_BADPARAMCOUNT);
+ }
+ else if (err != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+ if (hfdefn != HFUNCDEFN_Nil) {
+#if VBA3 && !EI_VBARUN && OE_WIN32
+ if (ptdata->QfdefnOfHfdefn(hfdefn)->CArgs() == 0) {
+ if (isModule)
+ IfFailGoTo(AddressOfMember(memid,
+ INVOKE_PROPERTYGET,
+ &pvTemplate),
+ Error);
+ goto LCollectionProperty;
+ }
+#else
+ if (ptdata->QfdefnOfHfdefn(hfdefn)->CArgs() == 0) {
+ goto LCollectionProperty;
+ }
+#endif
+ // Allow the property put function takes all of the arguments
+ // except for the RHS parameter. (vba2 bug #4481)
+ //
+ else if (ptdata->QfdefnOfHfdefn(hfdefn)->CArgs()
+ == pdispparams->cArgs - 1) {
+
+ fPropParamSplit = TRUE;
+ goto LCollectionProperty;
+ }
+ }
+#else // !EI_OB
+ // UNDONE OA95: more code could be shared between OA and OB.
+ if ((hfdefn = ptdata->HfdefnOfHmember(memid, DISPATCH_PROPERTYGET))
+ != HFUNCDEFN_Nil) {
+
+ if (ptdata->QfdefnOfHfdefn(hfdefn)->CArgs() == 0) {
+ goto LCollectionProperty;
+ }
+ // Allow the property put function takes all of the arguments
+ // except for the RHS parameter. (vba2 bug #4481)
+ //
+ else if (ptdata->QfdefnOfHfdefn(hfdefn)->CArgs()
+ == pdispparams->cArgs - 1) {
+
+ fPropParamSplit = TRUE;
+ goto LCollectionProperty;
+ }
+ }
+#endif // !EI_OB
+ }
+ }
+
+ hresult = HresultOfScode(DISP_E_BADPARAMCOUNT);
+ goto Error;
+ }
+
+ // Member not found... but there is one more special case to check for.
+ //
+ // This may be an indexed collection PropertyPut where the collection
+ // property itself has only a get method.
+
+ if (IsPropPut(wFlags)) {
+#if EI_OB
+ // We know there is no put/putref -- now ensure there is no putref/put
+ err = ptdata->HfdefnOfAnyHmember(memid,
+ (wFlags == DISPATCH_PROPERTYPUT)
+ ? DISPATCH_PROPERTYPUTREF
+ : DISPATCH_PROPERTYPUT,
+ &hfdefn,
+ &fClean);
+
+ if (err == TIPERR_FuncArityMismatch) {
+ return HresultOfScode(DISP_E_BADPARAMCOUNT);
+ }
+ else if (err != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+
+ if (hfdefn == HFUNCDEFN_Nil) {
+ // no put or putref -- see if there is a get
+ err = ptdata->HfdefnOfAnyHmember(memid,
+ DISPATCH_PROPERTYGET,
+ &hfdefn,
+ &fClean);
+
+ if (err == TIPERR_FuncArityMismatch) {
+ return HresultOfScode(DISP_E_BADPARAMCOUNT);
+ }
+ else if (err != TIPERR_None) {
+ return HresultOfTiperr(err);
+ }
+
+ if (hfdefn != HFUNCDEFN_Nil) {
+#if VBA3 && !EI_VBARUN && OE_WIN32
+ if (isModule)
+ IfFailGoTo(AddressOfMember( memid,
+ INVOKE_PROPERTYGET,
+ &pvTemplate),
+ Error);
+#endif
+ if (ptdata->QfdefnOfHfdefn(hfdefn)->CArgs() == 0) {
+ goto LCollectionProperty;
+ }
+ // Allow the property put function takes all of the arguments
+ // except for the RHS parameter. (vba2 bug #4481)
+ //
+ else if (ptdata->QfdefnOfHfdefn(hfdefn)->CArgs()
+ == pdispparams->cArgs - 1) {
+
+ fPropParamSplit = TRUE;
+ goto LCollectionProperty;
+ }
+ }
+ }
+#else // !EI_OB
+ // We know there is no put/putref -- now ensure there is no putref/put
+ if (ptdata->HfdefnOfHmember(memid,
+ (wFlags == DISPATCH_PROPERTYPUT) ?
+ DISPATCH_PROPERTYPUTREF :
+ DISPATCH_PROPERTYPUT
+ ) == HFUNCDEFN_Nil) {
+ // no put or putref -- see if there is a get
+ if ((hfdefn = ptdata->HfdefnOfHmember(memid, DISPATCH_PROPERTYGET))
+ != HFUNCDEFN_Nil) {
+
+ if (ptdata->QfdefnOfHfdefn(hfdefn)->CArgs() == 0) {
+ goto LCollectionProperty;
+ }
+ // Allow the property put function takes all of the arguments
+ // except for the RHS parameter. (vba2 bug #4481)
+ //
+ else if (ptdata->QfdefnOfHfdefn(hfdefn)->CArgs()
+ == pdispparams->cArgs - 1) {
+
+ fPropParamSplit = TRUE;
+ goto LCollectionProperty;
+ }
+ }
+ }
+#endif // !EI_OB
+//#if EI_OB
+
+ }
+
+ // Yet another special case to check for. If we have a base interface,
+ // then this member could be defined in it. Recurse.
+
+#if VBA3 && !EI_VBARUN && OE_WIN32
+ if (isModule) // for TKIND_MODULE, there is no base class
+ return HresultOfScode(DISP_E_MEMBERNOTFOUND);
+#endif
+
+#if EI_OB
+ DebAssert(GetTypeKind() == TKIND_INTERFACE || GetTypeKind() == TKIND_CLASS, "assuming interface");
+#else
+ DebAssert(GetTypeKind() == TKIND_INTERFACE, "assuming interface");
+#endif
+
+ if (ptdata->CBase() > 0) {
+ // recurse on first (only) base interface
+ DebAssert(ptdata->CBase() == 1, "no multiple-inheritance");
+ IfOleErrRet(GetTypeInfoOfImplType(this, 0, &ptinfo));
+ hresult = ptinfo->Invoke(pvInstance,
+ memid,
+ wFlags,
+ pdispparams,
+ pvarResult,
+ pexcepinfo,
+ puArgErr);
+ ptinfo->Release();
+ return hresult;
+ }
+
+ return HresultOfScode(DISP_E_MEMBERNOTFOUND);
+
+
+LInvokeStandard:;
+//upon entry :: if TKIND_MODULE case : pvTemplate is the native entry point
+// hfdefn describes the function
+
+// gather and coerce the actuals
+ hresult = GetInvokeArgs(hfdefn,
+ ptdata,
+ wFlags,
+ pdispparams,
+ &pvarRetval,
+ (VOID *)&bufRetval,
+ &pinvargs,
+ puArgErr,
+ FALSE);
+ if (hresult != NOERROR) {
+ goto Error;
+ }
+
+ // WARNING: All error paths after this point must free pinvargs!
+
+ // get (and potentially translate) the return type
+
+ qfdefn = ptdata->QfdefnOfHfdefn(hfdefn);
+
+#if EI_OB
+ fIsSub = qfdefn->IsSub(); // put in a local 'cause it's big & slow
+ // Error if we're trying to invoke a Basic Sub late-bound and our caller
+ // passed us a pVarResult parm (meaning that Basic code is calling trying
+ // to call a sub as a function). This is a compile-time error in the
+ // early-bound case. Latebound, the best we can do is a runtime error in
+ // the IDE. There will be no error in a made exe (since the default OLE
+ // implementation is used), but those are the breaks.
+ //
+ // Note that it is an error when a return value is expeccted by caller
+ // while calling a subroutine.
+ if (fIsSub && pvarResult != &varResult) {
+ hresult = HresultOfScode(DISP_E_TYPEMISMATCH); // CONSIDER: better error?
+ goto LError2;
+ }
+ if (fIsSub && !qfdefn->IsMunged()){
+#else // !EI_OB
+ if (qfdefn->IsSub()){
+#endif // !EI_OB
+ vtReturn = vtReturnTypeinfo = VT_EMPTY;
+ } else {
+#if EI_OB
+ hresult = VariantVtOfHtdefn(qfdefn->m_ftdefn.HtdefnResultUnmunged(),
+ ptdata,
+ qfdefn->m_ftdefn.IsSimpleTypeResultUnmunged(),
+ &fGotObjGuid,
+ // don't need the guid if Retval is an object
+ NULL,
+ &vtReturnTypeinfo);
+#else // EI_OLE
+ hresult = VariantVtOfHtdefn(qfdefn->m_ftdefn.HtdefnResult(),
+ ptdata,
+ qfdefn->m_ftdefn.IsSimpleTypeResult(),
+ &fGotObjGuid,
+ // don't need the guid if Retval is an object
+ NULL,
+ &vtReturnTypeinfo);
+#endif // EI_OLE
+
+ if (hresult != NOERROR) {
+ goto LError2;
+ } // Do we allow VT_HRESULT for module case??? We don't allow it for class's case....
+ vtReturn = (vtReturnTypeinfo == VT_HRESULT) ? VT_ERROR : vtReturnTypeinfo;
+ }
+
+ // call the low-level invocation helper
+
+ qfdefn = ptdata->QfdefnOfHfdefn(hfdefn);
+#if EI_OB
+ cc = qfdefn->m_ftdefn.CcUnmunged();
+#else // EI_OLE
+ cc = qfdefn->m_ftdefn.Cc();
+#endif // EI_OLE
+
+ qfdefn = ptdata->QfdefnOfHfdefn(hfdefn);
+
+
+#if VBA3 && !EI_VBARUN && OE_WIN32
+ if (isModule)
+ hresult = DoInvokeFunction(pvTemplate,
+ cc,
+ vtReturn,
+ pinvargs->cArgs,
+ pinvargs->rgvt,
+ (VARIANTARG FAR* FAR*)pinvargs->rgpvarg,
+ (VARIANT FAR*)pvarResult,
+ pexcepinfo);
+ else
+#endif
+ hresult = DoInvoke(pvInstance,
+ (SHORT)((VIRTUAL_FUNC_DEFN*)qfdefn)->Ovft(),
+ cc,
+ vtReturn,
+ pinvargs->cArgs,
+ pinvargs->rgvt,
+ (VARIANTARG FAR* FAR*)pinvargs->rgpvarg,
+ (VARIANT FAR*)pvarResult);
+
+ // copy back the Byref args passed to Byref Variants, if any
+ if (hresult == NOERROR) {
+ hresult = CopyBackByrefArgs(pinvargs);
+ }
+
+ // if the return type of this function is HRESULT, then we want to
+ // fill in the excepinfo structure if the function returned an error
+ if (hresult == NOERROR) {
+ if (vtReturnTypeinfo == VT_HRESULT) {
+ DebAssert(pvarResult->vt == VT_ERROR, "bad func return type");
+ if (FAILED(pvarResult->scode)) {
+ // Put the specific error the function returned into the
+ // excepinfo structure.
+ if (pexcepinfo != NULL) {
+ //
+ // UNDONE: need to check and see if this instance supports
+ // UNDONE: rich error information before we do the following...
+ //
+
+ GetErrorInfo(pexcepinfo); // zeros out *pexcepinfo
+ // stuff error code from function in excepinfo structure
+ pexcepinfo->scode = pvarResult->scode;
+ }
+ // signal that the excepinfo structure contains error info.
+ hresult = HresultOfScode(DISP_E_EXCEPTION);
+ }
+ else {
+ // if the retval arg was specified, then the function put it's real
+ // return value in *pvarRetval. Copy this to pvarResult. Ok to
+ // just overwrite *pvarResult because it's not an owner.
+ if (pvarRetval) {
+ DebAssert(pvarRetval->vt & VT_BYREF, "not a byref return");
+ vtReturn = (pvarRetval->vt & ~VT_BYREF);
+ if (vtReturn == VT_VARIANT) {
+ *pvarResult = bufRetval; // copy entire variant returned
+ } else {
+ pvarResult->vt = vtReturn; // set tag
+ memcpy(&pvarResult->iVal, &bufRetval, 8); // copy data
+ }
+ goto RealRetVal;
+ }
+ }
+ // HRESULT-returning function with no retval parm should act like a SUB
+ pvarResult->vt = VT_EMPTY;
+RealRetVal:;
+ }
+
+ // if we put the result into a temporary, must discard it
+ if (pvarResult == &varResult) {
+ VariantClear(pvarResult);
+ }
+ }
+
+LError2:
+ ReleaseInvokeArgs(pinvargs);
+
+ goto Error;
+
+LCollectionProperty:;
+ // upon entry : pvTemplate and hfdefn should be set up as LInvokeStandard
+
+ VARIANT varTmp;
+ // don't have to init this because routine is a property get function,
+ // and is guaranteed to return some sort of value in here.
+
+ qfdefn = ptdata->QfdefnOfHfdefn(hfdefn);
+
+ DebAssert(qfdefn->CArgs()==0
+ || fPropParamSplit && qfdefn->CArgs() == pdispparams->cArgs - 1,
+ ""); // munged arg count
+
+ DebAssert(qfdefn->InvokeKind() == INVOKE_PROPERTYGET, "");
+
+ // get the propget function's return type from the typelib
+#if EI_OB
+ hresult = VariantVtOfHtdefn(qfdefn->m_ftdefn.HtdefnResultUnmunged(),
+ ptdata,
+ qfdefn->m_ftdefn.IsSimpleTypeResultUnmunged(),
+ &fGotObjGuid,
+ // don't need the guid if Retval is an object
+ // UNDONE: maybe use the guid below???
+ NULL,
+ &vtReturnTypeinfo);
+#else // EI_OLE
+ hresult = VariantVtOfHtdefn(qfdefn->m_ftdefn.HtdefnResult(),
+ ptdata,
+ qfdefn->m_ftdefn.IsSimpleTypeResult(),
+ &fGotObjGuid,
+ // don't need the guid if Retval is an object
+ // UNDONE: maybe use the guid below???
+ NULL,
+ &vtReturnTypeinfo);
+#endif // EI_OLE
+
+ if (hresult != NOERROR)
+ goto Error;
+
+ if (qfdefn->CArgsUnmunged() == 0) {
+ // "normal" case of no retval/lcid hidden params, no param split
+ switch (vtReturnTypeinfo) {
+ case VT_DISPATCH:
+ case VT_VARIANT:
+ break; // these are ok
+ default:
+ hresult = HresultOfScode(DISP_E_NOTACOLLECTION);
+ goto Error;
+ } // end switch
+
+ qfdefn = ptdata->QfdefnOfHfdefn(hfdefn);
+#if EI_OB
+ cc = qfdefn->m_ftdefn.CcUnmunged();
+#else // EI_OLE
+ cc = qfdefn->m_ftdefn.Cc();
+#endif // EI_OLE
+
+ qfdefn = ptdata->QfdefnOfHfdefn(hfdefn);
+#if VBA3 && !EI_VBARUN && OE_WIN32
+ if (isModule)
+ hresult = DoInvokeFunction(pvTemplate,
+ cc,
+ vtReturnTypeinfo,
+ 0,
+ NULL,
+ NULL,
+ (VARIANT FAR *)&varTmp,
+ pexcepinfo);
+ else
+#endif
+ // Invoke the PropertyGet
+ hresult = DoInvoke(pvInstance,
+ (SHORT)((VIRTUAL_FUNC_DEFN*)qfdefn)->Ovft(),
+ (CALLCONV)cc,
+ vtReturnTypeinfo,
+ 0, NULL, NULL,
+ (VARIANT FAR *)&varTmp);
+ } else {
+ // Bummer -- we have lcid and/or retval hidden params
+ // UNDONE: (dougf) For code size, is there any way we can combine this with
+ // UNDONE: the InvokeStandard code above?
+
+ // alloc the invoke args structure & fill in lcid/retval args
+
+ hresult = GetInvokeArgs(hfdefn,
+ ptdata,
+ wFlags,
+ pdispparams,
+ &pvarRetval,
+ (VOID *)&bufRetval,
+ &pinvargs,
+ puArgErr,
+ fPropParamSplit);
+
+ if (hresult != NOERROR)
+ goto Error;
+
+ // WARNING: All error paths after this point must free pinvargs!
+
+ vtReturn = (vtReturnTypeinfo == VT_HRESULT) ? VT_ERROR : vtReturnTypeinfo;
+
+ switch (vtReturnTypeinfo) {
+ case VT_DISPATCH:
+ case VT_VARIANT:
+ break; // these are ok
+ case VT_HRESULT:
+ // ensure that the 'retval' type is VT_DISPATCH or VT_VARIANT
+ // error if no 'retval' type.
+ if (pvarRetval) {
+ // It's inconvienient to check the return type of 'retval' parm
+ // here (to see if it's VT_DISPATCH or VT_VARIANT). So we'll
+ // just go ahead and do the Invoke in this case, and catch the
+ // error later if it is a problem.
+ break;
+ }
+ // fall through to give error
+ default:
+ ReleaseInvokeArgs(pinvargs);
+ hresult = HresultOfScode(DISP_E_NOTACOLLECTION);
+ goto Error;
+ } // end of switch
+
+ qfdefn = ptdata->QfdefnOfHfdefn(hfdefn);
+#if EI_OB
+ cc = qfdefn->m_ftdefn.CcUnmunged();
+#else // EI_OLE
+ cc = qfdefn->m_ftdefn.Cc();
+#endif // EI_OLE
+
+ qfdefn = ptdata->QfdefnOfHfdefn(hfdefn);
+ // Invoke the PropertyGet
+#if VBA3 && !EI_VBARUN && OE_WIN32
+ if (isModule)
+ hresult = DoInvokeFunction(pvTemplate,
+ cc,
+ vtReturn,
+ pinvargs->cArgs,
+ pinvargs->rgvt,
+ (VARIANTARG FAR* FAR*)pinvargs->rgpvarg,
+ (VARIANT FAR*)pvarResult,
+ pexcepinfo);
+ else
+#endif
+ hresult = DoInvoke(pvInstance,
+ (SHORT)((VIRTUAL_FUNC_DEFN*)qfdefn)->Ovft(),
+ cc,
+ vtReturn,
+ pinvargs->cArgs,
+ pinvargs->rgvt,
+ (VARIANTARG FAR* FAR*)pinvargs->rgpvarg,
+ (VARIANT FAR*)&varTmp);
+
+ // if the return type of this function is HRESULT, then we want to
+ // fill in the excepinfo structure if the function returned an error
+ if (hresult == NOERROR) {
+ if (vtReturnTypeinfo == VT_HRESULT) {
+ DebAssert(varTmp.vt == VT_ERROR, "bad func return type");
+ if (varTmp.scode != NOERROR) {
+ // Ignore the specific error the function returned (since we have
+ // no place to put it), and fill in the excepinfo structure with
+ // a lame generic error.
+ if (pexcepinfo != NULL) {
+ // zero/NULL all fields initially
+ GetErrorInfo(pexcepinfo); // zeros out *pexcepinfo
+ // stuff error code from function in excepinfo structure
+ pexcepinfo->scode = GetScode(varTmp.scode);
+ }
+ // signal that the excepinfo structure contains error info.
+ hresult = HresultOfScode(DISP_E_EXCEPTION);
+ } else {
+ // if the retval arg was specified, then the function put it's real
+ // return value in *pvarRetval. Copy this to varTmp. Ok to
+ // just overwrite varTmp because it's not an owner.
+ if (pvarRetval) {
+ DebAssert(pvarRetval->vt & VT_BYREF, "not a byref return");
+ vtReturn = (pvarRetval->vt & ~VT_BYREF);
+ if (vtReturn == VT_VARIANT) {
+ varTmp = bufRetval; // copy entire variant returned
+ } else {
+ varTmp.vt = vtReturn; // set tag
+ memcpy(&varTmp.iVal, &bufRetval, 8); // copy data
+ }
+ }
+ }
+ }
+ }
+ ReleaseInvokeArgs(pinvargs);
+ }
+
+ if (hresult != NOERROR)
+ goto Error;
+
+ // If the property returns an object, then delegate to it
+
+ if (V_VT(&varTmp) != VT_DISPATCH) {
+ hresult = HresultOfScode(DISP_E_NOTACOLLECTION);
+ } else if (V_DISPATCH(&varTmp) == NULL) {
+ hresult = HresultOfScode(DISP_E_MEMBERNOTFOUND);
+
+ } else {
+ UINT cArgsDisp, cNamedArgsDisp;
+
+ if ((err = GetLcid(&lcid)) != TIPERR_None) {
+ hresult = HresultOfTiperr(err);
+ goto LError1;
+ }
+#if VBA3 && !EI_VBARUN && OE_WIN32
+ if (isModule)
+ hresult = DoInvokeFunction(pvTemplate,
+ cc,
+ vtReturn,
+ pinvargs->cArgs,
+ pinvargs->rgvt,
+ (VARIANTARG FAR* FAR*)pinvargs->rgpvarg,
+ (VARIANT FAR*)pvarResult,
+ pexcepinfo);
+ else
+#endif
+ // If we're splitting the parameters, only "pass"
+ // the RHS parameter. Fortunately, it's always the first
+ // in the pdisparams array. (vba2 bug #4481)
+ //
+ if (fPropParamSplit) {
+ cArgsDisp = pdispparams->cArgs;
+ cNamedArgsDisp = pdispparams->cNamedArgs;
+
+ pdispparams->cArgs = pdispparams->cNamedArgs = 1;
+ }
+
+ hresult = V_DISPATCH(&varTmp)->Invoke(DISPID_VALUE,
+ IID_NULL,
+ lcid,
+ wFlags,
+ pdispparams,
+ pvarResult,
+ pexcepinfo,
+ puArgErr);
+
+ // Fix the dispparams structure, if we've modified it. (vba2 bug #4481)
+ if (fPropParamSplit) {
+ pdispparams->cArgs = cArgsDisp;
+ pdispparams->cNamedArgs = cNamedArgsDisp;
+ }
+
+ // if we put the result into a temporary, must discard it
+ if (hresult == NOERROR && pvarResult == &varResult) {
+ VariantClearA(pvarResult);
+ }
+ }
+
+LError1:;
+ VariantClear(&varTmp);
+
+Error:
+#if EI_OB
+ if (fClean) {
+ ptdata->FreeFuncDefn(hfdefn);
+ }
+#endif // EI_OB
+ return hresult;
+}
+
+/***
+*PRIVATE HRESULT NEARCODE GEN_DTINFO::CoerceArg
+*Purpose:
+* Helper function for GetInvokeArgs
+* Coerces an a argument to a given type
+*
+*Entry:
+*
+*Exit:
+* return value = HRESULT
+*
+***********************************************************************/
+HRESULT NEARCODE GEN_DTINFO::CoerceArg
+(
+ VARIANTARG FAR* pvargSrc, // * to source variant
+ VARTYPE vt, // destination VT type
+ USHORT fGotObjGuid,
+ GUID FAR* pGuid,
+ INVOKEARGS FAR* pinvargs, // invoke args structure
+ UINT u // param index
+)
+{
+ VARIANTARG FAR* pvarg;
+ HRESULT hresult = NOERROR;
+
+ // attempt to coerce to the expected type
+
+ switch(vt) {
+ case VT_UI1:
+ case VT_I2:
+ case VT_I4:
+ case VT_R4:
+ case VT_R8:
+ case VT_CY:
+ case VT_DATE:
+ case VT_BSTR:
+ case VT_ERROR:
+ case VT_BOOL:
+ case VT_UNKNOWN:
+ case VT_DISPATCH:
+ if (V_VT(pvargSrc) == vt) {
+ // if type already correct, don't have to copy the variant (speed opt)
+ if (fGotObjGuid != 2
+ || vt & VT_ARRAY
+ || V_DISPATCH(pvargSrc) == NULL) {
+
+ goto NoChangeType;
+ }
+ // For object parms, QI to the desired interface/dispinterface
+ // (addref's the obj), and set the object pointer in our temp variant
+ pvarg = &pinvargs->rgvarg[u];
+ if ((V_DISPATCH(pvargSrc)->QueryInterface(*pGuid,
+ (LPVOID *)&V_DISPATCH(pvarg))) != NOERROR) {
+ hresult = HresultOfScode(DISP_E_TYPEMISMATCH);
+ break;
+ }
+ // update the tag of the temp variant, and set ptr so that we use it
+ V_VT(pvarg) = V_VT(pvargSrc);
+ pinvargs->rgpvarg[u] = pvarg;
+ break;
+ }
+ pvarg = &pinvargs->rgvarg[u];
+ hresult = VariantChangeType(pvarg, pvargSrc, 0, vt);
+ if (hresult != NOERROR) {
+ // If VariantChangeType returned a TypeMismatch, and the
+ // TypeMismatch was do to an attempt to pass an unsupplied
+ // optional param to a non variant argument, then translate
+ // the error to the more appropriate DISP_E_PARAMNOTOPTIONAL
+ //
+ // Remember: unsupplied optional params are passed by the
+ // client as VT_ERROR(DISP_E_PARAMNOTFOUND)
+ //
+ if (GetScode(hresult) == DISP_E_TYPEMISMATCH) {
+ if (V_VT(pvargSrc) == VT_ERROR
+ && V_ERROR(pvargSrc) == DISP_E_PARAMNOTFOUND)
+ {
+ hresult = HresultOfScode(DISP_E_PARAMNOTOPTIONAL);
+ }
+ }
+ break;
+ }
+ pinvargs->rgpvarg[u] = pvarg;
+ if (fGotObjGuid == 2) {
+ // For object parms, QI to the desired interface/dispinterface
+ // (addref's the obj), and set the object pointer in our temp variant
+ DebAssert(V_VT(pvarg) == VT_DISPATCH || V_VT(pvarg)==VT_UNKNOWN, "");
+ if (V_DISPATCH(pvarg)) {
+ V_DISPATCH(pvarg)->Release(); // release the extra ref that
+ // VariantChangeType added.
+ if ((V_DISPATCH(pvarg)->QueryInterface(*pGuid,
+ (LPVOID *)&V_DISPATCH(pvarg))) != NOERROR) {
+ V_VT(pvarg) = VT_EMPTY; // so we don't "re-release" it
+ hresult = HresultOfScode(DISP_E_TYPEMISMATCH);
+ break;
+ }
+ }
+ }
+ break;
+
+ case VT_VARIANT:
+NoChangeType:
+ pinvargs->rgpvarg[u] = pvargSrc;
+ break;
+
+ default:
+
+ // if the variant is an array, assume it is owned by the caller and
+ // therefore should not be freed by us
+ if (vt & VT_ARRAY)
+ pinvargs->rgbVarMustBeFreed[u] = FALSE;
+
+ if (vt & (VT_BYREF | VT_ARRAY)) {
+ // get ptr to a temp variant we can use
+ pvarg = &pinvargs->rgvarg[u];
+
+ // If the target argument is ByRef (or Array), then we
+ // require an exact match in type between formal and actual
+ // because we want the original copy to get updated, and
+ // we cant of course coerce the original in place (and we
+ // dont have rules for the coersion of an Array).
+ //
+ // if types match exactly, then we're fine
+ if (V_VT(pvargSrc) == vt) {
+
+ // If we're copying objects, make sure we have the correct
+ // types.
+ //
+ if (fGotObjGuid == 2
+ && !(vt & VT_ARRAY)
+ && V_DISPATCH(pvargSrc) != NULL
+ && *V_DISPATCHREF(pvargSrc) != NULL) {
+
+ // For object parms, QI to the desired interface/dispinterface
+ // (addref's the obj) and put it in our temp variant. Later,
+ // we'll add an extra level of indirection.
+ //
+ if ((*V_DISPATCHREF(pvargSrc))->QueryInterface(*pGuid,
+ (LPVOID *)&V_DISPATCH(pvarg)) != NOERROR) {
+
+ hresult = HresultOfScode(DISP_E_TYPEMISMATCH);
+ break;
+ }
+
+ // update the tag of the temp variant and save * to original
+ // byref variant for copy-back time.
+ //
+ V_VT(pvarg) = V_VT(pvargSrc) & ~VT_BYREF;
+ pinvargs->rgpvargByref[u] = pvargSrc;
+
+ goto CreateByrefTemp;
+ }
+ else {
+ pinvargs->rgpvarg[u] = pvargSrc;
+ }
+
+ break;
+ }
+
+ // Special case allowing a source of VT_BYREF VTARRAY, and target
+ // of a non-VT_BYREF VT_ARRAY, where the base VT types match.
+ // We do the de-referencing in this case.
+ if ( ((V_VT(pvargSrc) & (VT_BYREF | VT_ARRAY)) == (VT_BYREF | VT_ARRAY))
+ && ((vt & (VT_BYREF | VT_ARRAY)) == VT_ARRAY)
+ && ((V_VT(pvargSrc) & ~VT_BYREF) == vt) ) {
+
+ // dereference and copy the source variant
+ V_VT(pvarg) = vt;
+ V_ARRAY(pvarg) = *V_ARRAYREF(pvargSrc);
+ pinvargs->rgpvarg[u] = pvarg;
+
+ // flag this variant as owned by the caller, so we won't free it
+ pinvargs->rgbVarMustBeFreed[u] = FALSE;
+ break;
+ }
+
+ // special case allowing a source BYVAL to be passed to a target BYREF
+ if ((vt & VT_BYREF) && (V_VT(pvargSrc) & VT_BYREF) == 0) {
+ // change type of pvargSrc to the base VT-type, filling in
+ // pinvargs->rgpvarg[u]
+ hresult = CoerceArg(pvargSrc, (vt & ~VT_BYREF), fGotObjGuid, pGuid,
+ pinvargs, u);
+ if (hresult != NOERROR) {
+ break;
+ }
+ if (pinvargs->rgpvarg[u] != pvarg) {
+ // if CoerceArg was tricky and thought it didn't have to copy the
+ // arg, make a copy of it now.
+ DebAssert(pinvargs->rgpvarg[u] == pvargSrc, "");
+ hresult = VariantCopy(pvarg, pvargSrc);
+ if (hresult != NOERROR) {
+ break;
+ }
+ //flag this variant as owned by us, so it will be freed by us
+ pinvargs->rgbVarMustBeFreed[u] = TRUE;
+ // not needed (overwritten below)
+ //pinvargs->rgpvarg[u] = pvarg;
+ }
+
+CreateByrefTemp:
+ // Now set up a byref variant to point to this guy, and adjust
+ // rgpvarg[u] accordingly.
+ VARIANTARG * pvarg2;
+
+ pvarg2 = &pinvargs->rgvarg2[u];
+ V_VT(pvarg2) = vt;
+ if ((vt & ~VT_BYREF) == VT_VARIANT) {
+ V_BYREF(pvarg2) = (void *)pvarg; // point to variant
+ } else {
+ V_BYREF(pvarg2) = (void *)&pvarg->iVal; // point to data
+ }
+ pinvargs->rgpvarg[u] = pvarg2;
+ break;
+ }
+
+ // Suprise, suprise, it's another special case. This one allows a
+ // source BYREF to be passed to a target BYREF VARIANT.
+ if (vt == (VT_BYREF | VT_VARIANT) && (V_VT(pvargSrc) & VT_BYREF)) {
+ // In this case we make a copy of the value, and create a temp
+ // byref variant to pass to the function. After the function
+ // returns, the value in the temp variant is copied back into
+ // the original variant.
+ //
+ hresult = VariantCopyInd(pvarg, pvargSrc);
+ if (hresult != NOERROR) {
+ break;
+ }
+ //flag this variant as owned by us, so it will be freed by us
+ pinvargs->rgbVarMustBeFreed[u] = TRUE;
+
+ // save * to original byref variant for copy-back time.
+ pinvargs->rgpvargByref[u] = pvargSrc;
+ goto CreateByrefTemp;
+ }
+
+ hresult = HresultOfScode(DISP_E_TYPEMISMATCH);
+ break;
+ }
+
+ // Otherwise: unrecognized or unsupported member argument type.
+ // this means there is a problem with the given method description.
+ // Things such as VT_HRESULT, VT_VOID, and VT_NULL are bogus parm types,
+ // (but can be a valid function return type), so VariantVtOfHtdefn lets
+ // them slide, but we must reject them here.
+ hresult = HresultOfScode(DISP_E_BADVARTYPE);
+ break;
+ } // switch
+
+ return hresult;
+}
+
+/***
+*PRIVATE HRESULT NEARCODE GEN_DTINFO::GetInvokeArgs
+*Purpose:
+* Gather all arguments (looking up by position or name), coerce
+* to the expected type (if possible) and build a linearized
+* positional array of pointers to those arguments.
+*
+* Note: this is a helper for ITypeInfo::Invoke implementations
+*
+*Entry:
+*
+*Exit:
+* return value = HRESULT
+*
+* *ppinvargs = structure containing the collected arguments
+* *puArgErr = if there was an error coercing an argument, this is the
+* index in the pdispparams->rgvarg array of the problem arg.
+*
+***********************************************************************/
+HRESULT NEARCODE
+GEN_DTINFO::GetInvokeArgs(
+ HFUNC_DEFN hfdefn,
+ TYPE_DATA *ptdata,
+ WORD wFlags,
+ DISPPARAMS FAR* pdispparams,
+ VARIANT ** ppvarRetval,
+ VOID * pbufRetval,
+ INVOKEARGS FAR* FAR* ppinvargsOut,
+ UINT FAR* puArgErr,
+ BOOL fPropParamSplit)
+{
+ VARTYPE vt;
+ HRESULT hresult;
+ FUNC_DEFN *qfdefn;
+ HPARAM_DEFN hparamdefn;
+ UINT uTo, uFrom;
+ UINT uArgIndex, cArgsGiven, cArgsFunc, cArgsMunged;
+ UINT cArgsNonOptional, cArgsUsed;
+ TIPERROR err;
+ INVOKEARGS FAR* pinvargs;
+ VARIANTARG FAR* pvarg, FAR* pvargSrc, FAR* pvarg2;
+ PARAM_DEFN paramdefn;
+ BOOL fVarArg;
+ LONG saElemIndex;
+ UINT uSaArg;
+ USHORT fGotObjGuid;
+ GUID guid;
+ HTYPE_DEFN htdefn;
+#if EI_OLE
+ TYPE_DEFN *qtdefn;
+#endif // EI_OLE
+
+ qfdefn = ptdata->QfdefnOfHfdefn(hfdefn);
+ hparamdefn = (HPARAM_DEFN)qfdefn->m_ftdefn.m_hdefnFormalFirst;
+
+ cArgsFunc = qfdefn->CArgsUnmunged();
+ cArgsMunged = qfdefn->CArgs();
+ // don't include retval or lcid parms (if present) in non-optional
+ // count -- the user doesn't supply these.
+ cArgsNonOptional = cArgsMunged - qfdefn->CArgsOpt();
+ cArgsGiven = pdispparams->cArgs;
+ cArgsUsed = 0;
+
+ // If we have any non-optional parameters that come after any
+ // optional ones (such as RHS of prop functions), decrease
+ // the number of non-optional parameters by one.
+ //
+ if (qfdefn->IsPropertyLet()
+ || qfdefn->IsPropertySet()) {
+ DebAssert(cArgsNonOptional > 0, "not enough args");
+ cArgsNonOptional--;
+ }
+
+ fVarArg = (qfdefn->CArgsOpt() == -1);
+ uSaArg = cArgsMunged-1; // if we're a vararg function, this is the
+ // 0-based index of the last parameter (which
+ // is a SAFEARRAY of variants)
+#if ID_DEBUG
+ if (fVarArg) {
+ DebAssert(cArgsGiven >= uSaArg, "caller didn't check right");
+ }
+#endif
+
+ if ((hresult = AllocInvokeArgs(cArgsFunc,
+ fVarArg ? (cArgsGiven - uSaArg): -1,
+ &pinvargs)) != NOERROR) {
+ goto LError0;
+ }
+
+ // Loop over all of the arguments that this function expects and
+ // match it to the value that was passed in.
+ //
+ for (uTo = uFrom = 0; uTo < cArgsFunc; ++uTo)
+ {
+ // Get the expected argument type.
+#if EI_OB
+ DebAssert(hparamdefn != HPARAMDEFN_Nil, "number vs actual dont match");
+
+ // In OB we walk the linked list of PARAM_DEFN(s).
+ paramdefn = *ptdata->QparamdefnOfHparamdefn(hparamdefn);
+ hparamdefn = paramdefn.HparamdefnNext();
+#else //EI_OB
+ paramdefn = *ptdata->QparamdefnOfIndex(hparamdefn, uTo);
+#endif //EI_OB
+
+ htdefn = paramdefn.Htdefn();
+
+#if EI_OLE
+ qtdefn = paramdefn.IsSimpleType()
+ ? paramdefn.QtdefnOfSimpleType()
+ : ptdata->QtdefnOfHtdefn(htdefn);
+#endif // EI_OLE
+
+ // Get the type of this parameter.
+ hresult = VariantVtOfHtdefn(htdefn,
+ ptdata,
+ paramdefn.IsSimpleType(),
+ &fGotObjGuid,
+ &guid,
+ &vt);
+
+ if (hresult != NOERROR) {
+ goto LError1;
+ }
+
+ // Handle an LCID parameter.
+#if EI_OB
+ if (paramdefn.IsLCID())
+#else // EI_OLE
+ if (qtdefn->IsLCID())
+#endif // EI_OLE
+ {
+ // get & fill in the LCID param
+ pinvargs->rgvt[uTo] = VT_I4;
+ pvarg = &pinvargs->rgvarg[uTo];
+ pvarg->vt = VT_I4; // CONSIDER: redundant with rgvt[u]?
+
+ // get this typeinfo's lcid (from the containing typelib)
+ if ((err = GetLcid((DWORD *)&(pvarg->lVal))) != TIPERR_None) {
+ hresult = HresultOfTiperr(err);
+ goto LError1;
+ }
+
+ pinvargs->rgpvarg[uTo] = pvarg;
+ continue; // next param
+ }
+
+ // Handle a retval parameter.
+#if EI_OB
+ else if (paramdefn.IsRetval())
+#else // EI_OLE
+ else if (qtdefn->IsRetval())
+#endif // EI_OLE
+ {
+ DebAssert(vt & VT_BYREF, "non-byref retval param");
+ pinvargs->rgvt[uTo] = vt;
+ pvarg = &pinvargs->rgvarg[uTo];
+ pvarg->vt = vt;
+ pvarg->byref = pbufRetval; // where function should put it's data
+
+ // Clear the retval buffer (guaranteed to be as big as a variant).
+ memset(pbufRetval, 0, sizeof(VARIANT));
+ pinvargs->rgpvarg[uTo] = pvarg;
+ *ppvarRetval = pvarg; // return pointer to function retval
+
+ continue; // next param
+ }
+
+ // If this is a PARAMARRAY (VarArg), loop over the rest of the
+ // input parameters and add them to the array.
+ //
+ else if (fVarArg && uFrom == uSaArg) {
+ DebAssert((vt & ~VT_BYREF) == (VT_VARIANT | VT_ARRAY),
+ "vararg func with bad last parm");
+
+ // Set up the safearray.
+ pvarg = &pinvargs->rgvarg[uTo];
+ V_ARRAY(pvarg) = pinvargs->psa;
+
+ // If the paramarray is VT_BYREF, add the byref flag to the
+ // destination varg and adjust rgpvarg[uFrom] accordingly.
+ //
+ if (vt & VT_BYREF) {
+ pvarg2 = &pinvargs->rgvarg2[uTo];
+ V_VT(pvarg2) = vt;
+ V_ARRAYREF(pvarg2) = &pvarg->parray; // point to array
+
+ pinvargs->rgpvarg[uTo] = pvarg2;
+ pinvargs->rgvt[uTo] = vt;
+ }
+
+ // Add the rest of the given parameters to the paramarray.
+ for (; uFrom < cArgsGiven; uFrom++, cArgsUsed++) {
+ // Get the parameter.
+ hresult = IndexOfParam(pdispparams, uFrom, &uArgIndex);
+ if (hresult != NOERROR) {
+ goto LError1;
+ }
+
+ // Add the parameter.
+ saElemIndex = uFrom - uSaArg;
+ hresult = SafeArrayPutElement(pinvargs->psa,
+ &saElemIndex,
+ &pdispparams->rgvarg[uArgIndex]);
+
+ if (hresult != NOERROR) {
+ goto LError1;
+ }
+ }
+
+ continue; // next param
+ }
+
+ // Get the parameter that was passed in.
+ //
+ // special case the handling of the rhs of a property put
+ //
+ // if we are looking for the last arg in the list, and this is
+ // a property put function, the we know this argument is the
+ // "put-value" or right-hand-side of the property put, in which
+ // case we know it is passed in element 0 of the rgvarg array
+ // and is marked with the special name, DISPID_PROPERTYPUT
+ //
+ if (uTo == (cArgsFunc-1) && IsPropPut(wFlags)) {
+ if (pdispparams->cNamedArgs == 0
+ || pdispparams->rgdispidNamedArgs[0] != DISPID_PROPERTYPUT) {
+
+ hresult = HresultOfScode(DISP_E_PARAMNOTOPTIONAL); // CONSIDER: correct error?
+ }
+ uArgIndex = 0;
+ }
+ else {
+ hresult = IndexOfParam(pdispparams, uFrom, &uArgIndex);
+ }
+
+ // If the above lookup failed and the current parameter is optional,
+ // just set it to the default value. Otherwise return an error.
+ //
+ if (hresult != NOERROR) {
+ if (uFrom >= cArgsNonOptional) {
+ DebAssert(!fVarArg, "VarArgs can't coexist with optional params.");
+ DebAssert((vt & ~VT_BYREF) == VT_VARIANT, "Optional must be variant.");
+
+ // Set up the variant.
+ pinvargs->rgvt[uTo] = VT_VARIANT;
+ pvarg = &pinvargs->rgvarg[uTo];
+ pvarg->vt = VT_ERROR;
+ pvarg->scode = DISP_E_PARAMNOTFOUND;
+ pinvargs->rgpvarg[uTo] = pvarg;
+
+ // Now set up a byref variant to point to this guy, and adjust
+ // rgpvarg[uFrom] accordingly.
+ //
+ if (vt & VT_BYREF) {
+ pvarg2 = &pinvargs->rgvarg2[uTo];
+ V_VT(pvarg2) = vt;
+ V_BYREF(pvarg2) = (void *)pvarg; // point to variant
+
+ pinvargs->rgpvarg[uTo] = pvarg2;
+ pinvargs->rgvt[uTo] = vt;
+ }
+
+ uFrom++;
+ continue;
+ }
+ else {
+ goto LError1;
+ }
+ }
+
+ DebAssert(cArgsUsed < cArgsGiven, "Using too may args!");
+
+ // Do the copy.
+ pvargSrc = &pdispparams->rgvarg[uArgIndex];
+ pinvargs->rgvt[uTo] = vt;
+
+ // coerce the argument to the expected type
+ hresult = CoerceArg(pvargSrc, vt, fGotObjGuid, &guid, pinvargs, uTo);
+ if (hresult != NOERROR) {
+ *puArgErr = uArgIndex; // which arg got the error
+ goto LError1;
+ }
+
+ // If this is an 'out' parameter, free any resources currently
+ // stored in the input variant. Do this after CoerceArg to handle
+ // all the wierd cases that will result in CoerceArg spitting out a
+ // byref value when the input was not byref.
+ //
+#if EI_OB
+ if (paramdefn.IsOut() && !paramdefn.IsIn())
+#else // EI_OLE
+ TYPE_DEFN *qtdefn;
+
+ qtdefn = paramdefn.IsSimpleType()
+ ? paramdefn.QtdefnOfSimpleType()
+ : ptdata->QtdefnOfHtdefn(paramdefn.Htdefn());
+
+ if (qtdefn->IsModeOut())
+#endif // EI_OLE
+ {
+ pvargSrc = pinvargs->rgpvarg[uTo];
+ DebAssert(vt & VT_BYREF, "target must be byref");
+ DebAssert(V_ISBYREF(pvargSrc), "source must be byref");
+ switch(V_VT(pvargSrc)) {
+ case VT_BSTR | VT_BYREF:
+ SysFreeString(*V_BSTRREF(pvargSrc));
+ *V_BSTRREF(pvargSrc) = NULL;
+ break;
+
+ case VT_UNKNOWN | VT_BYREF:
+ if (V_UNKNOWNREF(pvargSrc) != NULL) {
+ if (*V_UNKNOWNREF(pvargSrc) != NULL) {
+ (*V_UNKNOWNREF(pvargSrc))->Release();
+ *V_UNKNOWNREF(pvargSrc) = NULL;
+ }
+ }
+ break;
+
+ case VT_DISPATCH | VT_BYREF:
+ if (V_DISPATCHREF(pvargSrc) != NULL) {
+ if (*V_DISPATCHREF(pvargSrc) != NULL) {
+ (*V_DISPATCHREF(pvargSrc))->Release();
+ *V_DISPATCHREF(pvargSrc) = NULL;
+ }
+ }
+ break;
+
+ default:
+ if(V_ISARRAY(pvargSrc)) {
+ IfFailRet(SafeArrayDestroy(*V_ARRAYREF(pvargSrc)));
+ *V_ARRAYREF(pvargSrc) = NULL;
+ }
+ }
+ }
+
+ // Next argument.
+ uFrom++; cArgsUsed++;
+ } // for
+
+ // Make sure we actually used all of the given arguments, unless
+ // we're processing a collection lookup.
+ //
+ // If we're splitting the parameters on a colletion lookup, we'll
+ // use all of the parameters passed in except one. (vba2 bug #4481)
+ //
+ if (cArgsUsed != cArgsGiven
+ && (!fPropParamSplit || cArgsUsed != cArgsGiven - 1)
+ && cArgsUsed) {
+
+ hresult = HresultOfScode(DISP_E_PARAMNOTFOUND);
+ goto LError1;
+ }
+
+ *ppinvargsOut = pinvargs;
+ return NOERROR;
+
+LError1:;
+ ReleaseInvokeArgs(pinvargs);
+ *ppinvargsOut = NULL;
+
+LError0:;
+ return hresult;
+}
+
+
+/***
+*PRIVATE HRESULT NEARCODE GEN_DTINFO::AllocInvokeArgs
+*Purpose:
+* Allocate and initialize an INVOKEARGS structure
+*
+*Entry:
+* cArgs = the count of args to be held by the invokeargs struct
+* cArgsVarArg = # of args that get put into a safearray trailing arg,
+* -1 if this isn't a vararg function.
+*
+*Exit:
+* return value = HRESULT
+*
+* *ppinvargs = ptr to a newly allocated INVOKEARGS struct
+*
+***********************************************************************/
+HRESULT NEARCODE
+GEN_DTINFO::AllocInvokeArgs(UINT cArgs, UINT cArgsVarArg, INVOKEARGS FAR* FAR* ppinvargs)
+{
+ INVOKEARGS FAR* pinvargs;
+
+#define CB_rgvarg (sizeof(VARIANTARG) * cArgs)
+#define CB_rgvarg2 (sizeof(VARIANTARG) * cArgs)
+#define CB_rgpvarg (sizeof(VARIANTARG FAR *) * cArgs)
+#define CB_rgpvargByref (sizeof(VARIANTARG FAR *) * cArgs)
+#define CB_rgvt (sizeof(VARTYPE) * cArgs)
+#define CB_rgbVarMustBeFreed (sizeof(BYTE) * cArgs)
+
+ if ((pinvargs = (INVOKEARGS *)MemAlloc(sizeof(INVOKEARGS)
+// NOTE: (OE_RISC) assumes that INVOKEARGS structure doesn't end in a SHORT
+ + CB_rgvarg
+ + CB_rgvarg2
+ + CB_rgpvarg
+ + CB_rgpvargByref
+ + CB_rgvt
+ + CB_rgbVarMustBeFreed
+ )) == NULL)
+ goto LError0;
+ ::new (pinvargs) INVOKEARGS;
+ pinvargs->cArgs = cArgs;
+ pinvargs->psa = NULL;
+ if (cArgs == 0) {
+ pinvargs->rgvarg = NULL;
+ pinvargs->rgpvarg = NULL;
+ pinvargs->rgvt = NULL;
+ pinvargs->rgbVarMustBeFreed = NULL;
+ // not needed
+ //pinvargs->rgvarg2 = NULL;
+ //pinvargs->rgpvargByref = NULL;
+ }else{
+ pinvargs->rgvarg = (VARIANTARG FAR *)((BYTE *)pinvargs
+ + sizeof(INVOKEARGS));
+ pinvargs->rgvarg2 = (VARIANTARG FAR *)((BYTE *)pinvargs
+ + sizeof(INVOKEARGS)
+ + CB_rgvarg);
+ pinvargs->rgpvarg = (VARIANTARG FAR * FAR *)((BYTE *)pinvargs
+ + sizeof(INVOKEARGS)
+ + CB_rgvarg
+ + CB_rgvarg2);
+ pinvargs->rgpvargByref = (VARIANTARG FAR * FAR *)((BYTE *)pinvargs
+ + sizeof(INVOKEARGS)
+ + CB_rgvarg
+ + CB_rgvarg2
+ + CB_rgpvarg);
+ pinvargs->rgvt = (VARTYPE FAR *)((BYTE *)pinvargs
+ + sizeof(INVOKEARGS)
+ + CB_rgvarg
+ + CB_rgvarg2
+ + CB_rgpvarg
+ + CB_rgpvargByref);
+ pinvargs->rgbVarMustBeFreed = (BYTE FAR*)((BYTE *)pinvargs
+ + sizeof(INVOKEARGS)
+ + CB_rgvarg
+ + CB_rgvarg2
+ + CB_rgpvarg
+ + CB_rgpvargByref
+ + CB_rgvt);
+
+ for (UINT u = 0; u < cArgs; ++u) {
+ V_VT(&pinvargs->rgvarg[u]) = VT_EMPTY;
+ pinvargs->rgpvargByref[u] = NULL;
+ pinvargs->rgbVarMustBeFreed[u] = TRUE; // assume we own all the variants
+ }
+
+ if (cArgsVarArg != -1) {
+ if (cArgsVarArg == 0) {
+ // SafeArrayCreate rejects 0 for cElements.
+ if (SafeArrayAllocDescriptor(1, &pinvargs->psa) != NOERROR) {
+ goto LError4; // if error, just assume out of memory.
+ }
+ }
+ else {
+ SAFEARRAYBOUND sabounds;
+ sabounds.cElements = cArgsVarArg;
+ sabounds.lLbound = 0;
+ if ((pinvargs->psa = SafeArrayCreate(VT_VARIANT,
+ 1,
+ &sabounds)) == NULL) {
+ goto LError4;
+ }
+ }
+ // set the last invoke arg to point to this array
+ VARIANTARG FAR* pvarg;
+ UINT uSaArg = cArgs-1;
+ pvarg = &pinvargs->rgvarg[uSaArg];
+ pinvargs->rgpvarg[uSaArg] = pvarg;
+ V_VT(pvarg) = VT_VARIANT | VT_ARRAY;
+ pinvargs->rgvt[uSaArg] = VT_VARIANT | VT_ARRAY;
+ pvarg->parray = pinvargs->psa;
+ }
+ }
+ *ppinvargs = pinvargs;
+ return NOERROR;
+
+LError4:;
+ MemFree(pinvargs);
+LError0:;
+ return HresultOfScode(E_OUTOFMEMORY);
+}
+
+
+/***
+*PRIVATE NEARCODE GEN_DTINFO::ReleaseInvokeArgs
+*Purpose:
+* Free the given INVOKEARGS structure
+*
+*Entry:
+* pinvargs = the structure to free
+*
+*Exit:
+* None
+*
+***********************************************************************/
+void NEARCODE
+GEN_DTINFO::ReleaseInvokeArgs(INVOKEARGS FAR* pinvargs)
+{
+ if (pinvargs != NULL) {
+ if (pinvargs->rgvarg != NULL) {
+ for (UINT u = 0; u < pinvargs->cArgs; ++u) {
+
+ // release the variant only if we own the memory. We won't if the
+ // variant is a byval array created by coercing a byref array to
+ // byval in CoerceArgs().
+ if (pinvargs->rgbVarMustBeFreed[u] != FALSE) {
+ VariantClear(&pinvargs->rgvarg[u]);
+ }
+ }
+ }
+ if (pinvargs->psa != NULL)
+ SafeArrayDestroy(pinvargs->psa);
+ MemFree(pinvargs);
+ }
+}
+
+
+/***
+*PRIVATE NEARCODE GEN_DTINFO::CopyBackByrefArgs
+*Purpose:
+* Copy back byref temp's that were created when calling a routine that
+* wants a BYREF VARIANT, but is given a BYREF <something else>
+*
+*Entry:
+* pinvargs = the structure containing the byref args to copy back
+*
+*Exit:
+* None
+*
+***********************************************************************/
+HRESULT NEARCODE
+GEN_DTINFO::CopyBackByrefArgs(INVOKEARGS FAR* pinvargs)
+{
+ VARIANT * pvargByrefOld;
+ VARIANT * pvargNew;
+ HRESULT hresult;
+ VARTYPE vtOld;
+
+ DebAssert (pinvargs != NULL, "");
+ for (UINT u = 0; u < pinvargs->cArgs; ++u) {
+ if ((pvargByrefOld = pinvargs->rgpvargByref[u]) != NULL) {
+
+ pvargNew = &pinvargs->rgvarg[u];
+
+ DebAssert(pvargByrefOld->vt & VT_BYREF, "");
+ vtOld = pvargByrefOld->vt & ~VT_BYREF;
+
+ // if the user changed the type of the byref variant during the invoke,
+ // attempt to change it back to the original type.
+ if (vtOld != pvargNew->vt) {
+ hresult = VariantChangeType(pvargNew, pvargNew, 0, vtOld);
+ if (hresult != NOERROR)
+ return hresult;
+ }
+
+ // Handle array.
+ if (vtOld & VT_ARRAY) {
+ SAFEARRAY FAR* psaOld, FAR* psaNew;
+ SAFEARRAYBOUND FAR* psaboundOld, FAR* psaboundNew;
+ ULONG cbData = 0L;
+ USHORT us;
+
+ psaOld = *pvargByrefOld->pparray;
+ psaNew = pvargNew->parray;
+
+ // If this is a fixd-size array, make sure the size of it
+ // hasn't changed.
+ //
+ if (psaOld && psaOld->fFeatures & FADF_FIXEDSIZE) {
+ if (psaOld->cDims != psaNew->cDims
+ || psaOld->cbElements != psaNew->cbElements) {
+
+ return HresultOfScode(DISP_E_TYPEMISMATCH);
+ }
+
+ if (psaOld->cDims){
+ psaboundOld = &psaOld->rgsabound[psaOld->cDims - 1];
+ psaboundNew = &psaNew->rgsabound[psaNew->cDims - 1];
+
+ cbData = (ULONG)psaOld->cbElements;
+
+ for(us = 0; us < psaOld->cDims; ++us){
+ // Make sure none of these have changed.
+ if (psaboundOld->cElements != psaboundNew->cElements
+ || psaboundOld->lLbound != psaboundNew->lLbound) {
+
+ return HresultOfScode(DISP_E_TYPEMISMATCH);
+ }
+
+ cbData *= psaboundOld->cElements;
+ --psaboundOld;
+ --psaboundNew;
+ }
+
+ // Copy the data from the new to the old.
+ hmemcpy(psaOld->pvData, psaNew->pvData, cbData);
+
+ // Delete the new array descriptor, but don't
+ // free any of the array's resources as ownership
+ // has been transferred.
+ //
+ DebAssert(!(psaNew->fFeatures & FADF_AUTO
+ && psaNew->fFeatures & FADF_STATIC
+ && psaNew->fFeatures & FADF_EMBEDDED),
+ "Can't free.");
+
+ psaNew->fFeatures = 0; // don't free any resources
+ (VOID)SafeArrayDestroy(psaNew); // Ignore the error, as there's
+ // no going back.
+ }
+ }
+
+ // If the array is redimmable, replace the old safearray with the
+ // new one.
+ //
+ else {
+ if (psaOld) {
+ DebAssert(!(psaOld->fFeatures & FADF_AUTO
+ && psaOld->fFeatures & FADF_STATIC
+ && psaOld->fFeatures & FADF_EMBEDDED),
+ "Can't free");
+
+ if (hresult = SafeArrayDestroy(psaOld)) {
+ (VOID)SafeArrayDestroy(psaNew);
+ return hresult;
+ }
+ }
+
+ *pvargByrefOld->pparray = psaNew;
+ }
+ }
+ else {
+ // Free the original byref variant's data
+ switch (vtOld) {
+ case VT_BSTR:
+ SysFreeString(*pvargByrefOld->pbstrVal);
+ break;
+ case VT_DISPATCH:
+ case VT_UNKNOWN:
+ if (*pvargByrefOld->ppdispVal != NULL) {
+ (*pvargByrefOld->ppdispVal)->Release();
+ }
+ break;
+#if ID_DEBUG
+ case VT_EMPTY:
+ case VT_NULL:
+ case VT_VARIANT:
+ DebAssert(FALSE, "bad orginal vartype");
+#endif //ID_DEBUG
+
+ default:
+ break;
+ }
+
+ // copy the new variant's data back over the original data
+#if EI_OLE
+ memcpy(pvargByrefOld->byref, &pvargNew->iVal, SizeofTdesckind((TYPEDESCKIND)vtOld, SYSKIND_CURRENT));
+#else //EI_OLE
+ memcpy(pvargByrefOld->byref, &pvargNew->iVal, SizeofTdesckind((TYPEDESCKIND)vtOld));
+#endif //EI_OLE
+ }
+
+ // mark the new variant as free, since ownership transfers to the
+ // old variant.
+ pvargNew->vt = VT_EMPTY;
+ }
+ }
+ return NOERROR;
+}
+
+
diff --git a/private/oleauto/src/typelib/gptbind.cxx b/private/oleauto/src/typelib/gptbind.cxx
new file mode 100644
index 000000000..9429b28f6
--- /dev/null
+++ b/private/oleauto/src/typelib/gptbind.cxx
@@ -0,0 +1,1526 @@
+/***
+*gptbind.cxx - GENPROJ_TYPEBIND class implementation
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* TYPEBIND for an Object Basic project.
+* Describes referenced project names, standard module names
+* and class modules names.
+* Note that in OB, referenced projects have an implicit
+* order such that (names in) the i'th referenced project hides the
+* (names in) i+1'th referenced project.
+* In a single project, if multiple modules present different
+* of the same name it is an ambiguity.
+* Methods are provided to bind to identifiers:
+* - at project-level.
+* - globals within standard modules (types and members).
+* - visible identifiers in referenced projects (includes
+* modules names and global members).
+*
+* Note that the project's project-level cache is validated
+* (as the disjunction of all its modules' caches) when
+* a GENPROJ_TYPEBIND is requested and it's invalid and all
+* the modules' caches are valid.
+*
+* An instance is embedded in an STL_TYPEBIND -- and the
+* implementation assumes this, i.e. that it can get at
+* its containing ITypeLib by subtracting its offset into
+* the containing instance from its this pointer to obtain
+* the ITypeLib instance. To this end, STL_TYPEBIND makes
+* available a public static const member with that value.@
+*
+*
+*Revision History:
+*
+* 16-Jun-92 ilanc: Created
+* 30-Jul-92 w-peterh: removed function overloading
+* 23-Feb-93 rajivk : Support for Predeclared Identifier
+* 30-Apr-93 w-jeffc: made DEFN data members private
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "silver.hxx"
+#include "typelib.hxx"
+
+#define GENPROJ_TYPEBIND_VTABLE
+#include "clutil.hxx" // [cfront] needed for HashOfHgnam which is
+ // needed by ncache.hxx etc. etc.
+#include "gptbind.hxx"
+#include "dtbind.hxx"
+#include "gtlibole.hxx"
+#include "gdtinfo.hxx"
+#include "exbind.hxx"
+
+#pragma hdrstop(RTPCHNAME)
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+char szOleGptbindCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleGptbindCxx
+#else
+static char szGptbindCxx[] = __FILE__;
+#define SZ_FILE_NAME szGptbindCxx
+#endif
+#endif
+
+#define MAXCOPY 32
+
+extern BOOL IsTypeBasicIntrinsic(TYPEDESCKIND tdesckind);
+
+
+
+LPOLESTR GENPROJ_TYPEBIND::szProtocolName = WIDE("MS-GENPROJ_TYPEBIND");
+// LPOLESTR GENPROJ_TYPEBIND::szBaseName = WIDE("MS-DEFN_TYPEBIND");
+
+CONSTDATA UINT GENPROJ_TYPEBIND::oGbindnametbl =
+ offsetof(GENPROJ_TYPEBIND, m_gbindnametbl);
+
+
+// empty dtor
+//
+
+// CONSIDER: inlining?
+
+#pragma code_seg(CS_INIT)
+GENPROJ_TYPEBIND::~GENPROJ_TYPEBIND() {}
+#pragma code_seg()
+
+// QueryProtocol method
+//
+LPVOID GENPROJ_TYPEBIND::QueryProtocol(LPOLESTR szInterfaceName)
+{
+ if (szInterfaceName == szProtocolName ||
+ ostrcmp(szInterfaceName, szProtocolName) == 0)
+ return this;
+ else
+ return DEFN_TYPEBIND::QueryProtocol(szInterfaceName);
+}
+
+
+/***
+*PUBLIC GENPROJ_TYPEBIND::Pgtlibole
+*Purpose:
+* Gets pointer to containing typelib.
+*
+*Implementation Notes:
+* NOTE: defined inline here and not in the header becuase
+* of mutual dependency between gtlibole and gptbind.
+* NOTE: this method is called in gbindtbl and so cannot be
+* inline. mikewo.
+*
+* Subtracts from this pointer the offset of this
+* embedded instance in container. Offset is obtained
+* from a GenericTypeLibOLE static member.
+*
+*Entry:
+*
+*Exit:
+* GenericTypeLibOLE *
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+GenericTypeLibOLE *GENPROJ_TYPEBIND::Pgtlibole() const
+{
+ return (GenericTypeLibOLE *)((BYTE *)this - GenericTypeLibOLE::oGptbind);
+}
+#pragma code_seg()
+
+
+
+/***
+*PUBLIC GENPROJ_TYPEBIND::Initializer - initialize an instance.
+*Purpose:
+* initializes a GENPROJ_TYPEBIND instance.
+*
+*Implementation Notes:
+*
+*Entry:
+* psheapmgr SHEAP_MGR for tables and caches.
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR GENPROJ_TYPEBIND::Init(SHEAP_MGR *psheapmgr)
+{
+ NAMMGR *pnammgr;
+ TIPERROR err;
+
+ DebAssert(psheapmgr != NULL, "GENPROJ_TYPEBIND: psheapmgr uninitialized.");
+
+ IfErrRet(Pgtlibole()->GetNamMgr(&pnammgr));
+
+ // Init block manager member.
+ IfErrRet(m_gbindnametbl.Init(psheapmgr, pnammgr));
+
+ // Init compstate member
+ m_compstateModule = CS_SEMIDECLARED;
+
+
+ return err;
+}
+
+
+/***
+*PUBLIC GENPROJ_TYPEBIND::Constructor - Construct an instance.
+*Purpose:
+* Constructs a GENPROJ_TYPEBIND instance.
+*
+*Implementation Notes:
+* Sets all contained pointers to sub-objects to NULL.
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+GENPROJ_TYPEBIND::GENPROJ_TYPEBIND()
+{
+}
+#pragma code_seg()
+
+
+
+
+
+
+
+
+
+
+/***
+*PUBLIC GENPROJ_TYPEBIND::AddNameToTable
+*Purpose:
+* Converts the given szName to an HLNAM and adds it to the
+* project-level binding table.
+*
+*Implementation Notes:
+*
+*Entry:
+* szName The name of the typeinfo
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR GENPROJ_TYPEBIND::AddNameToTable(LPSTR szName,
+ UINT ityp,
+ BOOL isTypeInfo)
+{
+ NAMMGR *pnammgr;
+ HLNAM hlnam;
+ BOOL isGlobal;
+ GEN_DTINFO *pgdti;
+ TIPERROR err;
+
+ // Get the hlnam for the type's name
+ IfErrRet(Pgtlibole()->GetTypeBind());
+ IfErrRet(Pgtlibole()->GetNamMgr(&pnammgr));
+
+ IfErrRet(pnammgr->HlnamOfStr(szName, &hlnam, FALSE, NULL));
+
+ // Determine if the type is global
+ if (isTypeInfo) {
+ IfErrRet(Pgtlibole()->GetGdtiOfItyp(ityp, &pgdti));
+ isGlobal = IsUnqualifiable(pgdti);
+ pgdti->Release();
+ }
+ else {
+ // Reference librarys are not "global"
+ isGlobal = FALSE;
+ }
+
+ // Add the type's name the project-level binding table.
+ err = m_gbindnametbl.AddNameToTable(hlnam,
+ ityp,
+ isTypeInfo,
+ isGlobal);
+
+ return err;
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC GENPROJ_TYPEBIND::RemoveNameFromTable
+*Purpose:
+* Converts the given szName to an HLNAM and removes it from the
+* project-level binding table.
+*
+*Implementation Notes:
+*
+*Entry:
+* szName The name of the typeinfo
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR GENPROJ_TYPEBIND::RemoveNameFromTable(LPOLESTR szName)
+{
+ NAMMGR *pnammgr;
+ HLNAM hlnam;
+ TIPERROR err;
+
+ // Get the hlnam for the type's name
+ IfErrRet(Pgtlibole()->GetTypeBind());
+ IfErrRet(Pgtlibole()->GetNamMgr(&pnammgr));
+
+ IfErrRet(pnammgr->HlnamOfStrW(szName, &hlnam, FALSE, NULL));
+
+ // Remove the type's name from the project-level binding table.
+ return m_gbindnametbl.RemoveNameFromTableOfHlnam(hlnam);
+}
+
+#if 0 //Dead Code
+/***
+*PUBLIC GENPROJ_TYPEBIND::VerifyNameOfOrdinal
+*Purpose:
+* Converts the given szName to an HLNAM and verifies that it
+* is the correct name for the given ordinal.
+*
+*Implementation Notes:
+*
+*Entry:
+* szName The name of the typeinfo
+* ityp The index for the name
+* isTypeInfo True if we're verifying a typeinfo
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR GENPROJ_TYPEBIND::VerifyNameOfOrdinal(LPSTR szName,
+ UINT ityp,
+ BOOL isTypeInfo)
+{
+ NAMMGR *pnammgr;
+ HLNAM hlnam;
+ TIPERROR err;
+
+ // Get the hlnam for the type's name
+ IfErrRet(Pgtlibole()->GetTypeBind());
+ IfErrRet(Pgtlibole()->GetNamMgr(&pnammgr));
+
+ IfErrRet(pnammgr->HlnamOfStr(szName, &hlnam, FALSE, NULL));
+
+ // Do the verification
+ return m_gbindnametbl.VerifyNameOfOrdinal(hlnam, ityp, isTypeInfo);
+}
+#endif //0
+
+/***
+*PROTECTED GENPROJ_TYPEBIND::BindAll - Bind to id.
+*Purpose:
+* Bind to type or non-type id in current proj
+* or referenced project.
+*
+*Implementation Notes:
+* Defer to BindProjLevel callback of current project --
+* if not found there iterate over referenced projects,
+* deferring likewise to BindDefnProjLevel respectively.
+*
+*Entry:
+* BindRefProjLevel Proj-level binding function callback for ref'ed projs (IN).
+* fuInvokeKind Invocation kind flags (IN).
+* access Visibility attr: private means everything etc. (IN)
+* compstate The state to bring each module to when we bind.
+* pexbind Pointer to caller-allocated struct for EXBIND (IN/OUT).
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+#define HACKERY
+#ifdef HACKERY
+TIPERROR tcomp(ITypeLibA *ptlibRef, ITypeCompA **pptcompRefLib)
+{
+ return TiperrOfHresult(ptlibRef->GetTypeComp(pptcompRefLib));
+}
+#endif
+TIPERROR GENPROJ_TYPEBIND::BindAll(
+ BOOL fWantType,
+ HGNAM hgnam,
+ UINT fuInvokeKind,
+ ACCESS access,
+ COMPSTATE compstate,
+ EXBIND *pexbind)
+{
+ TIPERROR err;
+
+ DebAssert(pexbind != NULL, "bad param.");
+
+ // First, consider current project.
+ // Note: We can bind to both PRIVATE and PUBLIC modules
+ // in the current proj.
+ //
+ IfErrRet(BindProjLevel(fWantType,
+ hgnam,
+ fuInvokeKind,
+ access, // mod-level
+ ACCESS_Private, // proj-level
+ compstate,
+ pexbind));
+
+
+ return TIPERR_None;
+
+ return err;
+}
+
+
+
+/***
+*PUBLIC GENPROJ_TYPEBIND::BindDefnStr - Bind to id.
+*Purpose:
+* Bind to id given a string (as opposed to an hgnam).
+*
+*
+*Entry:
+* szName Name of id to bind. (IN)
+* fuInvokeKind flagkind of invocation (IN).
+* access Visibility attr: private means everything etc. (IN)
+* pexbind Pointer to caller-allocated struct for EXBIND (IN/OUT).
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR GENPROJ_TYPEBIND::BindDefnStr(LPSTR szName,
+ UINT fuInvokeKind,
+ ACCESS access,
+ EXBIND *pexbind)
+{
+ NAMMGR *pnammgr;
+ HGNAM hgnam;
+ TIPERROR err;
+
+ IfErrRet(Pgtlibole()->GetNamMgr(&pnammgr));
+
+ // Map string to hlnam
+ IfErrRet(pnammgr->HgnamOfStr(szName, &hgnam));
+
+ // a good manager delegates...
+ if (err = BindAll(FALSE,
+ hgnam,
+ fuInvokeKind,
+ access,
+ Compstate(),
+ pexbind))
+ {
+ // In an error case, make sure we release any of those
+ // resources we've gathered.
+ //
+ ReleaseResources();
+ }
+
+ return err;
+}
+
+
+/***
+*PUBLIC GENPROJ_TYPEBIND::Release
+*Purpose:
+* Implementation of Release method.
+*
+*Implementation Notes:
+* Defer to typelib.
+*
+*Entry:
+*
+*Exit:
+***********************************************************************/
+
+VOID GENPROJ_TYPEBIND::Release()
+{
+ Pgtlibole()->Release();
+}
+
+
+/***
+*PUBLIC GENPROJ_TYPEBIND::AddRef
+*Purpose:
+* Implementation of AddRef method.
+*
+*Implementation Notes:
+* Defer to typelib.
+*
+*Entry:
+*
+*Exit:
+***********************************************************************/
+
+VOID GENPROJ_TYPEBIND::AddRef()
+{
+ // Defer to containing typelib
+ Pgtlibole()->AddRef();
+}
+
+
+TYPEKIND GENPROJ_TYPEBIND::GetTypeKind()
+{
+ return (TYPEKIND)0;
+}
+
+
+BOOL GENPROJ_TYPEBIND::IsProtocol()
+{
+ return FALSE;
+}
+
+
+USHORT GENPROJ_TYPEBIND::GetCbSize()
+{
+ return (USHORT)~0;
+}
+
+
+USHORT GENPROJ_TYPEBIND::GetAlignment()
+{
+ return (USHORT)~0;
+}
+
+
+/***
+*PUBLIC GENPROJ_TYPEBIND::Read - Read serialized image of GENPROJ_TYPEBIND.
+*Purpose:
+* Read serialized image of GENPROJ_TYPEBIND.
+*
+*Implementation Notes:
+* Serialized format:
+* byte containing COMPSTATE
+* serialized GENPROJ_BINDNAME_TABLE
+*
+*Entry:
+* pstrm - STREAM to read image from (IN).
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR GENPROJ_TYPEBIND::Read(STREAM *pstrm)
+{
+ BYTE bCompState;
+ TIPERROR err;
+
+ DebAssert(pstrm != NULL, "bad param.");
+
+ // Deserialize GENPROJ_TYPEBIND meta-info.
+ IfErrRet(pstrm->Read(&bCompState, sizeof(bCompState)));
+
+ // Deserialize BINDNAME_TABLE embedded member
+ IfErrRet(m_gbindnametbl.Read(pstrm));
+
+ m_compstateModule = (COMPSTATE)bCompState;
+ return TIPERR_None;
+}
+
+
+/***
+*PUBLIC GENPROJ_TYPEBIND::Write - Write image of GENPROJ_TYPEBIND.
+*Purpose:
+* Write image of GENPROJ_TYPEBIND.
+*
+*Implementation Notes:
+*
+*Entry:
+* pstrm - STREAM to read image to (IN).
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR GENPROJ_TYPEBIND::Write(STREAM *pstrm)
+{
+ BYTE bCompState = (BYTE)m_compstateModule;
+ TIPERROR err;
+
+ DebAssert(pstrm != NULL, "bad param.");
+
+ // Serialize GENPROJ_TYPEBIND meta-info.
+ IfErrRet(pstrm->Write(&bCompState, sizeof(bCompState)));
+
+ // serialize BINDNAME_TABLE embedded member
+ IfErrRet(m_gbindnametbl.Write(pstrm));
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GENPROJ_TYPEBIND::BindTypeDefnStr - Bind to a type.
+*Purpose:
+* Bind to a type given a string (as opposed to an hgnam).
+*
+*Implementation Notes:
+* Just defers to BindAll(szName).
+* CONSIDER: define shared function for BindDefnStr and BindTypeDefnStr
+* that abstract getting nammgr and mapping to hgnam.
+*
+*Entry:
+* szName Name of id to bind. (IN)
+* fuInvokeKind flagkind of invocation (IN).
+* access Visibility attr: private means everything etc. (IN)
+* pexbind Pointer to caller-allocated struct for EXBIND (IN/OUT).
+*
+*Exit:
+* None.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR GENPROJ_TYPEBIND::BindTypeDefnStr(LPSTR szName,
+ UINT, // fuInvokeKind: ignored
+ ACCESS access,
+ EXBIND *pexbind)
+{
+ NAMMGR *pnammgr;
+ HGNAM hgnam;
+ TIPERROR err;
+
+ IfErrRet(Pgtlibole()->GetNamMgr(&pnammgr));
+
+ // Map string to hlnam
+ IfErrRet(pnammgr->HgnamOfStr(szName, &hgnam));
+
+ // Bind to a type id in this or referenced project.
+ return BindAll(
+ TRUE, // want type
+ hgnam,
+ 0, // fuInvokeKind: ignored for types.
+ access,
+ Compstate(),
+ pexbind);
+}
+
+
+/***
+*PROTECTED GENPROJ_TYPEBINDs::BindProjLevel
+*Purpose:
+* Bind to type or non-type id at project level given callback.
+*
+*Implementation Notes:
+* Binds to a visible id at project-level:
+* - test project-level cache first.
+* - query project-level table first
+* - if not found then
+* iterate over each module deferring to module-level
+* callback to bind at module-level.
+*
+* CONSIDER: is there any need to distinguish between
+* dyn vs. proj typebind match???
+*
+*Entry:
+* BindModuleLevel Module-level binding function callback (IN).
+* hgnam Name of id to bind. (IN)
+* fuInvokeKind Flag word: invoke kinds (IN).s
+* accessMod Visibility attr for names at module-level
+* private means everything etc. (IN)
+* accessProj Visibility attr for names at proj-level (IN).
+* compstate What state to bring module to when bound.
+* pexbind Pointer to caller-allocated struct for EXBIND (IN/OUT).
+*
+*Exit:
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR GENPROJ_TYPEBIND::BindProjLevel(
+ BOOL fWantType,
+ HGNAM hgnam,
+ UINT fuInvokeKind,
+ ACCESS access,
+ ACCESS accessProj,
+ COMPSTATE compstate,
+ EXBIND *pexbind)
+{
+ BOOL fMatchProj;
+ UINT uOrdinal;
+ USHORT indexMatch;
+ GENPROJ_BIND_DESC gpbinddescMatch;
+ EXBIND exbindMatch;
+ GenericTypeLibOLE *pgtlibole = NULL;
+ DEFN_TYPEBIND *pdfntbindMod = NULL;
+ DEFN_TYPEBIND *pdfntbindRefLib = NULL;
+ DYN_TYPEBIND *pdtbindMod = NULL;
+ GENPROJ_TYPEBIND *pgptbindRefLib = NULL;
+ TYPE_DATA *ptdataMod = NULL;
+ HVAR_DEFN hvdefn;
+ ITypeLibA *ptlibRef = NULL;
+ GEN_DTINFO *pgdti = NULL;
+ BINDINFO bindinfoProjLevel;
+ TIPERROR err = TIPERR_None;
+ HLNAM hlnam;
+ NAMMGR *pnammgr;
+
+ DebAssert((pexbind != NULL), "bad param.");
+
+ pgtlibole = Pgtlibole(); // get containing typelib.
+ fMatchProj = FALSE; // be pessimistic
+
+
+ // Get containing typelib's nammgr
+ IfErrRet(pgtlibole->GetNamMgr(&pnammgr));
+
+
+ // Get the HLNAM of the HGNAM
+ hlnam = pnammgr->HlnamOfHgnam(hgnam);
+
+ // Look up name at project-level.
+ indexMatch = m_gbindnametbl.IndexOfHlnam(hlnam);
+
+ if (indexMatch != BIND_INVALID_INDEX) {
+ // We have a project-level match!
+ fMatchProj = TRUE;
+
+ // We cache all the attributes of gpbinddescMatch here
+ // since it's in movable memory. To do so we simply shallow
+ // copy it to a local stack-alloced BIND_DESC.
+ //
+ gpbinddescMatch = *(m_gbindnametbl.QgpbinddescOfIndex(indexMatch));
+
+ // Get the module or project's ordinal in its respective
+ // container collection.
+ //
+ uOrdinal = gpbinddescMatch.Ordinal();
+
+ // Then get its possibly cached typebind unless it's the
+ // the current project: in that case we already have
+ // its typebind, namely this.
+ // 0xFFFF means the current project -- all other modules and
+ // ref'ed projs have an ordinal >= 0 that is set when
+ // the BIND_DESC is created.
+ //
+ if (uOrdinal == (UINT)0xFFFF) {
+ // they want to bind to something in the current project...
+ bindinfoProjLevel.m_bindinfokind = BINDINFOKIND_OB;
+ bindinfoProjLevel.m_pdfntbind = this;
+ }
+ else if (gpbinddescMatch.IsTypeInfo()) {
+ // Create a bindinfo for this module.
+ bindinfoProjLevel.m_bindinfokind = BINDINFOKIND_OB;
+ bindinfoProjLevel.m_pdfntbind =
+ m_gbindnametbl.PdtbindOfOrdinal(uOrdinal);
+ }
+
+ // If we matched on a module then ensure that
+ // that its TYPEBIND is in the appropriate compstate.
+ // Likewise for a project.
+ // If we haven't yet cached the typebind for the module
+ // or project, then get the appropriate typebind and cache it now.
+ //
+ if (bindinfoProjLevel.IsEmpty() ||
+ (bindinfoProjLevel.BindInfoKind() == BINDINFOKIND_OB &&
+ bindinfoProjLevel.Pdfntbind() == NULL) ||
+ (bindinfoProjLevel.BindInfoKind() == BINDINFOKIND_NonOB &&
+ bindinfoProjLevel.Ptcomp() == NULL)) {
+ // This switches on proj vs. mod-level, and produces
+ // a non-null bindinfoProjLevel
+ //
+ if (gpbinddescMatch.IsTypeInfo()) {
+ // Get the gdtinfo for the module and then its typebind
+ IfErrRet(pgtlibole->GetGdtiOfItyp(uOrdinal, &pgdti));
+
+ // Get the typebind.
+ IfErrGo(pgdti->PdfntbindSemiDeclared(&pdfntbindMod));
+
+ pdtbindMod =
+ (DYN_TYPEBIND *)pdfntbindMod->QueryProtocol(DYN_TYPEBIND::szProtocolName);
+ DebAssert(pdtbindMod != NULL, "bad DYN_TYPEBIND.");
+
+ // bump internal refcount.
+ pdtbindMod->AddInternalRef();
+
+ // and cache.
+ m_gbindnametbl.SetPdtbindOfOrdinal(uOrdinal, pdtbindMod);
+
+ bindinfoProjLevel.m_bindinfokind = BINDINFOKIND_OB;
+ bindinfoProjLevel.m_pdfntbind = pdtbindMod;
+
+ // and release the typeinfo
+ RELEASE(pgdti);
+ }
+ } // if !bindinfoProjLevel.IsEmpty()
+
+ DebAssert(!bindinfoProjLevel.IsEmpty(),
+ "whoops! no proj-level typebind/typecomp.");
+
+ // Ensure that if a module-level typebind it's
+ // (1) That the access attribute matches.
+ // (2) in DECLARED if need be.
+ //
+ BOOL isClassOk;
+
+ if (gpbinddescMatch.IsTypeInfo()) {
+ pdtbindMod = (DYN_TYPEBIND *)
+ (bindinfoProjLevel.Pdfntbind()->
+ QueryProtocol(DYN_TYPEBIND::szProtocolName));
+ DebAssert(pdtbindMod != NULL, "bad DYN_TYPEBIND.");
+ // Note that for now the only
+ // types (i.e. modules) that are in the variable namespace are:
+ // appobj COCLASSes, ENUM, MODULE -- thus for others we fail to bind
+ // if the client wants to bind to a non-type. Eventually
+ // we'll explicitly flag each typeinfo as to whether its
+ // name is in the variable namespace.
+ //
+ TYPEKIND tkindMod = pdtbindMod->GetTypeKind();
+ // Either a class or coclass with either the appobject or the
+ // predeclared identifier is ok.
+ //
+ isClassOk =
+ (tkindMod == TKIND_COCLASS
+ )
+ && (pdtbindMod->Pdtroot()->GetTypeFlags() & TYPEFLAG_FAPPOBJECT
+ || pdtbindMod->Pdtroot()->GetTypeFlags() & TYPEFLAG_FPREDECLID);
+ if (!fWantType &&
+ !((tkindMod == TKIND_ENUM) ||
+ (tkindMod == TKIND_MODULE) ||
+ isClassOk))
+ {
+ fMatchProj = FALSE;
+ indexMatch = BIND_INVALID_INDEX;
+ goto NoProjLevelMatch;
+ }
+ if (IsMatchOfVisibility(pdtbindMod->Pdtroot()->Access(),
+ accessProj) == FALSE) {
+ // Matched private module and we want only public modules.
+ // "break" by resetting fMatchProj.
+ // Note: we reset indexMatch to BIND_INVALID_INDEX so that we can
+ // "reuse" it later -- this isn't strictly necesssary
+ // but we assert thus later...
+ //
+ fMatchProj = FALSE;
+ indexMatch = BIND_INVALID_INDEX;
+ }
+ else {
+ if (compstate == CS_DECLARED) {
+ IfErrGo(pdtbindMod->Pdtroot()->EnsureInDeclaredState());
+ }
+ else {
+ DebAssert(compstate == CS_SEMIDECLARED,
+ "bad compstate.");
+ }
+
+ // Check to see if we need to bind to the the predeclared
+ // identifier. Note that only class and coclass types
+ // that are flagged as appobjs or predeclared ids
+ // have predeclared ids. Note in addition that we only
+ // bind to the predeclared id if they want to bind to
+ // a non-type.
+ //
+ if (!fWantType && isClassOk)
+ {
+ ITypeInfoA *ptinfoPredeclared;
+ // Get the TYPE_DATA and the predeclared VAR_DEFN
+ ptdataMod = pdtbindMod->Ptdata();
+ hvdefn = pdtbindMod->HvdefnPredeclared();
+ // Set the output parameter and return
+ pexbind->SetBindKind(BKIND_OneVarMatch);
+ pexbind->SetHdefn(hvdefn);
+ pexbind->SetPtdata(ptdataMod);
+ ptinfoPredeclared = ptdataMod->Pdtroot()->Pgdtinfo();
+ pexbind->SetPtinfo(ptinfoPredeclared);
+ ptinfoPredeclared->AddRef(); // client must release
+ return TIPERR_None;
+ }
+ } // if visibility match
+ }
+
+ if (fMatchProj == TRUE) {
+ // Note that the only way the fMatchProj could have
+ // become reset is if the visibility attr didn't match.
+ //
+ // Setup result param.
+ if (bindinfoProjLevel.BindInfoKind() == BINDINFOKIND_OB) {
+ pexbind->SetPdfntbind(bindinfoProjLevel.Pdfntbind());
+ }
+ else {
+ }
+ pexbind->SetBindKind((BIND_KIND)(gpbinddescMatch.IsTypeInfo() ?
+ BKIND_DynTypeBindMatch :
+ BKIND_ProjTypeBindMatch));
+ return TIPERR_None;
+ }
+ } // if proj-level match
+
+NoProjLevelMatch:
+
+ // In the OLE case, don't attempt to bind in the modules
+ // if we are searching for a type.
+ //
+ if (fWantType)
+ return TIPERR_None;
+
+
+ // No match at proj-level, so try the individual modules...
+ //
+ DebAssert((fMatchProj == FALSE) &&
+ (indexMatch == BIND_INVALID_INDEX), "bad match.");
+
+ // Decide if we want to bind using the nammgr or the name cache
+ // optimizations. We want to use the name cache if:
+ // - we are attempting to bind to a type (OB only)
+ // or
+ // - the project only wants to bind to a public modules and
+ // the name is ambiguous.
+ //
+ if (fWantType
+ || !pnammgr->IsValidItyp(hlnam)
+ || accessProj == ACCESS_Public && pnammgr->IsAmbiguous(hlnam)) {
+ // Try to bind.
+ IfErrRet(BindModulesWithCaches(fWantType,
+ hgnam,
+ fuInvokeKind,
+ access,
+ accessProj,
+ compstate,
+ pexbind));
+ }
+ else {
+ // Try to bind.
+ IfErrRet(BindModulesWithNammgr(fWantType,
+ hgnam,
+ fuInvokeKind,
+ access,
+ accessProj,
+ compstate,
+ pexbind));
+ }
+
+ // Fall through...
+
+Error:
+ RELEASE(pgdti);
+ RELEASE(ptlibRef);
+ return err;
+}
+
+
+/***
+*PROTECTED GENPROJ_TYPEBINDs::BindModulesWithCaches
+*Purpose:
+* Bind to a type or nontype in the modules of this project
+*
+*Entry:
+* BindModuleLevel Module-level binding function callback (IN).
+* szName Name of id to bind. (IN)
+* fuInvokeKind Flag word: invoke kinds (IN).s
+* accessMod Visibility attr for names at module-level
+* private means everything etc. (IN)
+* accessProj Visibility attr for names at proj-level (IN).
+* compstate What state to bring module to when bound.
+* pexbind Pointer to caller-allocated struct for EXBIND (IN/OUT).
+*
+*Exit:
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR GENPROJ_TYPEBIND::BindModulesWithCaches(BOOL fWantType,
+ HGNAM hgnam,
+ UINT fuInvokeKind,
+ ACCESS access,
+ ACCESS accessProj,
+ COMPSTATE compstate,
+ EXBIND *pexbind)
+{
+ BOOL fMatch;
+ UINT ityp;
+ UINT iGlobalBucket, iGlobalBucketNext;
+ GENPROJ_BIND_DESC gpbinddescMatch;
+ EXBIND exbindMatch;
+ GenericTypeLibOLE *pgtlibole;
+ TIPERROR err;
+ NAMMGR *pnammgr;
+ HLNAM hlnam;
+
+ pgtlibole = Pgtlibole(); // get containing typelib.
+ fMatch = FALSE;
+
+ // Reset the exbind
+ *pexbind = EXBIND();
+
+ // Get containing typelib's nammgr
+ IfErrRet(pgtlibole->GetNamMgr(&pnammgr));
+
+ // Map string to hlnam
+ hlnam = pnammgr->HlnamOfHgnam(hgnam);
+
+ // Loop through the TypeInfos which expose global names, checking
+ // the name cache and (if there's a hit) attempting to bind to
+ // the name.
+ //
+ // Get the first type that exposes global names.
+ iGlobalBucket = m_gbindnametbl.IndexFirstGlobal();
+
+ while (iGlobalBucket != BIND_INVALID_INDEX) {
+ // Cache the next global so we don't have to redef later.
+ gpbinddescMatch = *(m_gbindnametbl.QgpbinddescOfIndex(iGlobalBucket));
+ iGlobalBucketNext = gpbinddescMatch.IndexNextGlobal();
+
+ // The last entry of the list is determined by a reference
+ // to itself.
+ //
+ if (iGlobalBucket == iGlobalBucketNext) {
+ iGlobalBucketNext = BIND_INVALID_INDEX;
+ }
+ ityp = gpbinddescMatch.Ordinal();
+
+ // We have the index of the TypeInfo we are most interested
+ // in, so attempt to bind.
+ //
+ // Keeps name cache stats
+ pgtlibole->DebSetNameCacheModTrys();
+
+ // Cache is not valid or the name is in the cache, try to bind
+ if (!pgtlibole->IsValidNameCache(ityp) ||
+ pgtlibole->IsNameInCache(ityp, hgnam)) {
+
+ // Keeps name cache stats
+ pgtlibole->DebSetNameCacheModHits();
+
+ // Try to bind.
+ IfErrGo(BindItyp(ityp,
+ fWantType,
+ hgnam,
+ fuInvokeKind,
+ access,
+ accessProj,
+ compstate,
+ &exbindMatch));
+
+ // Did we bind?
+ if (!exbindMatch.IsNoMatch()) {
+
+ // Keeps name cache stats
+ pgtlibole->DebSetNameCacheGlobHits();
+
+ if (fMatch == FALSE) {
+ // This is the first match, remember it...
+ // and hope we don't match again, cos if we do
+ // it's an ambiguity.
+ //
+ fMatch = TRUE;
+
+ // Setup OUT params.
+ // Note: we are copying handles or pointers.
+ // The pointers are owned by their binding table
+ // thus the client must eventually call ReleaseResources()
+ // and must guarantee not to cache them beyond that.
+ //
+ *pexbind = exbindMatch;
+ exbindMatch = EXBIND();
+ }
+ else {
+ err = TIPERR_AmbiguousName;
+ goto Error;
+ } // if previously matched
+ } // if match
+ } // if module visible
+ // Move on to the next name
+ iGlobalBucket = iGlobalBucketNext;
+ } // while in list
+ // Fall through...
+
+Error:
+ // In the error case, need to release the ptinfo from the first
+ // match and possibly a second ambiguous.
+ //
+ if (err != TIPERR_None) {
+ if (fMatch == TRUE) {
+ // We matched at least once and save the match in pexbind.
+ if (pexbind->Ptinfo() != NULL) {
+ pexbind->Ptinfo()->Release();
+ }
+ }
+ // If we matched twice -- so release the 2nd match as well.
+ if (exbindMatch.Ptinfo() != NULL) {
+ exbindMatch.Ptinfo()->Release();
+ }
+ }
+
+ return err;
+}
+
+
+/***
+*PROTECTED GENPROJ_TYPEBINDs::BindModulesWithNammgr
+*Purpose:
+* Bind to a type or nontype in the modules of this project
+*
+*Entry:
+* BindModuleLevel Module-level binding function callback (IN).
+* szName Name of id to bind. (IN)
+* fuInvokeKind Flag word: invoke kinds (IN).s
+* accessMod Visibility attr for names at module-level
+* private means everything etc. (IN)
+* accessProj Visibility attr for names at proj-level (IN).
+* compstate What state to bring module to when bound.
+* pexbind Pointer to caller-allocated struct for EXBIND (IN/OUT).
+*
+*Exit:
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR GENPROJ_TYPEBIND::BindModulesWithNammgr(BOOL fWantType,
+ HGNAM hgnam,
+ UINT fuInvokeKind,
+ ACCESS access,
+ ACCESS accessProj,
+ COMPSTATE compstate,
+ EXBIND *pexbind)
+{
+ UINT ityp;
+ HLNAM hlnam;
+ GenericTypeLibOLE *pgtlibole;
+ TIPERROR err;
+ NAMMGR *pnammgr;
+
+ pgtlibole = Pgtlibole(); // get containing typelib.
+
+ // Reset the exbind
+ *pexbind = EXBIND();
+
+ // Get containing typelib's nammgr
+ IfErrRet(pgtlibole->GetNamMgr(&pnammgr));
+
+ // Map hgnam to hlnam
+ hlnam = pnammgr->HlnamOfHgnam(hgnam);
+
+ // Check the nammgr to see if this name is valid and
+ // is global. If so, bind to it.
+ //
+ if (pnammgr->IsValidItyp(hlnam) && pnammgr->IsGlobal(hlnam)) {
+
+ // If this name is marked as ambiguous, return an error.
+ if (pnammgr->IsAmbiguous(hlnam)) {
+ return TIPERR_AmbiguousName;
+ }
+
+ ityp = pnammgr->ItypOfHlnam(hlnam);
+
+ // We have the index of the TypeInfo we are most interested
+ // in, so attempt to bind.
+ //
+ IfErrGo(BindItyp(ityp,
+ fWantType,
+ hgnam,
+ fuInvokeKind,
+ access,
+ accessProj,
+ compstate,
+ pexbind));
+ }
+
+Error:
+ // In the error case, need to release the ptinfo from the first
+ // match.
+ //
+ if (err != TIPERR_None) {
+ // We matched at least once and save the match in pexbind.
+ if (pexbind->Ptinfo() != NULL) {
+ pexbind->Ptinfo()->Release();
+ }
+ }
+
+ return err;
+}
+
+
+/***
+*PROTECTED GENPROJ_TYPEBIND::BindItyp
+*Purpose:
+* Attempt to bind to the given name in the given ityp.
+*
+*Implementation Notes:
+* Defers to generic id binder passing in callback to
+* use at module-level.
+*
+* NOTE: pexbind should be cleared before this function is called.
+* Also, pexbind is not cleaned up if there is an error, the caller
+* should do this.
+*
+*Entry:
+* ityp Index to the typeinfo to bind to
+* szName Name of type id to bind. (IN)
+* fuInvokeKind IGNORED FOR TYPES.
+* access Module-level visibility
+* accessProj Visibility attr for names at proj-level (IN).
+* compstate What state to bring module to when bound.
+* pexbind Pointer to caller-allocated struct for EXBIND (IN/OUT).
+*
+*Exit:
+*
+*Errors:
+* TIPERROR
+***********************************************************************/
+
+TIPERROR GENPROJ_TYPEBIND::BindItyp(UINT ityp,
+ BOOL fWantType,
+ HGNAM hgnam,
+ UINT fuInvokeKind,
+ ACCESS access,
+ ACCESS accessProj,
+ COMPSTATE compstate,
+ EXBIND *pexbind)
+{
+ GenericTypeLibOLE *pgtlibole = NULL;
+ DEFN_TYPEBIND *pdfntbindMod = NULL;
+ DYN_TYPEBIND *pdtbindMod = NULL;
+ GEN_DTINFO *pgdti = NULL;
+ BOOL fImplicitAppobj;
+ TIPERROR err = TIPERR_None;
+
+ DebAssert((pexbind != NULL), "bad param.");
+
+ pgtlibole = Pgtlibole(); // get containing typelib.
+
+ // If there's a module-level typebind in the BIND_DESC
+ // already use it,otherwise get the typeinfo for the module.
+ //
+ pdtbindMod = m_gbindnametbl.PdtbindOfOrdinal(ityp);
+
+ if (pdtbindMod != NULL) {
+#if ID_DEBUG
+ DebAssert(pdtbindMod->GetTypeKind() == TKIND_MODULE ||
+ pdtbindMod->GetTypeKind() == TKIND_ENUM ||
+ (pdtbindMod->Pdtroot()->GetTypeFlags() &
+ TYPEFLAG_FAPPOBJECT) != 0, "bad typebind.");
+#endif // ID_DEBUG
+
+ // Ensure that it's still in at least semi-declared.
+ // If not, rebuild...
+ //
+ if (pdtbindMod->Pdtroot()->CompState() < CS_SEMIDECLARED) {
+ // This doesn't bump refcount.
+ IfErrRet(pdtbindMod->Pdtroot()->PdfntbindSemiDeclared(&pdfntbindMod));
+ pdtbindMod = (DYN_TYPEBIND *)
+ pdfntbindMod->QueryProtocol(DYN_TYPEBIND::szProtocolName);
+ DebAssert(pdtbindMod != NULL, "bad DYN_TYPEBIND.");
+ }
+ }
+ else {
+ // No typebind loaded yet for this module, load it
+ // and see if it's standard -- if so, load its
+ // typebind and cache it. Don't forget to
+ // bump its internal refcount.
+ //
+ IfErrRet(pgtlibole->GetGdtiOfItyp(ityp, &pgdti));
+
+ // Switch on m_compstateModule -- which
+ // is set by proj-level GetDefnTypeBind[SemiDeclared].
+ // The idea is that when in "evalconstexpr" mode,
+ // the exmgr sets the compstate to SEMIDECLARED
+ // and if in "codegen" mode the DECLARED and
+ // here is where we switch on it.
+ // ISSUE: are there reentrancy probs? race-conditions?
+ //
+ // What we actually do is get a SEMIDECLARED
+ // typebind and attempt to match. If no match,
+ // then regardless of how m_compstateModule is set
+ // there's no point bringing all the way to DECLARED.
+ // If there is a match, then we bring the module
+ // to DECLARED iff the m_compstateModule is DECLARED.
+
+ // This doesn't bump refcount.
+ IfErrGo(pgdti->PdfntbindSemiDeclared(&pdfntbindMod));
+
+ pdtbindMod =
+ (DYN_TYPEBIND *)pdfntbindMod->QueryProtocol(DYN_TYPEBIND::szProtocolName);
+ DebAssert(pdtbindMod != NULL, "bad DYN_TYPEBIND.");
+
+ // Might as well cache the TYPEBIND we just loaded
+ // in the binding table
+ // and bump its internal refcount at this point
+ // to ensure that the module won't get unloaded.
+ //
+ pdtbindMod->AddInternalRef();
+
+ // Cache it.
+ m_gbindnametbl.SetPdtbindOfOrdinal(ityp, pdtbindMod);
+ } // if pdtbind != NULL
+
+ // We should reach here with non-NULL pdtbindMod,
+ // which means that either we had a cached one in
+ // our binding table or we just loaded one. In any
+ // event, it will be for a standard module
+ // or Class or CoClass.
+ //
+ DebAssert(pdtbindMod != NULL, "should have dtbind.");
+
+ // Ensure that we can see this module -- E.g.
+ // if we're referencing it from another project
+ // then it must be public.
+ //
+ if (IsMatchOfVisibility(pdtbindMod->Pdtroot()->Access(), accessProj)) {
+ // Determine whether we're binding to an implict appobj,
+ // if so, and we successfully bind we will want to actually
+ // return to our caller the VARDEFN of the appobj!
+ //
+ fImplicitAppobj =
+ pdtbindMod->Pdtroot()->GetTypeFlags() & TYPEFLAG_FAPPOBJECT;
+
+ // Try and bind in this module.
+ IfErrGo(pdtbindMod->BindIdDefn(fWantType,
+ hgnam,
+ fuInvokeKind,
+ access,
+ pexbind));
+
+ // Did we match?
+ if (!pexbind->IsNoMatch()) {
+ DebAssert(pexbind->IsFuncMatch() ||
+ pexbind->IsOneVarMatch() ||
+ pexbind->IsNestedTypeBindMatch(),
+ "bad match.");
+
+
+ // Ensure that exbind contains a pointer to
+ // the TypeInfo which we started with not the
+ // base class in which we found the member
+ // This is just needed for AppObject support.
+ // Only do this abomination if we're binding to
+ // a non-type id.
+ //
+ if (fImplicitAppobj & !fWantType) {
+ pexbind->Ptinfo()->Release();
+
+ // We need to get the typebind's typeinfo since
+ // we might have retrieved the typebind from
+ // the cache and thus never loaded its typeinfo.
+ //
+ pexbind->SetPtinfo(pdtbindMod->Pdtroot()->Pgdtinfo());
+ pdtbindMod->Pdtroot()->Pgdtinfo()->AddRef();
+
+ // Set the bindkind to implicit appobj
+ pexbind->SetBindKind(BKIND_ImplicitAppobjMatch);
+
+ // Set the vardefn to be the appobj's predeclared id.
+ pexbind->SetHdefn(pdtbindMod->HvdefnPredeclared());
+
+ // And finally its typedata
+ pexbind->SetPtdata(pdtbindMod->Ptdata());
+ } // if implicitappobj && !type
+ } // if we matched
+ } // if visible
+
+Error:
+ RELEASE(pgdti);
+
+ return err;
+}
+
+
+/***
+*PUBLIC GENPROJ_TYPEBIND::BindTypeDefnProjLevelStr
+*Purpose:
+* Bind to type at project level.
+*
+*Implementation Notes:
+* Map str to hgnam and defer to proj-level hgnam binder.
+*
+*Entry:
+* szName Name of type id to bind. (IN)
+* fuInvokeKind IGNORED FOR TYPES.
+* access Mod-level Visibility attr:
+* private means everything etc. (IN)
+* accessProj Proj-level Visibility attr:
+* pexbind Pointer to caller-allocated struct for EXBIND (IN/OUT).
+*
+*Exit:
+*
+*Errors:
+* TIPERROR
+***********************************************************************/
+
+TIPERROR GENPROJ_TYPEBIND::BindTypeDefnProjLevelStr(
+ LPSTR szName,
+ UINT, // fuInvokeKind: ignored
+ ACCESS access,
+ ACCESS accessProj,
+ EXBIND *pexbind)
+{
+ NAMMGR *pnammgr;
+ HLNAM hlnam;
+ HGNAM hgnam;
+ TIPERROR err;
+
+ // Bind to a non-type id in this project.
+ // Map str to hgnam and defer to hgnam binder.
+ //
+ IfErrRet(Pgtlibole()->GetNamMgr(&pnammgr));
+
+ // get the hlnam to pass to BindDefn
+ hlnam = pnammgr->HlnamOfStrIfExist(szName);
+
+ if (hlnam == HLNAM_Nil) {
+ // Make sure pexbind is set to nomatch
+ pexbind->SetBindKind(BKIND_NoMatch);
+
+ return TIPERR_None;
+ }
+
+ // Get the hgnam of this hlnam
+ IfErrRet(pnammgr->HgnamOfHlnam(hlnam, &hgnam));
+
+ return BindProjLevel(TRUE,
+ hgnam,
+ 0, // ignored
+ access,
+ accessProj,
+ Compstate(),
+ pexbind);
+}
+
+
+/***
+*PUBLIC GENPROJ_TYPEBIND::BindDefnProjLevelStr
+*Purpose:
+* Bind to non-type or type id at project level.
+*
+*Implementation Notes:
+* Map str to hgnam and defer to proj-level hgnam binder.
+*
+*Entry:
+* szName Name of id to bind. (IN)
+* fuInvokeKind invoke kind flags (IN)
+* access Mod-level Visibility attr:
+* private means everything etc. (IN)
+* accessProj Proj-level Visibility attr:
+* pexbind Pointer to caller-allocated struct for EXBIND (IN/OUT).
+*
+*Exit:
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR GENPROJ_TYPEBIND::BindDefnProjLevelStr(LPSTR szName,
+ UINT fuInvokeKind,
+ ACCESS access,
+ ACCESS accessProj,
+ EXBIND *pexbind)
+{
+ NAMMGR *pnammgr;
+ HGNAM hgnam;
+ HLNAM hlnam;
+ TIPERROR err;
+
+ // Bind to a non-type id in this project.
+ // Map str to hgnam and defer to hgnam binder.
+ //
+ IfErrRet(Pgtlibole()->GetNamMgr(&pnammgr));
+
+ // get the hlnam to pass to BindDefn
+ hlnam = pnammgr->HlnamOfStrIfExist(szName);
+
+ if (hlnam == HLNAM_Nil) {
+ // Make sure pexbind is set to nomatch
+ pexbind->SetBindKind(BKIND_NoMatch);
+
+ return TIPERR_None;
+ }
+
+ // Get the hgnam of this hlnam
+ IfErrRet(pnammgr->HgnamOfHlnam(hlnam, &hgnam));
+
+ return BindProjLevel(FALSE,
+ hgnam,
+ fuInvokeKind,
+ access,
+ accessProj,
+ Compstate(),
+ pexbind);
+}
+
+
+/***
+*PUBLIC GENPROJ_TYPEBIND::ReleaseResources
+*Purpose:
+* Release resources owned by proj-level binder.
+*
+*Implementation Notes:
+* Defers to binding table.
+*
+*Entry:
+*
+*Exit:
+*
+*Errors:
+* None
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+VOID GENPROJ_TYPEBIND::ReleaseResources()
+{
+ m_gbindnametbl.ReleaseResources();
+
+}
+#pragma code_seg()
+
+
+
+
+#if ID_DEBUG
+
+VOID GENPROJ_TYPEBIND::DebCheckState(UINT uLevel) const
+{
+ DebAssert(m_compstateModule == CS_SEMIDECLARED ||
+ m_compstateModule == CS_DECLARED, "bad compstate.");
+
+ m_gbindnametbl.DebCheckState(uLevel);
+}
+
+
+VOID GENPROJ_TYPEBIND::DebShowState(UINT uLevel) const
+{
+ DebPrintf("*** GENPROJ_TYPEBIND ***\n");
+
+ m_gbindnametbl.DebShowState(uLevel);
+}
+
+#endif // ID_DEBUG
diff --git a/private/oleauto/src/typelib/gptbind.hxx b/private/oleauto/src/typelib/gptbind.hxx
new file mode 100644
index 000000000..5021d4085
--- /dev/null
+++ b/private/oleauto/src/typelib/gptbind.hxx
@@ -0,0 +1,254 @@
+/***
+*gptbind.hxx - GENPROJ_TYPEBIND header file
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Implementation of TYPEBIND at project-level.
+*
+*Revision History:
+*
+* 13-Mar-92 ilanc: Created.
+* 30-Jul-92 w-peterh: removed function overloading
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#ifndef GENPROJ_TYPEBIND_HXX_INCLUDED
+#define GENPROJ_TYPEBIND_HXX_INCLUDED
+
+#include "stream.hxx"
+#include "dfntbind.hxx"
+#include "dtbind.hxx" // for DYN_TYPEBIND
+#include "defn.hxx" // for DEFN binding structs.
+#include "gbindtbl.hxx" // for GENPROJ_BINDNAME_TABLE
+// #include "gtlibole.hxx"
+
+
+class GenericTypeLibOLE;
+class EXBIND;
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szGPTBIND_HXX)
+#define SZ_FILE_NAME g_szGPTBIND_HXX
+#endif
+
+class GENPROJ_TYPEBIND;
+class MOCKUP_TYPEBIND;
+
+/***
+*class GENPROJ_TYPEBIND - 'gptbind': Generic proj-level binding impl
+*Purpose:
+* The class defines the project-level type bind.
+*
+***********************************************************************/
+
+class GENPROJ_TYPEBIND : public DEFN_TYPEBIND
+{
+ friend class GEN_PROJECT;
+ friend class GenericTypeLibOLE;
+
+public:
+ GENPROJ_TYPEBIND();
+ nonvirt TIPERROR Init(SHEAP_MGR *psheapmgr);
+
+ // overridden methods
+ virtual ~GENPROJ_TYPEBIND();
+ virtual LPVOID QueryProtocol(LPOLESTR szInterfaceName);
+ virtual VOID Release();
+ virtual VOID AddRef();
+
+ virtual TIPERROR GetTypeInfo(TYPEINFO **lplptinfo);
+ virtual TYPEKIND GetTypeKind();
+ virtual BOOL IsProtocol();
+ virtual USHORT GetCbSize();
+ virtual USHORT GetAlignment();
+
+ virtual TIPERROR BindDefnStr(LPSTR szName,
+ UINT fuInvokeKind,
+ ACCESS access,
+ EXBIND *pexbind);
+
+ virtual TIPERROR BindTypeDefnStr(LPSTR szName,
+ UINT fuInvokeKind,
+ ACCESS access,
+ EXBIND *pexbind);
+
+ virtual TIPERROR BindDefnProjLevelStr(LPSTR szName,
+ UINT fuInvokeKind,
+ ACCESS access,
+ ACCESS accessProj,
+ EXBIND *pexbind);
+
+ virtual TIPERROR BindTypeDefnProjLevelStr(LPSTR szName,
+ UINT, // fuInvokeKind: unused
+ ACCESS access,
+ ACCESS accessProj,
+ EXBIND *pexbind);
+
+
+
+
+ // introduced methods
+ nonvirt TIPERROR Read(STREAM *pstrm);
+ nonvirt TIPERROR Write(STREAM *pstrm);
+ nonvirt GenericTypeLibOLE *Pgtlibole() const;
+ nonvirt VOID ReleaseResources();
+
+ nonvirt TIPERROR AddNameToTable(LPSTR szName, UINT ityp, BOOL isTypeInfo);
+ nonvirt TIPERROR RemoveNameFromTable(LPOLESTR szName);
+#if 0
+ nonvirt TIPERROR VerifyNameOfOrdinal(LPSTR szName,
+ UINT ityp,
+ BOOL isTypeInfo);
+#endif
+
+ nonvirt const GENPROJ_BINDNAME_TABLE *Pgbindnametbl() const;
+
+ nonvirt TIPERROR BindProjLevel(BOOL fWantType,
+ HGNAM hgnam,
+ UINT fuInvokeKind,
+ ACCESS access,
+ ACCESS accessProj,
+ COMPSTATE compstate,
+ EXBIND *pexbind);
+
+ nonvirt TIPERROR BindAll(BOOL fWantType,
+ HGNAM hgnam,
+ UINT fuInvokeKind,
+ ACCESS access,
+ COMPSTATE compstate,
+ EXBIND *pexbind);
+
+
+ nonvirt COMPSTATE Compstate() const;
+
+ // Public data members
+ static LPOLESTR szProtocolName;
+ static LPSTR szBaseName;
+
+ static CONSTDATA UINT oGbindnametbl;
+
+#if ID_DEBUG
+ nonvirt VOID DebCheckState(UINT uLevel) const;
+ nonvirt VOID DebShowState(UINT uLevel) const;
+#else //!ID_DEBUG
+ nonvirt VOID DebCheckState(UINT uLevel) const {}
+ nonvirt VOID DebShowState(UINT uLevel) const {}
+#endif //!ID_DEBUG
+
+protected:
+
+ // Note: 1st parameter is of type member function.
+ nonvirt TIPERROR BindItyp(UINT ityp,
+ BOOL fWantType,
+ HGNAM hgnam,
+ UINT fuInvokeKind,
+ ACCESS access,
+ ACCESS accessProj,
+ COMPSTATE compstate,
+ EXBIND *pexbind);
+
+ // Note: 1st parameter is of type member function.
+ nonvirt TIPERROR BindModulesWithCaches(BOOL fWantType,
+ HGNAM hgnam,
+ UINT fuInvokeKind,
+ ACCESS access,
+ ACCESS accessProj,
+ COMPSTATE compstate,
+ EXBIND *pexbind);
+
+ // Note: 1st parameter is of type member function.
+ nonvirt TIPERROR BindModulesWithNammgr(BOOL fWantType,
+ HGNAM hgnam,
+ UINT fuInvokeKind,
+ ACCESS access,
+ ACCESS accessProj,
+ COMPSTATE compstate,
+ EXBIND *pexbind);
+
+private:
+ COMPSTATE m_compstateModule; // for BindDefnProjLevel()
+
+ // GENPROJ_BINDNAME_TABLE embedded instance
+ GENPROJ_BINDNAME_TABLE m_gbindnametbl;
+
+
+#ifdef GENPROJ_TYPEBIND_VTABLE
+#pragma VTABLE_EXPORT
+#endif
+};
+
+
+
+
+
+/***
+*PUBLIC GENPROJ_TYPEBIND::Pbindnametbl - accessor for BINDNAME_TABLE.
+*Purpose:
+* Gets BINDNAME_TABLE ptr.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* BINDNAME_TABLE *
+*
+***********************************************************************/
+
+inline const GENPROJ_BINDNAME_TABLE *GENPROJ_TYPEBIND::Pgbindnametbl() const
+{
+ return &m_gbindnametbl;
+}
+
+
+/***
+*PUBLIC GENPROJ_TYPEBIND::GetTypeInfo
+*Purpose:
+* N/A
+*
+*Implementation Notes:
+* Inapplicable to typelibs -- they don't have typeinfos.
+*
+*Entry:
+* pptinfo
+*Exit:
+* TIPERROR
+* Produces NULL ptr.
+*
+***********************************************************************/
+
+inline TIPERROR GENPROJ_TYPEBIND::GetTypeInfo(TYPEINFO **pptinfo)
+{
+ // Inapplicable to typelibs -- they don't have typeinfos.
+ DebAssert(pptinfo, "bad param.");
+
+ *pptinfo = NULL;
+ return TIPERR_None;
+}
+
+/***
+*PUBLIC GENPROJ_TYPEBIND::Compstate()
+*Purpose:
+* Gets the target compstate.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* BINDNAME_TABLE *
+*
+***********************************************************************/
+
+inline COMPSTATE GENPROJ_TYPEBIND::Compstate() const
+{
+ return m_compstateModule;
+}
+
+
+#endif // ! GENPROJ_TYPEBIND_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/gtlibole.cxx b/private/oleauto/src/typelib/gtlibole.cxx
new file mode 100644
index 000000000..9d37d0ec9
--- /dev/null
+++ b/private/oleauto/src/typelib/gtlibole.cxx
@@ -0,0 +1,6619 @@
+/**
+*gtlibole.cxx - GenericTypeLibOLE
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Implementation of the TypeLib protocol which supports reading
+* TypeLib's only. Derivatives of this implementation can support
+* reading and writing.
+* This TypeLib implementation uses an IStorage for storage.
+*
+*Implementation:
+* NOTE: currently 18-Mar-93 there are 3 funcs that can be the
+* first call into typelib.dll - these functions must call InitAppData().
+* CreateTypeLib, LoadTypeLib, RegisterTypeLib -- as you add
+* similar such funcs, you have to call InitAppData() as well!
+*
+* Type Entry Array:
+* The implementation uses an array of TYPE_ENTRY structures each of which
+* describes an element of the library. This array is stored in the
+* directory stream of the IStorage. Elements of the library are identified
+* by their index in this array. These indexes are sometimes encapsulated
+* as HTENTRYs (handles to type entries). The interface to ITypeLibs uses
+* indexes; however, it is possible that the implementation might change to
+* not treat the passed in indexes as indexes into the TYPE_ENTRY array and
+* in that case the concept of an HTENTRY would become useful.
+*
+* Local TypeIds
+* Currently the implementation of GenericTypeLibOLE always assumes that the
+* the TypeInfos stored in it are not separately registered since the
+* implementation of GetRegId always prepends the libid to the stored
+* local TypeId.
+* It would be possible to extend this implementation
+* so it maintained a flag indicating whether or not the types are
+* registered independently. Currently it is assumed that the library
+* is just registered.
+*
+* Hash Table:
+* A hash table which maps a TYPEID to the TYPE_ENTRY for the specified
+* type is maintained so that the GetTypeInfo function which returns
+* a TYPEINFO given its TYPEID can determine the correct TYPE_ENTRY quickly.
+*
+* Storage:
+* A GenericTypeLibOLE instance is stored within a SHEAP_MGR heap. It is stored
+* immediatly following the SHEAP_MGR instances. Operator new and operator
+* delete allocate/deallocate the SHEAP_MGR heap. The heap is used
+* to contain a BLK_DESC containing the TYPE_ENTRY array and a BLK_MGR
+* containing the hash table.
+*
+* STL_TYPEINFO:
+* The GenericTypeLibOLE implementation and its derivatives can not store any
+* implementation of the TYPEINFO protocol; they can only store TYPEINFO
+* implementations that derive from STL_TYPEINFO. STL_TYPEINFO is an
+* class which provides a partial implementation of the TYPEINFO protocol
+* and adds additional functions to support storing them in a GenericTypeLibOLE.
+* The STL_TYPEINFO and GenericTypeLibOLE implementations coordinate loading,
+* unloading, adding and removing the TypeInfo instance to/from the TypeLib.
+*
+* SUPPORT FOR UNLOADING GenericTypeLibOLEs AND CONTAINED STL_TYPEINFOs:
+* There are two types of references to the TYPEINFOs in a GenericTypeLibOLE.
+* An internal reference is a reference to a Type from another Type within
+* the TypeLib. An external reference is a reference from outside
+* the TypeLib. An external reference to a Type in a TypeLib is sufficient
+* to keep that Type and its containing TypeLib loaded. An internal
+* reference is sufficent to keep a Type loaded as long as there is one
+* Type in the containing TypeLib which has an external reference.
+* Once there are no external references to any Type in the TypeLib,
+* then the TypeLib and all containing Types are unloaded.
+* To implement this a STL_TYPEINFO has two counters: one for internal
+* and one for external references. Each external reference to a TypeInfo
+* is counted as an external reference to a TypeLib. Thus the reference
+* count of a TypeLib is equal to the sum of the external reference counts
+* of its contained Types plus the number of direct references to the
+* TypeLib from client code. The internal reference count is maintained
+* via the AddInternalRef and RelInternalRef methods.
+*
+* The reference from a TypeLib to one of its contained TypeInfos is not
+* reference counted at all. When an internal or external reference to
+* a STL_TYPEINFO is removed (by calling Release or RelInternalRef
+* respectively), if there are no more internal or external references
+* then the TypeInfo is deleted and the containing GenericTypeLibOLE
+* is notified that the TypeInfo has been deleted.
+*
+*Revision History:
+*
+* 25-Apr-91 alanc: Created.
+* 17-Sep-92 rajivk: added functions for editing modules. Edit & Continue
+* 15-Nov-92 rajivk: Support for Project Version Number
+* 15-Nov-92 rajivk: Added CanProjChange Support
+* 15-Nov-92 rajivk: Cyclic refrence of project not allowed
+* 04-Apr-93 RajivK: Support for Typelib on MAC
+*
+*****************************************************************************/
+
+#include "typelib.hxx"
+#include "silver.hxx"
+#include <new.h>
+#include <time.h>
+#include <stdlib.h>
+
+#include "gtlibole.hxx"
+#include "stltinfo.hxx"
+#include "gdtinfo.hxx"
+#include "clutil.hxx"
+#include "dfntcomp.hxx"
+#include "dfstream.hxx"
+#include "oletmgr.hxx"
+
+#pragma hdrstop(RTPCHNAME)
+
+
+#if OE_MACPPC
+// UNDONE: M68K: Make ifdef OE_MAC when using unified headers
+#include <macos\lowmem.h>
+#endif // OE_MACPPC
+
+#include <sys\types.h>
+#include <sys\stat.h>
+#if OE_MACPPC
+// UNDONE: M68K: Make ifdef OE_MAC when using unified headers
+#include <macos\lowmem.h>
+#endif // OE_MACPPC
+
+#if OE_WIN
+// WIN16 exe header format
+#include "newexe.h"
+#endif //OE_WIN
+#if OE_WIN16
+// WIN32 exe header format
+// Note: on Win32 the exe header definitions come from winnt.h
+typedef unsigned char UCHAR;
+typedef UCHAR FAR* PUCHAR;
+typedef USHORT FAR* PUSHORT;
+typedef ULONG FAR* PULONG;
+typedef VOID FAR* PVOID;
+typedef BOOL BOOLEAN;
+#include "ntimage.h"
+#endif //OE_WIN16
+
+#if OE_MAC
+#include "macos\errors.h"
+#define _llseek _lseek
+#define _lread _read
+#define _lclose _close
+#endif
+
+#if OE_MAC
+//defined in wlm\winuser.h, but including that gives lots of errors
+#define CF_PRIVATEFIRST 0x0200
+#endif //!EI_OB && OE_MAC
+
+#if OE_WIN32
+#include "ntstring.h"
+#endif
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+static char szgtliboleCxx[] = __FILE__;
+#define SZ_FILE_NAME szgtliboleCxx
+#endif
+
+extern "C" GUID CLSID_PSDispatch;
+extern "C" GUID CLSID_PSAutomation;
+
+// Define static class constants
+CONSTDATA WORD GenericTypeLibOLE::wFirstSerWord = 'G' * 256 + 'T' * 32 + 'L';
+
+
+// Serialization format version number
+// WARNING: this is FIXED for typelib V2 -- do not change or you will break
+// WARNING: V2 typelib.dll compatiblity
+CONSTDATA WORD GenericTypeLibOLE::wDefaultVersion = 03; // DO NOT CHANGE
+CONSTDATA WORD GenericTypeLibOLE::wDualVersion = 04; // DO NOT CHANGE
+CONSTDATA WORD GenericTypeLibOLE::wMaxVersion = 04; // DO NOT CHANGE
+
+CONSTDATA XCHAR GenericTypeLibOLE::chMinorVerNumSep = '/';
+CONSTDATA OLECHAR GenericTypeLibOLE::chLibIdSep = WIDE('*');
+CONSTDATA LPOLESTR GenericTypeLibOLE::szDirStreamName = WIDE("dir");
+CONSTDATA UINT GenericTypeLibOLE::oGptbind =
+ offsetof(GenericTypeLibOLE, m_gptbind);
+
+
+/***
+* BOOL FFullyQualified() - Is path fully-qualifed or not
+*
+* Purpose:
+* This function give a conservative guess as to whether the a path is
+* fully-qualifed or not. For the mac, this if if the name begins with
+* a colon. For Windows, this is if this is a UNC pathname, or if the
+* name is of the form <driveletter>:\<path>, we assume it's fully-qualifed
+* (may not be if the <path> contains "." or ".." in it)
+*
+* Inputs:
+* szFile - The pathname to check
+*
+* Outputs:
+* TRUE if fully-qualifed, FALSE if not
+*
+* Implementation:
+*
+*****************************************************************************/
+#pragma code_seg(CS_INIT)
+static BOOL FFullyQualified(LPCOLESTR szFile)
+{
+#if OE_MAC
+ // on mac, it's fully-qualified if it does not starts with a ':' and
+ // if it is not a file name(i.e there is a ":" in the path).
+ return ((*szFile != ':') && (xstrchr(xstrinc(szFile), ':')));
+#else //OE_MAC
+ LPOLESTR pch;
+
+ DebAssert(*szFile, "we assume at least 2 bytes in pathname");
+ pch = ostrinc((LPOLESTR)szFile); // get 2nd char
+ if ((*szFile == '\\' && *pch == '\\') || // UNC pathname
+ (*pch == ':' && *ostrinc(pch) == '\\') // path of the form: x:\y
+ ) {
+ return TRUE; // assume fully-qualifed
+ }
+ return FALSE; // not fully-qualifed
+#endif //OE_MAC
+}
+#pragma code_seg()
+
+
+/***
+* TIPERROR GetRegisteredPath - Gets a path from the registry.
+*
+* Purpose:
+* In win16/32, this is merely a wrapper on RegQueryValue with existence
+* checking thrown in. On the Mac, this first tries the specified
+* RegQueryValue and, if the retrieved path doesn't exist, looks in the
+* Alias subkey to get an alias record and uses that alias record to
+* find the path.
+*
+* Inputs:
+* Same as RegQueryValue, where hkey is the parent key, szSubkey is the
+* name of the subkey whose value holds the path and which itself may
+* have an "Alias" subkey.
+* fMustExist == TRUE if we're to check to see that the path/file exists.
+* Otherwise, we just return what's in the registry without
+* checking if it exists, is fully-qualified, etc.
+*
+* Outputs:
+* Same as RegQueryValue, except the error code returned is a TIPERROR.
+*
+*************************************************************************/
+#pragma code_seg( CS_QUERY )
+TIPERROR GetRegisteredPath(HKEY hkey,
+ LPOLESTR szSubkey,
+ LPOLESTR szPath,
+ LONG *pcbPath,
+ BOOL fMustExist)
+{
+ struct _stat statBuf;
+
+ if (oRegQueryValue(hkey, szSubkey, szPath, pcbPath) != ERROR_SUCCESS)
+ return TIPERR_RegistryAccess;
+
+ // Verify that the path is valid and return if it is.
+ if (fMustExist == FALSE || ostat(szPath, &statBuf) != -1)
+ return TIPERR_None;
+
+#if OE_MAC
+ if (*szPath != '\0') { // code below can't handle a null path string
+ // system7 always has an alias manager
+ AliasHandle halias;
+ long cbAlias;
+ HKEY hkeyPath;
+ TIPERROR err;
+ BOOL wasChanged;
+
+ if (RegOpenKey(hkey, szSubkey, &hkeyPath) != ERROR_SUCCESS)
+ return TIPERR_RegistryAccess;
+
+ // Determine the size of the registered alias.
+ if (RegQueryValueEx(hkeyPath, "Alias", NULL, NULL, NULL, &cbAlias) != ERROR_SUCCESS) {
+ err = TIPERR_PathNotFound;
+ goto Error;
+ }
+ DebAssert(cbAlias >= sizeof(AliasRecord), "GetRegisteredPath");
+
+ // Allocate memory for the alias record. NewHandle must be
+ // used for this because ResolveAlias may try to resize the
+ // alias record assuming it was allocated by NewHandle.
+ halias = (AliasHandle)NewHandle(cbAlias);
+ if (halias == NULL) {
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+
+ HLock((Handle)halias);
+ if (RegQueryValueEx(hkeyPath, "Alias", NULL, NULL, (unsigned char *)*halias, &cbAlias) != ERROR_SUCCESS) {
+ HUnlock((Handle)halias);
+ err = TIPERR_PathNotFound;
+ goto Error2;
+ }
+ HUnlock((Handle)halias);
+
+ // Convert the alias record to a path.
+ IfErrGo(GetPathFromAlias(halias, szPath, (UINT)*pcbPath, &wasChanged));
+
+ // If the alias record was updated during the resolution, write
+ // it back out to the registry. Ignore the error if this fails.
+ if (wasChanged) {
+ HLock((Handle)halias);
+ (void)RegSetValueEx(hkeyPath, "Alias", 0L, REG_BINARY, (char *)*halias, (*halias)->aliasSize);
+ HUnlock((Handle)halias);
+ }
+
+ // Now update the registered path, ignoring any errors.
+ (void)RegSetValue(hkeyPath, NULL, REG_SZ, szPath, *pcbPath);
+
+Error2:
+ // Release the alias record, now that we're done with it.
+ DisposeHandle((Handle)halias);
+
+Error:
+ RegCloseKey(hkeyPath);
+ return err;
+ }
+#endif // OE_MAC
+
+ return TIPERR_PathNotFound;
+}
+#pragma code_seg( )
+
+
+#pragma code_seg(CS_CREATE)
+/***
+* STDAPI CreateTypeLib() - Creates a new typelib.
+*
+* Purpose:
+* This function creates a new instance of GenericTypeLibOLE.
+* The storage object to which this typelib is saved can only be set via
+* GenericTypeLibOLE::SaveAllChanges.
+*
+* Inputs:
+* syskind - The target platform on which this typelib is expected
+* to be used.
+* szFile - The name of the file to which this typelib should be saved
+* when SaveAllChanges is called. This can be NULL if
+* SaveAllChanges will never be called.
+*
+* Outputs:
+* TIPERR_None is returned and *pptlib is set to the new typelib
+* if successful.
+*
+* Otherwise, *pptlib remains unchanged.
+*
+* Implementation:
+* This is implemented by simply creating a DOCFILE_BUNDLE and then
+* creating a new GenericTypeLibOLE with that bundle.
+* NOTE: since this can be the first call into typelib.dll
+* we must ensure that the APPDATA struct has been inited,
+* thus InitAppData().
+*
+*****************************************************************************/
+
+STDAPI
+CreateTypeLib(SYSKIND syskind, LPCOLESTR szFile, ICreateTypeLibA **ppctlib)
+{
+ TIPERROR err;
+ HRESULT hresult = NOERROR;
+ GenericTypeLibOLE *pgtlibole = NULL;
+
+#if !OE_WIN32
+ BOOL wasNoAppData;
+
+ // since this can be the first call into typelib.dll
+ TlsCleanupDeadTasks();
+
+ wasNoAppData = (Pappdata() == NULL);
+#endif // !OE_WIN32
+
+ // Initialize the per-client-app data structures, if they haven't
+ // already been allocated.
+ IfErrGo(InitAppData());
+
+ IfErrGoTo(GenericTypeLibOLE::Create(NULL, &pgtlibole), Error2);
+ IfErrGoTo(pgtlibole->SetLibId((LPOLESTR)szFile), Error2);
+ pgtlibole->m_syskind = syskind;
+ // The project is definitely modified (i.e. it hasn't been saved
+ // yet, so there unsaved changes), so mark it as such.
+ pgtlibole->m_fDirModified = TRUE;
+ pgtlibole->m_isModified = TRUE;
+
+ *ppctlib = pgtlibole;
+ return NOERROR;
+
+Error2:
+ if(pgtlibole != NULL)
+ pgtlibole->Release();
+
+#if !OE_WIN32
+ if (wasNoAppData)
+ ReleaseAppData();
+#endif // !OE_WIN32
+
+Error:
+
+ return HresultOfTiperr(err);
+}
+#pragma code_seg()
+
+/***
+* TIPERROR RegisterPathAndAlias - Registers a path (and alias on mac sys7).
+*
+* Purpose:
+* This is a helper routine used by RegisterTypeLib and
+* RegisterTypeLibFolder. It sets the value of hkeyPath to szPath
+* and, if we're on the mac system 7, creates a subkey called "Alias",
+* creates an alias record corresponding to the path, and sets the
+* value of the "Alias" subkey to the alias record.
+************************************************************************/
+#pragma code_seg(CS_INIT)
+static TIPERROR RegisterPathAndAlias(HKEY hkeyPath, LPOLESTR szPath)
+{
+ TIPERROR err = TIPERR_None;
+
+ if (oRegSetValue(hkeyPath, NULL, REG_SZ, szPath, ostrblen0(szPath)) != ERROR_SUCCESS)
+ return TIPERR_RegistryAccess;
+
+#if OE_MAC
+
+ {
+ // system7 always has an alias manager
+ AliasHandle halias;
+
+ // Convert the path to an alias record.
+ if(GetAliasFromPath(szPath, &halias) == TIPERR_None){
+
+ // Associate the alias record with the path key.
+ HLock((Handle)halias);
+ if (RegSetValueEx(hkeyPath, "Alias", 0L, REG_BINARY, (char *)*halias, (*halias)->aliasSize) != ERROR_SUCCESS) {
+ err = TIPERR_RegistryAccess;
+ }
+ HUnlock((Handle)halias);
+
+ // Release the alias record, now that it's in the registry.
+ DisposeHandle((Handle)halias);
+ }
+ }
+#endif // OE_MAC
+
+ return err;
+}
+
+#if OE_WIN
+/***
+*PUBLIC TIPERROR ErrOpenFile
+*Purpose:
+* Open the given file for reading. Returns a fully qualified filename
+* if successfully opened.
+*
+*Entry:
+* szFile = the file to open.
+*
+*Exit:
+* return value = TIPERROR
+*
+* *phfile = handle of the opened file
+* *plpstrPath = fully qualified path of the opened file
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR ErrOpenFile(LPOLESTR szFile, int *phfile, LPOLESTR *plpstrPath)
+{
+ int hfile;
+ OFSTRUCT of;
+ TIPERROR err;
+
+ if((hfile = oOpenFile(szFile, &of, OF_READ)) == HFILE_ERROR)
+ return TiperrOfOFErr(of.nErrCode);
+
+ if(plpstrPath != NULL)
+ {
+#if OE_WIN32
+ // On Win32, of.szPathName is an Ansi string (not Unicode or OEM code page)
+ int cchUnicode = MultiByteToWideChar(CP_ACP, 0, of.szPathName, -1, NULL, 0);
+
+ if (cchUnicode == 0)
+ IfErrGo(TIPERR_OutOfMemory);
+
+ if((*plpstrPath = (LPOLESTR)MemAlloc(cchUnicode*sizeof(OLECHAR))) == NULL){
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+ MultiByteToWideChar(CP_ACP, 0, of.szPathName, -1, *plpstrPath, cchUnicode);
+#else
+ if((*plpstrPath = (LPSTR)MemAlloc(strlen(of.szPathName)+1)) == NULL){
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+ // Convert fully qualified path back to Ansi char set (its OEM now)
+ OemToAnsi(of.szPathName, *plpstrPath);
+#endif
+ }
+
+ *phfile = hfile;
+ return TIPERR_None;
+
+Error:;
+ _lclose(hfile);
+ return err;
+}
+#endif // }
+
+
+/***
+*PRIVATE TIPERROR ErrOpen
+*Purpose:
+* Open the given file for reading. This is a helper for LoadTypeLib.
+*
+*Entry:
+* szFile = the file to open
+*
+*Exit:
+* return value = HRESULT
+*
+* *phfile = the handle of the newly opened file.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR ErrOpen(LPOLESTR szFileW, int *phfile)
+{
+ int hfile;
+
+#if OE_MAC
+ if((hfile = _sopen(szFileW,
+ (_O_BINARY|_O_RDONLY),
+ _SH_DENYNO,
+ (_S_IWRITE | _S_IREAD))) == -1)
+ {
+ // "too many files" on sopen sets errno, but not _macerrno
+ if (_macerrno == 0 && errno == EMFILE)
+ _macerrno = tmfoErr;
+ return TiperrOfOSErr((OSErr)_macerrno);
+ }
+#else // OE_MAC
+ OFSTRUCT of;
+#if OE_WIN32
+ LPSTR szFile;
+ TIPERROR err;
+
+ IfErrRet(TiperrOfHresult(ConvertStringToA(szFileW, &szFile)));
+#else //OE_WIN32
+ #define szFile szFileW
+#endif //OE_WIN32
+
+ if((hfile = _lopen(szFile, OF_READ)) == HFILE_ERROR){
+ // try again with OpenFile so we can get the extended-error info
+ if((hfile = OpenFile(szFile, &of, OF_READ)) == HFILE_ERROR) {
+#if OE_WIN32
+ ConvertStringFree(szFile);
+#endif //OE_WIN32
+ return TiperrOfOFErr(of.nErrCode);
+ }
+ }
+#if OE_WIN32
+ ConvertStringFree(szFile);
+#endif //OE_WIN32
+#endif // OE_MAC
+
+ *phfile = hfile;
+ return TIPERR_None;
+}
+
+// The following inline gives some bogus error on win16 (debug build),
+// so disable for now...
+//
+//inline
+HRESULT HrSeek(int hfile, long lOffset, int nOrigin)
+{
+ return _llseek(hfile, lOffset, nOrigin) == -1
+ ? HresultOfScode(TYPE_E_IOERROR) : NOERROR;
+}
+
+//inline
+HRESULT HrRead(int hfile, void HUGEP* pv, UINT cb)
+{
+ return _lread(hfile, pv, cb) == HFILE_ERROR
+ ? HresultOfScode(TYPE_E_IOERROR) : NOERROR;
+}
+
+//inline
+HRESULT HrCurPos(int hfile, ULONG *poCur)
+{
+ return (*poCur = _llseek(hfile, 0, SEEK_CUR)) == -1
+ ? HresultOfScode(TYPE_E_IOERROR) : NOERROR;
+}
+
+#if OE_WIN16
+// simple implementations of Unicode string routines
+UINT wcslen(USHORT FAR* lpwstr)
+{
+ UINT i;
+ for (i = 0; *lpwstr++; i++)
+ ;
+ return i;
+}
+
+// lame implementation of Unicode wcsicmp -- only checks for equality.
+// DO NOT use this for greater than/less than checks.
+UINT wcsicmp(USHORT FAR* lpwstr1, USHORT FAR* lpwstr2)
+{
+ USHORT ch1, ch2;
+
+ while (1) {
+ ch1 = *lpwstr1++;
+ ch2 = *lpwstr2++;
+ if (ch1 == 0 || ch2 == 0)
+ break;
+ if (tolower(LOBYTE(ch1)) != tolower(LOBYTE(ch2)))
+ return -1; // not equal
+ }
+ return ch1 || ch2;
+}
+#endif //OE_WIN16
+
+#if OE_WIN
+//
+// Find the directory entry in the given resource directory with
+// either the given name, or (if the name is NULL) the given ID.
+//
+#pragma code_seg(CS_INIT)
+HRESULT GetRsrcDirEntry(int hfile,
+ DWORD oRsrcDir,
+ WCHAR *pwchName,
+ DWORD dwId,
+ _IMAGE_RESOURCE_DIRECTORY_ENTRY *prsrcdirentry)
+{
+ UINT i;
+ HRESULT hresult, hresult2;
+ ULONG oCur, oString, oSave;
+ WORD wEntryNameLen, wNameLen;
+ _IMAGE_RESOURCE_DIRECTORY rsrcdir;
+
+ // Note: I dont support resource names >128 characters..
+ // if you really need this, then you'll need to modify this routine
+ WCHAR rgwchEntryName[128];
+ rgwchEntryName[0] = 0;
+
+ // save the current file offset
+ IfFailRet(HrCurPos(hfile, &oSave));
+
+ IfFailGo(HrSeek(hfile, oRsrcDir, SEEK_SET));
+ IfFailGo(HrRead(hfile, &rsrcdir, sizeof(rsrcdir)));
+
+ // If the given name is a wildcard, then just grab the first entry.
+ //
+ if(pwchName != NULL){
+ // Note: lstrlenW is not available on chicago, so use the C runtime
+ // routine, which is good enough for our purposes
+ wNameLen = wcslen(pwchName);
+ if(wNameLen == 1 && *pwchName == L'*'){
+ // make sure there is at least one entry
+ if(rsrcdir.NumberOfNamedEntries > 0 || rsrcdir.NumberOfIdEntries > 0){
+ IfFailGo(HrRead(hfile, prsrcdirentry, sizeof(*prsrcdirentry)));
+ goto Done;
+ }
+ }
+ }
+
+ if(pwchName == NULL){
+
+ //
+ // lookup the entry by ID
+ //
+
+ // skip the named entries
+ IfFailGo(HrSeek(hfile, rsrcdir.NumberOfNamedEntries * sizeof(_IMAGE_RESOURCE_DIRECTORY_ENTRY), SEEK_CUR));
+
+ for(i=0;; ++i){
+ if(i == rsrcdir.NumberOfIdEntries){
+ hresult = HresultOfScode(TYPE_E_CANTLOADLIBRARY);
+ goto Error; // didnt find it
+ }
+ IfFailGo(HrRead(hfile, prsrcdirentry, sizeof(*prsrcdirentry)));
+ if(prsrcdirentry->Name & IMAGE_RESOURCE_NAME_IS_STRING){
+ // Were supposed to be in the ID section of the directory,
+ // if this bit is set, then the image is toast...
+ DebAssert(0, "");
+ hresult = HresultOfScode(TYPE_E_CANTLOADLIBRARY);
+ goto Error;
+ }
+ if(prsrcdirentry->Name == dwId){
+ break; // Got It!
+ }
+ }
+ }else{
+
+ //
+ // lookup the entry by Name
+ //
+
+ if(wNameLen >= DIM(rgwchEntryName)){
+ // see note above wrt limitation on length of name
+ hresult = HresultOfScode(E_INVALIDARG);
+ goto Error;
+ }
+
+ for(i = 0;; ++i){
+ if(i == rsrcdir.NumberOfNamedEntries){
+ hresult = HresultOfScode(TYPE_E_CANTLOADLIBRARY);
+ goto Error;
+ }
+ IfFailGo(HrRead(hfile, prsrcdirentry, sizeof(*prsrcdirentry)));
+ if((prsrcdirentry->Name & IMAGE_RESOURCE_NAME_IS_STRING) == 0){
+ // We are searching the named portion of the table,
+ // If this bit isn't set, then the image must be toast...
+ DebAssert(0/*UNREACHED*/, "");
+ // but we may have a bogus image, so bag out..
+ hresult = HresultOfScode(TYPE_E_CANTLOADLIBRARY);
+ goto Error;
+ }
+ IfFailGo(HrCurPos(hfile, &oCur)); // save the current position
+ oString = (prsrcdirentry->Name & ~IMAGE_RESOURCE_NAME_IS_STRING) + oRsrcDir;
+ IfFailGo(HrSeek(hfile, oString, SEEK_SET));
+ IfFailGo(HrRead(hfile, &wEntryNameLen, sizeof(wEntryNameLen)));
+ if(wEntryNameLen == wNameLen){
+ IfFailGo(HrRead(hfile, rgwchEntryName, wEntryNameLen * sizeof(WCHAR)));
+ rgwchEntryName[wEntryNameLen] = L'\0';
+ }
+ IfFailGo(HrSeek(hfile, oCur, SEEK_SET)); // back to where we were
+ // Note: lstrcmpiW is not available on chicago, so use the C runtime
+ // routine, which is good enough for our purposes
+ if(wcsicmp(rgwchEntryName, pwchName) == 0) {
+ break; // Found the type entry!
+ }
+ }
+ }
+
+Done:;
+
+ hresult = NOERROR;
+
+Error:;
+ hresult2 = HrSeek(hfile, oSave, SEEK_SET);
+ return hresult == NOERROR ? hresult2 : hresult;
+}
+
+
+/***
+*HRESULT GetOffsetOfResource
+*Purpose:
+* Locate the typelib resource withing the given executable,
+* and return its offset.
+*
+*Entry:
+* hfile = the file handle of the executable.
+* pexehdr = ptr to the exe file header.
+*
+*Exit:
+* return value = HRESULT
+*
+* *poResource = typelib resource offset
+*
+*Note:
+* This is a helper for LoadTypeLib
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+HRESULT GetOffsetOfResource(int hfile,
+ CHAR *pchName,
+ int resID,
+ _IMAGE_DOS_HEADER *pexehdr,
+ long *poResource,
+ long *pcbResource)
+{
+#define CCH_MAX 128 // maximum resource name size.
+ HRESULT hresult;
+ DWORD dwSignature;
+
+ DebAssert(strlen(pchName) < CCH_MAX, "Name too long.");
+
+ // Seek to the beginning of the PE header
+ IfFailGo(HrSeek(hfile, pexehdr->e_lfanew, SEEK_SET));
+
+ // read and verify the NT PE signature
+ // for win16 exe's, this is the combination of ne_magic, ne_ver, & ne_rev.
+ IfFailGo(HrRead(hfile, &dwSignature, sizeof(dwSignature)));
+
+ if (dwSignature == IMAGE_NT_SIGNATURE) {
+//
+// For a description of the Win32 PE File format, including a description
+// of the format of the .rsrc (resource) section, take a look at:
+//
+// MSDN#7 - "The Portable Executable File Format From Top To Bottom"
+//
+
+ int i;
+ WORD w;
+ BOOL fIsDir;
+ ULONG oRsrc;
+ ULONG oRsrcDir;
+ WCHAR rs_string[CCH_MAX + 1];
+
+ _IMAGE_FILE_HEADER pehdr;
+ _IMAGE_SECTION_HEADER secthdr;
+ _IMAGE_RESOURCE_DATA_ENTRY rsrcdataentry;
+ _IMAGE_RESOURCE_DIRECTORY_ENTRY rsrcdirentry;
+
+// the following describes the resource directory path we're trying to find
+static struct rsrcpath {
+ WCHAR *pwchName;
+ DWORD dwId;
+} rgrsrcpath[] = {
+ { NULL, 0 } // type
+ , { NULL, 1 } // name
+ , { L"*", 0 } // language (we currently ignore this)
+};
+
+ // Convert the inputted ANSI string to a wide-character string.
+#if OE_WIN16
+ mbstowcs(rs_string, pchName, 128);
+#else // !OE_WIN16
+ MultiByteToWideChar(CP_ACP, 0, pchName,
+ xstrclen(pchName)+1, rs_string, 128);
+#endif // !OE_WIN16
+
+ // REVIEW: hack-o-rama
+ rgrsrcpath[0].pwchName = rs_string;
+ rgrsrcpath[1].dwId = resID;
+
+ // Read the PE header
+ IfFailGo(HrRead(hfile, &pehdr, sizeof(pehdr)));
+
+ // Skip over the "optional" header.
+ IfFailGo(HrSeek(hfile, pehdr.SizeOfOptionalHeader, SEEK_CUR));
+
+ // Search the section headers for .rsrc...
+ for(w = 0;; ++w){
+ if(w == pehdr.NumberOfSections){
+ // didnt find the .rsrc section
+ hresult = HresultOfScode(TYPE_E_CANTLOADLIBRARY);
+ goto Error;
+ }
+ IfFailGo(HrRead(hfile, &secthdr, sizeof(secthdr)));
+#if OE_WIN16
+ #define lstrcmpiA lstrcmpi
+#endif //OE_WIN16
+ if(lstrcmpiA((const char*)&secthdr.Name, ".rsrc") == 0)
+ break;
+ }
+
+ // start at the root of the resource section
+ oRsrcDir = oRsrc = secthdr.PointerToRawData;
+
+ // the following code expects the resource path to be non-empty
+ DebAssert(DIM(rgrsrcpath) > 0, "");
+
+ for(i = 0;; ++i){
+
+ IfFailGo(GetRsrcDirEntry(hfile,
+ oRsrcDir,
+ rgrsrcpath[i].pwchName,
+ rgrsrcpath[i].dwId,
+ &rsrcdirentry));
+
+ fIsDir = (rsrcdirentry.OffsetToData & IMAGE_RESOURCE_DATA_IS_DIRECTORY) != 0;
+ // compute the file offset of the location pointed at by this entry
+ oRsrcDir = oRsrc + (rsrcdirentry.OffsetToData & ~IMAGE_RESOURCE_DATA_IS_DIRECTORY);
+
+ if(i == DIM(rgrsrcpath)-1){
+ // were at the end of the path - so we expect a leaf
+ if(fIsDir){
+ // image must be toast...
+ hresult = HresultOfScode(TYPE_E_CANTLOADLIBRARY);
+ goto Error;
+ }
+
+ // We have found the location of the data node.. seek to it,
+ // extract the virtual address of the resource, and convert
+ // this into an absolute file offset.
+ //
+ // Note: all the offsets in the resource directory tree are
+ // relative to the beginning of .rsrc, *except* for the final
+ // offset to the resource, which is virtual.
+ //
+ IfFailGo(HrSeek(hfile, oRsrcDir, SEEK_SET));
+ IfFailGo(HrRead(hfile, &rsrcdataentry, sizeof(rsrcdataentry)));
+ *poResource = (rsrcdataentry.OffsetToData - secthdr.VirtualAddress) + oRsrc;
+ *pcbResource = rsrcdataentry.Size;
+ break;
+ }
+
+ // were not at the end of the path, so this should be a subdir
+ if(!fIsDir){
+ // image must be toast...
+ hresult = HresultOfScode(TYPE_E_CANTLOADLIBRARY);
+ goto Error;
+ }
+ }
+
+ // successfully handled WIN32 EXE
+ return NOERROR;
+
+ // now check for win16 EXE format.
+ // LOWORD(dwSignature) is the ne_magic field of the WIN16 header if this
+ // is really a win16 EXE..
+ } else if(LOWORD(dwSignature) == IMAGE_OS2_SIGNATURE) {
+
+ WORD i;
+ char rs_len, cbName = xstrblen(pchName);
+ char rs_string[CCH_MAX+1];
+ USHORT usRsrcAlign;
+ IMAGE_OS2_HEADER newexe;
+ struct rsrc_nameinfo nameinfo;
+ struct rsrc_typeinfo typeinfo;
+ ULONG oCur, oString, oRsrcTable;
+
+ //
+ // Read and verify the remainder of the new-exe header.
+ //
+ IfFailGo(HrRead(hfile, (char far *)&newexe+sizeof(dwSignature), sizeof(newexe) - sizeof(dwSignature)));
+
+ //
+ // Compute the absolute offset in the file of the resource table.
+ //
+ // exe_ndr.e_lfanew = offset of new exehdr
+ // new_exe.ne_rsrctab = offset of resource table, relative to the
+ // beginning of the new-exe hdr.
+ // new_exe.cres = number of resource segments
+
+ if (newexe.ne_rsrctab != newexe.ne_restab) {
+ // if there are any resources in this EXE/DLL
+ // (yes, this check assumes that all linkers put the resident names table
+ // immediately after the resource table, but Windows' loader makes this
+ // assumption, too.
+
+ oRsrcTable = pexehdr->e_lfanew + newexe.ne_rsrctab;
+ IfFailGo(HrSeek(hfile, oRsrcTable, SEEK_SET));
+ IfFailGo(HrRead(hfile, &usRsrcAlign, sizeof(usRsrcAlign)));
+
+ //
+ // Search the resource table entries for the resource
+ // of type "typelib", with an ID of 1.
+ //
+
+ while(1){
+
+ // read the resource type-id
+ IfFailGo(HrRead(hfile, &typeinfo.rt_id, sizeof(typeinfo.rt_id)));
+
+ if(typeinfo.rt_id == 0) // end of table marker.. nothing else to look at
+ break;
+
+ // read the count of resources of this type
+ IfFailGo(HrRead(hfile, &typeinfo.rt_nres, sizeof(typeinfo.rt_nres)));
+ // some other thing that isnt used (but read to keep us in sync)
+ IfFailGo(HrRead(hfile, &typeinfo.rt_proc, sizeof(typeinfo.rt_proc)));
+
+ // If the entry is for resources of type "typelib", then scan
+ // the actual resources for one with an ID of 1.
+ //
+ if((typeinfo.rt_id & RSORDID) == 0){
+
+ // save the current position...
+ IfFailGo(HrCurPos(hfile, &oCur));
+
+ // Seek to the string table, and grab the type name.
+ oString = oRsrcTable + typeinfo.rt_id;
+ IfFailGo(HrSeek(hfile, oString, SEEK_SET));
+ IfFailGo(HrRead(hfile, &rs_len, sizeof(rs_len)));
+ // If the string length looks right, then go ahead and grab the string
+ if(rs_len == cbName){
+ IfFailGo(HrRead(hfile, &rs_string, cbName));
+ rs_string[cbName] = '\0';
+ }
+ // seek back to current position
+ IfFailGo(HrSeek(hfile, oCur, SEEK_SET));
+
+ if(rs_len == cbName && lstrcmpi(rs_string, pchName)==0){
+
+ // we have found the set of resources of type "typelib",
+ // The guy we are looking for is either here, or nowhere
+
+ for(i = 0; i < typeinfo.rt_nres; ++i){
+ IfFailGo(HrRead(hfile, &nameinfo, sizeof(nameinfo)));
+ if(nameinfo.rn_id == (RSORDID | resID)){
+ // Found it!
+ // Compute and return the offset of the actual resource.
+ *poResource = ((ULONG)nameinfo.rn_offset) << usRsrcAlign;
+ *pcbResource = ((ULONG)nameinfo.rn_length) << usRsrcAlign;
+ return NOERROR;
+ }
+ }
+ // If its not in the "typelib" directory, then its not in the exe
+ hresult = HresultOfScode(TYPE_E_CANTLOADLIBRARY);
+ goto Error;
+ }
+ }
+ // This is not the resource type we are looking for, so skip
+ // over the nameinfo records for all resources of this type
+ IfFailGo(HrSeek(hfile, typeinfo.rt_nres * sizeof(nameinfo), SEEK_CUR));
+ }
+ }
+
+ } // not WIN32 PE header not WIN16 EXE header, or some error
+
+ // no typelibs in the .EXE
+ hresult = HresultOfScode(TYPE_E_CANTLOADLIBRARY);
+
+Error:;
+ return hresult;
+}
+
+/***
+*HRESULT GetOffsetOfTypeLibResource
+*Purpose:
+* Locate the typelib resource withing the given executable,
+* and return its offset.
+*
+*Entry:
+* hfile = the file handle of the executable.
+* pexehdr = ptr to the exe file header.
+*
+*Exit:
+* return value = HRESULT
+*
+* *poResource = typelib resource offset
+*
+*Note:
+* This is a helper for LoadTypeLib
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+HRESULT GetOffsetOfTypeLibResource(int hfile,
+ int resID,
+ _IMAGE_DOS_HEADER *pexehdr,
+ long *poResource,
+ long *pcbResource)
+{
+ return GetOffsetOfResource(hfile,
+ "typelib",
+ resID,
+ pexehdr,
+ poResource,
+ pcbResource);
+}
+#endif //OE_WIN
+
+
+struct LoadInfo
+{
+ LPOLESTR lpstrPath;// fully qualified path
+ int hfile;
+ BOOL fRegister; // does the typelib need to be registered?
+ BOOL fIsTypeLib;
+#if OE_WIN
+ BOOL fIsExe; // does the path name an exe or dll?
+ int resID; // the typelib resource ID to use
+ SYSKIND syskind; // the syskind of the exe/dll
+ _IMAGE_DOS_HEADER exehdr;
+#endif
+};
+
+#pragma code_seg(CS_INIT)
+void InitLoadInfo(LoadInfo *ploadinfo)
+{
+ ploadinfo->lpstrPath = NULL;
+ ploadinfo->hfile = -1;
+ ploadinfo->fRegister = FALSE;
+ ploadinfo->fIsTypeLib = FALSE;
+#if OE_WIN
+ ploadinfo->fIsExe = FALSE;
+ ploadinfo->resID = -1;
+ ploadinfo->syskind = SYSKIND_CURRENT;
+#endif //OE_WIN
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_INIT)
+void UninitLoadInfo(LoadInfo *ploadinfo)
+{
+#if OE_WIN
+ MemFree(ploadinfo->lpstrPath);
+#else
+ FreeBstr(ploadinfo->lpstrPath);
+#endif
+ ploadinfo->lpstrPath = NULL;
+ if(ploadinfo->hfile != -1)
+ _lclose(ploadinfo->hfile);
+ ploadinfo->hfile = -1;
+}
+#pragma code_seg()
+
+#if OE_WIN
+/***
+*TIPERROR NEARCODE VerifyIsExeOrTlb
+*Purpose:
+* Determine if the loadinfo is a .exe file or a standalone typelib.
+*
+*Entry:
+* ploadinfo = loadinfo with a valid hfile
+*
+*Exit:
+* TIPERR_FileNotFound - file is neither .exe nor .tlb
+* TIPERR_None - ploadinfo->fIsExe, ploadinfo->fIsTypeLib, ploadinfo->exehdr
+* updated
+*
+* File pointer is unchanged after the call
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR NEARCODE VerifyIsExeOrTlb(LoadInfo *ploadinfo)
+{
+ LONG oCur;
+ TIPERROR err = TIPERR_FileNotFound; // asume the worst
+
+ // save the current offset
+ if((oCur = _llseek(ploadinfo->hfile, 0, SEEK_CUR)) != -1){
+
+ // rewind the file if necessarry
+ if(oCur == 0 || _llseek(ploadinfo->hfile, 0, SEEK_SET) != -1){
+
+ if(_lread(ploadinfo->hfile, &ploadinfo->exehdr, sizeof(ploadinfo->exehdr)) != HFILE_ERROR){
+
+ if (ploadinfo->exehdr.e_magic == IMAGE_DOS_SIGNATURE) {
+
+ // the file is a .exe
+ if(ploadinfo->resID == -1)
+ ploadinfo->resID = 1; // default to resource ID 1, if non specified
+ ploadinfo->fIsExe = TRUE;
+ err = TIPERR_None; // indicate success
+
+ } else if ( ((GTLibStgHdr*)&(ploadinfo->exehdr))->ulSignature == GTLIBSTORAGE_SIGNATURE ) {
+
+ // the file is a typelib
+
+ // Make sure the caller didn't specify a resource ID. We
+ // definately don't know how to deal with this.
+ if(ploadinfo->resID == -1) {
+ ploadinfo->fIsTypeLib = TRUE;
+ err = TIPERR_None; // indicate success
+ }
+
+ } // else fall out with TIPERR_FileNotFound
+
+ }
+ // restore to original offset
+ _llseek(ploadinfo->hfile, oCur, SEEK_SET);
+
+ }
+
+ }
+ return err;
+}
+#pragma code_seg()
+#endif //OE_WIN
+
+// Attempt to split a resource id off the end of the given string
+//WARNING: If SplitResID returns TIPERR_None, the '\' between
+//WARNING: the file name and the resource ID has been replaced by
+//WARNING: a '\0' character. IN OTHER WORDS, szFile HAS BEEN
+//WARNING: MODIFIED! *(*pszResID+1)='\\' will repair szFile.
+#pragma code_seg(CS_INIT)
+TIPERROR SplitResID(LPOLESTR szFile, LPOLESTR *pszResID)
+{
+ int len;
+ LPOLESTR pch;
+ LPOLESTR pchEnd;
+
+ len = ostrlen(szFile);
+ DebAssert(len > 0, "");
+
+ pchEnd = &szFile[len-1];
+ for(pch = pchEnd; *pch >= '0' && *pch <= '9'; --pch)
+ {
+ if(pch == szFile)
+ return TIPERR_ElementNotFound; // didn't find it
+ }
+
+ if(pch == pchEnd || *pch != '\\')
+ return TIPERR_ElementNotFound;
+
+ // Split the resource ID off by replacing the preceeding '\' by a '\0'
+ *pch = '\0';
+ *pszResID = pch+1;
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+/***
+*PRIVATE TIPERROR FindTypeLibUnqual
+*Purpose:
+* Locate and classify the typelib based on the given unqualified
+* fielname.
+*
+*Entry:
+* szFile = the file to open
+*
+*Exit:
+* return value = TIPERROR
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR FindTypeLibUnqual(LPOLESTR szFile, LoadInfo *ploadinfo)
+{
+ int hfile;
+ TIPERROR err;
+
+ hfile = -1;
+
+#if OE_MAC
+
+ BSTRA lpstrPath = NULL;
+
+ // On the Mac, check for the file in the registered Typelib Folder
+ // if a typelib folder is registered.
+ IfErrGo(MacFileSearch(szFile, &lpstrPath));
+ IfErrGo(ErrOpen(lpstrPath, &hfile));
+
+#else // OE_MAC
+
+ UINT cbPath;
+ UINT cbResID;
+ LPOLESTR lpstrPath=NULL;
+ LPOLESTR lpstrTemp;
+ LPOLESTR pchResID;
+
+ err = ErrOpenFile(szFile, &hfile, &lpstrPath);
+
+ switch((ULONG)err){
+ case (ULONG)TIPERR_None:
+ break;
+ case (ULONG)TIPERR_FileNotFound:
+ case (ULONG)TIPERR_PathNotFound:
+ // Try to split a resource ID off the end of the name, and
+ // then open...
+ if(SplitResID(szFile, &pchResID) == TIPERR_None){
+ if(ErrOpenFile(szFile, &hfile, &lpstrPath) == TIPERR_None){
+ // Glue the fully qualified filename, and the resource ID
+ // back together into a fully qualified specifier
+ cbPath = ostrlen(lpstrPath);
+ cbResID = ostrlen(pchResID);
+ if((lpstrTemp = (LPOLESTR)MemAlloc((cbPath+1+cbResID+1)*sizeof(OLECHAR))) == NULL){
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+ memcpy(lpstrTemp, lpstrPath, cbPath*sizeof(OLECHAR));
+ lpstrTemp[cbPath] = '\\';
+ memcpy(&lpstrTemp[1+cbPath], pchResID, cbResID*sizeof(OLECHAR));
+ lpstrTemp[1+cbPath+cbResID] = (OLECHAR)0; // Null terminate
+ ploadinfo->resID = oatoi(pchResID);
+ MemFree(lpstrPath);
+ lpstrPath = lpstrTemp;
+ err = TIPERR_None;
+ }
+ // replace the '\' in szFile (hammered by SplitResID)
+ *(pchResID-1)='\\';
+ }
+ IfErrGo(err);
+ break;
+ default:
+ goto Error;
+ }
+#endif
+
+ DebAssert(hfile != -1, "");
+ ploadinfo->hfile = hfile;
+ hfile = -1;
+ ploadinfo->lpstrPath = lpstrPath;
+ err = TIPERR_None;
+
+Error:;
+#if OE_MAC
+ FreeBstr(lpstrPath);
+#endif
+ if(hfile != -1)
+ _lclose(hfile);
+ return err;
+}
+#pragma code_seg()
+
+/***
+*PRIVATE TIPERROR FindTypeLib
+*Purpose:
+* Locate and classify the typelib indicated by the given name.
+*
+*Entry:
+* szFile = the file to localte
+*
+*Exit:
+* return value = TIPERROR.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR FindTypeLib(LPOLESTR szFile, LoadInfo *ploadinfo)
+{
+ TIPERROR err;
+
+ DebAssert(szFile != NULL && szFile[0] != WIDE('\0'), "");
+
+ if(FFullyQualified(szFile))
+ {
+ err = ErrOpen(szFile, &ploadinfo->hfile);
+#if OE_WIN
+ if(err == TIPERR_FileNotFound
+ || err == TIPERR_PathNotFound){
+ LPOLESTR pchResID;
+ // Try to strip off a resource ID, and then open
+ if(SplitResID(szFile, &pchResID) == TIPERR_None) {
+ if((err = ErrOpen(szFile, &ploadinfo->hfile)) == TIPERR_None)
+ ploadinfo->resID = oatoi(pchResID);
+ // replace the '\' char in szFile (hammered by SplitResID)
+ *(pchResID-1)='\\';
+ }
+ }
+#endif //OE_WIN
+ IfErrGo(err);
+ if((ploadinfo->lpstrPath = (LPOLESTR)MemAlloc(ostrblen0(szFile)*sizeof(OLECHAR))) == NULL) {
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+ ostrcpy(ploadinfo->lpstrPath, szFile);
+ }
+ else
+ {
+ ploadinfo->fRegister = TRUE;
+ IfErrGo(FindTypeLibUnqual(szFile, ploadinfo));
+ }
+
+ // If we get here, then we must have opened something...
+ DebAssert(ploadinfo->hfile != -1, "");
+
+#if OE_WIN
+ IfErrGo(VerifyIsExeOrTlb(ploadinfo));
+#else //OE_MAC
+ ploadinfo->fIsTypeLib = TRUE;
+#endif //OE_WIN
+
+ return TIPERR_None;
+
+Error:;
+ UninitLoadInfo(ploadinfo);
+ return err;
+}
+#pragma code_seg()
+
+/***
+* STDAPI LoadTypeLib() - Loads an existing typelib
+*
+* Purpose:
+* This function creates a new instance of GenericTypeLibOLE.
+* The storage object to which this typelib is saved can only be set via
+* GenericTypeLibOLE::SaveAllChanges.
+*
+* Inputs:
+* szFile - The file containing the stand-alone GenericTypeLibOLE.
+*
+* Outputs:
+* TIPERR_None is returned and *pptlib is set to the new typelib
+* if successful.
+*
+* Otherwise, *pptlib remains unchanged.
+*
+* Implementation:
+* This is implemented by simply opening a docfile and then
+* loading a new GenericTypeLibOLE from that docfile.
+* NOTE: since this can be the first call into typelib.dll
+* we must ensure that the APPDATA struct has been inited,
+* thus InitAppData().
+*
+*****************************************************************************/
+
+#pragma code_seg(CS_INIT)
+STDAPI LoadTypeLib(LPCOLESTR szFile, ITypeLibA **pptlib)
+{
+ LONG offset;
+ TIPERROR err;
+ HRESULT hresult;
+ LoadInfo loadinfo;
+ ITypeLibA *ptlib;
+ IStorageA *pstg;
+ ILockBytesA *plockbytes;
+ GenericTypeLibOLE *pgtlibole;
+ LONG cbResource;
+
+#if !OE_WIN32
+ BOOL fWasNoAppData;
+
+ // since this can be the first call into typelib.dll
+ TlsCleanupDeadTasks();
+#endif //!OE_WIN32
+
+ if (szFile == NULL || pptlib == NULL)
+ return HresultOfScode(E_INVALIDARG);
+
+ pstg = NULL;
+ pgtlibole = NULL;
+ plockbytes = NULL;
+ InitLoadInfo(&loadinfo);
+
+#if !OE_WIN32
+ fWasNoAppData = (Pappdata() == NULL);
+#endif // !OE_WIN32
+
+ // Initialize the per-client-app data structures, if they haven't
+ // already been allocated.
+ IfErrGo(InitAppData());
+
+ // code can't deal well with an empty string, so check for it here.
+ if (*szFile == OLESTR('\0'))
+ IfErrGoTo(TIPERR_FileNotFound, TipError);
+
+ // if the pathname is fully-qualified and it is already cached, AddRef
+ // and return it without checking whether the image exists on disk or not.
+ // This saves time in the case that stdole.tlb is referenced using a
+ // fully-qualified path.
+ if(FFullyQualified(szFile) &&
+ (ptlib = Poletmgr()->LookupTypeLib((LPOLESTR)szFile)) != NULL) {
+ goto DoAddRefAndReturn;
+ }
+
+ if(FindTypeLib((LPOLESTR)szFile, &loadinfo) == TIPERR_None)
+ {
+ // If the specified typelib was already loaded, just AddRef and
+ // return it.
+ if((ptlib = Poletmgr()->LookupTypeLib(loadinfo.lpstrPath)) != NULL){
+ UninitLoadInfo(&loadinfo);
+DoAddRefAndReturn:
+ ptlib->AddRef();
+ *pptlib = ptlib;
+ return NOERROR;
+ }
+
+ offset = 0;
+ cbResource = 0;
+#if OE_WIN
+ if(loadinfo.fIsExe){
+ IfFailGo(GetOffsetOfTypeLibResource(loadinfo.hfile,
+ loadinfo.resID,
+ &loadinfo.exehdr,
+ &offset,
+ &cbResource));
+ }
+#endif //OE_WIN
+
+ // Create an IStorage for type typelib
+ IfFailGo(CreateFileLockBytesOnHFILE(loadinfo.hfile, FALSE, offset, cbResource, &plockbytes));
+ loadinfo.hfile = -1; // file is now owned by the lockbytes
+ IfFailGo(GTLibStorage::OpenForReadOnly(plockbytes, &pstg));
+ RELEASE(plockbytes); // lockbytes will be released when storage is
+
+ // Create the TypeLib
+ IfErrGoTo(GenericTypeLibOLE::Create(pstg, &pgtlibole), TipError);
+ RELEASE(pstg);
+ IfErrGoTo(pgtlibole->SetLibId(loadinfo.lpstrPath), TipError);
+ IfErrGoTo(pgtlibole->SetDirectory(loadinfo.lpstrPath), TipError);
+
+ // Load type TypeLib
+ IfErrGoTo(pgtlibole->Read(), TipError);
+
+ // Tell the type manager about the newly loaded typelib.
+ IfErrGo(Poletmgr()->TypeLibLoaded(loadinfo.lpstrPath, pgtlibole));
+
+ // But don't change the help file if it hasn't already been changed.
+ // Ignore any failure from RegisterTypeLib at this point.
+ if(loadinfo.fRegister)
+ hresult = RegisterTypeLib(pgtlibole, loadinfo.lpstrPath, NULL);
+ }
+ else
+ {
+ // Attempt to parse the given name into a moniker, and bind to it.
+ // This enables binding to non OLE typelib implementations, including
+ // implementations that have no corresponding persistent representation.
+
+ IBindCtx *pbc;
+ IMoniker *pmk;
+ ULONG chEaten;
+
+ hresult = CreateBindCtx(0, &pbc);
+ if(hresult == NOERROR){
+ BSTR bstr;
+ bstr = SysAllocString(szFile);
+ if (bstr == NULL)
+ hresult = HresultOfScode(E_OUTOFMEMORY);
+ else {
+ hresult = MkParseDisplayName(pbc, bstr, &chEaten, &pmk);
+ SysFreeString(bstr);
+ if(hresult == NOERROR){
+ hresult = pmk->BindToObject(pbc,
+ NULL,
+ IID_ITypeLib,
+ (void**)&pgtlibole);
+ pmk->Release();
+ }
+ }
+ pbc->Release();
+ }
+
+ // translate to a reasonable typelib error, if necessarry
+ if(hresult != NOERROR){
+ hresult = HresultOfScode(TYPE_E_CANTLOADLIBRARY);
+ goto Error;
+ }
+ }
+
+ UninitLoadInfo(&loadinfo);
+ *pptlib = pgtlibole;
+ return NOERROR;
+
+TipError:;
+ hresult = HresultOfTiperr(err);
+
+Error:
+ if(pgtlibole != NULL)
+ pgtlibole->Release();
+ if(pstg != NULL)
+ pstg->Release();
+ if(plockbytes != NULL)
+ plockbytes->Release();
+ UninitLoadInfo(&loadinfo);
+
+#if !OE_WIN32
+ if(fWasNoAppData && Pappdata() != NULL)
+ ReleaseAppData();
+#endif // !OE_WIN32
+
+ return hresult;
+}
+#pragma code_seg()
+
+/***
+* STDAPI RegisterTypeLib() - Registers a typelib with the registry
+*
+* Purpose:
+* RegisterTypeLib adds information to the registry for the
+* specified TypeLib. After the TypeLib is
+* registered then LoadRegTypeLib can be used to load the type library.
+*
+* Inputs:
+* ptlib - the typelib to register (IN)
+* szFullPath - Its complete path. (IN)
+* szHelpDir - Where to find help directory. (IN)
+* If this is NULL and there is already a HELPDIR, don't
+* change the HELPDIR string. If this is NULL and there
+* isn't a HELPDIR, then take the helpdir from szFullPath.
+*
+* Outputs:
+*
+* Implementation:
+* We register the following bits of info:
+* Guid
+* Docstring
+* Major.Minor version numbers
+* Lcid
+* Help directory
+* Platform
+*
+* The typelib subkey hierarchy looks like this:
+* \ [root]
+* TypeLib
+* {GUID}
+* Version [major.minor] = <docstring>
+* HELPDIR = <some-dir>
+* FLAGS = <typelib flags>
+* <LCID>
+* <PLATFORM> = <fullpath of typelib>
+*
+* The interface subkey hierarchy looks like this:
+* \ [root]
+* Interface
+* {<iid of interface>} = <typeinfo name>
+* ProxyStubClsid = {GUID of ProxyStubClsid}
+* NumMethods = 7
+* BaseInterface = { GUID of IDispatch }
+*
+* NOTE: since this can be the first call into typelib.dll
+* we must ensure that the APPDATA struct has been inited,
+* thus InitAppData().
+*
+******************************************************************************/
+
+/***
+*PRIVATE
+*Purpose:
+* Helper for RegisterTypeLib. Creates a subkey under the given
+* key, with the given name, and the given value.
+*
+*Entry:
+* hkey = the registry key under which to create the subkey.
+* szSubKey = the name of the subkey.
+* szValue = the value to assign to the sub key.
+* cbValue = the length of the value string
+*
+*Exit:
+* return value = TIPERROR.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR
+RegCreateSubKey(HKEY hkey, LPOLESTR szSubKey, LPOLESTR szValue, int cbValue)
+{
+ HKEY hkeySub;
+ TIPERROR err;
+
+ err = TIPERR_RegistryAccess; // pessimism...
+ if(oRegCreateKey(hkey, szSubKey, &hkeySub) == ERROR_SUCCESS){
+ if(oRegSetValue(hkeySub, NULL, REG_SZ, szValue, cbValue) == ERROR_SUCCESS){
+ err = TIPERR_None;
+ }
+ RegCloseKey(hkeySub);
+ }
+ return err;
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_INIT)
+STDAPI RegisterTypeLib(ITypeLibA *ptlib, LPOLESTR szFullPath, LPOLESTR szHelpDir)
+{
+ TIPERROR err = TIPERR_None;
+ TLIBATTR *ptlibattr;
+ LPOLESTR szSys;
+ HKEY hkeyTypelib, hkeyGuid, hkeyVersion, hkeyLcid, hkeyPlatform, hkeyHelpdir, hkeyFlags;
+ OLECHAR rgchVer[4+1+4+1]; // maj.min\0
+ OLECHAR rgchVerMinor[4+1]; // XXXX\0
+ OLECHAR rgchLcid[4+1]; // XXXX\0
+ OLECHAR rgchFlags[4+1]; // XXXX\0
+// OLECHAR rgchNumMethods[5+1]; // XXXXX\0
+ LPOLESTR pchEnd;
+ OLECHAR chSave;
+ BSTR bstrDocString;
+ OLECHAR szGuidTypeLib[CCH_SZGUID0];
+ OLECHAR szGuidTypeInfo[CCH_SZGUID0];
+// LPOLESTR szGuidBaseInterface;
+ LPOLESTR szGuidPS;
+ BSTR bstrName;
+ HKEY hkeyInterface;
+ HKEY hkeyGuidTypeinfo;
+ TYPEATTR *ptypeattr;
+ USHORT ustiCount;
+ ITypeInfoA *pitinfo;
+ TYPEKIND typekind;
+ UINT i;
+static OLECHAR szGuidIDispatch[] = WIDE("{00020400-0000-0000-C000-000000000046}");
+static OLECHAR szGuidPSDispatch[] = WIDE("{00020420-0000-0000-C000-000000000046}");
+static OLECHAR szGuidPSAutomation[] = WIDE("{00020424-0000-0000-C000-000000000046}");
+
+
+ if (ptlib == NULL || szFullPath == NULL) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+#if !OE_MAC
+ LPOLESTR lpstrUNC=NULL;
+ IfErrGo(ConvertPathToUNC(szFullPath, &lpstrUNC));
+
+ // If the file is on the net, then use the UNC name instead.
+ if (lpstrUNC != NULL)
+ szFullPath = lpstrUNC;
+#endif // !OE_MAC
+
+ // Get the typelib's guid and version number.
+ IfErrGo(TiperrOfHresult(ptlib->GetLibAttr(&ptlibattr)));
+
+ // Verify that the syskind of the typelib is compatible with the platform.
+ // Also, get the subkey string for the syskind.
+ // Do this validation FIRST so that we don't end up half-registering
+ // the typelib if we get an error here.
+ switch (ptlibattr->syskind) {
+#if OE_MAC
+ case SYS_MAC:
+ szSys = "mac";
+ break;
+#endif // OE_MAC
+
+#if OE_WIN32 || OE_WIN16
+ case SYS_WIN32:
+ szSys = WIDE("win32");
+ break;
+
+ case SYS_WIN16:
+ szSys = WIDE("win16");
+ break;
+#endif // OE_WIN16 || OE_WIN32
+
+ default:
+ err = TIPERR_LibNotRegistered;
+ goto Error2;
+ }
+
+ // Now create the typelibs subkey.
+ if (oRegCreateKey(HKEY_CLASSES_ROOT, WIDE("TypeLib"), &hkeyTypelib) != ERROR_SUCCESS) {
+ err = TIPERR_RegistryAccess;
+ goto Error2;
+ }
+
+ // Convert the guid into the registry string format.
+ StringFromGUID2(ptlibattr->guid, szGuidTypeLib, CCH_SZGUID0);
+
+ if (oRegCreateKey(hkeyTypelib, szGuidTypeLib, &hkeyGuid) != ERROR_SUCCESS) {
+ err = TIPERR_RegistryAccess;
+ goto Error4;
+ }
+
+ // Now create the major.minor version subkey under guid.
+ // Convert the major and minor vernums to hex strings...
+ //
+ oultoa(ptlibattr->wMajorVerNum, rgchVer, 16);
+ oultoa(ptlibattr->wMinorVerNum, rgchVerMinor, 16);
+
+ // Tack them together with a dividing ".".
+ pchEnd = ostrchr(rgchVer, '\0'); // find end
+ *pchEnd++ = '.'; // add the dot
+ *pchEnd = '\0'; // null terminate again
+ ostrcat(rgchVer, rgchVerMinor); // concatenate
+
+ // Now create the subkey
+ if (oRegCreateKey(hkeyGuid, rgchVer, &hkeyVersion) != ERROR_SUCCESS) {
+ err = TIPERR_RegistryAccess;
+ goto Error5;
+ }
+
+ // Now set the doc string value
+ IfErrGoTo(TiperrOfHresult(ptlib->GetDocumentation(-1,
+ NULL,
+ &bstrDocString,
+ NULL,
+ NULL)),
+ Error6);
+
+ // And set its value.
+ if (oRegSetValue(hkeyVersion,
+ NULL,
+ REG_SZ,
+ (bstrDocString) ? bstrDocString : WIDE(""),
+ (bstrDocString) ? ostrblen0(bstrDocString) : 1) != ERROR_SUCCESS) {
+ err = TIPERR_RegistryAccess;
+ goto Error7;
+ }
+
+ // Now create the FLAGS subkey in under the version subkey
+ if (oRegCreateKey(hkeyVersion, WIDE("FLAGS"), &hkeyFlags) != ERROR_SUCCESS) {
+ err = TIPERR_RegistryAccess;
+ goto Error7;
+ }
+ // Get flags value in hex with no leading zeros
+ oultoa(ptlibattr->wLibFlags, rgchFlags, 16);
+
+ // And set the value.
+ if (oRegSetValue(hkeyFlags,
+ NULL,
+ REG_SZ,
+ rgchFlags,
+ ostrblen0(rgchFlags)) != ERROR_SUCCESS) {
+ err = TIPERR_RegistryAccess;
+ }
+ RegCloseKey(hkeyFlags);
+ if (err != TIPERR_None)
+ goto Error7;
+
+ // Now create the lcid subkey in hex string under version subkey
+ oultoa(ptlibattr->lcid, rgchLcid, 16);
+
+ // Now create the subkey
+ if (oRegCreateKey(hkeyVersion, rgchLcid, &hkeyLcid) != ERROR_SUCCESS) {
+ err = TIPERR_RegistryAccess;
+ goto Error7;
+ }
+
+ // Now create the subkey
+ if (oRegCreateKey(hkeyLcid, szSys, &hkeyPlatform) != ERROR_SUCCESS) {
+ err = TIPERR_RegistryAccess;
+ goto Error8;
+ }
+
+ // And set its value
+ IfErrGoTo(RegisterPathAndAlias(hkeyPlatform, szFullPath), Error9);
+
+ // If the HELPDIR was not specified and there is already a HELPDIR
+ // in the registry, don't do anything to the existing HELPDIR item.
+ // Otherwise, create the HELPDIR subkey under the version.
+ if (szHelpDir != NULL ||
+ oRegOpenKey(hkeyVersion, WIDE("HELPDIR"), &hkeyHelpdir) != ERROR_SUCCESS) {
+
+ if (oRegCreateKey(hkeyVersion, WIDE("HELPDIR"), &hkeyHelpdir) != ERROR_SUCCESS) {
+ err = TIPERR_RegistryAccess;
+ goto Error9;
+ }
+
+ // If szHelpDir wasn't specified, use szFullPath without the filename.
+ if (szHelpDir == NULL) {
+ szHelpDir = szFullPath;
+ pchEnd = GetPathEnd(szFullPath);
+ if (pchEnd == NULL) {
+ pchEnd = szFullPath;
+ }
+ chSave = *pchEnd;
+ *pchEnd = '\0';
+ }
+ else
+ pchEnd = NULL;
+
+ // Set the HELPDIR value.
+ err = RegisterPathAndAlias(hkeyHelpdir, szHelpDir);
+ // UNDONE: if this fails, the error is never reported. Intentional?
+
+ if (pchEnd != NULL)
+ *pchEnd = chSave;
+ }
+
+ RegCloseKey(hkeyHelpdir);
+
+ // Now register all the typeinfo that supports IDISPATCH interface.
+ //
+ // Get the count of typeinfo.
+ ustiCount = ptlib->GetTypeInfoCount();
+
+ // Now create the interface subkey.
+ if (oRegCreateKey(HKEY_CLASSES_ROOT, WIDE("Interface"), &hkeyInterface) != ERROR_SUCCESS) {
+ err = TIPERR_RegistryAccess;
+ goto Error9;
+ }
+
+ // For each typeinfo in the typelib register it's dispinterface/interface.
+ for (i=0; i < ustiCount; i++) {
+ // get the typekind
+ IfErrGoTo(TiperrOfHresult(ptlib->GetTypeInfoType(i, &typekind)), Error12);
+
+ // Check if this typeinfo's supports IDispatch interface
+ if (typekind == TKIND_DISPATCH || typekind == TKIND_INTERFACE) {
+
+ // Get the pointer to the typeinfo
+ IfErrGoTo(TiperrOfHresult(ptlib->GetTypeInfo(i, &pitinfo)), Error12);
+
+ // Get the type attribute of this typeinfo
+ IfErrGoTo(TiperrOfHresult(pitinfo->GetTypeAttr(&ptypeattr)), Error13);
+
+ if (ptypeattr->wTypeFlags & (TYPEFLAG_FOLEAUTOMATION | TYPEFLAG_FDUAL)) {
+ szGuidPS = szGuidPSAutomation;
+ } else {
+ if (typekind == TKIND_INTERFACE) {
+ goto DontRegisterInteface; // don't register non-OA interfaces
+ }
+ szGuidPS = szGuidPSDispatch;;
+ }
+
+ // Convert the guid into the registry string format.
+ StringFromGUID2(ptypeattr->guid, szGuidTypeInfo, CCH_SZGUID0);
+
+#if 0
+ // DUAL intefaces. It was added so that we would allow a user to
+ // specify their own custom remoting code for an interface & not have
+ // it overwritten by RegisterTypeLib. But the other scenario is more
+ // important.
+ if (ptypeattr->wTypeFlags & (TYPEFLAG_FOLEAUTOMATION | TYPEFLAG_FDUAL)) {
+ // if this guid already exists, leave it alone
+ if (oRegOpenKey(hkeyInterface, szGuidTypeInfo, &hkeyGuidTypeinfo) == ERROR_SUCCESS) {
+ goto DontRegisterInteface1; // don't re-register this interface
+ }
+ }
+#endif //0
+
+ // Get the Name of the typeinfo
+ IfErrGoTo(TiperrOfHresult(ptlib->GetDocumentation(i,
+ &bstrName,
+ NULL,
+ NULL,
+ NULL)), Error14);
+
+ // Now create the guid subkey under Interface
+ if (oRegCreateKey(hkeyInterface, szGuidTypeInfo, &hkeyGuidTypeinfo) != ERROR_SUCCESS) {
+ err = TIPERR_RegistryAccess;
+ goto Error16;
+ } // if
+
+ // And set the name of the typeinfo
+ if (oRegSetValue(hkeyGuidTypeinfo,
+ NULL,
+ REG_SZ,
+ bstrName,
+ ostrblen0(bstrName)) != ERROR_SUCCESS) {
+ err = TIPERR_RegistryAccess;
+ goto Error17;
+ }
+
+#if 0
+ // Dont register either "NumMethods" or "BaseInterface"
+ // anymore. They are largely cosmetic, and we cant afford
+ // the registry space (just used it below for the 2 kinds of
+ // ProxyStubClsid's)
+
+ IfErrGoTo(RegCreateSubKey(hkeyGuidTypeinfo,
+ WIDE("BaseInterface"),
+ szGuidBaseInterface,
+ CCH_SZGUID0), Error17);
+
+ IfErrGoTo(RegCreateSubKey(hkeyGuidTypeinfo,
+ WIDE("NumMethods"),
+ rgchNumMethods,
+ ostrblen0(rgchNumMethods)), Error17);
+#endif
+
+#define SZ_ProxyStubClsid1 WIDE("ProxyStubClsid")
+#if OE_WIN
+#define SZ_ProxyStubClsid2 WIDE("ProxyStubClsid32")
+#endif
+ IfErrGoTo(RegCreateSubKey(hkeyGuidTypeinfo,
+ SZ_ProxyStubClsid1,
+ szGuidPS,
+ CCH_SZGUID0), Error17);
+
+#if OE_WIN
+ // Have to create both 16-bit & 32-bit keys on win16 & win32, since
+ // we don't know whether or not the user will try to do 16-32 interop
+ // stuff.
+ IfErrGoTo(RegCreateSubKey(hkeyGuidTypeinfo,
+ SZ_ProxyStubClsid2,
+ szGuidPS,
+ CCH_SZGUID0), Error17);
+#endif //OE_WIN
+
+ IfErrGoTo(RegCreateSubKey(hkeyGuidTypeinfo,
+ WIDE("TypeLib"),
+ szGuidTypeLib,
+ CCH_SZGUID0), Error17);
+
+ FreeBstr(bstrName);
+ bstrName = NULL;
+
+//DontRegisterInteface1:
+ RegCloseKey(hkeyGuidTypeinfo);
+
+DontRegisterInteface:
+ // Release the typeinfo and the type attribute.
+ pitinfo->ReleaseTypeAttr(ptypeattr);
+ pitinfo->Release();
+
+ } // if
+
+ } // for loop
+
+ // Go to Error12 to clean up the resources.
+ goto Error12;
+
+Error17:
+ RegCloseKey(hkeyGuidTypeinfo);
+ // fall through...
+
+Error16:
+ FreeBstr(bstrName);
+ // Fall through...
+
+Error14:
+ pitinfo->ReleaseTypeAttr(ptypeattr);
+ // Fall through...
+
+Error13:
+ pitinfo->Release();
+ // Fall through...
+
+Error12:
+ RegCloseKey(hkeyInterface);
+ // Fall through...
+
+Error9:
+ RegCloseKey(hkeyPlatform);
+ // fall through...
+
+Error8:
+ RegCloseKey(hkeyLcid);
+ // fall through...
+
+Error7:
+ FreeBstr(bstrDocString);
+ // fall through...
+
+Error6:
+ RegCloseKey(hkeyVersion);
+ // fall through...
+
+Error5:
+ RegCloseKey(hkeyGuid);
+ // fall through...
+
+Error4:
+ RegCloseKey(hkeyTypelib);
+ // fall through...
+
+Error2:
+ ptlib->ReleaseTLibAttr(ptlibattr);
+ // fall through...
+
+Error:
+#if !OE_MAC
+ MemFree(lpstrUNC);
+#endif // !OE_MAC
+ return HresultOfTiperr(err);
+}
+#pragma code_seg()
+
+#if OE_MAC
+
+/***
+* STDAPI LoadTypeLibFS - Loads a typelib given an FSSpec.
+***************************************************************/
+#pragma code_seg(CS_INIT)
+STDAPI LoadTypeLibFSp(const FSSpec *pfsspec, ITypeLibA **pptlib)
+{
+ XCHAR rgchPathName[256];
+ HRESULT hresult;
+
+ // if vRefNum and parID are both 0, then call LoadTypeLib
+ // with just the name (to force the search).
+ if (pfsspec->vRefNum == 0 && pfsspec->parID == 0) {
+ memcpy(rgchPathName, pfsspec->name+1, pfsspec->name[0]);
+ rgchPathName[pfsspec->name[0]] = '\0';
+ }
+ else {
+ IfOleErrRet(HresultOfTiperr(GetPathFromFSSpec(pfsspec,
+ rgchPathName,
+ sizeof(rgchPathName))));
+ }
+ return LoadTypeLib(rgchPathName, pptlib);
+}
+#pragma code_seg()
+
+/***
+* STDAPI RegisterTypeLibFolder() - Registers the typelib folder.
+*
+* Purpose:
+* RegisterTypeLibFolder is only available on the Mac. It stores in the
+* registry the location of the standard TypeLib folder. This folder
+* is searched for requested typelibs by LoadTypeLib as a last resort.
+* The specified path is always put in the registry. On System 7, the
+* corresponding alias record is also stored in the registry so that
+* the user can move the typelib folder around without invalidating the
+* registry.
+*
+* Inputs:
+* szFullPath - Its complete path. This must not end with a colon. (IN)
+*
+* Implementation:
+* The subkey hierarchy looks like this:
+* \ [root]
+* TypeLib
+* TypeLibFolder=<szFullPath>
+* Alias=<alias> [system 7 only]
+*
+* NOTE: since this can be the first call into typelib.dll
+* we must ensure that the APPDATA struct has been inited,
+* thus InitAppData().
+*
+******************************************************************************/
+#pragma code_seg(CS_INIT)
+STDAPI RegisterTypeLibFolder(LPSTR szFullPath)
+{
+ HKEY hkeyPath;
+ TIPERROR err = TIPERR_None;
+
+ // Create the TypeLibFolder key...
+ if (RegCreateKey(HKEY_CLASSES_ROOT, "TypeLibFolder", &hkeyPath) != ERROR_SUCCESS) {
+ err = TIPERR_RegistryAccess;
+ goto Error;
+ }
+
+ // ...and set its value.
+ err = RegisterPathAndAlias(hkeyPath, szFullPath);
+
+ RegCloseKey(hkeyPath);
+
+Error:
+ return HresultOfTiperr(err);
+}
+#pragma code_seg()
+
+/***
+* STDAPI QueryTypeLibFolder() - Returns path of the registered typelib folder.
+*
+* Purpose:
+* QueryTypeLibFolder is only available on the Mac. It returns the path
+* of the registered typelib folder if it is registered and the registered
+* folder exists. The folder's location is recorded both as a path and
+* as an alias record. If the path exists, that is returned. Otherwise,
+* the alias is used to get the folder's path. If that succeeds, the
+* registered path is updated and returned.
+*
+* Inputs:
+* None.
+*
+* Outputs:
+* On success, *pbstr is set to an allocate BSTR containing the path.
+* If there is no typelib folder entry, RegistryAccess is returned.
+* If the registered folder cannot be located, even through the alias,
+* PathNotFound is returned.
+*
+******************************************************************************/
+#pragma code_seg(CS_INIT)
+STDAPI QueryTypeLibFolder(LPBSTRA pbstr)
+{
+ TIPERROR err = TIPERR_None;
+ LONG cbPath;
+ XSZ mszPath;
+ BSTRA bstr;
+
+ mszPath = (XSZ)GetMemPool(MEMPOOL_1024_0);
+ cbPath = (LONG)MemPoolSize(MEMPOOL_1024_0);
+
+ // Lookup the path from the registry, ensuring it exists.
+ IfErrGo(GetRegisteredPath(HKEY_CLASSES_ROOT, "TypeLibFolder", mszPath, &cbPath, TRUE));
+
+ if ((bstr = AllocBstr(mszPath)) == NULL) {
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+
+ *pbstr = bstr;
+
+Error:
+ FreeMemPool(mszPath);
+ return HresultOfTiperr(err);
+}
+#pragma code_seg()
+#endif // OE_MAC
+
+
+/***
+*PROTECTED GenericTypeLibOLE::operator new
+*Purpose:
+* Allocates space for a GenericTypeLibOLE
+*
+*Implementation Notes:
+* Allocates a SHEAP_MGR segment and returns a pointer into segment
+* immediately following the SHEAP_MGR instance.
+* The heap is initialized with enough reserved space to contain the
+* SHEAP_MGR instance and the GenericTypeLibOLE (or derived) instance.
+*
+*Entry:
+* size - this is the size of GenericTypeLibOLE or the derived instance
+*
+*Exit:
+* pointer to location at which the GenericTypeLibOLE or derived instance
+* is to be constructed
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+VOID* GenericTypeLibOLE::operator new(size_t size)
+{
+ SHEAP_MGR *psheapmgr;
+ TIPERROR err;
+
+ err = SHEAP_MGR::Create(&psheapmgr, sizeof(SHEAP_MGR) + size);
+
+ if (err != TIPERR_None) {
+ return NULL;
+ }
+ else {
+ return psheapmgr + 1;
+ }
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GenericTypeLibOLE::Init
+*Purpose:
+* Initializes a new GenericTypeLibOLE.
+*
+*Entry:
+* szLibIdFile - In EI_OB, this is the libId of the typelib, or NULL if it
+* is not known. In the OLE implementation this is the filename.
+* psheapmgr - pointer to SHEAP_MGR instance used for initializing
+* blkdesc's belonging to the GenericTypeLibOLE.
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR GenericTypeLibOLE::Init()
+{
+ UINT i;
+ TIPERROR err;
+
+ m_cRefs = 1;
+ m_cTypeEntries = 0;
+ m_pstg = NULL;
+ m_pstgContainer = NULL;
+ m_wLibFlags = 0;
+ m_lSampleHashVal = 0;
+
+ m_lcidZero = FALSE;
+
+ m_lcid = GetUserDefaultLCID(); // Get the systems default LCID
+ if (!VerifyLcid(m_lcid)) { // for typelib.dll, if the lcid is bad,
+ m_lcid = 0x0409; // then we assume International English
+ m_lcidZero = TRUE; // set the flag to indicate that the lib's
+ // lcid was 0
+ }
+
+ // cache DBCS flag
+ m_isDBCS = IsDBCS(m_lcid);
+
+ // Initialize each bucket list to empty
+ for (i = 0; i < GTLIBOLE_cBuckets; i++)
+ m_rghteBucket[i] = HTENTRY_Nil;
+
+ SHEAP_MGR *psheapmgr = Psheapmgr();
+ IfErrRet(m_nammgr.Init(psheapmgr));
+ IfErrRet(m_bdte.Init(psheapmgr, 0));
+ IfErrRet(m_bmData.Init(psheapmgr));
+ IfErrRet(m_gptbind.Init(psheapmgr));
+
+ IfErrRet(m_nammgr.SetGtlibole(this));
+
+ IfErrRet(m_dstrmgr.Init());
+
+
+ return TIPERR_None;
+}
+
+/***
+*PUBLIC GenericTypeLibOLE::Create
+*Purpose:
+* Create and initialize a typelib instance.
+*
+*Entry:
+* None
+*
+*Exit:
+* return value = TIPERROR
+*
+* *pptlib = ptr to the newly created typelib instance.
+*
+***********************************************************************/
+TIPERROR
+GenericTypeLibOLE::Create(IStorageA *pstg, GenericTypeLibOLE **pptlib)
+{
+ TIPERROR err;
+ GenericTypeLibOLE *ptlib;
+
+ if ((ptlib = new GenericTypeLibOLE) == NULL) {
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+
+ // Here we initialize the protected m_psheapmgr member.
+ // Since we know that operator new returns a pointer to
+ // memory allocated immediately after a SHEAP_MGR instance,
+ // we simply initialize m_psheapmgr accordingly.
+ //
+ ptlib->m_psheapmgr = (SHEAP_MGR *)ptlib - 1;
+#if OE_SEGMENTED
+ DebAssert(OOB_OFFSETOF(ptlib->m_psheapmgr) == 0,
+ "Heap manager not on seg boundary");
+#endif
+
+ IfErrGo(ptlib->Init());
+
+ if(pstg != NULL){
+ pstg->AddRef();
+ ptlib->m_pstg = pstg;
+ }
+
+ *pptlib = ptlib;
+ return TIPERR_None;
+
+Error:;
+ return err;
+}
+#pragma code_seg()
+
+/***
+*PUBLIC GenericTypeLibOLE::QueryInterface
+*Purpose:
+* Implementation of QueryInterface method.
+* Only supports casting to ITypeLibA and ICreateTypeLibA.
+*
+*Entry:
+* riid - Interface GUID
+* ppv - LPVOID * that receives the requested protocol.
+*
+*Exit:
+* Return NOERROR or ReportResult(0, E_NOINTERFACE, 0, 0)
+***********************************************************************/
+#pragma code_seg( CS_CORE2 )
+STDMETHODIMP
+GenericTypeLibOLE::QueryInterface(REFIID riid, LPVOID FAR* ppv)
+{
+ *ppv = NULL; // required by OLE
+ if(riid == IID_IUnknown){
+ *ppv = (LPVOID)(IUnknown*)(ITypeLibA*)this;
+ }else
+ if(riid == IID_ICreateTypeLibA){
+ *ppv = (LPVOID)(ICreateTypeLibA*)this;
+ }else
+ if(riid == IID_ITypeLibA
+ || riid == IID_IGenericTypeLibOLE
+ ){
+ *ppv = (LPVOID)(ITypeLibA*)this;
+ }
+
+ if(*ppv == NULL)
+ return HresultOfScode(E_NOINTERFACE);
+ ((IUnknown*)*ppv)->AddRef();
+ return NOERROR;
+}
+#pragma code_seg( )
+
+/***
+*PUBLIC GenericTypeLibOLE::AddRef
+*Purpose:
+* Increment reference count of the typelib
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+STDMETHODIMP_(ULONG)
+GenericTypeLibOLE::AddRef()
+{
+ // WARNING : WARNING : We set the count to -1 when the typelib is
+ // being destructed. m_cRefs is geing used as a semaphore
+ // to ensure that we do not get into a recursive release.
+ // Hence do not bump up the count if the typelib is being
+ // destructed.
+ if (m_cRefs != -1) {
+ m_cRefs++;
+ }
+ return m_cRefs;
+}
+#pragma code_seg( )
+
+
+
+/***
+*PUBLIC GenericTypeLibOLE::GenericTypeLibOLE
+*Purpose:
+* Initialize members of GenericTypeLibOLE so release can be called even
+* if initialization fails.
+* need to initialize const/static class members
+* since cfront is buggy and we have no ctor linker.
+*
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+GenericTypeLibOLE::GenericTypeLibOLE()
+{
+ m_cRefs = 1;
+ m_cTypeEntries = 0;
+ m_pstg = NULL;
+ m_pstgContainer = NULL;
+ m_hlnamLib = HLNAM_Nil;
+ m_hszDefaultTITypeId = HCHUNK_Nil;
+ m_hasValidDiskImageNameCache = (USHORT)FALSE;
+ m_lPosGptbind = -1;
+ m_fGptbindDeserialized = FALSE;
+ m_fDstrmgrDeserialized = FALSE;
+ m_lPosDstrmgr -1;
+ m_wCurVersion = wDefaultVersion;
+ m_fNammgrDeserialized = FALSE;
+ m_lPosNammgr = -1;
+ m_lPosRgnamcache = -1;
+ m_fDirModified = FALSE;
+ m_isModified = FALSE;
+ m_hszDocString = HCHUNK_Nil;
+ m_dwHelpContext = 0;
+ m_hszHelpFile = HCHUNK_Nil;
+ m_psheapmgr = NULL;
+ m_wMajorVerNum = 0;
+ m_wMinorVerNum = 0;
+ m_guid = IID_NULL;
+ m_hszFile = HCHUNK_Nil;
+ m_hszDirectory = HCHUNK_Nil;
+ // Bump the count of typelib currently loaded.
+ Pappdata()->m_cTypeLib++;
+
+ m_syskind = SYSKIND_CURRENT;
+
+#if ID_DEBUG
+ m_szDebName[0] = 0;
+#endif // ID_DEBUG
+
+ // moved setting of m_lcid and m_codepageSrc/Dst to Init()
+
+ DebResetNameCacheStats();
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GenericTypeLibOLE::Release
+*Purpose:
+* Release a reference to the TypeLib.
+* Frees the TypeLib if no more references.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+STDMETHODIMP_(ULONG)
+GenericTypeLibOLE::Release()
+{
+ ULONG cRefs;
+
+ // WARNING : We set the count to -1 when the typelib is
+ // being destructed. m_cRefs is geing used as a semaphore
+ // to ensure that we do not get into a recursive release.
+ // Hence if m_cRefs == -1 then return as we are already
+ // in the process of destructing this LIB.
+ if (m_cRefs == -1)
+ return m_cRefs;
+
+ DebAssert(m_cRefs > 0, "underflow.");
+
+ // Error generation suspended.
+ DebSuspendError();
+
+ m_cRefs--;
+ cRefs = m_cRefs;
+ if (m_cRefs == 0) {
+
+ APP_DATA *pappdata = Pappdata();
+
+ // if this is the last reference to stdole.tlb, invalidate the
+ // appdata cache
+ if (this == pappdata->m_ptlibStdole)
+ pappdata->m_ptlibStdole = NULL;
+
+ // WARNING : WARNING : We set the count to -1 when the typelib is
+ // being destructed. m_cRefs is geing used as a semaphore
+ // to ensure that we do not get into a recursive release.
+ m_cRefs = (ULONG)-1;
+ delete this;
+ Poletmgr()->TypeLibUnloaded(this);
+ }
+
+ // Error generation resumed.
+ DebResumeError();
+ return cRefs;
+}
+#pragma code_seg()
+
+/***
+*PUBLIC GenericTypeLibOLE::~GenericTypeLibOLE
+*Purpose:
+* Release resources of GenericTypeLibOLE
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+GenericTypeLibOLE::~GenericTypeLibOLE()
+{
+ UINT i;
+
+ // Release the lib's binding resources.
+ // This walks the proj-level binding table and releases
+ // external references to other projects (recursively).
+ //
+ ReleaseResources();
+
+ // Before releasing the resources, make sure that there is
+ // no internal refrences within the project.
+ for (i = 0; i < m_cTypeEntries; i++) {
+ if (Qte(i)->m_pstltinfo != NULL) {
+ if (Qte(i)->m_pstltinfo->PstltiPartner() != NULL) {
+ Qte(i)->m_pstltinfo->PstltiPartner()->RemoveInternalRefs();
+ }
+ Qte(i)->m_pstltinfo->RemoveInternalRefs();
+ }
+ }
+
+ for (i = 0; i < m_cTypeEntries; i++) {
+ while (Qte(i)->m_pdfstrm != NULL) {
+ Qte(i)->m_pdfstrm->Release();
+ }
+ }
+
+ // Release the resourses owned by the TYPE_ENTRY table which are
+ // external to the GenericTypeLibOLE's heap.
+ // Elements of the heap don't need to be released since the whole
+ // heap will be released.
+ // Note that some TYPEINFOs may still be loaded due to internal
+ // references from other TYPEINFOs in this ITypeLib.
+ for (i = 0; i < m_cTypeEntries; i++) {
+ // !!!!!!HACK ALERT!!!!!
+ // In EI_OLE, we know the truetype of the typeinfo is GEN_DTINFO
+ // and that it was allocated via MemAlloc and that global delete
+ // is not allowed. So explicitly call its destructor and use
+ // MemFree to deallocate it.
+ // THIS WILL BREAK IF THE TRUETYPE EVER CHANGES TO SOMETHING ELSE.
+ //////////////////////////////////////////////////////////////////
+ if (Qte(i)->m_pstltinfo != NULL) {
+ if (Qte(i)->m_pstltinfo->PstltiPartner() != NULL) {
+ ((GEN_DTINFO *)(Qte(i)->m_pstltinfo->PstltiPartner()))
+ ->GEN_DTINFO::~GEN_DTINFO();
+ MemFree(Qte(i)->m_pstltinfo->PstltiPartner());
+ }
+
+ ((GEN_DTINFO *)(Qte(i)->m_pstltinfo))->GEN_DTINFO::~GEN_DTINFO();
+ MemFree(Qte(i)->m_pstltinfo);
+ }
+ RelTypeEntExtResources(i);
+ }
+
+ if (m_pstg != NULL) {
+ m_pstg->Release();
+ }
+
+}
+#pragma code_seg()
+
+
+
+
+/***
+*PUBLIC GenericTypeLibOLE::Deleting
+*Purpose:
+* Called by a TypeInfo when its last external reference has been released.
+*
+*Entry:
+* hte - handle for the TypeInfo being deleted
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#if OE_MAC
+#pragma code_seg(CS_INIT)
+#endif
+VOID GenericTypeLibOLE::Deleting(HTENTRY hte)
+{
+ Qte(hte)->m_pstltinfo = NULL;
+}
+#if OE_MAC
+#pragma code_seg()
+#endif
+
+/***
+*PUBLIC GenericTypeLibOLE::GetTypeInfoCount
+*Purpose:
+* Return the number of TypeInfos contained in the library.
+*
+*Entry:
+* None.
+*
+*Exit:
+* returns number of TypeInfos
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+UINT GenericTypeLibOLE::GetTypeInfoCount()
+{
+ return m_cTypeEntries;
+}
+#pragma code_seg( )
+
+
+
+/***
+*PUBLIC GenericTypeLibOLE::GetDocumentation
+*Purpose:
+* Return the various pieces of documentation about the specified type
+* (or the current typelib).
+*
+*Entry:
+* i - index of TypeInfo whose documentation is to be returned.
+* This should be -1 if the typelib's documentation is desired instead.
+*
+*Exit:
+* HRESULT
+* The info corresponding to each pointer is set appropriately, provided
+* that pointer is not NULL. The strings are allocated as BSTRs and must
+* be freed (eventually) by the caller.
+*
+* If an error occurs, the pointers are not modified.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+HRESULT GenericTypeLibOLE::GetDocumentation(INT i,
+ LPBSTR lpbstrName,
+ LPBSTR lpbstrDocString,
+ LPDWORD lpdwHelpContext,
+ LPBSTR lpbstrHelpFile)
+{
+ BSTRA bstrName = NULL;
+ BSTR bstrDocString = NULL;
+ BSTR bstrHelpFile = NULL;
+ DWORD dwHelpContext;
+ TIPERROR err = TIPERR_None;
+ NAMMGR *pnammgr;
+ HRESULT hresult;
+
+ // Get the help file, if it is requested. Note that this is the
+ // same regardless of the value of the index.
+ if (lpbstrHelpFile != NULL) {
+
+ // If the helpfile is not known, just return NULL.
+ if (m_hszHelpFile == HCHUNK_Nil) {
+ *lpbstrHelpFile = NULL;
+ goto AfterHelpFile;
+ }
+
+
+ // The OLE implementation prepends the registered HELPDIR to the
+ // helpfile name.
+ TLIBKEY tlibkey;
+ TLIBATTR *ptlibattr;
+ long cbDir;
+ OLECHAR szDir[256];
+ OLECHAR szGuid[CCH_SZGUID0];
+
+ // Get the typelib's guid and version number.
+ IfErrGo(TiperrOfHresult((GetLibAttr(&ptlibattr))));
+
+ // Convert the guid into the registry string format.
+ StringFromGUID2(ptlibattr->guid, szGuid, CCH_SZGUID0);
+
+ // Open the registry key for the typelib. Fail if there is no entry
+ // for this typelib.
+ err = OpenTypeLibKey(
+ szGuid,
+ ptlibattr->wMajorVerNum,
+ ptlibattr->wMinorVerNum,
+ &tlibkey);
+
+ // Free the TLIBATTR now that we're done with it.
+ ReleaseTLibAttr(ptlibattr);
+
+ // If the typelib is registered, use the registered helpdir.
+ if (err == TIPERR_None) {
+ cbDir = sizeof(szDir)/sizeof(OLECHAR); //NOTE: this is really cchDir on OE_WIN32
+ // Verify that the path exists.
+ err = GetRegisteredPath(tlibkey.hkeyVers, WIDE("HELPDIR"), szDir, &cbDir, TRUE);
+ CloseTypeLibKey(&tlibkey);
+ if (err == TIPERR_None)
+ cbDir = ostrblen(szDir);
+ }
+
+ // If the typelib wasn't registered or there was an error in getting
+ // the registered helpdir, just use its current directory.
+ if (err != TIPERR_None) {
+ cbDir = ostrblen(QszOfHsz(m_hszDirectory));
+ if (cbDir != 0) {
+ ostrcpy(szDir, QszOfHsz(m_hszDirectory));
+ }
+ szDir[cbDir] = '\0';
+ }
+
+ m_bmData.Lock();
+ err = MakeAbsolutePath(szDir, QszOfHsz(m_hszHelpFile), &bstrHelpFile);
+ m_bmData.Unlock();
+ if (err)
+ goto Error;
+ }
+
+AfterHelpFile:
+
+ if (i == -1) {
+ if ((lpbstrName != NULL) && (m_hlnamLib != HLNAM_Nil)) {
+ // Get the name of the project/typelib from the Nammgr.
+ IfErrGo(GetNamMgr(&pnammgr));
+
+ IfErrGo(pnammgr->BstrOfHlnam(m_hlnamLib, &bstrName));
+
+ }
+ if (lpbstrDocString != NULL) {
+ IfErrGo(GetBStrOfHsz(&m_bmData, m_hszDocString, &bstrDocString));
+ }
+ if (lpdwHelpContext != NULL) {
+ dwHelpContext = m_dwHelpContext;
+ }
+ }
+ else {
+ if ((UINT)i >= m_cTypeEntries) {
+ err = TIPERR_ElementNotFound;
+ goto Error;
+ }
+ if (lpbstrName != NULL) {
+ IfErrGo(GetNamMgr(&pnammgr));
+
+ if (Qte(i)->m_ste.m_hlnamType != HLNAM_Nil)
+ IfErrGo(pnammgr->BstrOfHlnam(Qte(i)->m_ste.m_hlnamType, &bstrName));
+ }
+
+ if (lpbstrDocString != NULL) {
+ DOCSTR_MGR *pdstrmgr;
+ TIPERROR err;
+ BYTE *pbChunkStr;
+
+ if (Qte(i)->m_ste.m_hszEncodedDocString != HCHUNK_Nil) {
+ // Get the doc string manager.
+ IfErrGo(GetDstrMgr(&pdstrmgr));
+
+ pbChunkStr = m_bmData.QtrOfHandle(Qte(i)->m_ste.m_hszEncodedDocString);
+
+ // Get the decoded Doc string.
+ //
+ IfErrGo(pdstrmgr->GetDecodedDocStrOfHst(pbChunkStr, &bstrDocString));
+
+ }
+
+ }
+ if (lpdwHelpContext != NULL) {
+ dwHelpContext = Qte(i)->m_ste.m_dwHelpContext;
+ }
+ }
+
+ if (lpbstrName != NULL) {
+#if OE_WIN32
+ IfErrGo(TiperrOfHresult(ConvertBstrToWInPlace((BSTR *)&bstrName)));
+#endif
+ *lpbstrName = (BSTR)bstrName;
+ }
+ if (lpbstrDocString != NULL)
+ *lpbstrDocString = bstrDocString;
+ if (lpbstrHelpFile != NULL) {
+ *lpbstrHelpFile = (BSTR)bstrHelpFile;
+ }
+ if (lpdwHelpContext != NULL)
+ *lpdwHelpContext = dwHelpContext;
+
+ return NOERROR;
+
+Error:
+ hresult = HresultOfTiperr(err);
+
+ FreeBstrA(bstrName);
+ FreeBstr(bstrDocString);
+ FreeBstr(bstrHelpFile);
+ return hresult;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GenericTypeLibOLE::IsName
+*Purpose:
+* Tests whether name is defined in library. Returns true if the passed
+* in name matches the name of any type, member name, or parameter name.
+* If a matching name is found then the szNameBuf is modified to so that
+* characters are cased according to how they appear in the library.
+*
+*Entry:
+* szNameBuf : String that needs to be searched.
+* lHashVal : Hashvalue of the string that needs to be searched.
+*
+*Exit:
+* lpfName : True if the name was found in the Lib. else false.
+* HRESULT : Error
+*
+***********************************************************************/
+
+HRESULT GenericTypeLibOLE::IsName(OLECHAR FAR* szNameBuf,
+ unsigned long lHashVal,
+ int FAR* lpfName)
+{
+ NAMMGR *pnammgr;
+ TIPERROR err= TIPERR_None;
+#if OE_WIN32
+ CHAR FAR* szNameBufA;
+ HRESULT hresult;
+#else //OE_WIN32
+ #define szNameBufA szNameBuf
+#endif //OE_WIN32
+
+ if (szNameBuf == NULL || lpfName == NULL) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+#if OE_WIN32
+ hresult = ConvertStringToA(szNameBuf, &szNameBufA);
+ if (hresult != NOERROR) {
+ return hresult;
+ }
+#endif //OE_WIN32
+
+ if (!IsHashValCompatible(lHashVal, GetSampleHashVal())) {
+ // hash value is not compatible hence we need to recalculate the hash
+ // value
+ lHashVal = LHashValOfNameSysA(GetSyskind(), GetLcid(), szNameBufA);
+
+ }
+ // Ensure that the nammgr is read from the disk if it has not been
+ // read yet and do a quick check to see if this name is in the
+ // TypeLib at all..
+ //
+ IfErrGo(GetNamMgr(&pnammgr));
+ err = pnammgr->IsName(szNameBufA, lHashVal, lpfName);
+
+#if OE_WIN32
+ if (err == TIPERR_None && *lpfName) {
+ // If name, found, copy name we found back. No need to do a length
+ // check on the output buffer, since the string is guaranteed to be the
+ // same length coming out as it was coming in.
+ UINT cb = xstrblen0(szNameBufA);
+ MultiByteToWideChar(CP_ACP, 0, szNameBufA, cb, szNameBuf, cb);
+ }
+#endif //OE_WIN32
+
+Error:
+#if OE_WIN32
+ ConvertStringFree(szNameBufA);
+#endif //OE_WIN32
+ return HresultOfTiperr(err);
+}
+
+/***
+*PUBLIC GenericTypeLibOLE::FindName
+*Purpose:
+* Find the first cFound entries in this TypeLib return
+* their TypeInfos and MEMBERIDs
+*
+*Entry:
+* szNameBuf : String that needs to be found.
+* lHashVal : Hashvalue of the string that needs to be searched.
+* pcFound : The size of the TypeInfo/MEMBERID arrays.
+*
+*Exit:
+* rgptinfo : Holds the ptinfos where the name is found.
+* rgmemid : Holds the MEMBERID of the name in the corresponding
+* TypeLib, MEMBERID_NIL if the name is a class.
+* pcFound : The number of times the name appears in this TypeLib
+* HRESULT : Error
+*
+***********************************************************************/
+
+HRESULT GenericTypeLibOLE::FindName(OLECHAR FAR* szNameBuf,
+ unsigned long lHashVal,
+ ITypeInfoA FAR* FAR* rgptinfo,
+ MEMBERID FAR* rgmemid,
+ unsigned short FAR* pcFound)
+{
+ BOOL fName;
+ NAMMGR *pnammgr;
+ TIPERROR err= TIPERR_None;
+#if OE_WIN32
+ HRESULT hresult;
+ char FAR* szNameBufA;
+#else //OE_WIN32
+ #define szNameBufA szNameBuf
+#endif //OE_WIN32
+
+ if (!szNameBuf || !rgptinfo || !rgmemid || !pcFound) {
+ return HresultOfScode(E_INVALIDARG);
+ }
+
+#if OE_WIN32
+ IfOleErrRet(ConvertStringToA(szNameBuf, &szNameBufA));
+#endif //OE_WIN32
+
+ if (!IsHashValCompatible(lHashVal, GetSampleHashVal())) {
+ // hash value is not compatible hence we need to recalculate the hash
+ // value
+ lHashVal = LHashValOfNameSysA(GetSyskind(), GetLcid(), szNameBufA);
+
+ }
+
+ // Ensure that the nammgr is read from the disk if it has not been
+ // read yet and do a quick check to see if this name is in the
+ // TypeLib at all..
+ //
+ IfErrGo(GetNamMgr(&pnammgr));
+
+ IfErrGo(pnammgr->IsName(szNameBufA, lHashVal, &fName));
+
+ // If the name exists and we are interested in knowing anything
+ // else, defer to FindMembers to get the names.
+ //
+ if (fName && *pcFound) {
+ err = FindMembers(szNameBufA, lHashVal, rgptinfo, rgmemid, pcFound);
+ }
+ else {
+ // We didn't find it, so return nothing.
+ *pcFound = 0;
+ }
+
+Error:
+#if OE_WIN32
+ ConvertStringFree(szNameBufA);
+#endif //OE_WIN32
+ return HresultOfTiperr(err);
+}
+
+
+/***
+*PUBLIC GenericTypeLibOLE::GetLibAttr
+*Purpose:
+* Allocates and returns a TLIBATTR structure containing various
+* attributes of this typelib.
+*
+*Entry:
+*
+*Exit:
+* *pptlibattr - A callee-allocated structure filled with attributes.
+* The caller is responsible for eventually freeing the memory associated
+* with this structure by calling the non-member function ReleaseTLibAttr().
+* HRESULT
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+HRESULT GenericTypeLibOLE::GetLibAttr(TLIBATTR **pptlibattr)
+{
+ TLIBATTR *ptlibattr;
+ TIPERROR err=TIPERR_None;
+
+ if (pptlibattr == NULL)
+ return HresultOfScode(E_INVALIDARG);
+
+ // Allocate the TLIBATTR structure.
+ if ((ptlibattr = (TLIBATTR *)MemAlloc(sizeof(TLIBATTR))) == NULL)
+ return HresultOfScode(E_OUTOFMEMORY);
+
+ // if the lcid was set to be zero then return 0 as the lcid.
+ if (m_lcidZero)
+ ptlibattr->lcid = 0;
+ else
+ ptlibattr->lcid = m_lcid;
+
+
+ ptlibattr->syskind = (SYSKIND)m_syskind;
+ ptlibattr->wLibFlags = m_wLibFlags;
+
+ ptlibattr->wMajorVerNum = m_wMajorVerNum;
+ ptlibattr->wMinorVerNum = m_wMinorVerNum;
+ ptlibattr->guid = m_guid;
+
+ *pptlibattr = ptlibattr;
+ return NOERROR;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC void GenericTypeLibOLE::ReleaseTLibAttr
+*Purpose:
+* Frees a TLIBATTR structure allocated by GetLibAttr.
+* ptlibattr may be NULL, in which case this method does nothing.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+void GenericTypeLibOLE::ReleaseTLibAttr(TLIBATTR *ptlibattr)
+{
+ if (ptlibattr != NULL) {
+ MemFree(ptlibattr);
+ }
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*HRESULT GenericTypeLibOLE::CreateTypeInfo
+*
+*Entry:
+* szName - The new typeinfo's name.
+* tkind - The kind of type to be represented by the new typeinfo.
+*
+*Exit:
+* *ppictinfo - Points at the new typeinfo if successful.
+***********************************************************************/
+HRESULT GenericTypeLibOLE::CreateTypeInfo(LPOLESTR szName, TYPEKIND tkind, ICreateTypeInfoA **ppictinfo)
+{
+ TIPERROR err;
+ GEN_DTINFO *pgdtinfo;
+
+ // Create the typeinfo.
+ err = GEN_DTINFO::Create(&pgdtinfo,
+ tkind,
+ FALSE,
+ ACCESS_Public
+ , GetSyskind()
+ );
+ if (err) goto Error;
+
+ // Add it to the specified project.
+ if (err = Add(pgdtinfo, szName))
+ pgdtinfo->Release();
+ else
+ *ppictinfo = pgdtinfo;
+
+ // FALL THROUGH!!!
+
+Error:
+ return HresultOfTiperr(err);
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_CREATE)
+/***
+*HRESULT GenericTypeLibOLE::SetDocString
+*
+*Entry:
+* szDocString - The new documentation string.
+***********************************************************************/
+HRESULT GenericTypeLibOLE::SetDocString(LPOLESTR szDoc)
+{
+ return HresultOfTiperr(ResetHsz(szDoc, &m_hszDocString));
+}
+#pragma code_seg()
+
+/***
+*HRESULT GenericTypeLibOLE::SetHelpFileName
+*
+*Entry:
+* szHelpFileName - The new help file name.
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+HRESULT GenericTypeLibOLE::SetHelpFileName(LPOLESTR szHelpFileName)
+{
+ return HresultOfTiperr(ResetHsz(szHelpFileName, &m_hszHelpFile));
+}
+#pragma code_seg()
+
+/***
+*HRESULT GenericTypeLibOLE::SetHelpContext
+*
+*Entry:
+* dwHelpContext - The new help context.
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+HRESULT GenericTypeLibOLE::SetHelpContext(DWORD dwHelpContext)
+{
+ m_dwHelpContext = dwHelpContext;
+ return NOERROR;
+}
+#pragma code_seg()
+
+/***
+*HRESULT GenericTypeLibOLE::SetLibFlags
+*
+*Entry:
+* uLibFlags -- the library flags
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+HRESULT GenericTypeLibOLE::SetLibFlags(UINT uLibFlags)
+{
+ DebAssert(((uLibFlags & ~(LIBFLAG_FRESTRICTED
+ | LIBFLAG_FCONTROL
+ | LIBFLAG_FHIDDEN
+ )) == 0), "invalid flags");
+ m_wLibFlags = (WORD)uLibFlags;
+ return NOERROR;
+}
+#pragma code_seg()
+
+
+
+
+/***
+*HRESULT GenericTypeLibOLE::SetLcid
+*
+*Entry:
+* lcid - The new lcid.
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+HRESULT GenericTypeLibOLE::SetLcid(LCID lcid)
+{
+ NAMMGR *pnammgr;
+ TIPERROR err;
+
+ // Make this call to nammgr only after setting the LCID.
+ IfErrRetHresult(GetNamMgr(&pnammgr));
+
+ // in typelib if the passed in lcid is zero then we default to
+ // US english.
+ if (lcid == 0x0000) {
+ m_lcid = 0x0409;
+ m_lcidZero = TRUE;
+ }
+ else {
+ // Verify Lcid
+ // check if the LCID is correct
+ if (!VerifyLcid(lcid)) {
+ return HresultOfScode(TYPE_E_UNKNOWNLCID);
+ }
+
+ m_lcid = lcid;
+ m_lcidZero = FALSE;
+ }
+
+ // cache DBCS flag
+ m_isDBCS = IsDBCS(m_lcid);
+
+ return HresultOfTiperr(err);
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GenericTypeLibOLE::GetTypeComp
+*Purpose:
+* Return a ITypeComp for binding to globals defined by the library.
+* NOTE: the above function will vanish eventually.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+HRESULT GenericTypeLibOLE::GetTypeComp(ITypeCompA **pptcomp)
+{
+ CDefnTypeComp *pdfntcomp;
+ TIPERROR err;
+
+ if (pptcomp == NULL)
+ return HresultOfScode(E_INVALIDARG);
+
+ // Deserialize/create the binding table
+ IfErrGo(GetTypeBind());
+
+ // Create a CDefnTypeComp to return to the user who must
+ // must release it eventually...
+ //
+ IfErrGo(CDefnTypeComp::Create(&pdfntcomp, &m_gptbind));
+ *pptcomp = pdfntcomp;
+ // fall through...
+
+Error:
+ return HresultOfTiperr(err);
+}
+
+
+
+
+
+
+#pragma code_seg(CS_INIT)
+TIPERROR GenericTypeLibOLE::SetDirectory(LPOLESTR szFile)
+{
+ LPOLESTR sz;
+ OLECHAR ch;
+ TIPERROR err;
+
+ // Find the first character beyond the directory portion of szFile.
+ // This is either the last backslash, the last colon, or the beginning
+ // of szFile, whichever comes last.
+ if ((sz = GetPathEnd(szFile)) == NULL)
+ sz = szFile;
+
+ // Temporarily set that character to \0 to turn szFile into a
+ // zero-terminated directory string.
+ ch = *sz;
+ *sz = '\0';
+
+ // Set m_hszDirectory to this string.
+ err = ResetHsz(szFile, &m_hszDirectory);
+
+ // Restore szFile and return.
+ *sz = ch;
+ return err;
+}
+#pragma code_seg()
+
+
+#if 0 //Dead Code
+/***
+*PUBLIC GenericTypeLibOLE::GetLibid - return libid
+*Purpose:
+* Return the TypeLib's Libid.
+*
+*Entry:
+* pbstr - set to point to a BSTR containing the library's registered id
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR GenericTypeLibOLE::GetLibId(BSTR *pbstr)
+{
+ BSTR bstrPath;
+ TIPERROR err;
+
+ IfErrRet(GetBStrOfHsz(&m_bmData, m_hszFile, &bstrPath));
+
+ // Note that this is not the infinite recursion that it looks like.
+ // GetLibIdOfTypeLib will only call this method if the true type of
+ // the typelib is an OB implementation, which is not the case here.
+ err = GetLibIdOfTypeLib(this, bstrPath?bstrPath:WIDE(""), pbstr);
+ FreeBstr(bstrPath);
+ return err;
+}
+#pragma code_seg( )
+#endif //0
+
+#pragma code_seg(CS_INIT)
+TIPERROR
+GenericTypeLibOLE::SetLibId(LPOLESTR szLibId)
+{
+ TIPERROR err;
+
+ if(szLibId == NULL)
+ return TIPERR_None;
+ IfErrRet(CreateHsz(szLibId, &m_hszFile));
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GenericTypeLibOLE::GetTypeInfoOfGuid
+*Purpose:
+* Return the TypeInfo with a specified GUID. Note that this always
+* fails in the OB version.
+*
+*Entry:
+* guid - The guid to be mapped to a typeinfo.
+* pptinfo - return parameter for TypeInfo
+*
+*Exit:
+* TIPERROR
+* Increments reference count of the TYPEINFO and ITypeLib
+***********************************************************************/
+
+HRESULT GenericTypeLibOLE::GetTypeInfoOfGuid (REFGUID guid, ITypeInfoA **pptinfo)
+{
+ UINT ite;
+
+ if (pptinfo == NULL)
+ return HresultOfScode(E_INVALIDARG);
+
+ for (ite = 0; ite < m_cTypeEntries; ite++) {
+ if (Qte(ite)->m_ste.m_guid == guid)
+ return GetTypeInfo(ite, pptinfo);
+ }
+
+ return HresultOfScode(TYPE_E_ELEMENTNOTFOUND);
+}
+
+
+/***
+*PUBLIC GenericTypeLibOLE::GetTypeInfo
+*Purpose:
+* Return the TypeInfo of a specified TYPE_ENTRY.
+*
+*Entry:
+* hte - handle to a TYPE_ENTRY
+* pptypeinfo - return parameter for TypeInfo
+*
+*Exit:
+* HRESULT
+* Increments reference count of the ITypeInfo and ITypeLib
+***********************************************************************/
+#pragma code_seg( CS_CORE2 )
+
+HRESULT GenericTypeLibOLE::GetTypeInfo(UINT hte, ITypeInfoA **pptinfo)
+{
+ TIPERROR err;
+ STL_TYPEINFO *pstltinfo;
+ IMPMGR *pimpmgr = NULL;
+
+ if (hte >= m_cTypeEntries || pptinfo == NULL)
+ return HresultOfScode(E_INVALIDARG);
+
+ if (Qte(hte)->m_pstltinfo == NULL) {
+ //load the TYPEINFO and return it
+
+ // We blindly assume that the created instance is
+ // or singly inherits STL_TYPEINFO
+ IfErrGo( CreateInstance(GetQszTypeInfoTypeId(hte),
+ (void **)&pstltinfo) );
+
+ Qte(hte)->m_pstltinfo = pstltinfo;
+
+ pstltinfo->SetContainingTypeLib(this);
+
+ pstltinfo->SetHTEntry(hte);
+
+#if ID_DEBUG
+ // Store the typeinfo's name.
+ NAMMGR *pnammgr;
+ BSTRA bstrName;
+ HLNAM hlnam = Qte(hte)->m_ste.m_hlnamType;
+
+ if (GetNamMgr(&pnammgr) == TIPERR_None && hlnam != HLNAM_Nil) {
+ if (pnammgr->BstrOfHlnam(hlnam, &bstrName) == TIPERR_None) {
+ strncpy(Qte(hte)->m_pstltinfo->m_szDebName, bstrName, DEBNAMESIZE-1);
+ m_szDebName[DEBNAMESIZE - 1] = 0;
+ FreeBstrA(bstrName);
+ }
+ }
+#endif // ID_DEBUG
+
+ IfErrGoTo(pstltinfo->Read(), Error2);
+
+ // There is no guarentee (because of dual intefaces) that
+ // the typeinfo we just loaded will be the one we return.
+ //
+ Qte(hte)->m_pstltinfo->AddRef();
+ pstltinfo->Release();
+ }
+ else {
+ Qte(hte)->m_pstltinfo->AddRef();
+ }
+
+ *pptinfo = (ITypeInfoA*) Qte(hte)->m_pstltinfo;
+
+ return NOERROR;
+
+Error2:
+ Qte(hte)->m_pstltinfo->SetContainingTypeLib(NULL);
+ Qte(hte)->m_pstltinfo = NULL;
+ // FALL THROUGH!!!
+
+Error:
+ return HresultOfTiperr(err);
+}
+#pragma code_seg( )
+
+
+
+/***
+*PUBLIC GenericTypeLibOLE::GetGdtiOfItyp
+*Purpose:
+* Get the GEN_DTINFO of a typeinfo
+*
+*Entry:
+*
+*Exit:
+*
+*Errors:
+* None
+*
+***********************************************************************/
+#pragma code_seg( CS_CORE2 )
+TIPERROR GenericTypeLibOLE::GetGdtiOfItyp(UINT ityp, GEN_DTINFO **ppgdti)
+{
+ ITypeInfoA *ptinfo;
+ HRESULT hresult;
+
+ // Get the typeinfo for the module and then its typebind.
+ IfOleErrRetTiperr(GetTypeInfo(ityp, &ptinfo));
+
+ // Get the gdtinfo for this ole type and thence its typebind.
+ // Note that it's ok to *cast* the typeinfo to a gdtinfo
+ // since this type is contained in the current typelib
+ // and we own its implementation. Note in addition that
+ // that we can't QueryInterface to gdti since ole typeinfos
+ // don't publicly acknowledge their gdtinfo'edness.
+ //
+ *ppgdti = (GEN_DTINFO *)ptinfo;
+
+
+ return TIPERR_None;
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC GenericTypeLibOLE::GetTypeInfoType
+*Purpose:
+* Return the TypeInfo of a specified TYPE_ENTRY.
+*
+*Entry:
+* hte - handle to a TYPE_ENTRY
+* ptypekind - return parameter for typekind
+*
+*Exit:
+* HRESULT
+***********************************************************************/
+
+#pragma code_seg(CS_INIT)
+HRESULT GenericTypeLibOLE::GetTypeInfoType(UINT hte, TYPEKIND * ptypekind)
+{
+ if (hte >= m_cTypeEntries || ptypekind == NULL)
+ return HresultOfScode(E_INVALIDARG);
+
+ *ptypekind = (TYPEKIND)Qte(hte)->m_ste.m_typekind;
+
+ return NOERROR;
+}
+#pragma code_seg()
+
+
+/***
+*TIPERROR GetCompressedTypeId - Returns a compressed typeid.
+*
+*Purpose:
+* This method is called by WriteTypeId or GetFunctionIdOfExBind to get a
+* typeinfo's typeid in the compressed typeid format. The typeinfo can be
+* any implementation of ITypeInfo and it may reside in any typelib, though
+* it must either be an OB project or registered in the system.
+*
+* The returned typeId is in a compressed a form which can only be
+* interpreted by the GetTypeInfoOfCompressedTypeId method.
+*
+*Inputs:
+* ptinfo - The typeinfo whose typeId we are writing out.
+*
+*Outputs:
+* Allocates the compressed typeid string in a BSTR assigned to *pbstrOut.
+* TIPERROR
+***************************************************************************/
+TIPERROR GenericTypeLibOLE::GetCompressedTypeId(ITypeInfoA *ptinfo, BSTR *pbstrOut)
+{
+ TIPERROR err= TIPERR_None;
+ HRESULT hresult;
+ ITypeLibA *ptlib;
+ UINT itype;
+ UINT hlib;
+ BSTR bstrOut, bstrPath, bstrLibId = NULL;
+ OLECHAR *pchEnd;
+ OLECHAR rgchTypeId[3+4+1+4+1]; // *\R<hlib>*<itype><0>
+ USHORT cbBstrLibId, cbRgchTypeId;
+ NAMMGR *pnammgr;
+ HLNAM hlnam;
+
+ // Get the ref'd typeinfo's containing typelib.
+ // Note that this doesn't allocate any memory, since the typelib
+ // must already be loaded (because the typeinfo is loaded).
+ IfOleErrRetTiperr(ptinfo->GetContainingTypeLib(&ptlib, &itype));
+
+ // If the ref'd typeinfo is in this typelib, then use
+ // the "same typelib" value for hlib when compressing the LibId.
+ // Otherwise, try some other means of compression.
+ if (ptlib == this) {
+ hlib = 0xffff;
+ }
+ else {
+ // Get the LibId of the ref'd typeinfo's typelib. This libid
+ // will contain no path if ptlib is an OLE typelib.
+ IfErrGo(GetLibIdOfTypeLib(ptlib, WIDE(""), &bstrLibId));
+
+ // Now get the path corresponding to this typelib.
+ // This is guaranteed to give us the path we need because
+ // the referenced typelib must be registered in all cases
+ // where we need the path.
+ IfErrGo(GetPathOfLibId(bstrLibId, &bstrPath));
+
+ // Replace bstrLibId with a version that has the path.
+ FreeBstr(bstrLibId);
+ bstrLibId = NULL;
+ err = GetLibIdOfTypeLib(ptlib, bstrPath, &bstrLibId);
+ FreeBstr(bstrPath);
+ if (err != TIPERR_None)
+ goto Error;
+
+ // In the OLE version, set hlib to the hlnam of bstrLibId and
+ // use that hlib for the compression.
+ IfErrGo(GetNamMgr(&pnammgr));
+#if OE_WIN32
+ LPSTR lpszLibId;
+
+ IfErrGo(TiperrOfHresult(ConvertStringToA(bstrLibId, &lpszLibId)));
+
+ err = pnammgr->HlnamOfStr(lpszLibId, &hlnam, TRUE, NULL);
+
+ ConvertStringFree(lpszLibId);
+ if (err)
+ goto Error;
+#else
+ IfErrGo(pnammgr->HlnamOfStr(bstrLibId, &hlnam, TRUE, NULL));
+#endif
+ hlib = hlnam;
+ FreeBstr(bstrLibId);
+ bstrLibId = NULL;
+ }
+
+ // If, at this point, bstrLibId is NULL, then hlib contains
+ // the ushort to use for the libId portion of the typeId.
+ // In this case, the libId portion is *\R<hex ascii of hlib>
+ // Otherwise, bstrLibId holds the uncompressed libId portion
+ // and should be used to generate the uncompressed typeId and
+ // then freed.
+
+ // Now, construct the typeId in rgchTypeId.
+ // If the typeinfo is not an STL_TYPEINFO or REC_TYPEINFO, the format is:
+ // <libId>*#<hex ascii of itype>
+ // If the typeinfo is an STL_TYPEINFO or REC_TYPEINFO, the format is:
+ // <libId>*<localTypeId>
+ // Note that we only attempt to generate the STL_TYPEINFO/REC_TYPEINFO
+ // case in the OB implementation.
+
+ pchEnd = rgchTypeId;
+
+ // If we can used the compressed libId format, then put the "<libId>*"
+ // into rgchTypeId. Otherwise, just put the "*" in.
+ if (bstrLibId == NULL) {
+ ostrcpy(pchEnd, WIDE("*\\R"));
+ oultoa(hlib, pchEnd+3, 16);
+ pchEnd = ostrchr(rgchTypeId, '\0');
+ }
+
+ *pchEnd++ = chLibIdSep;
+ *pchEnd = '\0';
+
+ // In the OLE implementation, just return the non-stltinfo format.
+ *pchEnd++ = '#';
+ oultoa(itype, pchEnd, 16);
+
+ // At this point, the full compressed typeId is obtained by concatenating
+ // bstrLibId (if not NULL) and rgchTypeId. Create it.
+ /////////////////////////////////////////////////////////////////////
+
+ // Compute the length of each portion of the typeId.
+ if (bstrLibId != NULL)
+ cbBstrLibId = ostrblen(bstrLibId);
+ else
+ cbBstrLibId = 0;
+
+ cbRgchTypeId = ostrblen(rgchTypeId);
+
+ // Allocate a buffer of the correct size.
+ bstrOut = AllocBstrLen(NULL, cbBstrLibId+cbRgchTypeId);
+ if (bstrOut == NULL) {
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+
+
+ // Copy bstrLibId, if not NULL, into bstrOut.
+ if (bstrLibId != NULL)
+ ostrcpy(bstrOut, bstrLibId);
+
+ // Copy rgchTypeId.
+ ostrcpy(bstrOut+cbBstrLibId, rgchTypeId);
+
+ *pbstrOut = bstrOut;
+
+Error:
+ FreeBstr(bstrLibId);
+ ptlib->Release();
+ return err;
+}
+
+
+/***
+*TIPERROR FindMembers - Locate all instances of the given name
+*
+*Purpose:
+* Search the project-level (type) names and modules to find all
+* instances of a given name. Place the typinfos where the name
+* was found and the name's MEMBERID into a given array, when the
+* array is filled, only increment the count of the number of
+* names found.
+*
+* If the name is found at the project level (is a type), the MEMBERID
+* is set to MEMBERID_NULL.
+*
+*Inputs:
+* szName - The name to search for.
+* lHashVal - Passed to bind.
+* pcSearch - The size of the rgptinfo and rgid arrays.
+*
+*Outputs:
+* rgptinfo - An array of typinfos where the names were found.
+* rgid - The MEMBERID of the name in the respective typeinfo.
+* pcSearch - On successful completion, contains the number of
+* names found (may be more than the size of the array).
+* Returns ...
+*
+***************************************************************************/
+TIPERROR GenericTypeLibOLE::FindMembers(LPSTR szName,
+ ULONG lHashVal,
+ ITypeInfoA **rgptinfo,
+ MEMBERID *rgmemid,
+ USHORT *pcSearch)
+{
+ UINT cArraySize;
+ UINT cNamesFound = 0;
+ UINT iName;
+ UINT uOrdinal, ityp, ctyp;
+ UINT itypFirstGlobal;
+ BOOL fMultiple;
+
+ HGNAM hgnam;
+ HLNAM hlnam;
+
+ NAMMGR *pnammgr;
+ const GENPROJ_BINDNAME_TABLE *pgbindnametbl;
+
+ USHORT ibinddesc;
+ GENPROJ_BIND_DESC projbinddesc;
+
+ ITypeInfoA *ptinfo;
+ DEFN_TYPEBIND *pdfntbindMod;
+ DYN_TYPEBIND *pdtbindMod;
+ GEN_DTINFO *pgdti;
+ EXBIND exbindMatch;
+
+ HRESULT hresult;
+ TIPERROR err = TIPERR_None;
+
+ DebAssert(rgptinfo && rgmemid && pcSearch, "Bad args");
+ DebAssert(*pcSearch, "Zero parameter");
+
+ cArraySize = *pcSearch;
+
+
+ // Get typelib's nammgr
+ IfErrRet(GetNamMgr(&pnammgr));
+
+ // Get the gptbind
+ IfErrRet(GetTypeBind());
+
+ // Get the nametable
+ pgbindnametbl = m_gptbind.Pgbindnametbl();
+ DebAssert(pgbindnametbl != NULL, "No BINDNAME_TABLE");
+
+ // Map string to hgnam and hlnam
+ IfErrRet(pnammgr->HgnamOfStr(szName, &hgnam));
+ hlnam = pnammgr->HlnamOfHgnam(hgnam);
+
+ // Check the project level names (types)
+ ibinddesc = pgbindnametbl->IndexOfHlnam(hlnam);
+
+ if (ibinddesc != BIND_INVALID_INDEX) {
+ // We have a project-level match!
+
+ // We cache all the attributes of qbinddescMatch here
+ // since it's in movable memory. To do so we simply shallow
+ // copy it to a local stack-alloced BIND_DESC.
+ //
+ projbinddesc = *(pgbindnametbl->QgpbinddescOfIndex(ibinddesc));
+
+ // Get the module or project's ordinal in its respective
+ // container collection.
+ //
+ uOrdinal = projbinddesc.Ordinal();
+
+ // We only care about a module/class match, so just
+ // ignore a referenced project match.
+ //
+ if (projbinddesc.IsTypeInfo()) {
+ // Store the typeinfo into the given arrays.
+
+ // Get the typeinfo for the module.
+ IfOleErrRetTiperr(GetTypeInfo(uOrdinal, &ptinfo));
+
+ // Add the module to the output array.
+ rgptinfo[cNamesFound] = ptinfo;
+ rgmemid[cNamesFound] = MEMBERID_NIL;
+
+ // Increment the number of names found.
+ if (++cNamesFound == cArraySize) {
+ *pcSearch = cNamesFound;
+ return TIPERR_None;
+ }
+
+ } // of if module/class
+ } // of found project-level match
+
+ // If the ityp stored in the name manager is not valid, we
+ // don't have any more instances of the name and may return.
+ //
+ if (!pnammgr->IsValidItyp(hlnam)) {
+ *pcSearch = cNamesFound;
+ return TIPERR_None;
+ }
+
+ fMultiple = pnammgr->IsMultiple(hlnam);
+
+ // Get the ityp from the name manager, which represents the first
+ // instance of the name in the TypeLib.
+ //
+ itypFirstGlobal = pnammgr->ItypOfHlnam(hlnam);
+
+
+ // If IsMultiple is set, check the name cache and bind. If not,
+ // bind anyway. If more names are required, move on to the next
+ // TypeInfo and try again.
+ // Note: the following loop wraps around from itypFirstGlobal back again
+ // if need be...
+ //
+ BOOL fFirst = TRUE;
+ for (ctyp = GetTypeInfoCount(), ityp = itypFirstGlobal;
+ fFirst || ityp != itypFirstGlobal;
+ fFirst = FALSE, ityp = (ityp + 1) % ctyp)
+
+ { // start of FOR loop
+
+#if ID_DEBUG
+ if (fMultiple) {
+ // Keeps name cache stats
+ DebSetNameCacheModTrys();
+ }
+#endif // ID_DEBUG
+
+ DebSetNameCacheModTrys();
+
+ // Check the name cache
+ if (!fMultiple ||
+ !IsValidNameCache(ityp) ||
+ IsNameInCache(ityp, hgnam)) {
+
+#if ID_DEBUG
+ if (fMultiple) {
+ // Keeps name cache stats
+ DebSetNameCacheModHits();
+ }
+#endif // ID_DEBUG
+
+ // We hit the name cache, so try to bind to the name.
+ // So we start by loading the GEN_DTINFO..
+ // Don't forget to Release eventually.
+ //
+ IfErrGo(GetGdtiOfItyp(ityp, &pgdti));
+
+ // This doesn't bump refcount.
+ IfErrGoTo(pgdti->PdfntbindSemiDeclared(&pdfntbindMod), Error2);
+
+ pdtbindMod =
+ (DYN_TYPEBIND *)pdfntbindMod->QueryProtocol(DYN_TYPEBIND::szProtocolName);
+ DebAssert(pdtbindMod != NULL, "bad DYN_TYPEBIND.");
+
+ // We should reach here with non-NULL pdtbindMod.
+ // It will be for a standard module, a Class
+ // or a CoClass
+ //
+ DebAssert(pdtbindMod != NULL, "should have dtbind.");
+
+ // Try and bind in this module. We don't want to attempt
+ // to bind to a type because OLE projects don't have nested
+ // types and OB nested types are uninteresting.
+ //
+ IfErrGoTo(pdtbindMod->BindIdDefn(FALSE,
+ hgnam,
+ 0, // first match
+ ACCESS_Private,
+ &exbindMatch),
+ Error2);
+
+ // Check the results to see if we actually bound.
+ if (exbindMatch.IsOneVarMatch() || exbindMatch.IsFuncMatch()) {
+ DebAssert(cNamesFound < cArraySize, "Bad array index");
+
+ // Add the module to the output array.
+ rgptinfo[cNamesFound] = exbindMatch.Ptinfo();
+ rgptinfo[cNamesFound]->AddRef();
+
+ if (exbindMatch.IsOneVarMatch()) {
+ VAR_DEFN *qvdefn;
+
+ qvdefn = exbindMatch.Ptdata()->
+ QvdefnOfHvdefn(exbindMatch.Hvdefn());
+
+ DebAssert(qvdefn->IsMemberVarDefn(), "bad defn");
+ rgmemid[cNamesFound] = ((MBR_VAR_DEFN *)qvdefn)->Hmember();
+ }
+ else {
+ // Func defn
+ FUNC_DEFN *qfdefn;
+ qfdefn = exbindMatch.Ptdata()->
+ QfdefnOfHfdefn(exbindMatch.Hfdefn());
+
+ rgmemid[cNamesFound] = qfdefn->Hmember();
+ }
+
+ // Check the ptinfo/memid pair we just found against
+ // all of the others in the output arrays. If there is
+ // a duplicate, remove it.
+ //
+ // This search winds up being an O(n^2) operation, but the
+ // size of the array passed into FindName are usually small
+ // so it probably isn't worth doing something to speed
+ // this up.
+ //
+ ptinfo = rgptinfo[cNamesFound];
+ for (iName = 0; iName < cNamesFound; iName++) {
+ if (rgptinfo[iName] == ptinfo
+ && rgmemid[iName] == rgmemid[cNamesFound]) {
+
+ // Release the typeinfo, decrement the count of names
+ // found so it will still be correct when it is incremented
+ // below.
+ //
+ ptinfo->Release();
+ cNamesFound--;
+ break;
+ }
+ }
+
+ // Increment the number of names found. Stop if either
+ // we found all of the names the user wants OR if
+ // IsMultiple is not set.
+ //
+ if (++cNamesFound == cArraySize || !fMultiple) {
+ *pcSearch = cNamesFound;
+ goto Error3;
+ }
+ } // match
+
+ if (!exbindMatch.IsNoMatch()) {
+ exbindMatch.Ptinfo()->Release();
+ }
+ new (&exbindMatch) EXBIND; // re-init for next time through loop
+
+ // Move on to the next TypInfo
+ RELEASE(pgdti);
+ } // name cache hit
+ } // for
+
+ *pcSearch = cNamesFound;
+
+ return TIPERR_None;
+
+Error3:
+ if (exbindMatch.Ptinfo())
+ exbindMatch.Ptinfo()->Release();
+
+ // Fall through
+
+Error2:
+ RELEASE(pgdti);
+
+ // Fall through
+Error:
+ // Release whatever we have found if we're in error
+ if (err != TIPERR_None) {
+ for (ityp = 0; ityp < cNamesFound; ityp++) {
+ rgptinfo[ityp]->Release();
+ }
+ }
+
+ return err;
+}
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*TIPERROR WriteTypeId - Writes out a compressed typeid for the import manager.
+*
+*Purpose:
+* This method is called by the import manager when it wants to write out
+* the typeid of a typeinfo referenced by the import manager. The typeinfo
+* can be any implementation of ITypeInfo and it may reside in any typelib,
+* though it must either be an OB project or registered in the system.
+* It writes out the typeId in a compressed a form which can only be
+* interpreted by the GetTypeInfoOfCompressedTypeId method.
+*
+* Note that this method allocates memory and so can fail in low memory
+* situations. It is the import manager's responsibility to succeed in
+* its write despite this failure.
+*
+*Inputs:
+* pstrm - The stream to which the typeId should be written.
+* ptinfo - The typeinfo whose typeId we are writing out.
+*
+*Outputs:
+* TIPERROR
+***************************************************************************/
+TIPERROR GenericTypeLibOLE::WriteTypeId(STREAM *pstrm, ITypeInfoA *ptinfo)
+{
+ TIPERROR err;
+ BSTRA bstr;
+ USHORT cb;
+
+ IfErrRet(GetCompressedTypeId(ptinfo, (BSTR *)&bstr));
+
+#if OE_WIN32
+ // Read and write ANSI strings
+
+ IfErrRet(TiperrOfHresult(ConvertBstrToAInPlace(&bstr)));
+#endif
+
+ cb = (USHORT)xstrblen(bstr);
+ IfErrGo(pstrm->WriteUShort(cb));
+ err = pstrm->Write(bstr, cb);
+
+Error:
+ FreeBstrA(bstr);
+ return err;
+}
+#pragma code_seg()
+
+/***
+*TIPERROR TypeInfoFromCompressedTypeId - Loads a typeinfo, given a compressed typeid.
+*
+*Purpose:
+* This method is called by the import manager and funcId dereferencers
+* to map a compressed typeid to the specified typeinfo. This method,
+* despite its name, can also handle a normal typeId. It defers to the
+* typemgr to perform the dereference if the typeid is not in the compressed
+* (*\R) format.
+*
+*Inputs:
+* szTypeId - The typeid to map to a typeinfo.
+*
+*Outputs:
+* TIPERROR
+***************************************************************************/
+TIPERROR GenericTypeLibOLE::TypeInfoFromCompressedTypeId(LPOLESTR szTypeId, ITypeInfoA **pptinfo)
+{
+ WORD hlib, itype;
+ TIPERROR err;
+ ITypeLibA *ptlib;
+
+ // If the typeId is not a compressed typeId form, just defer to
+ // GetTypeInfoOfTypeId.
+ if (GetLibIdKind(szTypeId) != LIBIDKIND_Compressed) {
+ return GetTypeInfoOfTypeId(szTypeId, pptinfo);
+ }
+
+ // Otherwise, decode the compressed format.
+ /////////////////////////////////////////////////
+
+ szTypeId += 3;
+
+ // Get the hlib from the libId.
+ hlib = (WORD)ostrtoul(szTypeId, &szTypeId, 16);
+ if (szTypeId[0] != chLibIdSep)
+ return TIPERR_BadTypeId;
+
+ // If the typeId is a numeric index, decode it into itype
+ // and set szTypeId to NULL to indicate we are using an index.
+ if (szTypeId[1] == '#') {
+ itype = (WORD)ostrtoul(szTypeId+2, NULL, 16);
+ szTypeId = NULL;
+ }
+
+ // Otherwise, point szTypeId at the local typeId we'll use.
+ // In the non-OLE case, this can't happen, so return an error
+ // about the corrupted typeId.
+ else {
+ return TIPERR_BadTypeId;
+ }
+
+ // If hlib is 0xffff, then the desired typeinfo is contained within
+ // this typelib. In this case, addref this typelib so we can safely
+ // release it at the end.
+ if (hlib == 0xffff) {
+ AddRef();
+ ptlib = this;
+ }
+
+ // Otherwise, the exact meaning of hlib depends on whether this is
+ // the OB or OLE implementation of GenericTypeLibOLE.
+ else {
+ BSTR bstr;
+ NAMMGR *pnammgr;
+
+ // hlib is an hlnam in this typelib's local name manager.
+ // Map it to a true LibId and load the typelib from that.
+ IfErrRet(GetNamMgr(&pnammgr));
+ IfErrRet(pnammgr->BstrWOfHlnam(hlib, &bstr));
+
+ err = GetRegLibOfLibId(bstr, &ptlib);
+
+ FreeBstr(bstr);
+ if (err != TIPERR_None)
+ return err;
+ }
+
+ // ptlib now points at the typelib containing the desired typeinfo.
+ // Get the (itype)th typeinfo within that typelib.
+ DebAssert(szTypeId == NULL, "TypeInfoFromCompressedTypeId: szTypeId not NULL");
+ err = TiperrOfHresult(ptlib->GetTypeInfo(itype, pptinfo));
+
+ // Finally, release the typelib containing the typeinfo.
+ ptlib->Release();
+
+ return err;
+}
+
+
+/***
+*PROTECTED GenericTypeLibOLE::AddTypeEntry
+*Purpose:
+* Add a type entry of the specified name for the specified kind of
+* typeinfo to this typelib.
+*
+*Entry:
+* szName - The name.
+* szTypeInfoTypeId - The typeId of the truetype of the typeinfo.
+*
+*Exit:
+* *phte is set to the index of the new type entry.
+* TIPERROR
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+TIPERROR GenericTypeLibOLE::AddTypeEntry(LPSTR szName, LPOLESTR szTypeInfoTypeId, HTENTRY *phte)
+{
+ LPOLESTR qszLocalTypeId;
+ UINT ihteBucket;
+ HTENTRY hte;
+ TYPE_ENTRY *qte;
+ TIPERROR err;
+ USHORT usTemp;
+ HCHUNK hchunkTypeId, hsz;
+ NAMMGR *pnammgr;
+ HGNAM hgnam;
+ HLNAM hlnam;
+
+ // Generate an error if the name being added is not new or if the
+ // returned error is not one of TIPERR_ModuleNotFound and
+ // TIPERR_ElementNotFound.
+ //
+ err = GetIndexOfName(szName, &usTemp);
+
+ if (err == TIPERR_None) {
+ err = TIPERR_ModNameConflict;
+ goto Done;
+ }
+ else if (err != TIPERR_ElementNotFound) {
+ goto Done;
+ }
+
+
+ // Create a local typeId (it'll just be a timestamp).
+ IfErrRet( MakeLocalTypeId(&hchunkTypeId) );
+ qszLocalTypeId = QszOfHsz(hchunkTypeId);
+
+ ihteBucket = IhteHash(qszLocalTypeId);
+
+#if ID_DEBUG
+ // Search in the bucket list for an entry with a matching local TypeId.
+ // Return an error if one is found.
+
+ hte = m_rghteBucket[ihteBucket];
+ for (;;) {
+
+ // If the end of the bucket list is reached ...
+ if (hte == HTENTRY_Nil) {
+ break;
+ }
+
+ qte = Qte(hte);
+
+ // This entry in the bucket list matches ...
+ if (!ostrcmp(QszOfHsz(qte->m_ste.m_hszLocalTypeId), qszLocalTypeId)) {
+ DebAssert(0, "Timestamped localtypeid conflicted with existing typeid");
+ }
+
+ hte = qte->m_hteNext;
+ } // end for-ever
+#endif // ID_DEBUG
+
+ // Set the directory's modified flag to TRUE.
+ IfErrGoTo(SetModified(TRUE), ReleaseChunk);
+ m_fDirModified = TRUE;
+
+ // Allocate a new entry and link it to the front of the list
+ if (err = m_bdte.Realloc(m_bdte.CbSize() + sizeof(TYPE_ENTRY)) )
+ goto ReleaseChunk;
+
+ hte = m_cTypeEntries++;
+
+ qte = Qte(hte);
+ ::new (qte) TYPE_ENTRY;
+
+ // initialize the fields of the type element
+ qte->m_ste.m_hszLocalTypeId = hchunkTypeId;
+ qte->m_hteNext = m_rghteBucket[ihteBucket];
+ m_rghteBucket[ihteBucket] = hte;
+
+ // Get the nammgr
+ IfErrGoTo(GetNamMgr(&pnammgr), DeleteEntry);
+
+ // Get the Hlnam for the type's name and cache the hlnam.
+ // The last "TRUE" in the param list means that the case of the
+ // name should not be changed. (This sets the "sticky" bit.)
+ //
+ IfErrGoTo(pnammgr->HlnamOfStr(szName, &hlnam, FALSE,
+ NULL, TRUE), DeleteEntry);
+
+ Qte(hte)->m_ste.m_hlnamType = hlnam;
+
+ // If TypeId of TypeInfo is not the default TypeId then set the
+ // TYPEENTRY's TypeInfo's TypeId.
+ if (ostrcmp(szTypeInfoTypeId, GetQszTypeInfoTypeId(hte)) != 0) {
+ if (err = CreateHsz(szTypeInfoTypeId, &hsz))
+ goto DeleteEntry;
+
+ Qte(hte)->m_ste.m_hszTypeInfoTypeId = hsz;
+ }
+
+ // Create an entry in any event for this (possibly new) name
+ // in the nammgr
+ // so that other functions that optimize lookup/binding
+ // by first searching the nametable won't prematurely fail.
+ // The problem is that only once the binder has done its thing
+ // will this name necessarily be in the name table.
+ //
+ IfErrGoTo(pnammgr->HgnamOfStr(szName, &hgnam), DeleteEntry);
+
+
+ // Grow namcache array if there is one...
+ if (m_bdRgnamcache.IsValid()) {
+ IfErrGoTo(m_bdRgnamcache.Realloc(
+ m_bdRgnamcache.CbSize() + sizeof(NAME_CACHE)),
+ DeleteEntry);
+
+ // Invalidate the new cache entry, we haven't incremented
+ // m_cTypeEntries yet. Acutally, this assertion isn't too
+ // useful as we set this value above.
+ //
+ DebAssert(hte + 1 == m_cTypeEntries, "bad type index.");
+
+ InvalidateNameCache(hte);
+ // WARNING: currently no errors can occur after this, thus there
+ // is no need for any shrink cleanup code.
+ }
+
+ *phte = hte;
+
+ err = TIPERR_None;
+ goto Done;
+
+DeleteEntry:
+ // Delete the type entry, this removes the qte from the
+ // bucket list and decrements m_cTypeEntry.
+ //
+ GenericTypeLibOLE::UnAddTypeEntry(hte);
+
+ goto Done;
+
+ReleaseChunk:
+ m_bmData.FreeChunk(hchunkTypeId, CCH_TIMESTAMP_LENGTH*sizeof(OLECHAR));
+
+Done:
+ return err;
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PROTECTED GenericTypeLibOLE::UnAddTypeEntry
+*Purpose:
+* Performs error-recovery cleanup if an error occurred between a
+* call to AddTypeEntry and when the corresponding typeinfo was actually
+* made available to the typelib.
+*
+*Entry:
+* hte - The index of the typeentry to be removed. This must be the
+* element most recently added by AddTypeEntry.
+*
+***********************************************************************/
+void GenericTypeLibOLE::UnAddTypeEntry(UINT hte)
+{
+ UINT ihteBucket;
+
+ // The element is assumed to be at the front of a bucket list.
+ // Find it and unlink the element from the bucket list.
+ for (ihteBucket = 0;
+ ihteBucket < GTLIBOLE_cBuckets && m_rghteBucket[ihteBucket] != hte;
+ ihteBucket++);
+ m_rghteBucket[ihteBucket] = Qte(hte)->m_hteNext;
+
+ GenericTypeLibOLE::DestructTypeEntry(hte);
+ m_bdte.Realloc(m_bdte.CbSize() - sizeof(TYPE_ENTRY));
+ m_cTypeEntries--;
+}
+#pragma code_seg()
+
+
+
+/***
+*PROTECTED GenericTypeLibOLE::CreateInstance
+*Purpose:
+* This function creates an instance creates a TypeInfo instances
+* given the TYPEID for the TypeInfo.
+* For now just hard code the TYPEIDs that can be
+* be stored in the ITypeLib. Eventually we will call
+* the CreateInstance function which uses the registry.
+* When this is eliminated delete includes for btinfo.
+* This function is virtual so GEN_PROJECT can override it and
+* allow construction of BASIC and MACRO TYPEINFOs.
+* Disallowing them here avoids the need to link with ic.lib.
+*
+*Entry:
+* szTypeId - TypeId of TypeInfo to be created
+* ppvoid - returns pointer to the created instance
+*
+*Exit:
+* TIPERROR
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR GenericTypeLibOLE::CreateInstance(LPOLESTR szTypeId, void **ppvoid)
+{
+ TIPERROR err;
+
+ if (ostrcmp(szTypeId, GEN_DTINFO::szProtocolName) == 0) {
+ IfErrRet( GEN_DTINFO::Create((GEN_DTINFO **)ppvoid) );
+ }
+ else
+ DebHalt("GenericTypeLibOLE::CreateInstance: unexpected TYPEID");
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+/***
+*PROTECTED GenericTypeLibOLE::IhteHash - hash function
+*Purpose:
+* Map LocalTypeId to index into the bucket table.
+*
+*Entry:
+* TypeId - class id to be mapped to a bucket number
+* Only that part of the string preceeding the minor version
+* number separator is used in computing the hash value.
+*
+*Exit:
+* ihtype - index into bucket array
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+UINT GenericTypeLibOLE::IhteHash(TYPEID LocalTypeId)
+{
+ return HashSzTerm(LocalTypeId, chMinorVerNumSep) % GTLIBOLE_cBuckets;
+}
+#pragma code_seg( )
+
+
+
+/***
+*PUBLIC GenericTypeLibOLE::GetTypeBind
+*Purpose:
+* Build bindnametable for proj.
+*
+*Entry:
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR GenericTypeLibOLE::GetTypeBind()
+{
+ STREAM *pstrm;
+ NAMMGR *pnammgr;
+ TIPERROR err;
+
+ // Ensure nammgr has been deserialized.
+ IfErrRet(GetNamMgr(&pnammgr));
+
+ // Test if gptbind has been serialized ever or if it has
+ // already been deserialized, if not, no gptbind to read.
+ //
+ if ((m_fGptbindDeserialized == FALSE) && (m_lPosGptbind != -1)) {
+
+ IfErrRet(OpenTypeStream((UINT)-1, SOM_Read, &pstrm));
+
+ // No need to init the gptbind. It is embedded and thus
+ // is constructed at container construction time, in addition
+ // is inited at container's init time.
+ // And seek to where the gptbind should be.
+ //
+ IfErrGo(pstrm->SetPos(m_lPosGptbind));
+ IfErrGo(m_gptbind.Read(pstrm));
+ m_fGptbindDeserialized = TRUE;
+
+ // At this point stream position is exactly at start
+ // of the NAME_CACHE array, cache the stream position
+ // and use it later...
+ //
+ IfErrGo(pstrm->GetPos(&m_lPosRgnamcache));
+
+ // Close the stream
+ pstrm->Release();
+
+ // Read in the name cache as well since the binder uses the
+ // namecache as an optimization. Note that if this didn't
+ // happen here, the binder would still work correctly albeit
+ // more slowly.
+ //
+ IfErrRet(ReadNameCacheArray());
+ }
+
+ return TIPERR_None;
+
+Error:
+ // Close the stream
+ pstrm->Release();
+ return err;
+}
+#pragma code_seg( )
+
+
+
+
+
+
+/***
+*PROTECTED GenericTypeLibOLE::GetBinddescOfSzName
+*
+*Inputs:
+* szName The name of a module or ref'd lib to be bound to (IN).
+* Note: must be unqualifed --
+* call GetRgbstrOfSzName to parse.
+* pbinddesc Produced BIND_DESC for name (OUT).
+* Caller allocated!!
+*
+*Outputs:
+* TIPERR_ELementNotFound if not found.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR GenericTypeLibOLE::GetBinddescOfSzName(LPSTR szName,
+ GENPROJ_BIND_DESC *pprojbinddesc)
+{
+ NAMMGR *pnammgr;
+ HLNAM hlnam;
+ BOOL fChanged;
+ USHORT ibinddesc;
+ TIPERROR err = TIPERR_None;
+
+ DebAssert(pprojbinddesc != NULL, "null param.");
+
+ // Get the typelib-level nammgr
+ IfErrRet(GetNamMgr(&pnammgr));
+
+ // NOTE: can't optimize this lookup by testing for name's
+ // presence in nammgr before using the binder cos there's
+ // no certainty that name has been entered into nammgr yet.
+ // If it hasn't the binder will create the entry.
+ //
+ // Look for the name in the project-level binder.
+ IfErrRet(pnammgr->HlnamOfStr(szName, &hlnam, FALSE, &fChanged));
+ IfErrRet(GetTypeBind());
+
+ ibinddesc =m_gptbind.Pgbindnametbl()->IndexOfHlnam(hlnam);
+ if (ibinddesc != BIND_INVALID_INDEX) {
+ // Setup output param -- must copy since can't return pointer
+ // to movable memory.
+ //
+ *pprojbinddesc = *(m_gptbind.Pgbindnametbl()->
+ QgpbinddescOfIndex(ibinddesc));
+
+ return TIPERR_None;
+ }
+ return TIPERR_ElementNotFound;
+}
+#pragma code_seg( )
+
+
+
+
+/***
+*PUBLIC GenericTypeLibOLE::GetIndexOfName
+*Purpose:
+* Return the Hte of the TYPEENTRY containing the specified name.
+*
+*Entry:
+* szName - name to search for
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR GenericTypeLibOLE::GetIndexOfName(LPSTR szName, WORD *pw)
+{
+ GENPROJ_BIND_DESC binddesc;
+ TIPERROR err;
+
+ err = GetBinddescOfSzName(szName, &binddesc);
+
+
+ if (err != TIPERR_None) {
+ return err;
+ }
+
+ // Make sure we have a module (and not e.g. a ref'ed typelib/proj)
+ if (binddesc.IsTypeInfo()) {
+ *pw = (WORD)binddesc.Ordinal();
+ return TIPERR_None;
+ }
+ else {
+ return TIPERR_ElementNotFound;
+ }
+}
+#pragma code_seg( )
+
+
+
+
+
+/***
+*PROTECTED GenericTypeLibOLE::GetStorage - Get the IStorage for this typelib
+*Purpose:
+* Open or create the IStorage for this typelib, given the current
+* LibId.
+*
+*Entry:
+* stgm - The mode in which the IStorage should be opened.
+*
+*Exit:
+* If ppstg is NULL, then m_pstg is set to the desired IStorage, and
+* m_pstgContainer is set to its container storage if there is one (or
+* NULL if not).
+*
+* If ppstg is not NULL, the *ppstg is set to the desired storage and
+* there must not be a container storage.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR GenericTypeLibOLE::GetStorage(DWORD stgm, IStorageA **ppstg)
+{
+
+ // If compiling for typelib.dll, the IStorage is guaranteed to
+ // be a stand-alone docfile or dll-embedded docfile. Open it.
+ HRESULT hresult;
+ IStorageA *pstg;
+#if !OE_MACPPC
+ IStorageA *pstgSub;
+ GUID guid;
+#endif // OE_MACPPC
+ ILockBytesA *plockbytes;
+
+ m_bmData.Lock();
+
+ if (stgm & STGM_CREATE) {
+ IfOleErrGo(OpenFileLockBytes(TRUE, QszLibIdOrFile(), &plockbytes));
+ hresult = GTLibStorage::Create(plockbytes, m_cTypeEntries+2, &pstg);
+ plockbytes->Release();
+ if (hresult != NOERROR)
+ goto Error;
+ }
+ else {
+ // first try to open this as a stand-alone type library. Reasons
+ // for doing this first instead of the DLL lookup are:
+ // (a) More likely to be stand-alone file than embedded as a resource,
+ // so it will require less disk hits.
+ // (b) LoadLibrary has an annoying habbit of sometimes putting up
+ // a dialog if it can't find the file.
+ // (c) We are better able to control the search semantics by not
+ // even attempting to load the file as a DLL if can't load it
+ // as a standard file.
+ // (d) LoadLibary prints a (benign) message that it failed when
+ // running under debug Windows.
+ hresult = OpenFileLockBytes(FALSE, QszLibIdOrFile(), &plockbytes);
+ if (hresult == NOERROR) {
+ // only continue if we found the file & were able to open it ok.
+ // now check the signature, etc, to see if it's really a stand-alone
+ // type libary. In the case of trying to load a DLL/EXE, this check
+ // will fail.
+ hresult = GTLibStorage::OpenForReadOnly(plockbytes, &pstg);
+ plockbytes->Release();
+#if 0
+#if !OE_MAC
+ if (hresult != NOERROR) {
+ // most likely failed the signature check -- try it again as a DLL
+
+ // Ignore the error code if attempt to load it as a DLL fails, since
+ // DLL load errors are somewhat bogus. We're better off reporting
+ // the signature check error (TYPE_E_INVDATAREAD) that we got above.
+ if (DllResourceLockBytes::Open(QszLibIdOrFile(), &plockbytes) != NOERROR) {
+ goto Error;
+ }
+ hresult = GTLibStorage::OpenForReadOnly(plockbytes, &pstg);
+ plockbytes->Release();
+ }
+#endif
+#endif //!OE_MAC
+ }
+
+ if (hresult != NOERROR)
+ goto Error;
+
+// UNDONE: PPC: [jimcool]: Temp, remove Docfile dependency (1-29-94)
+#if !OE_MACPPC
+ // If we did successfully open the docfile, check the GUID of the
+ // object stored in it.
+
+ hresult = ReadClassStg(pstg, &guid);
+ if (hresult != NOERROR)
+ goto Error2;
+
+ // If the object stored in the docfile is not a typelib, look for
+ // a substorage named '\6TYPELIB'.
+ if (guid != CLSID_GenericTypeLibOLE) {
+ hresult = pstg->OpenStorage(OLESTR("\006TypeLib"),
+ NULL, stgm, NULL, 0L, &pstgSub);
+ if (hresult != NOERROR)
+ goto Error2;
+
+ // If we found a \6TypeLib substorage, verify it contains a typelib.
+ hresult = ReadClassStg(pstg, &guid);
+ if (hresult != NOERROR) {
+ pstgSub->Release();
+ goto Error2;
+ }
+ DebAssert(guid == CLSID_GenericTypeLibOLE, "");
+
+ // If the substorage contains a typelib, store the docfile IStorage
+ // away so we can close it later.
+ m_pstgContainer = pstg;
+ pstg = pstgSub;
+
+ DebAssert(ppstg == NULL, "GetStorage");
+ }
+#endif // OE_MACPPC
+ }
+
+ m_bmData.Unlock();
+ if (ppstg == NULL)
+ m_pstg = pstg;
+ else
+ *ppstg = pstg;
+ return TiperrOfHresult(hresult);
+
+#if !OE_MACPPC
+Error2:
+#endif // OE_MACPPC
+ pstg->Release();
+
+Error:
+ m_bmData.Unlock();
+ return TiperrOfHresult(hresult);
+
+}
+#pragma code_seg()
+
+
+/***
+*PROTECTED GenericTypeLibOLE::Read - read GenericTypeLibOLE directory
+*Purpose:
+* Deserialize the directory.
+* Note that this function just opens the directory stream and
+* calls the (possibly overridden) function Read(STREAM).
+*
+*Entry:
+* none
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR GenericTypeLibOLE::Read()
+{
+ STREAM *pstrm;
+ TIPERROR err;
+
+ BOOL wasStgOpen = (m_pstg != NULL);
+
+ IfErrRet(OpenTypeStream((UINT)-1, SOM_Read, &pstrm));
+ err = Read(pstrm);
+
+ // In ole build only, if this call to read actually opened the
+ // typelib's file, make sure the file isn't closed until the typelib
+ // itself is actually released.
+ if (!wasStgOpen)
+ m_pstg->AddRef();
+
+ pstrm->Release();
+
+ return err;
+}
+#pragma code_seg()
+
+
+/***
+*PROTECTED GenericTypeLibOLE::ReadNameCacheArray - read in NAME_CACHE array.
+*Purpose:
+* Deserialize the NAME_CACHE is there is one.
+*
+*Entry:
+* none
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+#pragma code_seg( CS_CORE2 )
+TIPERROR GenericTypeLibOLE::ReadNameCacheArray()
+{
+ STREAM *pstrm;
+ USHORT hasValidDiskImageNameCache;
+ TIPERROR err;
+
+ // Test if library has been deserialized --
+ // if not, no cache to read.
+ //
+ if (m_lPosRgnamcache == -1)
+ return TIPERR_None;
+
+ // Otherwise open the stream.
+ IfErrRet(OpenTypeStream((UINT)-1, SOM_Read, &pstrm));
+
+ // And seek to where the namcache should be.
+ IfErrGoTo(pstrm->SetPos(m_lPosRgnamcache), Error2);
+
+ // First determine if there is in fact a serialized NAME_CACHE.
+ IfErrGoTo(pstrm->Read(&hasValidDiskImageNameCache,
+ sizeof(hasValidDiskImageNameCache)),
+ Error2);
+ m_hasValidDiskImageNameCache = (USHORT)hasValidDiskImageNameCache;
+
+ // Then read it in... if there is one.
+ if (m_hasValidDiskImageNameCache) {
+ if (!m_bdRgnamcache.IsValid()) {
+ IfErrGoTo(m_bdRgnamcache.Init(Psheapmgr(), 0), Error2);
+ }
+ IfErrGoTo(m_bdRgnamcache.Read(pstrm), Error3);;
+ }
+
+ pstrm->Release();
+ return TIPERR_None;
+
+Error3:
+ m_bdRgnamcache.Free();
+ // fall through...
+
+Error2:
+ pstrm->Release();
+ return err;
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC GenericTypeLibOLE::AddNameToCache
+*Purpose:
+* Adds given name to a given cache.
+* If not loaded, loads and validates the NAME_CACHE array.
+* Updates both given type's cache and project's cache.
+*
+*Entry:
+* inamcache index of TYPEINFO in library + 1 (IN)
+* hgnam Global name handle to add (IN).
+*
+*Exit:
+* TIPERROR
+* Updated NAME_CACHE array.
+*
+***********************************************************************/
+TIPERROR GenericTypeLibOLE::AddNameToCache(UINT inamcache, HGNAM hgnam)
+{
+ TIPERROR err;
+
+ DebAssert(inamcache < m_cTypeEntries, "bad type index.");
+
+ IfErrRet(LoadNameCache());
+
+ // add name to type's cache
+ Rgnamcache()[inamcache].AddNameToCache(hgnam);
+
+ return TIPERR_None;
+}
+
+
+/***
+*PUBLIC GenericTypeLibOLE::LoadNameCache
+*Purpose:
+* Loads/Inits namecache array by either deserializing or
+* creating a new one.
+* If not loaded, loads and validates the NAME_CACHE array.
+*
+*Entry:
+*
+*Exit:
+* TIPERROR
+* Updated NAME_CACHE array.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR GenericTypeLibOLE::LoadNameCache()
+{
+ UINT inamcacheCur;
+ BOOL hasLibChanged = FALSE;
+ TIPERROR err = TIPERR_None;
+
+ // If it hasn't been loaded or created yet...
+ if (m_bdRgnamcache.IsValid() == FALSE) {
+
+ // Then load in a serialized cache if there is one...
+ // This might create a valid cache in memory.
+ //
+ IfErrRet(ReadNameCacheArray());
+
+ if (m_bdRgnamcache.IsValid()) {
+ hasLibChanged = (m_bdRgnamcache.CbSize()/sizeof(NAME_CACHE)
+ != (USHORT)m_cTypeEntries);
+
+ if (hasLibChanged) {
+ // If the lib has changed since the cache was serialized
+ // then free it... it'll be initialized later as if there never
+ // was a cache.
+ //
+ m_bdRgnamcache.Free();
+ }
+ }
+
+ if (!m_bdRgnamcache.IsValid() || hasLibChanged) {
+ // If the lib has changed or there is no valid cache,
+ // then create a new initialized cache:
+ // one for each type and one for the project.
+ //
+ IfErrGo(m_bdRgnamcache.Init(Psheapmgr(),
+ m_cTypeEntries * sizeof(NAME_CACHE)));
+
+ // Iterate over the the array, invalidating the caches.
+ // NOTE: Invalidating a cache sets all its bits to zero
+ // and its state to invalid. It is still ok
+ // to set a bit in an invalid cache, the cache
+ // becomes valid if and when the last bit is set:
+ // For types this happens when the last name
+ // has been added to its binding table
+ // i.e. in DYN_TYPEMEMBERS::BuildBindNameTable().
+ // For the project this happens iff all of its
+ // type's caches are valid. This is detected
+ // likewise in DYN_TYPEMEMBERS::BuildBindNameTable().
+ // The point is that the validity of the cache
+ // only determines whether it can be relied upon
+ // for binding purposes.
+ //
+ for (inamcacheCur = 0;
+ inamcacheCur < m_cTypeEntries;
+ inamcacheCur++) {
+ // Treat array as namecache array.
+ // CONSIDER: using placement syntax to explicitly
+ // construct NAME_CACHEs -- ctor Invalidate()'s cache.
+ //
+ Rgnamcache()[inamcacheCur].Invalidate();
+ }
+ }
+ }
+ // else there's a loaded name cache array
+ // so just use it...
+ //
+ DebAssert(m_bdRgnamcache.IsValid(), "bad cache.");
+ DebAssert(m_bdRgnamcache.CbSize() % sizeof(NAME_CACHE) == 0,
+ "bad cache.");
+ DebAssert(m_bdRgnamcache.CbSize()/sizeof(NAME_CACHE) == (USHORT)m_cTypeEntries,
+ "bad cache.");
+
+ // fall through...
+
+Error:
+ return err;
+}
+#pragma code_seg( )
+
+
+/***
+*PROTECTED GenericTypeLibOLE::ReadString - read a string into m_bmData
+*Purpose:
+* Read in a word-length-prefixed string and allocate it in the data
+* block manager. If the 2-byte length is 0xffff, then don't even
+* allocate a zero-length string. Instead, just set *phsz to HCHUNK_Nil.
+*
+*Entry:
+* pstrm - The stream from which to read the string.
+*
+*Exit:
+* *phsz is set to refer to the allocated string in the block manager.
+*
+* TIPERROR
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR GenericTypeLibOLE::ReadString(STREAM *pstrm, HCHUNK *phsz)
+{
+ XSZ sz;
+ USHORT cb;
+ HCHUNK hsz;
+ TIPERROR err;
+
+ IfErrRet(pstrm->Read(&cb, sizeof(USHORT)));
+#if HP_BIGENDIAN
+ cb = SwapShort(cb);
+#endif
+
+ // If the length is ~0, just set *phsz to HCHUNK_Nil and return.
+ if (cb == (USHORT)~0) {
+ *phsz = HCHUNK_Nil;
+ return TIPERR_None;
+ }
+
+#if OE_WIN32
+ int cchUnicode;
+ LPOLESTR lpwstr = NULL;
+
+ // Translate Ansi strings to Unicode on-the-fly
+ sz = (XSZ)MemAlloc(cb+sizeof(XCHAR));
+ if (sz == NULL)
+ return TIPERR_OutOfMemory;
+
+ IfErrGo(pstrm->Read(sz, cb));
+ sz[cb++] = '\0'; // add the null-terminator
+
+ cchUnicode = MultiByteToWideChar(CP_ACP, 0, sz, cb, NULL, 0);
+ if (cchUnicode == 0)
+ return TIPERR_OutOfMemory;
+
+ IfErrGo(m_bmData.AllocChunk(&hsz, cchUnicode*sizeof(OLECHAR)));
+
+ m_bmData.Lock();
+ lpwstr = (LPOLESTR)QtrOfHChunk(hsz);
+ cchUnicode = MultiByteToWideChar(CP_ACP, 0, sz, cb, lpwstr, cchUnicode);
+ *phsz = hsz;
+ err = TIPERR_None;
+
+Error:
+ m_bmData.Unlock();
+ MemFree(sz);
+
+#else
+ // Allocate enough space for a zero-terminated string of that length.
+ IfErrRet(m_bmData.AllocChunk(&hsz, cb + sizeof(XCHAR)));
+
+ m_bmData.Lock();
+ sz = (XSZ)QtrOfHChunk(hsz);
+ IfErrGo(pstrm->Read(sz, cb));
+ sz[cb] = 0;
+ *phsz = hsz;
+ err = TIPERR_None;
+
+Error:;
+ m_bmData.Unlock();
+#endif
+
+ return err;
+}
+#pragma code_seg()
+
+/***
+*PROTECTED GenericTypeLibOLE::WriteString - write out a string.
+*Purpose:
+* Write out a string specified by an HSZ in the format:
+* 2 byte length
+* string without zero terminator
+*
+* If hsz is HCHUNK_Nil, write out 0xffff for the length
+* and don't write out any string bytes.
+*
+*Entry:
+* pstrm - The stream to which to write the string.
+* hsz - The string to write out.
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR GenericTypeLibOLE::WriteString(STREAM *pstrm, HCHUNK hsz)
+{
+ TIPERROR err;
+ USHORT cb;
+ XSZ qsz;
+
+ // If hsz is HCHUNK_Nil, just write out ~0 to indicate there is
+ // no string.
+ if (hsz == HCHUNK_Nil)
+ return pstrm->WriteUShort((USHORT)~0);
+
+ // Get the string and its length.
+#if OE_WIN32
+ // write Ansi strings for Win16, Mac compatibility
+
+ LPOLESTR lpwstr;
+ int cchUnicode;
+
+ qsz = NULL;
+
+ m_bmData.Lock();
+ lpwstr = (LPOLESTR)QtrOfHChunk(hsz);
+ cchUnicode = wcslen(lpwstr)+1;
+
+ cb = WideCharToMultiByte(CP_ACP, 0, lpwstr, cchUnicode, NULL, 0, NULL, NULL);
+ if (cb == 0)
+ IfErrGo(TIPERR_OutOfMemory);
+
+ qsz = (XSZ)MemAlloc(cb);
+ if (qsz == NULL)
+ IfErrGo(TIPERR_OutOfMemory);
+
+ WideCharToMultiByte(CP_ACP, 0, lpwstr, cchUnicode, qsz, cb, NULL, NULL);
+
+#else
+ m_bmData.Lock();
+ qsz = (XSZ)QtrOfHChunk(hsz);
+
+ cb = xstrblen(qsz);
+
+#endif
+
+ // Write out the length.
+ IfErrGo(pstrm->WriteUShort(cb));
+
+ // Write out the string.
+ err = pstrm->Write(qsz, cb);
+
+Error:
+ m_bmData.Unlock();
+#if OE_WIN32
+ MemFree(qsz);
+#endif
+ return err;
+}
+#pragma code_seg()
+
+/***
+*PROTECTED GenericTypeLibOLE::Read - read TypeLib directory
+*Purpose:
+* Read in GenericTypeLibOLE.
+* NOTE: that if this function fails, the TypeLib is left in an
+* indeterminate state and should be deleted.
+*
+*Entry:
+* pstrm
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR GenericTypeLibOLE::Read(STREAM *pstrm)
+{
+ UINT i;
+ ULONG dw;
+ HCHUNK hsz;
+ TIPERROR err;
+ HTENTRY hte;
+ USHORT usHlnam;
+ WORD w;
+ GUID guid;
+ BYTE *qbChunkStr;
+ HCHUNK hchunk;
+ USHORT usEncodedDocStrSize;
+
+
+// The first chunk of stuff written out in the typelib header
+#pragma pack(1)
+typedef struct tagCHUNK1 {
+ WORD wFirstWord;
+ WORD wVersion;
+ USHORT usHlnam;
+} CHUNK1;
+#pragma pack()
+#define CHUNK1_Layout "sss"
+
+// The second chunk of stuff written out in the typelib header.
+#pragma pack(1)
+typedef struct tagCHUNK2 {
+ ULONG dwHelpContext;
+ USHORT syskind;
+ LCID lcid;
+ USHORT usTmp;
+ USHORT wLibFlags;
+ USHORT wMajorVerNum;
+ USHORT wMinorVerNum;
+ GUID guid;
+ HTENTRY rghteBucket[GTLIBOLE_cBuckets];
+ USHORT cTypeEntries;
+} CHUNK2;
+#pragma pack()
+
+// Note: the 'chunk2' layout string only describes the struct up to,
+// but not including rghteBucket. Everything after must be swapped by hand.
+#define CHUNK2_Layout "lslssss" GUID_Layout
+
+ CHUNK1 chunk1;
+ CHUNK2 chunk2;
+
+
+ IfErrRet(pstrm->Read(&chunk1, sizeof(chunk1)));
+#if HP_BIGENDIAN
+ SwapStruct(&chunk1, CHUNK1_Layout);
+#endif
+
+ if(chunk1.wFirstWord != wFirstSerWord || DebErrorNow(TIPERR_InvDataRead))
+ return TIPERR_InvDataRead;
+ if(chunk1.wVersion > wMaxVersion
+ || DebErrorNow(TIPERR_UnsupFormat)) {
+
+ return TIPERR_UnsupFormat;
+ }
+
+ m_wCurVersion = chunk1.wVersion;
+
+ m_hlnamLib = (HLNAM)chunk1.usHlnam;
+
+ // Read in default TYPEINFO TypeId
+ IfErrRet(ReadString(pstrm, &m_hszDefaultTITypeId));
+
+ // Read in documentation string.
+ IfErrRet(ReadString(pstrm, &m_hszDocString));
+
+ // Read in helpfile name.
+ IfErrRet(ReadString(pstrm, &m_hszHelpFile));
+
+ IfErrRet(pstrm->Read(&chunk2, sizeof(chunk2)));
+#if HP_BIGENDIAN
+ SwapStruct(&chunk2, CHUNK2_Layout);
+ SwapShortArray(chunk2.rghteBucket, DIM(chunk2.rghteBucket));
+ chunk2.cTypeEntries = SwapShort(chunk2.cTypeEntries);
+#endif
+
+ m_dwHelpContext = chunk2.dwHelpContext;
+ m_lcid = chunk2.lcid;
+ m_wLibFlags = chunk2.wLibFlags;
+ m_lcidZero = (BOOL)chunk2.usTmp;
+ m_wMajorVerNum = chunk2.wMajorVerNum;
+ m_wMinorVerNum = chunk2.wMinorVerNum;
+ m_guid = chunk2.guid;
+ m_syskind = chunk2.syskind;
+ DebAssert(DIM(m_rghteBucket) == GTLIBOLE_cBuckets, "");
+ memcpy(m_rghteBucket, chunk2.rghteBucket, sizeof(m_rghteBucket));
+
+ IfErrRet(m_bdte.Realloc(chunk2.cTypeEntries * sizeof(TYPE_ENTRY)));
+
+ // Note that if we break out of this loop because of errors,
+ // m_cTypeEntries equals the number of entries which have been
+ // constructed and must be freed.
+
+ m_cTypeEntries = 0;
+ for (i = 0; i < chunk2.cTypeEntries; ++i) {
+ ::new (Qte(i)) TYPE_ENTRY;
+ m_cTypeEntries++;
+ IfErrRet(ReadString(pstrm, &hsz));
+ Qte(i)->m_ste.m_hszStrm = hsz;
+ IfErrRet(ReadString(pstrm, &hsz));
+ Qte(i)->m_ste.m_hszLocalTypeId = hsz;
+ IfErrRet(ReadString(pstrm, &hsz));
+ Qte(i)->m_ste.m_hszTypeInfoTypeId = hsz;
+ IfErrRet(pstrm->ReadUShort(&usHlnam));
+ Qte(i)->m_ste.m_hlnamType = (HLNAM) usHlnam;
+
+ // Read the size of the encoded doc string.
+ IfErrRet(pstrm->ReadUShort(&usEncodedDocStrSize));
+ Qte(i)->m_ste.m_usEncodedDocStrSize = usEncodedDocStrSize;
+
+ // Read the sting if there is one.
+ if (usEncodedDocStrSize > 0) {
+ // allocated space for the encoded string.
+ IfErrRet(m_bmData.AllocChunk(&hchunk, usEncodedDocStrSize));
+ qbChunkStr = m_bmData.QtrOfHandle(hchunk);
+ // Read the encoded doc string.
+ IfErrRet(pstrm->Read(qbChunkStr, usEncodedDocStrSize));
+ Qte(i)->m_ste.m_hszEncodedDocString = hchunk;
+ }
+ else
+ Qte(i)->m_ste.m_hszEncodedDocString = HCHUNK_Nil;
+ IfErrRet(ReadString(pstrm, &hsz));
+ Qte(i)->m_ste.m_hszHelpFile = hsz;
+ IfErrRet(pstrm->ReadULong(&dw));
+ Qte(i)->m_ste.m_dwHelpContext = dw;
+ IfErrRet(pstrm->ReadUShort(&hte));
+ Qte(i)->m_hteNext = hte;
+ IfErrRet(pstrm->Read(&guid, sizeof(guid)) );
+#if HP_BIGENDIAN
+ SwapStruct(&guid, GUID_Layout);
+#endif
+ Qte(i)->m_ste.m_guid = guid;
+ IfErrRet(pstrm->ReadUShort(&w));
+ Qte(i)->m_ste.m_typekind = w;
+ }
+
+ // Read the position of the nammgr. [we demand load it],
+ // we cache the stream position and use it later...
+ // Note that the namecache array immediately follows it...
+ // In addition note that the nammgr must be deserialized
+ // before (temporally and physically) the namecache array.
+ //
+ IfErrRet(pstrm->ReadULong((ULONG *)&m_lPosNammgr));
+
+ // At this point stream position is at the start of DOCSTR_MGR.
+ // We demand load the doc manager hence cache the position.
+ IfErrRet(pstrm->GetPos(&m_lPosDstrmgr));
+
+#if ID_DEBUG
+ // Store the typelib's name.
+ NAMMGR *pnammgr;
+ BSTRA bstrName;
+
+ if (GetNamMgr(&pnammgr) == TIPERR_None && m_hlnamLib != HLNAM_Nil) {
+ if (pnammgr->BstrOfHlnam(m_hlnamLib, &bstrName) == TIPERR_None) {
+ strncpy(m_szDebName, bstrName, DEBNAMESIZE - 1);
+ m_szDebName[DEBNAMESIZE - 1] = 0;
+ FreeBstrA(bstrName);
+ }
+ }
+#endif // ID_DEBUG
+
+ return NOERROR;
+}
+#pragma code_seg()
+
+/***
+*PUBLIC GenericTypeLibOLE::InvalidateNameCache
+*Purpose:
+* Invalidates a given module's namecache if there is a cache at all.
+* NOTE: DOES NOT invalidate project's cache.
+* Since the project's cache is at offset zero
+* in the cache array, clients must increment
+* their type index when calling this func.
+* Note it is ok to call this function with inamcache == 0 since
+* that refers to the project's cache.
+*
+*Entry:
+* inamcache index of TYPEINFO in library + 1.
+*
+*Exit:
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+VOID GenericTypeLibOLE::InvalidateNameCache(UINT inamcache)
+{
+ if (m_bdRgnamcache.IsValid()) {
+ DebAssert(inamcache <= m_cTypeEntries, "bad type index.");
+
+ // Invalidate i'th name cache
+ Rgnamcache()[inamcache].Invalidate();
+ }
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC GenericTypeLibOLE::QtrOfHChunk
+*Purpose:
+* Return the pointer to data contained in a given chunk of m_bmData.
+* If hv is HCHUNK_Nil returns NULL.
+*
+*Entry:
+* hv - hchunk of chunk containing the data.
+*
+*Exit:
+* returns a pointer into the chunk.
+* This pointer will be invalidated by heap movement.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+VOID *GenericTypeLibOLE::QtrOfHChunk(HCHUNK hv)
+{
+ return (hv == HCHUNK_Nil) ? NULL : m_bmData.QtrOfHandle(hv);
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GenericTypeLibOLE::QszLibIdOrFile
+*Purpose:
+* Return a pointer to the LibId string. This may point into
+* m_bmData, so don't hold onto it too long.
+*
+*Entry:
+* None
+*
+*Exit:
+* Returns a pointer into the chunk if the LibId is known.
+* Returns NULL if the LibId is not known.
+* This pointer may be invalidated by heap movement.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+LPOLESTR GenericTypeLibOLE::QszLibIdOrFile()
+{
+ return (m_hszFile == HCHUNK_Nil) ? NULL : (LPOLESTR)m_bmData.QtrOfHandle(m_hszFile);
+}
+#pragma code_seg()
+
+/***
+*PUBLIC GenericTypeLibOLE::QszOfHsz
+*Purpose:
+* Return the string contained in a given chunk of m_bmData
+* If hsz is HCHUNK_Nil returns an empty string
+*
+*Entry:
+* hsz - hchunk of chunk containing the string
+*
+*Exit:
+* returns a pointer into the chunk.
+* This pointer will be invalidated by heap movement.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+LPOLESTR GenericTypeLibOLE::QszOfHsz(HCHUNK hsz)
+{
+ return (hsz == HCHUNK_Nil) ? WIDE("") : (LPOLESTR)m_bmData.QtrOfHandle(hsz);
+}
+#pragma code_seg( )
+
+
+/***
+*PROTECTED GenericTypeLibOLE::GetQszTypeInfoTypeId
+*Purpose:
+* Function which returns an SZ containing the TYPEID of the TYPEINFO
+* of a Type stored in the ITypeLib.
+* Note that this returns an sz which may point in to a moveable heap.
+* It is a non-public function.
+*
+*Entry:
+* hte - handle for the TYPEENTRY whose TYPEINFO's TYPEID is to be
+* returned.
+*
+*Exit:
+* returns sz containing the TYPEID
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+LPOLESTR GenericTypeLibOLE::GetQszTypeInfoTypeId(HTENTRY hte)
+{
+ HCHUNK hsz;
+
+ hsz = Qte(hte)->m_ste.m_hszTypeInfoTypeId;
+ if (hsz != HCHUNK_Nil)
+ return QszOfHsz(hsz);
+ else if (m_hszDefaultTITypeId != HCHUNK_Nil)
+ return QszOfHsz(m_hszDefaultTITypeId);
+ else
+ // If no default was set then use GEN_DTINFO
+ return GEN_DTINFO::szProtocolName;
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC GenericTypeLibOLE::ReleaseResources
+*Purpose:
+* Release resources owned by proj-level binder.
+*
+*Implementation Notes:
+* Defers to binder.
+*
+*Entry:
+*
+*Exit:
+*
+*Errors:
+* None
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+VOID GenericTypeLibOLE::ReleaseResources()
+{
+ m_gptbind.ReleaseResources();
+}
+#pragma code_seg()
+
+/***
+*PUBLIC GenericTypeLibOLE::Add
+*Purpose:
+* Add a TYPEINFO to the GenericTypeLibOLE.
+* Note that this increments the reference count of the ITypeLib by
+* the number of references to the TYPEINFO so their reference
+* counts are in sync.
+* The reference count of the TYPEINFO is not changed and if the caller's
+* reference is the only one then the TYPEINFO will be deleted when
+* he releases his reference.
+* Add returns an error if there is a TypeInfo in the TypeLib whose
+* LocalTypeId matches the TypeId passed in regardless of what the
+* minor version number is.
+* There is no need to support having two TypeInfos whose TypeId's
+* differ only in their minor version number since the one with the
+* highest version number would always be the one that should be
+* retrieved from the TypeLib anyway.
+* Returns an error if the name of the TypeInfo being added matches the
+* name of a TypeInfo already in the library.
+*
+* NOTE: the namecache array is grown appropriately as well -- in addition
+* the project-level cache is invalidated. Note that
+* the namcache array must parallel the typeentry array.
+*
+*Entry:
+* pgdtinfo - pointer to GEN_DTINFO to be added
+* szName - name of the TYPEINFO being added
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR GenericTypeLibOLE::Add(GEN_DTINFO *pgdtinfo, LPOLESTR szName)
+{
+ HTENTRY hte;
+ TIPERROR err;
+#if OE_WIN32
+ LPSTR szNameA;
+
+ IfErrRet(TiperrOfHresult(ConvertStringToA(szName, &szNameA)));
+#else
+ #define szNameA szName
+#endif
+ // Add the new typeentry.
+ IfErrGoTo(AddTypeEntry(szNameA, pgdtinfo->SzTypeIdofTypeInfo(), &hte), ErrorRet);
+
+ // NOTE: any errors after this point must release the type entry
+
+ // Tell the TypeInfo about its container
+ pgdtinfo->SetContainingTypeLib(this);
+
+ // Assign the pointer to the TYPEINFO
+ Qte(hte)->m_pstltinfo = pgdtinfo;
+
+ // Tell the typeinfo its index in this typelib.
+ pgdtinfo->SetHTEntry(hte);
+
+ pgdtinfo->AddInternalRef();
+ pgdtinfo->m_isModified = TRUE;
+
+ SetTypeKind(hte, pgdtinfo->GetTypeKind());
+
+ // Add the name to the binding table
+ IfErrGo(GetTypeBind());
+ IfErrGo(m_gptbind.AddNameToTable(szNameA, hte, TRUE));
+
+ goto ErrorRet;
+
+Error:
+ UnAddTypeEntry(hte); // undo the AddTypeEntry
+
+ErrorRet:
+#if OE_WIN32
+ ConvertStringFree(szNameA);
+#else
+ #undef szNameA
+#endif
+ return err;
+}
+#pragma code_seg()
+
+/***
+*PUBLIC UpdateTypeId - Creates a new typeId for an existing typeinfo
+*Purpose:
+* This method creates a new TypeId for the specified typeinfo. It
+* is called whenever a change is made to a typeinfo that would prevent
+* code that is compiled against that typeinfo from working. In effect,
+* the typeinfo has become a new type and so needs a new typeId.
+*
+*Entry:
+* itype - The index (ite or hte) of the typeentry for the type.
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+#pragma code_seg(CS_LAYOUT)
+TIPERROR GenericTypeLibOLE::UpdateTypeId(UINT hteUpdate)
+{
+ LPOLESTR qszLocalTypeId;
+ HTENTRY *qhtePrev;
+ TYPE_ENTRY *qteUpdate;
+ int ihte;
+
+ DebAssert(hteUpdate != HTENTRY_Nil, "UpdateTypeId");
+
+ m_bmData.Lock();
+ qteUpdate = Qte(hteUpdate);
+ qszLocalTypeId = QszOfHsz(qteUpdate->m_ste.m_hszLocalTypeId);
+
+ // Remove hteUpdate from the hash table.
+ qhtePrev = QHteRef(hteUpdate);
+ *qhtePrev = qteUpdate->m_hteNext;
+
+ // Update the typeId in place (i.e. we don't have to change the
+ // allocated space for the typeId). We can do this because
+ // MakeLocalTypeId allocated enough space for the largest possible
+ // timestamp.
+ DebAssert(ostrlen(qszLocalTypeId) <= CCH_TIMESTAMP_LENGTH, "UpdateTypeId");
+ GetTimeStamp(qszLocalTypeId);
+
+ // Put the type entry back into the hash table, in the bucket list
+ // corresponding to the new typeId.
+ ihte = IhteHash(qszLocalTypeId);
+ m_bmData.Unlock();
+ qteUpdate->m_hteNext = m_rghteBucket[ihte];
+ m_rghteBucket[ihte] = hteUpdate;
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+/***
+*PROTECTED GenericTypeLibOLE::CreateHsz
+*Purpose:
+* Allocata a new chunk in m_mbData and copy an LPOLESTR into it
+*
+*Entry:
+* sz - contains to be copied to the new chunk
+* phchunk - returns a pointer to the newly allocated chunk
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR GenericTypeLibOLE::CreateHsz(LPOLESTR sz, HCHUNK *phchunk)
+{
+ UINT cb;
+ TIPERROR err;
+ HCHUNK hchunk;
+
+ cb = ostrblen(sz)*sizeof(OLECHAR);
+ IfErrRet( m_bmData.AllocChunk(&hchunk, cb+sizeof(OLECHAR)) );
+ ostrcpy((LPOLESTR)m_bmData.QtrOfHandle(hchunk), sz);
+ *phchunk = hchunk;
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+/***
+*PROTECTED GenericTypeLibOLE::MakeLocalTypeId
+*Purpose:
+* Create an hchunk containing the LocalTypeId by concatenating the
+* passed in minor version number and a separator character
+* on to the passed in TypeId.
+*
+*Entry:
+* None
+*
+*Exit:
+* pchunkTypeId - for returning the TypeId
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR GenericTypeLibOLE::MakeLocalTypeId(HCHUNK *phchunkTypeId)
+{
+ TIPERROR err;
+
+ // Allocate space for the timestamp (er, typeid).
+ IfErrRet(m_bmData.AllocChunk(phchunkTypeId, (CCH_TIMESTAMP_LENGTH+1)*sizeof(OLECHAR)));
+
+ // Get the new typeId into the allocated space.
+ m_bmData.Lock();
+ GetTimeStamp((LPOLESTR)m_bmData.QtrOfHandle(*phchunkTypeId));
+ m_bmData.Unlock();
+
+ return TIPERR_None;
+}
+#pragma code_seg( )
+
+
+
+/***
+*PROTECTED GenericTypeLibOLE::HteRef
+*Purpose:
+* Return a pointer to the reference of a given HTE.
+* Normally this will be a pointer to the m_hteNext field of
+* the TYPE_ENTRY which preceeds it in the bucket. If it is
+* the first entry in the bucket list then a pointer to
+* the head of the bucket list is returned.
+*
+*Entry:
+* ptinfo - pointer to TYPEINFO whose hte reference is returned
+*
+*Exit:
+* HTENTRY * - pointer to word that contains the passed in hte.
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+HTENTRY *GenericTypeLibOLE::QHteRef(HTENTRY hteSearch)
+{
+ HTENTRY *qhte;
+
+ m_bmData.Lock();
+
+ // Set qhte to point to the entry in the bucket array which
+ // is the head of the list that contains the TYPEENTRY whose
+ // handle was passed in.
+ qhte = m_rghteBucket +
+ IhteHash(QszOfHsz(Qte(hteSearch)->m_ste.m_hszLocalTypeId));
+
+ m_bmData.Unlock();
+
+ // Scan down the bucket list for the entry which preceeds
+ // the one we are looking for
+ while (*qhte != hteSearch) {
+ DebAssert(*qhte != HTENTRY_Nil, "HteRef: Entry Table messed up");
+
+ // set qhte to point to the hteNext field of the entry referenced
+ // by qhte
+ qhte = &(Qte(*qhte)->m_hteNext);
+ }
+ return qhte;
+}
+#pragma code_seg( )
+
+
+/***
+*PROTECTED GenericTypeLibOLE::Write - write GenericTypeLibOLE directory
+*Purpose:
+* Serialize GenericTypeLibOLE directory. Note that this function invokes
+* the (possibly overridden) Write(STREAM) function.
+*
+*Entry:
+* none
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR GenericTypeLibOLE::Write()
+{
+ STREAM *pstrm;
+ TIPERROR err, err2;
+
+ IfErrRet(OpenTypeStream((UINT)-1, SOM_Write, &pstrm));
+
+ if (!(err = Write(pstrm))) {
+ err = SetModified(FALSE);
+ }
+
+ err2 = pstrm->Release();
+ if (err == TIPERR_None)
+ err = err2;
+
+
+ return err;
+}
+#pragma code_seg()
+
+
+
+/***
+*PROTECTED GenericTypeLibOLE::Write - write GenericTypeLibOLE directory
+*Purpose:
+* Serialize GenericTypeLibOLE directory.
+*
+*Entry:
+* pstrm - stream to which GenericTypeLibOLE is written
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR GenericTypeLibOLE::Write(STREAM *pstrm)
+{
+ TIPERROR err;
+ USHORT hasValidDiskImageNameCache;
+ UINT i;
+ TYPE_ENTRY *pte;
+ LONG lNammgrPos = 0;
+ LONG lPosTmp = 0;
+ USHORT usTmp;
+ BYTE *qbChunkStr;
+
+ m_bmData.Lock();
+
+ // Write out identification byte and version number
+ IfErrGo( pstrm->WriteUShort(wFirstSerWord) );
+
+ IfErrGo( pstrm->WriteUShort(m_wCurVersion) );
+
+ // Write out hlnam of the typelib
+ IfErrGo( pstrm->WriteUShort(m_hlnamLib) );
+
+ // Write out default TYPEINFO TYPEID
+ IfErrGo(WriteString(pstrm, m_hszDefaultTITypeId));
+
+ // Write out documentation string.
+ IfErrGo( WriteString(pstrm, m_hszDocString) );
+
+ // Write out helpfile name.
+ IfErrGo( WriteString(pstrm, m_hszHelpFile) );
+
+ // Write out help context.
+ IfErrGo( pstrm->WriteULong(m_dwHelpContext) );
+
+ // Write out the platform for which this is compiled.
+ IfErrGo( pstrm->WriteUShort(m_syskind) );
+
+ // Write out the local code for this project
+ IfErrGo( pstrm->WriteULong(m_lcid) );
+ usTmp = (USHORT) m_lcidZero;
+ IfErrRet(pstrm->WriteUShort(usTmp));
+
+
+ // Write out the flags
+ IfErrGo( pstrm->WriteUShort(m_wLibFlags) );
+
+
+ // Write the version number of the project (GenericTypeLibOLE)
+ IfErrGo(pstrm->WriteUShort(m_wMajorVerNum));
+ IfErrGo(pstrm->WriteUShort(m_wMinorVerNum));
+
+#if HP_BIGENDIAN
+ // Before serializing GUID swap the bytes on Big-Endian machine
+ SwapStruct(&m_guid, GUID_Layout);
+#endif // !HP_BIGENDIAN
+
+ err = pstrm->Write(&m_guid, sizeof(GUID));
+
+#if HP_BIGENDIAN
+ // restore the guid structure even in case of error
+ SwapStruct(&m_guid, GUID_Layout);
+#endif // !HP_BIGENDIAN
+
+ IfErrGo(err);
+
+ // Swap the bucket entries.
+#if HP_BIGENDIAN
+ SwapShortArray(m_rghteBucket, sizeof(m_rghteBucket)/sizeof(HTENTRY));
+#endif
+
+ // Write out hash table
+ err = pstrm->Write(m_rghteBucket, sizeof(m_rghteBucket));
+
+ // swap back before handling the error.
+#if HP_BIGENDIAN
+ SwapShortArray(m_rghteBucket, sizeof(m_rghteBucket)/sizeof(HTENTRY));
+#endif
+
+ IfErrGo(err);
+
+ // Write out number of type entries then the type entry array
+ IfErrGo( pstrm->WriteUShort(m_cTypeEntries) );
+
+ for (i = 0; i < m_cTypeEntries; i++) {
+ pte = Qte(i);
+ IfErrGo( WriteString(pstrm, pte->m_ste.m_hszStrm) );
+ IfErrGo( pstrm->WriteUShort(CCH_TIMESTAMP_LENGTH) );
+#if OE_WIN32
+ CHAR szTemp[CCH_TIMESTAMP_LENGTH];
+ NoAssertRetail(WideCharToMultiByte(CP_ACP, 0,
+ QszOfHsz(pte->m_ste.m_hszLocalTypeId), CCH_TIMESTAMP_LENGTH,
+ szTemp, CCH_TIMESTAMP_LENGTH,
+ NULL, NULL), "Timestamp must only contain ANSI chars");
+ IfErrGo( pstrm->Write(szTemp, CCH_TIMESTAMP_LENGTH) );
+#else
+ IfErrGo( pstrm->Write(QszOfHsz(pte->m_ste.m_hszLocalTypeId), CCH_TIMESTAMP_LENGTH) );
+#endif
+ IfErrGo( WriteString(pstrm, pte->m_ste.m_hszTypeInfoTypeId) );
+ IfErrGo( pstrm->WriteUShort(pte->m_ste.m_hlnamType) );
+ // write out the string.
+ IfErrGo( pstrm->WriteUShort(pte->m_ste.m_usEncodedDocStrSize) );
+
+ // write out the string only if there is one.
+ if (pte->m_ste.m_usEncodedDocStrSize > 0) {
+ qbChunkStr = m_bmData.QtrOfHandle(pte->m_ste.m_hszEncodedDocString);
+
+ // Write the encoded doc string.
+ err = pstrm->Write(qbChunkStr, pte->m_ste.m_usEncodedDocStrSize);
+ }
+#if ID_DEBUG
+ else
+ DebAssert(pte->m_ste.m_hszEncodedDocString == HCHUNK_Nil, " should be nil");
+#endif
+
+ IfErrGo( WriteString(pstrm, pte->m_ste.m_hszHelpFile) );
+ IfErrGo( pstrm->WriteULong(pte->m_ste.m_dwHelpContext) );
+ IfErrGo( pstrm->WriteUShort(pte->m_hteNext) );
+
+#if HP_BIGENDIAN
+ // Before serializing GUID swap the bytes on Big-Endian machine
+ SwapStruct(&pte->m_ste.m_guid, GUID_Layout);
+#endif // !HP_BIGENDIAN
+
+ err = pstrm->Write(&pte->m_ste.m_guid, sizeof(GUID));
+
+#if HP_BIGENDIAN
+ // restore the guid structure even in case of error
+ SwapStruct(&pte->m_ste.m_guid, GUID_Layout);
+#endif // !HP_BIGENDIAN
+
+ IfErrGo( pstrm->WriteUShort(pte->m_ste.m_typekind) );
+
+ IfErrGo(err);
+
+ }
+
+ // Get the position so that we can seek back and write the position
+ // of the nammgr.
+ IfErrGo(pstrm->GetPos(&lPosTmp));
+
+ // Write out 0 temporarily. Latter we will write the serialized
+ // position of the Nammgr.
+ IfErrGo(pstrm->WriteULong(lNammgrPos));
+
+ // Write out embedded doc string manager
+ IfErrGo(m_dstrmgr.Write(pstrm));
+
+ // save the current position (this is the position where the nammgr
+ // will be read from.
+ IfErrGo(pstrm->GetPos(&lNammgrPos));
+
+ // Go back and write the position of the nammgr.
+ IfErrGo(pstrm->SetPos(lPosTmp));
+ IfErrGo(pstrm->WriteULong(lNammgrPos));
+ // reset the position
+ IfErrGo(pstrm->SetPos(lNammgrPos));
+
+ // Write out embedded proj-level nammgr.
+ IfErrGo(m_nammgr.Write(pstrm));
+
+ // Write out embedded proj-level typebind.
+ IfErrGo(m_gptbind.Write(pstrm));
+
+ // Finally write out the Rgnamcache if there is one.
+ // Note that we always write a single flag byte indicating
+ // whether in fact a valid array follows.
+ // WARNING: GenericTypeLibOLE::Read() assumes that this array
+ // is the last element in its serialization stream.
+ //
+ hasValidDiskImageNameCache = (USHORT)m_bdRgnamcache.IsValid();
+ IfErrGo(pstrm->Write(&hasValidDiskImageNameCache,
+ sizeof(hasValidDiskImageNameCache)));
+ if (hasValidDiskImageNameCache) {
+ IfErrGo(m_bdRgnamcache.Write(pstrm));
+ }
+
+ // Set this to -1 to indicate that we no longer know or care about
+ // serialization offset of the name cache (if it was blown away
+ // before the write, it wasn't written, so we shouldn't try to
+ // load it. If it exists when it's written, we don't need to load it).
+ m_lPosRgnamcache = -1;
+
+ // fall through...
+
+Error:
+ m_bmData.Unlock();
+ return err;
+}
+#pragma code_seg()
+
+
+
+
+/***
+*PUBLIC GenericTypeLibOLE::SaveOrCopyChanges
+*Purpose:
+* Write the typelib to the specified IStorage. shouldCopy determines
+* whether or not the "dirty" state of the typelib is preserved.
+*
+*Entry:
+* pstg - The IStorage to which the typelib should be saved.
+* The caller is expected to release pstg -- this method
+* does not assume ownership.
+* shouldCopy - If TRUE, then the "dirty" state is preserved. Otherwise,
+* the typelib's dirty state is set to clean.
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR GenericTypeLibOLE::SaveOrCopyChanges(IStorageA *pstg, BOOL shouldCopy)
+{
+ UINT i;
+ TIPERROR err;
+ STL_TYPEINFO *pstltinfo;
+ ITypeCompA *ptcompLib;
+
+ // In the non-OB case, we ensure that the typelib-level
+ // binding tables have been built so that they will get
+ // serialized, to do so we just get the typelib's ITypeComp,
+ // which immediately release since we're just interested in
+ // the side-effects of getting it.
+ //
+ IfErrRet(TiperrOfHresult(GetTypeComp(&ptcompLib)));
+ ptcompLib->Release();
+
+ // If we currently have an open IStorage, close it.
+ if (m_pstg != NULL) {
+ m_pstg->Release();
+ }
+
+ m_pstg = pstg;
+
+ // WARNING: all errors paths after this point must NULL out m_pstg.
+
+ // Write out each of the dirty typeinfos. If we're copying,
+ // all of the typeinfo's are written, regardless of the dirty flag.
+ for (i = 0; i < m_cTypeEntries; i++) {
+ pstltinfo = Qte(i)->m_pstltinfo;
+
+ // If we have the dispinterface protion of a dual interface,
+ // save the interface portion instead.
+ //
+ if (pstltinfo->PstltiPartner() != NULL) {
+ pstltinfo = pstltinfo->PstltiPartner();
+ }
+
+ if (pstltinfo != NULL) {
+ if (pstltinfo->IsModified()) {
+ err = pstltinfo->Write();
+ if (err)
+ goto Error;
+ }
+ }
+ }
+
+ // Write out the directory.
+ IfErrGo( Write() );
+
+
+ // Mark the IStorage of the OLE typelib with the GUID of the
+ // typelib implementation.
+
+ err = TiperrOfHresult(WriteClassStg((IStorage *)m_pstg,
+ CLSID_GenericTypeLibOLE));
+
+ // Also mark the IStorage with the TYPELIB format.
+ // VBA2: We may eventually need to define a real clipboard format
+ // constant for a typelib. Right now, we just use a random one
+ // that WriteFmtUserTypeStg doesn't complain about.
+ if (err == TIPERR_None) {
+
+ err = TiperrOfHresult(WriteFmtUserTypeStgA(m_pstg,
+ 0x200,
+ OLESTR("TYPELIB")));
+
+ }
+
+
+Error:
+ m_pstg = NULL;
+
+
+ return err;
+}
+#pragma code_seg()
+
+
+#if OE_MAC
+
+#pragma code_seg(CS_CREATE)
+
+#if OE_MAC68K
+inline long LMGetCurDirStore() { return (*((long*)0x398)); };
+inline void LMSetCurDirStore(const long l) { *((long*)0x398)=l; };
+inline short LMGetSFSaveDisk() { return (*((short*)0x214)); };
+inline void LMSetSFSaveDisk(const short s) { *((short*)0x214)=s; };
+#endif
+#define MAX_PAS_STRLEN 255
+#define MAX_FILENAME_LEN 32
+
+/***
+* PRIVATE GetFSSpecOfPartialPath
+*Purpose:
+* Creates an FSSpec from a full or partially specified path.
+*
+* This is similar in function to GetPathname() + GetFSSpecOfAliasPath except
+* it's faster than either one of those.
+*
+*Entry:
+* pszFileName = Full or partial path
+* pfspec = pointer to completed FSSpec.
+* fResolveFileAliases = Indicates whether or not file aliases are to be resolved.
+* (Aliases along the path are always resolved, but not necc. the teminal file/folder)
+*
+* Note: Currently limited to 256 character strings.
+*
+*Exit:
+* result code signifies error
+*
+* For RTScript, the 90% cases will either error out up top (script > 32 chars, no ':'),
+* or not require a call to GetPathFromFSSpec().
+*
+*Exceptions:
+*
+***********************************************************************/
+TIPERROR GetFSSpecOfPartialPath(char *pszFileName, FSSpec* pfspec, BOOL fResolveFileAliases)
+{
+ char* pColn;
+ short sLen;
+ OSErr ec;
+ TIPERROR err;
+ BOOL fAliasSeen;
+ char pchPathname[MAX_PAS_STRLEN+1];
+
+ // If filename is > 32chars, it must have at least 1 ':'
+ // or we can say it isn't a file right now.
+ sLen = strlen(pszFileName);
+ pColn= strchr(pszFileName,':');
+ if (!sLen || ((sLen > MAX_FILENAME_LEN) && !pColn) ) {
+ return TiperrOfOSErr(fnfErr);
+ }
+
+ // Convert to Pascal String:
+ memcpy(pchPathname+1, pszFileName, sLen);
+ pchPathname[0]=(char)(sLen & 0xFF);
+
+ // Get Current directory for partial path & file resolution:
+ ec = FSMakeFSSpec(-LMGetSFSaveDisk(), LMGetCurDirStore(), (unsigned char*)pchPathname, pfspec);
+ err = TiperrOfOSErr(ec);
+
+ // If an error, it means one of two things:
+ // 1) we couldn't find the file,
+ // or 2) the path contains aliases.
+ if (ec == fnfErr) {
+ pColn = (char*)memchr(pchPathname+1,':',*pchPathname);
+ if (pColn) {
+ // UNDONE MAC: We're looking at an alias in the path.
+ // For now I do something rude: convert the FSSpec back to a full path, and then
+ // call GetFSSpecOfAliasPath. This works, and this is an uncommon case, so it's not
+ // too critical. If it wasn't 1:00 AM, I'd probably move portions of GetFSSpecOfAliasPath
+ // into here & do it right.
+ err = GetPathFromFSSpec(pfspec, pchPathname, MAX_PAS_STRLEN);
+ if (err == TIPERR_None) {
+ err = GetFSSpecOfAliasPath(pchPathname, pfspec, &fAliasSeen, &pColn, fResolveFileAliases);
+ }
+ }
+ }
+
+ return err;
+}
+
+#define TYPE_TYPELIB 'OTLB'
+#define TYPE_NULL ' '
+#define CREATOR_TYPELIB 'Ole2'
+
+/***
+ * FSetMacFileType - set MAC file type in resource fork
+ *
+ * Purpose:
+ * Set the file type field in the file resource fork to OTLB (for typelibs)
+ *
+ * Entry:
+ * pchPath - path to file
+ *
+ * Exit:
+ * Return FALSE if error setting fields.
+ *
+ * Exceptions:
+ ***********************************************************************/
+
+BOOL FSetMacFileType(CHAR * pchPath)
+{
+ OSErr oserr;
+ FSSpec fspec;
+ FInfo fndrInfo;
+
+
+ // Get FSSpec (resolve aliases in path but not file):
+ if (GetFSSpecOfPartialPath(pchPath, &fspec, FALSE) != NOERROR)
+ return FALSE;
+
+ // Get FInfo:
+ if ((oserr = FSpGetFInfo(&fspec, &fndrInfo)) != noErr)
+ return FALSE;
+
+#if 0
+ // determine if creator is to be set
+ if (fndrInfo.fdCreator == TYPE_NULL)
+#endif //0
+ fndrInfo.fdCreator = CREATOR_TYPELIB;
+
+ // set the file type
+ fndrInfo.fdType = TYPE_TYPELIB;
+
+ // Set File Info:
+ if ((oserr = FSpSetFInfo(&fspec, &fndrInfo)) != noErr)
+ return FALSE;
+
+ // Flush Vol info so Finder will pick up changes:
+ if ((oserr = FlushVol(NULL, fspec.vRefNum)) != noErr)
+ return FALSE;
+
+ return TRUE;
+}
+#pragma code_seg()
+#endif //EI_OLE && OE_MAC
+
+/***
+*PUBLIC GenericTypeLibOLE::SaveAllChanges
+*Purpose:
+* Save all TypeInfo's in the library which have been modified
+* (or added to the library) without being saved.
+*
+*Entry:
+* None
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE )
+HRESULT GenericTypeLibOLE::SaveAllChanges()
+{
+ IStorageA *pstg;
+ HRESULT hresult;
+ TIPERROR err;
+ UINT i, uLen;
+ GEN_DTINFO *pgdtinfo;
+ LPSTR lpstr;
+ BYTE *qbChunkStr;
+ HCHUNK hchunk;
+
+
+ // Tell the DocStr_Mgr to process all the doc strings.
+ IfErrRetHresult(m_dstrmgr.ProcessDocStrings());
+
+ // Inform all the TYPE_ENTRIES to update the doc strings.
+ //
+ // Walk all the type entries
+ for (i = 0; i < m_cTypeEntries; i++) {
+ pgdtinfo = (GEN_DTINFO *) Qte(i)->m_pstltinfo;
+ DebAssert(pgdtinfo != NULL, " all typeinfo's should be loaded ");
+
+ // If we have the dispinterface portion of a dual interface,
+ // get the interface.
+ //
+ if (pgdtinfo->IsDualDispinterface()) {
+ pgdtinfo = pgdtinfo->PgdtinfoPartner();
+ }
+
+ IfErrRetHresult(
+ pgdtinfo->Pdtroot()->Pdtmbrs()->Ptdata()->UpdateDocStrings());
+
+ // Save the encoded doc string for each TYPE ENTRY also.
+ //
+ if (Qte(i)->m_ste.m_hszEncodedDocString != HCHUNK_Nil) {
+ // ask the doc str manager for the encoded string.
+ IfErrRetHresult(
+ m_dstrmgr.GetEncodedDocStrOfHst(Qte(i)->m_ste.m_hszEncodedDocString,
+ &lpstr,
+ &uLen));
+ DebAssert(lpstr != NULL, "");
+
+ // save the encoded string in the blkmgr.
+ err = m_bmData.AllocChunk(&hchunk, uLen);
+
+ if (err != TIPERR_None) {
+ MemFree(lpstr);
+ return HresultOfTiperr(err);
+ }
+
+ qbChunkStr = m_bmData.QtrOfHandle(hchunk);
+ memcpy(qbChunkStr, lpstr, uLen);
+ // save the size of the encode doc sting
+ Qte(i)->m_ste.m_usEncodedDocStrSize = uLen;
+
+ Qte(i)->m_ste.m_hszEncodedDocString = hchunk;
+
+ // Free the clients memory
+ MemFree(lpstr);
+ } // if
+ } // for loop
+
+ IfErrRetHresult(GetStorage(STGM_READWRITE | STGM_SHARE_EXCLUSIVE | STGM_CREATE, &pstg));
+ hresult = SaveAllChanges(pstg);
+ if (hresult == NOERROR)
+ hresult = pstg->Commit(0L);
+ if (hresult != NOERROR) {
+#if OE_WIN32
+ LPSTR szFileA;
+
+ IfErrRetHresult(ConvertStringToA(QszOfHsz(m_hszFile), &szFileA));
+ remove(szFileA);
+ ConvertStringFree(szFileA);
+#else
+ remove(QszOfHsz(m_hszFile)); // kill off partial file
+#endif
+ }
+ pstg->Release();
+
+#if OE_MAC
+ if (hresult == NOERROR) {
+ // Now that the file is closed, set the file type of this typelib to OTLB.
+ // Ignore any errors, since we don't want the failure of this routine to
+ // keep us from getting our valid typelib.
+ FSetMacFileType(QszOfHsz(m_hszFile));
+ }
+#endif //OE_MAC
+
+ return hresult;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GenericTypeLibOLE::SaveAllChanges
+*Purpose:
+* Save all TypeInfo's in the library which have been modified
+* (or added to the library) without being saved.
+*
+*Entry:
+* pstg - The IStorage to which the typelib should be saved.
+* The caller is expected to release pstg -- this method
+* does not assume ownership.
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+HRESULT GenericTypeLibOLE::SaveAllChanges(IStorageA *pstg)
+{
+ return HresultOfTiperr(SaveOrCopyChanges(pstg, FALSE));
+
+
+}
+#pragma code_seg()
+
+
+/***
+*PROTECTED GenericTypeLibOLE::ResetHsz
+*Purpose:
+* Allocate a new chunk in m_mbData and copy an LPSTR into it
+*
+*Entry:
+* sz - contains to be copied to the new chunk
+* phchunk - returns a pointer to the newly allocated chunk
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR GenericTypeLibOLE::ResetHsz(LPOLESTR sz, HCHUNK *phchunk)
+{
+ TIPERROR err;
+ HCHUNK hchunkSave;
+
+ IfErrRet(SetModified(TRUE));
+ m_fDirModified = TRUE;
+
+ hchunkSave = *phchunk;
+
+ IfErrRet(CreateHsz(sz, phchunk));
+
+ // Release the old chunk
+ if (hchunkSave != HCHUNK_Nil)
+ DeleteHsz(hchunkSave);
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC GenericTypeLibOLE::SetTypeDocString
+*Purpose:
+* Set the documentation string of the ith TypeInfo.
+*
+*Entry:
+* i - index of TypeInfo to be changed
+* szDocString - new docstring.
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+TIPERROR GenericTypeLibOLE::SetTypeDocString(UINT i, LPOLESTR szDocString)
+{
+ TIPERROR err;
+
+ DOCSTR_MGR *pdstrmgr;
+
+ IfErrRet(GetDstrMgr(&pdstrmgr));
+
+ // get the handle for the help string.
+ // Note:- This is a temporary handle. This handle is replaced
+ // when we do SaveAllChanges. We update this handle by a handle to
+ // the encoded string.
+ //
+#if OE_WIN32
+ LPSTR lpstrA;
+
+ IfErrRet(TiperrOfHresult(ConvertStringToA(szDocString, &lpstrA)));
+ err = pdstrmgr->GetHstOfHelpString(lpstrA, &(Qte(i)->m_ste.m_hszEncodedDocString));
+ ConvertStringFree(lpstrA);
+ IfErrRet(err);
+#else
+ IfErrRet(pdstrmgr->GetHstOfHelpString(szDocString,
+ &(Qte(i)->m_ste.m_hszEncodedDocString)));
+#endif //OE_WIN32
+
+
+ return err;
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC GenericTypeLibOLE::SetTypeHelpContext
+*Purpose:
+* Set the help context of the ith TypeInfo.
+*
+*Entry:
+* i - index of TypeInfo to be changed
+* dwHelpContext - The new help context.
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+TIPERROR GenericTypeLibOLE::SetTypeHelpContext(UINT i, DWORD dwHelpContext)
+{
+
+ Qte(i)->m_ste.m_dwHelpContext = dwHelpContext;
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC GenericTypeLibOLE::SetVersion
+*Purpose:
+* Set the version number associated with the TypeLib
+*
+*Entry:
+* wMajorVerNum - The major version number.
+* wMinorVerNum - The minor version number.
+*
+*Exit:
+* HRESULT
+*
+***********************************************************************/
+
+HRESULT GenericTypeLibOLE::SetVersion(WORD wMajorVerNum, WORD wMinorVerNum)
+{
+ m_wMajorVerNum = wMajorVerNum;
+ m_wMinorVerNum = wMinorVerNum;
+
+ return NOERROR;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC GenericTypeLibOLE::SetName
+*Purpose:
+* Set the name associated with the TypeLib
+*
+*Entry:
+* szName - the name
+*
+*Exit:
+* HRESULT
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+HRESULT GenericTypeLibOLE::SetName(LPOLESTR szNameW)
+{
+ TIPERROR err = TIPERR_None;
+ NAMMGR *pnammgr;
+ HLNAM hlnamOld = m_hlnamLib;
+#if OE_WIN32
+ LPSTR szName;
+#else
+ #define szName szNameW
+#endif
+
+ IfErrRetHresult(GetNamMgr(&pnammgr));
+
+#if OE_WIN32
+ // convert the name to Ansi
+ IfErrRet(ConvertStringToA(szNameW, &szName));
+#endif
+ IfErrGo(pnammgr->HlnamOfStr(szName, &m_hlnamLib, TRUE, NULL));
+
+
+#if OE_WIN32
+ ConvertStringFree(szName);
+#endif // OE_WIN32
+
+ return NOERROR;
+
+Error:
+ // Restore original name.
+ m_hlnamLib = hlnamOld;
+#if OE_WIN32
+ ConvertStringFree(szName);
+#else //OE_WIN32
+ #undef szName
+#endif //OE_WIn32
+ return HresultOfTiperr(err);
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC GenericTypeLibOLE::SetGuid
+*Purpose:
+* Set the guid associated with the TypeLib
+*
+*Entry:
+* guid - the guid
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+HRESULT GenericTypeLibOLE::SetGuid(REFGUID guid)
+{
+ m_guid = guid;
+ return NOERROR;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC TIPERROR GenericTypeLibOLE::SetModified
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR GenericTypeLibOLE::SetModified(BOOL isModified)
+{
+ TIPERROR err = TIPERR_None;
+
+ // If the modified state is already correct, don't bother with it.
+ if (isModified == m_isModified)
+ return TIPERR_None;
+
+ // If we are clearing the modified flag, it means we've just saved all
+ // changes or decided to trash all changes. In either case, the
+ // directory mod flag should be cleared. On the other hand, we don't
+ // want to set the directory mod flag just because some contained
+ // typeinfo changed.
+ if (!isModified) {
+ m_fDirModified = FALSE;
+
+ }
+
+ // This flag is always changed.
+ m_isModified = isModified;
+
+ return err;
+}
+#pragma code_seg()
+
+
+
+
+/***
+*PUBLIC GenericTypeLibOLE::GetNamMgr - return pointer to the NAMMGR
+*Purpose:
+* Produce the typelib's nammgr. If necessary deserialized from
+* stream if there is a serialized image and hasn't been deserialized
+* yet.
+* Note: sets the namecache stream offset as a side-effect.
+*
+*Entry:
+* None.
+*
+*Exit:
+* *ppnammgr
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR GenericTypeLibOLE::GetNamMgr(NAMMGR **ppnammgr)
+{
+ STREAM *pstrm;
+ TIPERROR err;
+
+ DebAssert(ppnammgr != NULL, "null param.");
+ DebAssert(m_nammgr.IsValid(), "whoops! nammgr should be valid.");
+
+ // Test if nammgr has been serialized ever or if it has
+ // already been deserialized, if not, no nammgr to read.
+ //
+ if ((m_fNammgrDeserialized == FALSE) && (m_lPosNammgr != -1)) {
+ // Otherwise open the stream.
+
+ IfErrRet(OpenTypeStream((UINT)-1, SOM_Read, &pstrm));
+
+ // No need to init the NamMgr. It is embedded and thus
+ // is constructed at container construction time, in addition
+ // is inited at container's init time.
+ // And seek to where the nammgr should be.
+ //
+ IfErrGo(pstrm->SetPos(m_lPosNammgr));
+ IfErrGo(m_nammgr.Read(pstrm));
+ m_fNammgrDeserialized = TRUE;
+
+ // At this point stream postion is at the start of the
+ // proj-level typebind. However since we don't want to
+ // load it now (we demand load it at bind time),
+ // we cache the stream position and use it later...
+ //
+ IfErrGo(pstrm->GetPos(&m_lPosGptbind));
+
+ // Close the stream
+ pstrm->Release();
+ }
+
+ // setup output param
+ *ppnammgr = &m_nammgr;
+ return TIPERR_None;
+
+Error:
+ pstrm->Release();
+ return err;
+}
+#pragma code_seg()
+
+/***
+*PUBLIC GenericTypeLibOLE::GetDstrMgr - Get the string manager
+*Purpose:
+*
+* Returns the docstring manager.
+*
+*Entry:
+* None.
+*
+*Exit:
+* *ppdstrmgr
+*
+***********************************************************************/
+
+TIPERROR GenericTypeLibOLE::GetDstrMgr(DOCSTR_MGR **ppdstrmgr)
+{
+ STREAM *pstrm;
+ TIPERROR err;
+
+ DebAssert(ppdstrmgr != NULL, "null param.");
+
+ // Test if nammgr has been serialized ever or if it has
+ // already been deserialized, if not, no nammgr to read.
+ //
+ if ((m_fDstrmgrDeserialized == FALSE) && (m_lPosNammgr != -1)) {
+ // Otherwise open the stream.
+
+ IfErrGoTo(OpenTypeStream((UINT)-1, SOM_Read, &pstrm), Error);
+
+ // No need to init the NamMgr. It is embedded and thus
+ // is constructed at container construction time, in addition
+ // is inited at container's init time.
+ // And seek to where the nammgr should be.
+ //
+ IfErrGo(pstrm->SetPos(m_lPosDstrmgr));
+ IfErrGo(m_dstrmgr.Read(pstrm));
+ m_fDstrmgrDeserialized = TRUE;
+
+ // Close the stream
+ pstrm->Release();
+ }
+
+ // setup output param
+ *ppdstrmgr = &m_dstrmgr;
+ return TIPERR_None;
+
+Error:
+ pstrm->Release();
+ return err;
+
+
+}
+
+
+/***
+* OpenTypeStream - Open a typeinfo's STREAM.
+*
+* Purpose:
+* This method is called by a contained typeinfo whenever that typeinfo
+* wants to read or write its data.
+*
+* Inputs:
+* hte - The index of the typeinfo whose stream is to be opened.
+* som - The access mode of the STREAM. See DOCFILE_STREAM::Open for
+* details.
+*
+* Outputs:
+* TIPERROR
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR GenericTypeLibOLE::OpenTypeStream(UINT hte, STREAM_OPEN_MODE som, STREAM **ppstrm)
+{
+ TIPERROR err;
+ HCHUNK hchunk;
+ LPOLESTR lpstrStream;
+
+
+ // If m_szCopyTmp is NULL, then just open the stream inside the current
+ // storage object.
+
+ DebAssert(hte == -1 || som == SOM_Write || Qte(hte)->m_ste.m_hszStrm != HCHUNK_Nil, "OpenTypeStream");
+
+ // If the DOCFILE_STREAM for the typeinfo is already open, just
+ // AddRef and return it. Note that we must be attempting to open for
+ // readonly permissions in this case.
+ if (hte != -1 && Qte(hte)->m_pdfstrm != NULL) {
+ DebAssert(som == SOM_Read, "OpenTypeStream");
+ Qte(hte)->m_pdfstrm->AddRef();
+ *ppstrm = Qte(hte)->m_pdfstrm;
+ return TIPERR_None;
+ }
+
+ // If there isn't yet a name for the stream, make one (from a timestamp).
+ // NOTE: Don't be confused by the name "MakeLocalTypeId". We're NOT
+ // making a typeId. We are making a stream name which will not change
+ // for the persistent life of the typeinfo.
+ if (hte != -1 && Qte(hte)->m_ste.m_hszStrm == HCHUNK_Nil) {
+ IfErrRet(MakeLocalTypeId(&hchunk));
+ Qte(hte)->m_ste.m_hszStrm = hchunk;
+ }
+
+ if (m_pstg == NULL) {
+ IfErrRet(GetStorage(((som==SOM_Read)?STGM_READ:STGM_READWRITE) | STGM_SHARE_EXCLUSIVE, NULL));
+ }
+ else {
+ m_pstg->AddRef();
+ if (m_pstgContainer != NULL)
+ m_pstgContainer->AddRef();
+ }
+
+ m_bmData.Lock();
+ if (hte == -1)
+ lpstrStream = GenericTypeLibOLE::szDirStreamName;
+ else {
+ lpstrStream = QszOfHsz(Qte(hte)->m_ste.m_hszStrm);
+ }
+
+ err = DOCFILE_STREAM::Open(&m_pstg, &m_pstgContainer,
+ (hte == -1) ? NULL : this,
+ hte,
+ EI_OB,
+ lpstrStream,
+ som, ppstrm);
+ m_bmData.Unlock();
+ return err;
+}
+#pragma code_seg()
+
+
+
+#if ID_DEBUG
+
+/***
+*PUBLIC GenericTypeLibOLE::DebCheckState
+*Purpose:
+* Check internal state of GenericTypeLibOLE object.
+*
+*Entry:
+* uLevel - no checking is done if uLevel < 0
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+void GenericTypeLibOLE::DebCheckState(UINT uLevel)
+{
+ UINT iBucket, cTypeEntries;
+ TYPE_ENTRY *qte;
+ LPOLESTR qsz;
+ HTENTRY hte;
+ STL_TYPEINFO *pstltinfo;
+
+ m_bmData.Lock();
+
+ // Walk the Type_Entries by walking the hash table buckets
+
+ cTypeEntries = 0;
+ for (iBucket = 0; iBucket < GTLIBOLE_cBuckets; iBucket++) {
+ hte = m_rghteBucket[iBucket];
+ while (hte != HTENTRY_Nil) {
+ cTypeEntries++;
+ qte = Qte(hte);
+
+ //
+ // Check the TYPE_ENTRY
+ //
+
+ // Ensure that this entry is in the right hash table
+ qsz = QszOfHsz(qte->m_ste.m_hszLocalTypeId);
+ DebAssert(iBucket == IhteHash(qsz), "");
+
+ // Ensure that the TypeInfo has the correct handle for itself
+ if ((pstltinfo = qte->m_pstltinfo) != NULL) {
+ DebAssert(pstltinfo->m_hte == hte, "");
+ }
+
+ // Ensure that there is an sz name string
+ DebAssert(qte->m_ste.m_hlnamType != HLNAM_Nil, "");
+
+ hte = qte->m_hteNext;
+ } // while
+ } // for
+ // Ensure that number of entries in hash table matches number of entries
+ DebAssert(cTypeEntries == m_cTypeEntries, "");
+
+ // Ensure that the size of m_bdte is correct
+ DebAssert(m_bdte.CbSize() == cTypeEntries * sizeof(TYPE_ENTRY), "");
+
+ m_bmData.Unlock();
+
+ // Check the binding tables
+ m_gptbind.DebCheckState(uLevel);
+}
+
+
+
+#endif // ID_DEBUG
+
+// catches vector destructor code generation
+#if OE_MAC
+#pragma code_seg(CS_INIT)
+#endif
diff --git a/private/oleauto/src/typelib/gtlibole.hxx b/private/oleauto/src/typelib/gtlibole.hxx
new file mode 100644
index 000000000..d1586de6f
--- /dev/null
+++ b/private/oleauto/src/typelib/gtlibole.hxx
@@ -0,0 +1,1220 @@
+/***
+*gtlibole.hxx - GenericTypeLibOLE header file
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Defines GenericTypeLibOLE interface which is an implementation
+* of the IDynTypeLib protocol which allows TYPEINFOs to be
+* dynamically added.
+*
+*Revision History:
+*
+* 14-Dec-92 mikewo: Created.
+*
+*****************************************************************************/
+
+#ifndef GTLIBOLE_HXX_INCLUDED
+#define GTLIBOLE_HXX_INCLUDED
+
+#include "clutil.hxx" // needed for SYSKIND_CURRENT
+#include "xstring.h"
+#include "blkmgr.hxx"
+#include "dfstream.hxx"
+#include "ncache.hxx" // NAME_CACHE
+#include "gptbind.hxx" // GENPROJ_TYPEBIND
+#include "nammgr.hxx" // needed for embedded NAMMGR
+#include "obguid.h"
+#include <time.h>
+
+#include "dstrmgr.hxx"
+
+#if OE_WIN32
+#include "oautil.h"
+#endif // OE_WIN32
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szGTLIBOLE_HXX)
+#define SZ_FILE_NAME g_szGTLIBOLE_HXX
+#endif
+
+TIPERROR GetRegisteredPath(HKEY hkey,
+ LPOLESTR szSubkey,
+ LPOLESTR szPath,
+ LONG *pcbPath,
+ BOOL fMustExist);
+
+
+#define GTLIBOLE_cBuckets 32
+
+#define DEBNAMESIZE 32
+
+// An HTENTRY is an opaque handle for a TYPE_ENTRY in a GenericTypeLibOLE
+// Their internal representation is an index into the TYPE_ENTRY array.
+typedef USHORT HTENTRY;
+
+#define HTENTRY_Nil 0xFFFF
+
+class STL_TYPEINFO;
+class GEN_PROJECT;
+class GEN_DTINFO;
+
+class DOCSTR_MGR;
+
+
+class SER_TYPE_ENTRY
+{
+public:
+ HCHUNK m_hszStrm; // The name of the stream for this typeinfo.
+ HCHUNK m_hszLocalTypeId; // The local typeId of this type.
+ HLNAM m_hlnamType; // This type's name.
+ HCHUNK m_hszTypeInfoTypeId; // The typeId of the true type of the
+ // TYPEINFO instance representing this
+ // type, HCHUNK_Nil if that is the default
+ // TYPEINFO true type for this typelib.
+ USHORT m_usEncodedDocStrSize;
+ HCHUNK m_hszEncodedDocString; // The encoded doc string for this type.
+
+ ULONG m_dwHelpContext; // The help context for this type.
+ HCHUNK m_hszHelpFile; // The help filename for this type.
+ GUID m_guid; // The typeinfo's guid.
+ USHORT m_typekind; // The kind of typeinfo's this is
+
+ SER_TYPE_ENTRY();
+};
+
+/***
+*class TYPE_ENTRY - 'te'
+*Purpose:
+* A GenericTypeLibOLE maintains a TYPE_ENTRY instance for each type which
+* it contains.
+***********************************************************************/
+
+class TYPE_ENTRY
+{
+public:
+
+ // These items are not serialized.
+ HTENTRY m_hteNext; // The next type entry in the hash list.
+ STL_TYPEINFO *m_pstltinfo;
+ // The TYPEINFO for this type, or NULL if
+ // not currently loaded.
+ DOCFILE_STREAM *m_pdfstrm; // The module's DOCFILE_STREAM, or NULL if it
+ // isn't currently open.
+
+ // One of these (never both) is serialized.
+ SER_TYPE_ENTRY m_ste; // The serialized data in the type entry.
+
+ TYPE_ENTRY();
+};
+
+
+/***
+*PUBLIC SER_TYPE_ENTRY::SER_TYPE_ENTRY
+*Purpose:
+* Construct a SER_TYPE_ENTRY.
+***********************************************************************/
+
+inline SER_TYPE_ENTRY::SER_TYPE_ENTRY()
+{
+ m_hszStrm = HCHUNK_Nil;
+ m_hszLocalTypeId = HCHUNK_Nil;
+ m_hlnamType = HLNAM_Nil;
+ m_hszTypeInfoTypeId = HCHUNK_Nil;
+ m_usEncodedDocStrSize = 0;
+ m_hszEncodedDocString = HCHUNK_Nil;
+
+ m_hszHelpFile = HCHUNK_Nil;
+ m_dwHelpContext = 0; // default help context is 0 (not -1)
+
+ m_guid = IID_NULL;
+ m_typekind = TKIND_MAX;
+}
+
+
+/***
+*PUBLIC TYPE_ENTRY::TYPE_ENTRY
+*Purpose:
+* Construct a TYPE_ENTRY.
+***********************************************************************/
+
+inline TYPE_ENTRY::TYPE_ENTRY()
+{
+ m_pstltinfo = NULL;
+ m_pdfstrm = NULL;
+}
+
+
+/***
+*class GenericTypeLibOLE - 'gtlibole'
+*Purpose:
+* Implementation of the ITypeLib protocol which supports reading
+* TypeLib's only, and the ICreateTypeLib protocol which supports
+* creating new typelibs.
+* A hash table is used for looking up a TypeInfo in the TypeLib based
+* on its GUID.
+***********************************************************************/
+
+class GenericTypeLibOLE : public ITypeLibA, public ICreateTypeLibA
+{
+friend STL_TYPEINFO;
+friend TYPEMGR;
+friend DOCFILE_STREAM;
+
+friend HRESULT STDAPICALLTYPE CreateTypeLib(SYSKIND syskind, LPCOLESTR szFile, ICreateTypeLibA FAR* FAR* lplptlib);
+friend HRESULT STDAPICALLTYPE LoadTypeLib(LPCOLESTR szFile, ITypeLibA **pptlib);
+
+//#if FV_UNICODE_OLE
+//friend HRESULT STDAPICALLTYPE CreateTypeLibW(SYSKIND syskind, LPCOLESTR szFile, ICreateTypeLib FAR* FAR* lplptlib);
+//#endif //FV_UNICODE_OLE
+
+
+#if ID_TEST
+friend TIPERROR GetSheapSize(UINT argc, BSTRA *rglstr);
+#endif
+
+public:
+ static TIPERROR Create(IStorageA *pstg, GenericTypeLibOLE **pptlib);
+ virtual TIPERROR Init(void);
+
+ // *** IUnknown methods ***
+ STDMETHOD(QueryInterface)(REFIID riid, VOID FAR* FAR* ppvObj);
+ STDMETHOD_(ULONG, AddRef)(void);
+ STDMETHOD_(ULONG, Release)(void);
+
+ // *** ITypeLib methods ***
+ STDMETHOD_(unsigned int, GetTypeInfoCount)(void);
+ STDMETHOD(GetTypeInfo)(UINT index,
+ ITypeInfoA FAR* FAR* lplptinfo);
+ STDMETHOD(GetTypeInfoType)(UINT index,
+ TYPEKIND FAR* ptypekind);
+ STDMETHOD(GetTypeInfoOfGuid)(REFGUID guid,
+ ITypeInfoA FAR* FAR* lplptinfo);
+ STDMETHOD(GetLibAttr)(TLIBATTR FAR* FAR* lplptlibattr);
+ STDMETHOD(GetTypeComp)(ITypeCompA FAR* FAR* lplptcomp);
+ STDMETHOD(GetDocumentation)(INT index,
+ LPBSTR lpbstrName,
+ LPBSTR lpbstrDocString,
+ LPDWORD lpdwHelpContext,
+ LPBSTR lpbstrHelpFile);
+ STDMETHOD(IsName)(OLECHAR FAR* szNameBuf,
+ unsigned long lHashVal,
+ int FAR* lpfName);
+ STDMETHOD(FindName)(OLECHAR FAR* szNameBuf,
+ unsigned long lHashVal,
+ ITypeInfoA FAR* FAR* rgptinfo,
+ MEMBERID FAR* rgmemid,
+ unsigned short FAR* pcFound);
+ STDMETHOD_(void, ReleaseTLibAttr)(TLIBATTR FAR* lptlibattr);
+
+ // *** ICreateTypeLib methods ***
+ STDMETHOD(CreateTypeInfo)(LPOLESTR szName,
+ TYPEKIND tkind,
+ ICreateTypeInfoA FAR* FAR* ppctinfo);
+ STDMETHOD(SetName)(LPOLESTR szName);
+ STDMETHOD(SetVersion)(WORD wMajorVerNum, WORD wMinorVerNum);
+ STDMETHOD(SetGuid)(REFGUID guid);
+ STDMETHOD(SetDocString)(LPOLESTR szDoc);
+ STDMETHOD(SetHelpFileName)(LPOLESTR szHelpFileName);
+ STDMETHOD(SetHelpContext)(DWORD dwHelpContext);
+ STDMETHOD(SetLcid)(LCID lcid);
+ STDMETHOD(SetLibFlags)(UINT uLibFlags);
+ STDMETHOD(SaveAllChanges)(void);
+
+ STDMETHOD(SaveAllChanges)(IStorageA FAR *pstg);
+
+ nonvirt TIPERROR GetGdtiOfItyp(UINT ityp, GEN_DTINFO **ppgdti);
+
+ nonvirt TIPERROR SaveOrCopyChanges(IStorageA *pstg, BOOL shouldCopy);
+ nonvirt TIPERROR GetIndexOfName(LPSTR szName, WORD *pw);
+ nonvirt TIPERROR GetTypeInfoLocal(TYPEID szLocalTypeId,
+ ITypeInfoA **pptinfo);
+
+ nonvirt TIPERROR GetIndexOfLocalRegId(LPOLESTR szLocalTypeId, WORD *pw);
+ nonvirt TIPERROR GetCompressedTypeId(ITypeInfoA *ptinfo, BSTR *pbstrOut);
+ nonvirt TIPERROR WriteTypeId(STREAM *pstrm, ITypeInfoA *ptinfo);
+ nonvirt TIPERROR TypeInfoFromCompressedTypeId(LPOLESTR szTypeId,
+ ITypeInfoA **pptinfo);
+
+
+ nonvirt TIPERROR FindMembers(LPSTR szName,
+ unsigned long lHashVal,
+ ITypeInfoA **rgptinfo,
+ MEMBERID *rgmemid,
+ USHORT *pcSearch);
+
+ // NAME_CACHE methods
+ nonvirt BOOL IsExistNameCache() const;
+ nonvirt BOOL IsValidNameCache(UINT inamcache) const;
+ nonvirt BOOL IsNameInCache(UINT inamcache, HGNAM hgnam) const;
+ nonvirt TIPERROR LoadNameCache();
+ nonvirt VOID InvalidateNameCache(UINT inamcache);
+ nonvirt VOID SetValidNameCache(UINT inamcache);
+ nonvirt TIPERROR AddNameToCache(UINT inamcache, HGNAM hgnam);
+
+ nonvirt TIPERROR Add(GEN_DTINFO *pstltinfo, LPOLESTR szName);
+ nonvirt TIPERROR UpdateTypeId(UINT itype);
+
+ nonvirt TIPERROR SetTypeName(UINT i, LPOLESTR szName);
+ nonvirt TIPERROR SetTypeDocString(UINT i, LPOLESTR szDocString);
+ nonvirt TIPERROR SetTypeHelpContext(UINT i, DWORD dwHelpContext);
+ nonvirt VOID GetTypeGuid(UINT i, GUID FAR *pguid);
+ nonvirt VOID SetTypeGuid(UINT i, REFGUID guid);
+ nonvirt VOID SetTypeKind(UINT i, TYPEKIND tkind);
+ nonvirt TIPERROR GetHstOfHelpString(XSZ_CONST szDocStr, HST *hst);
+ nonvirt TIPERROR EncodeHelpStrings();
+ nonvirt TIPERROR GetDstrMgr(DOCSTR_MGR **ppdstrmgr);
+
+ nonvirt BOOL IsModified();
+ nonvirt TIPERROR SetModified(BOOL isModified);
+
+
+ nonvirt BOOL StriEq(XSZ_CONST szStr1, XSZ_CONST szStr2);
+
+ nonvirt TIPERROR GetDirectory(BSTR *pbstr);
+
+ nonvirt TIPERROR SetLibId(LPOLESTR szLibId);
+#if 0
+ nonvirt TIPERROR GetLibId(BSTR *pbstr);
+#endif
+
+ nonvirt TIPERROR GetStorage(DWORD stgm, IStorageA **ppstg);
+ nonvirt TIPERROR OpenTypeStream(UINT hte,
+ STREAM_OPEN_MODE som,
+ STREAM **ppstrm);
+
+ // Release binding resources method.
+ nonvirt VOID ReleaseResources();
+
+ // Method to create proj-level typebind
+ nonvirt TIPERROR GetTypeBind();
+
+ // Method to lookup a name in proj-level binding table
+ nonvirt TIPERROR GetBinddescOfSzName(LPSTR szName,
+ GENPROJ_BIND_DESC *pprojbinddesc);
+
+ // Method to map a qualified name to a typelib
+ nonvirt TIPERROR GetTypelibOfRgbstr(UINT cNames,
+ BSTRA *rgbstr,
+ ITypeLibA **pptlib);
+
+ // Method to map a non-qualified name to a typeinfo
+ nonvirt TIPERROR GetTypeInfoOfSzName(LPSTR szName,
+ ITypeInfoA **pptinfo);
+
+ // Accessor to produce embedded typebind
+ nonvirt GENPROJ_TYPEBIND *Pgptbind();
+
+ // NAMMGR methods
+ TIPERROR GetNamMgr(NAMMGR **ppnammgr);
+ ULONG GetSampleHashVal();
+
+ nonvirt LCID GetLcid();
+ nonvirt SYSKIND GetSyskind();
+ nonvirt SHEAP_MGR *Psheapmgr();
+
+ nonvirt TYPE_ENTRY *Qte(HTENTRY hte) const;
+
+ nonvirt BOOL IsProjectDBCS() { return m_isDBCS; };
+
+ USHORT MajorVerNum();
+ VOID SetMajorVerNum(USHORT wVer);
+
+ USHORT MinorVerNum();
+ VOID SetMinorVerNum(USHORT wVer);
+
+ GUID Guid();
+ VOID SetLibGuid(GUID guid);
+
+ // Versioning information.
+ WORD GetVersion();
+ VOID SetDualTypeLib();
+
+// Debugging methods
+#if ID_DEBUG
+ nonvirt VOID DebCheckState(UINT uLevel);
+ nonvirt VOID DebShowState(UINT uLevel);
+#else //!ID_DEBUG
+ nonvirt VOID DebCheckState(UINT uLevel) {}
+ nonvirt VOID DebShowState(UINT uLevel) {}
+#endif //!ID_DEBUG
+
+ // Offset of embedded GENPROJ_TYPEBIND member
+ // used to get pointer to STL_TYPEBIND instance
+ // from within the embedded member.
+ // NOTE: we don't make this protected and provide a public
+ // accessor since such a method would want to be inline
+ // and would reference the protected static member in the
+ // header file -- which eventually results in an unresolved
+ // external in hxxtoinc.
+ // I.e. leave this as a public member -- when we can
+ // use a compiler the correctly implements const static
+ // initializers then this can be a const (and thus safe).
+ //
+ static CONSTDATA UINT oGptbind;
+
+#if ID_DEBUG
+ // Used for typelib leak reporting.
+ CHAR *SzDebName();
+ ULONG CRefs();
+#endif // ID_DEBUG
+
+ // Access functions for name cache stats
+ nonvirt VOID DebResetNameCacheStats();
+
+ nonvirt VOID DebSetNameCacheModTrys();
+ nonvirt VOID DebSetNameCacheModHits();
+ nonvirt VOID DebSetNameCacheGlobHits();
+
+ nonvirt UINT DebGetNameCacheModHits();
+ nonvirt UINT DebGetNameCacheModTrys();
+ nonvirt UINT DebGetNameCacheGlobHits();
+
+protected:
+ // CONSIDER: make both operator new and operator delete
+ // private and "undefined" -- i.e. assert in debug --
+ // in addition, "macro expand" the respective calls
+ // to new and delete in CreateNew() and Release(). The
+ // advantage is that it's clearer to the reader what is
+ // actually going on in terms of memory mgmt and stresses
+ // that the only way to alloc/free instances is via
+ // the Create/Release paradigm.
+ //
+ void *operator new(size_t cbSize);
+ GenericTypeLibOLE();
+ virtual ~GenericTypeLibOLE();
+
+ nonvirt TIPERROR Read();
+ nonvirt TIPERROR Read(STREAM *pstrm);
+ nonvirt UINT IhteHash(TYPEID TypeId);
+ nonvirt VOID RelTypeEntExtResources(HTENTRY hte);
+ nonvirt VOID *QtrOfHChunk(HCHUNK hv);
+ nonvirt LPOLESTR QszLibIdOrFile();
+ nonvirt LPOLESTR QszOfHsz(HCHUNK hsz);
+ nonvirt LPOLESTR SzLocalTypeId(TYPEID TypeId);
+ nonvirt LPOLESTR GetQszTypeInfoTypeId(HTENTRY hte);
+ nonvirt TIPERROR SetDirectory(LPOLESTR szFile);
+ nonvirt TIPERROR MakeRelativeLibId(LPOLESTR szLibId, LPOLESTR *pmszLibIdRel);
+ nonvirt TIPERROR CreateInstance(LPOLESTR szTypeId, void **ppvoid);
+
+// Modification and writing methods.
+ nonvirt TIPERROR AddTypeEntry(LPSTR szName,
+ LPOLESTR szTypeInfoTypeId,
+ HTENTRY *phte);
+ nonvirt void UnAddTypeEntry(UINT hte);
+ nonvirt TIPERROR MakeLocalTypeId(HCHUNK *phchunkTypeId);
+ nonvirt TIPERROR CreateHsz(LPOLESTR sz, HCHUNK *phchunk);
+ nonvirt HTENTRY *QHteRef(HTENTRY i);
+ nonvirt TIPERROR ResetHsz(LPOLESTR sz, HCHUNK *phchunk);
+ nonvirt VOID DeleteHsz(HCHUNK hchunk);
+ nonvirt TIPERROR Write();
+ nonvirt TIPERROR Write(STREAM *pstrm);
+ nonvirt VOID DestructTypeEntry(HTENTRY hte);
+ nonvirt TIPERROR CloneChunk(HCHUNK hSrc, UINT cbSrc, HCHUNK *phDest);
+ nonvirt TIPERROR CloneString(HCHUNK hszSrc, HCHUNK *phszDest);
+
+ // Serialization helper functions
+ nonvirt TIPERROR ReadString(STREAM *pstrm, HCHUNK *phsz);
+ nonvirt TIPERROR WriteString(STREAM *pstrm, HCHUNK hsz);
+
+#if ID_DEBUG
+ // The name of this typelib.
+ CHAR m_szDebName[DEBNAMESIZE];
+#endif // ID_DEBUG
+
+ BOOL m_fDirModified; // Is the directory info modified?
+
+ BOOL m_isModified;
+ // Is the directory info or any contained typeinfo modified?
+
+// Methods accessed by STL_TYPEINFO
+ nonvirt VOID Deleting(HTENTRY hte);
+
+ // NAME_CACHE methods
+ nonvirt TIPERROR ReadNameCacheArray();
+ nonvirt NAME_CACHE *Rgnamcache() const;
+
+// static constant data members
+ static CONSTDATA WORD wFirstSerWord;
+ static CONSTDATA WORD wDefaultVersion;
+ static CONSTDATA WORD wDualVersion;
+ static CONSTDATA WORD wMaxVersion;
+ static CONSTDATA XCHAR chMinorVerNumSep;
+ static CONSTDATA OLECHAR chLibIdSep;
+ static CONSTDATA LPOLESTR szDirStreamName;
+
+// non-static data members
+ // Not needed really for Win16 but useful for other
+ // platforms.
+ // CONSIDER: synthesize for Win16 from selector and offset 0.
+ // Note: must be protected so that derived classes
+ // can initialize.
+ //
+ SHEAP_MGR *m_psheapmgr;
+
+ BLK_DESC m_bdte;
+ BLK_MGR m_bmData;
+ IStorageA *m_pstg;
+ IStorageA *m_pstgContainer; // NULL unless m_pstg is a substorage.
+ ULONG m_cRefs;
+ HCHUNK m_hszDirectory;
+ // The directory containing this typelib. Set by LoadTypeLib.
+ // Never ends in a backslash in non-mac builds. HCHUNK_Nil if not known.
+
+ HCHUNK m_hszFile;
+ // The full path, or HCHUNK_Nil if unknown.
+
+ // These members (or the data referenced by the HCHUNKs) are all
+ // serialized, except where noted.
+ HTENTRY m_rghteBucket[GTLIBOLE_cBuckets];
+ HCHUNK m_hlnamLib;
+ USHORT m_cTypeEntries;
+ HCHUNK m_hszDefaultTITypeId;
+ HCHUNK m_hszDocString; // The lib's short doc string.
+ ULONG m_dwHelpContext; // The lib's help context.
+ HCHUNK m_hszHelpFile; // The lib's help filename.
+ USHORT m_syskind; // The lib's current syskind.
+ LCID m_lcid; // the lib's language id
+ BOOL m_lcidZero; // Was this typelib created with lcid == 0;
+ WORD m_wCurVersion; // The version of this typelib.
+ USHORT m_wLibFlags; // the lib's flags
+
+ USHORT m_wMajorVerNum; // The major and minor version numbers
+ USHORT m_wMinorVerNum; // of the typelib.
+ GUID m_guid; // The lib's GUID.
+
+ // These members are not serialized.
+
+ BOOL m_fNamespaceChange;
+ ULONG m_lSampleHashVal; // for space optimization(e.g nammgr)
+
+ // The embedded GENPROJ_TYPEBIND -- this is serialized.
+ GENPROJ_TYPEBIND m_gptbind;
+
+ // Serialization position of m_gptbind
+ // set by GenericTypeLibOLE::Read() and used by
+ // GenericTypeLibOLE::GetTypeBind()
+ //
+ LONG m_lPosGptbind;
+
+ // Indicates whether gptbind has been deserialized.
+ BOOL m_fGptbindDeserialized;
+
+
+ // REVISION MARK: 22-Feb-93 ilanc: added following line
+ //
+ // Nammgr related data members
+ //
+
+ // Serialization position of NAMMGR array:
+ // set by GenericTypeLibOLE::Read() and used by
+ // GenericTypeLibOLE::GetNamMgr()
+ //
+ LONG m_lPosNammgr;
+
+ // Indicates whether nammgr has been deserialized.
+ BOOL m_fNammgrDeserialized;
+
+ // The nammgr itself. This is serialized.
+ NAMMGR m_nammgr;
+
+ // END OF REVISION MARK: 22-Feb-93 ilanc
+
+ //
+ // Name cache related data members
+ //
+
+ // Serialization position of NAME_CACHE array:
+ // set by GenericTypeLibOLE::GetNamMgr() and used by
+ // GenericTypeLibOLE::ReadNameCacheArray()
+ //
+ LONG m_lPosRgnamcache;
+
+ // flag word: note only a single bit is really needed here
+ // so if you want more flags, turn this into a bitfield.
+ //
+ USHORT m_hasValidDiskImageNameCache;
+
+ // The cache itself. This is serialized.
+ // Note: the cache is loaded iff its BLK_DESC is valid.
+ // When constructed it is invalidated so that
+ // deserialization will Init(), and then
+ // actually read it in.
+ //
+ BLK_DESC m_bdRgnamcache;
+ // Persistent Name cache array --
+ // 0th element is project's cache, 1..N are TYPEINFO's.
+
+ BOOL m_isDBCS; // TRUE iff lcid is a double-byte locale id
+
+ // Serialization position of DOCSTR_MGR
+ // GenericTypeLibOLE::GetDstrMgr()
+ //
+ LONG m_lPosDstrmgr;
+
+ // Indicates whether nammgr has been deserialized.
+ BOOL m_fDstrmgrDeserialized;
+
+ DOCSTR_MGR m_dstrmgr;
+
+#if ID_TEST
+ // Name cache statistics
+ UINT m_cNameCacheModTrys;
+ UINT m_cNameCacheModHits;
+ UINT m_cNameCacheGlobHits;
+#endif
+
+private:
+ // NOTE: must be declared inline since defined later inline and
+ // cfront otherwise complains that declared with
+ // external linkage and used before defined as inline.
+ // I believe that this is because a derived class's dtor
+ // is implicitly declared and defined as inline. (???)
+ // 10-Jun-92 ilanc
+ //
+ inline void operator delete(void *pv);
+
+};
+
+
+/***
+*PRIVATE GenericTypeLibOLE::operator delete
+*Purpose:
+* Deletes the SHEAP_MGR instance that held the GenericTypeLibOLE instance.
+*
+*Entry:
+* pv - Pointer to GenericTypeLibOLE to delete.
+* NOTE: we assume that the truetype of pv is GenericTypeLibOLE
+* and thus we know we can cast and correctly offset
+* into the instance to retrieve the m_psheapmgr datamember.
+*
+* Disaster will result if the dtor ever decides to delete
+* the m_psheapmgr member itself or just reset it.
+*
+* NOTE: operator delete MUST be private in all implementations
+* of GenericTypeLibOLE (as of today 06-Aug-92 GenericTypeLibOLE
+* and GEN_PROJECT) since we want to *require*
+* it being called from virtual Release() such that the
+* true type of pv be known. By making it private we ensure
+* that a base operator delete can't be called.
+*
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+inline VOID GenericTypeLibOLE::operator delete(void *pv)
+{
+ // delete ((SHEAP_MGR *)pv - 1);
+ // 09-Jun-92 ilanc
+ DebAssert( ((GenericTypeLibOLE *)pv)->m_psheapmgr != NULL,
+ "null sheapmgr.");
+ delete ((GenericTypeLibOLE *)pv)->m_psheapmgr;
+}
+
+
+/***
+*PROTECTED GenericTypeLibOLE::Qte
+*Purpose:
+* Method to map hte to pointer to TYPE_ENTRY
+*
+*Entry:
+* hte - handle for the TYPE_ENTRY
+*
+*Exit:
+* Qte - pointer to the TYPE_ENTRY
+*
+***********************************************************************/
+
+inline TYPE_ENTRY *GenericTypeLibOLE::Qte(HTENTRY hte) const
+{
+ DebAssert(hte * sizeof(TYPE_ENTRY) <= m_bdte.CbSize(), "Out of bounds");
+
+ return ((TYPE_ENTRY *)m_bdte.QtrOfBlock()) + hte;
+}
+
+
+/***
+*PUBLIC GenericTypeLibOLE::IsModified
+* This is a internal flag. There is a external flag added to GenProj
+* to track the changes due to user action.
+*Exit:
+* BOOL - TRUE if the project has changes to save.
+*
+***********************************************************************/
+inline BOOL GenericTypeLibOLE::IsModified()
+{
+ return m_isModified;
+}
+
+
+/***
+*PUBLIC GenericTypeLibOLE::Psheapmgr
+*Purpose:
+* To return a pointer to the SHEAP_MGR associated with a GenericTypeLibOLE
+* or any ITypeLib whose new operation delegates to GenericTypeLibOLE::new
+*
+*Entry:
+*
+*Exit:
+* Return a pointer to the SHEAP_MGR
+*
+***********************************************************************/
+
+inline SHEAP_MGR *GenericTypeLibOLE::Psheapmgr()
+{
+ DebAssert(m_psheapmgr != NULL, "uninitialized SHEAP_MGR.");
+
+ return m_psheapmgr;
+}
+
+
+/***
+*PUBLIC GenericTypeLibOLE::Pgptbind
+*Purpose:
+* Produces pointer to embedded proj-level typebind.
+*
+*Entry:
+*
+*Exit:
+* Return a pointer to the GENPROJ_TYPEBIND
+*
+***********************************************************************/
+
+inline GENPROJ_TYPEBIND *GenericTypeLibOLE::Pgptbind()
+{
+ return &m_gptbind;
+}
+
+
+/***
+*PUBLIC GenericTypeLibOLE::RelTypeEntExtResources
+*Purpose:
+* Release the resources owned by a TYPE_ENTRY which are external
+* to a TypeLib; i.e. not in the TypeLib's heap.
+*
+*Entry:
+* hte - index to TYPE_ENTRY
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+inline VOID GenericTypeLibOLE::RelTypeEntExtResources(HTENTRY hte)
+{
+}
+
+
+/***
+*IsExistNameCache() - does name cache exist at all?
+*Purpose:
+* Tests whether cache exists at all -- whether it was
+* loaded or created.
+*
+*Entry:
+* None.
+*
+*Exit:
+* TRUE if BLK_DESC containing cache has been inited.
+* FALSE otherwise.
+***********************************************************************/
+
+inline BOOL GenericTypeLibOLE::IsExistNameCache() const
+{
+ return m_bdRgnamcache.IsValid();
+}
+
+
+/***
+*Rgnamcache() - Get pointer to NAME_CACHE array
+*Purpose:
+* Returns a pointer the NAME_CACHE array
+*
+*Entry:
+* None.
+*
+*Exit:
+* Returns a pointer to the NAME_CACHE array. The pointer
+* is only valid for a short time.
+*
+***********************************************************************/
+
+inline NAME_CACHE *GenericTypeLibOLE::Rgnamcache() const
+{
+ return (NAME_CACHE *)m_bdRgnamcache.QtrOfBlock();
+}
+
+
+/***
+*PUBLIC GenericTypeLibOLE::IsValidNameCache
+*Purpose:
+* Tests if a given type's NAME_CACHE is valid.
+* If not loaded, does NOT load the NAME_CACHE array.
+*
+*Entry:
+* inamcache index of TYPEINFO in library + 1.
+* Zero is reserved for project's cache.
+*
+*Exit:
+* TRUE if type's NAME_CACHE loaded and valid
+* FALSE otherwise.
+*
+***********************************************************************/
+
+inline BOOL GenericTypeLibOLE::IsValidNameCache(UINT inamcache) const
+{
+ return IsExistNameCache() && Rgnamcache()[inamcache].IsValid();
+}
+
+
+/***
+*PUBLIC GenericTypeLibOLE::IsNameInCache
+*Purpose:
+* Tests if a given name is in a given cache.
+* If not loaded, does NOT load the NAME_CACHE array.
+*
+*Entry:
+* inamcache index of TYPEINFO in library + 1.
+* hgnam Global name handle to test for.
+*
+*Exit:
+* TRUE if type's NAME_CACHE loaded, valid and name is in cache.
+* FALSE otherwise.
+*
+***********************************************************************/
+
+inline BOOL GenericTypeLibOLE::IsNameInCache(UINT inamcache, HGNAM hgnam) const
+{
+ return IsExistNameCache() && Rgnamcache()[inamcache].IsNameInCache(hgnam);
+}
+
+
+/***
+*PUBLIC GenericTypeLibOLE::SetValidNameCache
+*Purpose:
+* Sets a given name cache to be valid.
+*
+*Entry:
+* inamcache index of TYPEINFO in library + 1.
+*
+*Exit:
+* None
+***********************************************************************/
+
+inline VOID GenericTypeLibOLE::SetValidNameCache(UINT inamcache)
+{
+ Rgnamcache()[inamcache].SetValid();
+}
+
+/***
+*PUBLIC GenericTypeLibOLE::DestructTypeEntry
+*Purpose:
+* Release all resources owned by a TYPE_ENTRY.
+*
+*Entry:
+* hte - pointer to the TYPE_ENTRY whose resources are to be released.
+*
+*Exit:
+* None.
+***********************************************************************/
+
+inline VOID GenericTypeLibOLE::DestructTypeEntry(HTENTRY hte)
+{
+ // Release all external resources.
+ RelTypeEntExtResources(hte);
+
+ // Release all resources allocated to m_bmData.
+ DeleteHsz(Qte(hte)->m_ste.m_hszLocalTypeId);
+ DeleteHsz(Qte(hte)->m_ste.m_hszTypeInfoTypeId);
+
+}
+
+
+
+/***
+* BOOL StrEqi
+*
+* Purpose: locale-specific string equality.
+* returns TRUE if equal, FALSE if not equal
+* case/accent insensitive, according to codepage/locale specified.
+*
+* Inputs:
+* szStr1 : String to be compared
+* szStr2 : String to be compared
+*
+*
+* Outputs: BOOL : return TRUE if the strings passed in are equal
+* else return FALSE
+*
+*NOTE:- Defer to nammgr.
+*****************************************************************************/
+inline BOOL GenericTypeLibOLE::StriEq(XSZ_CONST szStr1, XSZ_CONST szStr2)
+{
+ DebAssert(m_nammgr.IsValid() && m_fNammgrDeserialized == TRUE ,
+ "whoops! nammgr should be valid and deserialized.");
+
+ return m_nammgr.StriEq(szStr1, szStr2);
+}
+
+/***
+*PUBLIC GenericTypeLibOLE::GetLcid()
+*Purpose:
+*
+*Entry:
+* None
+*
+*Exit:
+* Returns the local code of the project
+*
+***********************************************************************/
+inline LCID GenericTypeLibOLE::GetLcid()
+{
+ return m_lcid;
+}
+
+/***
+*PUBLIC GenericTypeLibOLE::GetSyskind()
+*Purpose:
+*
+*Entry:
+* None
+*
+*Exit:
+* Returns the local code of the project
+*
+***********************************************************************/
+inline SYSKIND GenericTypeLibOLE::GetSyskind()
+{
+ return (SYSKIND)m_syskind;
+
+}
+
+/***
+*PUBLIC GenericTypeLibOLE::ResetNameCacheStats()
+*Purpose:
+*
+*Entry:
+* None
+*
+*Exit:
+* None
+*
+***********************************************************************/
+inline VOID GenericTypeLibOLE::DebResetNameCacheStats()
+{
+#if ID_TEST
+ m_cNameCacheModTrys =
+ m_cNameCacheModHits =
+ m_cNameCacheGlobHits = 0;
+#endif // ID_TEST
+}
+
+
+
+/***
+*PUBLIC GenericTypeLibOLE::VerifyProjChange()
+*Purpose:
+* Returns the sample hash value. This is calculated when the typelib is
+* loaded.
+*
+*Entry:
+* None
+*
+*Exit:
+* None
+*
+***********************************************************************/
+inline ULONG GenericTypeLibOLE::GetSampleHashVal()
+{
+ // if the hash value is not initialized yet then initialize it now.
+ if (m_lSampleHashVal == 0) {
+#if OE_WIN32
+ m_lSampleHashVal = LHashValOfNameSysW(GetSyskind(), GetLcid(), L" ");
+#else
+ m_lSampleHashVal = LHashValOfNameSysA(GetSyskind(), GetLcid(), " ");
+#endif
+ }
+ return m_lSampleHashVal;
+}
+
+
+
+/***
+*PROTECTED GenericTypeLibOLE::DeleteHsz
+*Purpose:
+* Release the chunk that an Hsz is stored in.
+*
+*Entry:
+* hsz - hchunk of m_bmData which contains an xsz
+*
+*Exit:
+* None
+*
+***********************************************************************/
+
+
+inline VOID GenericTypeLibOLE::DeleteHsz(HCHUNK hchunk)
+{
+ if (hchunk != HCHUNK_Nil)
+ m_bmData.FreeChunk(hchunk, ostrblen0(QszOfHsz(hchunk)));
+}
+
+
+/***
+*PUBLIC GenericTypeLibOLE::GetTypeGuid
+*Purpose:
+* Set the guid of the ith TypeInfo.
+*
+*Entry:
+* i - index of TypeInfo to be changed
+* guid - The new guid.
+*
+*Exit:
+* HRESULT
+*
+***********************************************************************/
+inline VOID GenericTypeLibOLE::GetTypeGuid(UINT i, GUID FAR *pguid)
+{
+ DebAssert(i >= 0 || i < m_cTypeEntries, "GetTypeGuid");
+ *pguid = Qte(i)->m_ste.m_guid;
+}
+
+/***
+*PUBLIC GenericTypeLibOLE::SetTypeGuid
+*Purpose:
+* Set the guid of the ith TypeInfo.
+*
+*Entry:
+* i - index of TypeInfo to be changed
+* guid - The new guid.
+*
+*Exit:
+* None
+*
+***********************************************************************/
+inline VOID GenericTypeLibOLE::SetTypeGuid(UINT i, REFGUID guid)
+{
+ DebAssert(i >= 0 || i < m_cTypeEntries, "SetTypeGuid");
+
+ Qte(i)->m_ste.m_guid = guid;
+}
+
+/***
+*PUBLIC GenericTypeLibOLE::SetTypeKind
+*Purpose:
+* Set the guid of the ith TypeInfo.
+*
+*Entry:
+* i - index of TypeInfo to be changed
+* tkind - The new typekind.
+*
+*Exit:
+* HRESULT
+*
+***********************************************************************/
+inline VOID GenericTypeLibOLE::SetTypeKind(UINT i, TYPEKIND tkind)
+{
+ DebAssert(i >= 0 || i < m_cTypeEntries, "SetTypeKind");
+
+ Qte(i)->m_ste.m_typekind = tkind;
+}
+
+
+
+/***
+*PUBLIC MajorVerNum
+*Purpose:
+* Setter and getter for m_wMajorVerNum.
+*
+*Entry:
+* None
+*
+*Exit:
+* None
+*
+***********************************************************************/
+inline USHORT GenericTypeLibOLE::MajorVerNum()
+{
+ return m_wMajorVerNum;
+}
+
+inline VOID GenericTypeLibOLE::SetMajorVerNum(USHORT wVer)
+{
+ m_wMajorVerNum = wVer;
+}
+
+
+
+/***
+*PUBLIC MinorVerNum
+*Purpose:
+* Setter and getter for m_wMinorVerNum.
+*
+*Entry:
+* None
+*
+*Exit:
+* None
+*
+***********************************************************************/
+inline USHORT GenericTypeLibOLE::MinorVerNum()
+{
+ return m_wMinorVerNum;
+}
+
+inline VOID GenericTypeLibOLE::SetMinorVerNum(USHORT wVer)
+{
+ m_wMinorVerNum = wVer;
+}
+
+
+
+
+/***
+*PUBLIC Guid
+*Purpose:
+* Setter and getter for m_guid
+*
+*Entry:
+* None
+*
+*Exit:
+* None
+*
+***********************************************************************/
+
+inline GUID GenericTypeLibOLE::Guid()
+{
+ return m_guid;
+}
+
+inline VOID GenericTypeLibOLE::SetLibGuid(GUID guid)
+{
+ m_guid = guid;
+}
+
+
+/***
+*PUBLIC Guid
+*Purpose:
+* Setter and getter for m_wCurVersion.
+*
+*Entry:
+* None
+*
+*Exit:
+* None
+*
+***********************************************************************/
+
+inline WORD GenericTypeLibOLE::GetVersion()
+{
+ return m_wCurVersion;
+}
+
+inline VOID GenericTypeLibOLE::SetDualTypeLib()
+{
+ m_wCurVersion = wDualVersion;
+}
+
+#if ID_DEBUG
+/***
+*PUBLIC SzDebName, CRefs
+*Purpose:
+* Accessor functions for memory leak reporting.
+*
+*Entry:
+* None
+*
+*Exit:
+* None
+*
+***********************************************************************/
+
+inline CHAR *GenericTypeLibOLE::SzDebName()
+{
+ return m_szDebName;
+}
+
+inline ULONG GenericTypeLibOLE::CRefs()
+{
+ return m_cRefs;
+}
+#endif // ID_DEBUG
+
+/***
+*PUBLIC GenericTypeLibOLE::GetSetNameCacheProjTrys()
+*Purpose:
+*
+*Entry:
+* None
+*
+*Exit:
+* None
+*
+***********************************************************************/
+inline VOID GenericTypeLibOLE::DebSetNameCacheModTrys()
+{
+#if ID_TEST
+ m_cNameCacheModTrys++;
+#endif // ID_TEST
+}
+
+inline VOID GenericTypeLibOLE::DebSetNameCacheModHits()
+{
+#if ID_TEST
+ m_cNameCacheModHits++;
+#endif // ID_TEST
+}
+
+inline VOID GenericTypeLibOLE::DebSetNameCacheGlobHits()
+{
+#if ID_TEST
+ m_cNameCacheGlobHits++;
+#endif // ID_TEST
+}
+
+/***
+*PUBLIC GenericTypeLibOLE::GetNameCacheProjTrys()
+*Purpose:
+*
+*Entry:
+* None
+*
+*Exit:
+* returns m_cNameCacheProjTrys
+*
+***********************************************************************/
+inline UINT GenericTypeLibOLE::DebGetNameCacheModTrys()
+{
+#if ID_TEST
+ return m_cNameCacheModTrys;
+#else
+ return 0;
+#endif // ID_TEST
+}
+
+inline UINT GenericTypeLibOLE::DebGetNameCacheModHits()
+{
+#if ID_TEST
+ return m_cNameCacheModHits;
+#else
+ return 0;
+#endif // ID_TEST
+}
+
+inline UINT GenericTypeLibOLE::DebGetNameCacheGlobHits()
+{
+#if ID_TEST
+ return m_cNameCacheGlobHits;
+#else
+ return 0;
+#endif // ID_TEST
+}
+
+
+#endif // ! GTLIBOLE_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/gtlibstg.cxx b/private/oleauto/src/typelib/gtlibstg.cxx
new file mode 100644
index 000000000..69e33d690
--- /dev/null
+++ b/private/oleauto/src/typelib/gtlibstg.cxx
@@ -0,0 +1,1609 @@
+/***
+*gtlibstg.cxx - Light-weight implementations of IStorage and IStream.
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This is used in IE_OLE build only as the default underlying IStorage
+* and IStream implementations for serializing ITypeLib.
+*
+*Revision History:
+* [00] Sept-01-93 mikewo: Created
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "typelib.hxx"
+#include "silver.hxx"
+#include "xstring.h"
+#include "cltypes.hxx"
+#include "clutil.hxx"
+#include "gtlibstg.hxx"
+
+#pragma hdrstop(RTPCHNAME)
+
+#if OE_MAC
+#include <ctype.h>
+#include "macos\resource.h"
+#include "macos\errors.h"
+#include "macos\files.h"
+#endif
+
+#if OE_WIN16
+#include "dos.h"
+#endif // OE_WIN16
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+static char szOleGtlibstgCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleGtlibstgCxx
+#else
+static char szGtlibstgCxx[] = __FILE__;
+#define SZ_FILE_NAME szGtlibstgCxx
+#endif
+#endif //ID_DEBUG
+
+#if OE_MAC
+#define _llseek _lseek // UNDONE MAC: (dougf) correct?
+#endif //OE_MAC
+
+/////////////////////////////////////////////////////////////////////////////
+// Implementation of GTLibStorage
+/////////////////////////////////////////////////////////////////////////////
+
+
+#define CB_GTLIBSTREAM_NAME_MAX 11
+
+// The streaminfo structure used in memory.
+struct StreamInfo {
+ ULONG ulCb; // Length of the stream.
+ union {
+ ULONG ulOffset; // Offset of the stream from the start of the lockbytes.
+ struct {
+ USHORT istrminfoOrg;
+ USHORT istrminfoCur;
+ } map;
+ };
+ LPSTR szName; // Pointer into the name table of the stream's name.
+};
+
+// The streaminfo structure that appears in the serialized format.
+// In the file, there is an array of these which is sorted alphabetically
+// by stream name.
+struct SerStreamInfo {
+ ULONG ulCb; // Length of the stream.
+ USHORT wOffsetName; // Offset of the name in the name table.
+ USHORT wNextStream; // Index into this array of the next stream.
+ // This linked list specifies the order of the
+ // actual stream data in the file.
+};
+
+#define SZ_GTLibStgHdr_Swap "lssss" GUID_Layout
+#define SZ_SerStreamInfo_Swap "lss"
+
+/***
+* OpenForReadOnly - Opens a GTLibStorage on the specified ILockBytes.
+****************************************************************************/
+#pragma code_seg(CS_INIT)
+HRESULT GTLibStorage::OpenForReadOnly(ILockBytesA FAR *plockbytes, IStorageA FAR * FAR *ppstg)
+{
+ BYTE rgbHeaderBuf[256];
+ HRESULT hresult;
+ GTLibStorage FAR *pgtlstg;
+ ULONG cbRead, ulOffset;
+ ULARGE_INTEGER uli;
+ UINT cstrm, cbSer, cbMem, istrm, istrmNext;
+ SerStreamInfo *pserstrminfo;
+ StreamInfo *pstrminfo, *pstrminfoLim;
+ LPSTR szNameTable;
+ LPVOID pvHdrData;
+
+ // Read the header and a bunch of bytes following it, hoping to get
+ // the entire directory table in this one read.
+ uli.LowPart = uli.HighPart = 0;
+ IfOleErrRet(plockbytes->ReadAt(uli, rgbHeaderBuf, sizeof(rgbHeaderBuf), &cbRead));
+#if HP_BIGENDIAN
+ SwapStruct(rgbHeaderBuf, SZ_GTLibStgHdr_Swap);
+#endif // HP_BIGENDIAN
+
+ // If there weren't even enough bytes for the header or if the signature
+ // is wrong, then return INVDATAREAD.
+ if (cbRead < sizeof(GTLibStgHdr) ||
+ ((GTLibStgHdr *)rgbHeaderBuf)->ulSignature != GTLIBSTORAGE_SIGNATURE)
+ return HresultOfScode(TYPE_E_INVDATAREAD);
+
+ cstrm = ((GTLibStgHdr *)rgbHeaderBuf)->wCStrm;
+ cbSer = cstrm * sizeof(SerStreamInfo) + ((GTLibStgHdr *)rgbHeaderBuf)->wCbNameTable;
+ cbMem = cstrm * sizeof(StreamInfo) + ((GTLibStgHdr *)rgbHeaderBuf)->wCbNameTable;
+
+ // Allocate enough memory to hold the stream directory and the name table.
+ if ((pvHdrData = MemAlloc(cbMem)) == NULL)
+ return HresultOfScode(E_OUTOFMEMORY);
+
+ cbRead -= sizeof(GTLibStgHdr);
+ pserstrminfo = (SerStreamInfo *)(((BYTE *)pvHdrData)+cbMem-cbSer);
+
+ // Copy the already-read part of the table from rgbHeaderBuf.
+ memcpy(pserstrminfo, rgbHeaderBuf+sizeof(GTLibStgHdr),
+ (cbRead>cbSer)?cbSer:(UINT)cbRead);
+
+ // If there is any more header info to read, read it.
+ if (cbRead < cbSer) {
+
+ DebAssert(cbRead == sizeof(rgbHeaderBuf)-sizeof(GTLibStgHdr), "OpenForReadOnly");
+ uli.LowPart = sizeof(rgbHeaderBuf);
+ IfOleErrGo(plockbytes->ReadAt(uli,
+ ((BYTE *)pserstrminfo)+sizeof(rgbHeaderBuf)-sizeof(GTLibStgHdr),
+ cbSer-(sizeof(rgbHeaderBuf)-sizeof(GTLibStgHdr)),
+ &cbRead));
+
+ if (cbRead != cbSer-(sizeof(rgbHeaderBuf)-sizeof(GTLibStgHdr))) {
+ hresult = HresultOfScode(TYPE_E_INVDATAREAD);
+ goto Error;
+ }
+ }
+
+#if HP_BIGENDIAN
+ SwapStructArray(pserstrminfo, cstrm, SZ_SerStreamInfo_Swap);
+#endif // HP_BIGENDIAN
+
+ szNameTable = (LPSTR)(pserstrminfo + cstrm);
+
+ // Now expand the serialized table into the in-mem table.
+ for (pstrminfo = (StreamInfo *)pvHdrData, pstrminfoLim = pstrminfo+cstrm;
+ pstrminfo < pstrminfoLim; pstrminfo++, pserstrminfo++) {
+
+ DebAssert((LPVOID)(pstrminfo+1) <= (LPVOID)(pserstrminfo+1), "OpenForReadOnly");
+
+ pstrminfo->ulCb = pserstrminfo->ulCb;
+ pstrminfo->ulOffset = (signed short)pserstrminfo->wNextStream;
+ pstrminfo->szName = szNameTable+pserstrminfo->wOffsetName;
+ }
+
+ pstrminfo -= cstrm;
+
+ // Compute the offset of the first byte of the first stream.
+ ulOffset = sizeof(GTLibStgHdr)+cbSer+((GTLibStgHdr *)rgbHeaderBuf)->wCbExtra;
+
+ // Walk the linked list to compute the offset of each stream.
+ for (istrm = ((GTLibStgHdr *)rgbHeaderBuf)->wStreamFirst;
+ istrm != ~0;
+ istrm = istrmNext) {
+ istrmNext = (int)pstrminfo[istrm].ulOffset;
+ pstrminfo[istrm].ulOffset = ulOffset;
+ ulOffset += pstrminfo[istrm].ulCb;
+ }
+
+ // Now that we've computed all the info we need, instantiate and
+ // initialize the desired GTLibStorage.
+
+ if ((pgtlstg = MemNew(GTLibStorage)) == NULL) {
+ hresult = HresultOfScode(E_OUTOFMEMORY);
+ goto Error;
+ }
+
+ ::new (pgtlstg) GTLibStorage;
+
+ pgtlstg->m_cRefs = 1;
+
+ plockbytes->AddRef();
+ pgtlstg->m_plockbytes = plockbytes;
+
+ pgtlstg->m_guid = ((GTLibStgHdr *)rgbHeaderBuf)->guid;
+ pgtlstg->m_rgstrminfo = pstrminfo;
+ pgtlstg->m_pvHdrData = pvHdrData;
+ pgtlstg->m_cstrminfo = cstrm;
+ *ppstg = pgtlstg;
+ return NOERROR;
+
+Error:
+ MemFree(pvHdrData);
+ return hresult;
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_INIT)
+GTLibStorage::GTLibStorage()
+{
+ m_cRefs = 1;
+ m_plockbytes = NULL;
+ m_rgstrminfo = NULL;
+ m_pvHdrData = NULL;
+ m_cstrminfo = 0;
+ m_ulOffsetNext = 0;
+ m_szNameFirst = NULL;
+ m_szNameLim = NULL;
+ m_istrminfoOpen = (UINT)-1;
+ m_guid = CLSID_NULL;
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_INIT)
+GTLibStorage::~GTLibStorage()
+{
+ if (m_plockbytes != NULL)
+ m_plockbytes->Release();
+
+ MemFree(m_pvHdrData);
+}
+#pragma code_seg()
+
+HRESULT GTLibStorage::QueryInterface(REFIID riid, LPVOID FAR *ppvObj)
+{
+ if (riid == IID_IStorageA) {
+ AddRef();
+ *ppvObj = this;
+ return S_OK;
+ }
+ else {
+ *ppvObj = NULL;
+ return HresultOfScode(E_NOINTERFACE);
+ }
+}
+
+#pragma code_seg(CS_INIT)
+ULONG GTLibStorage::AddRef()
+{
+ return ++m_cRefs;
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_INIT)
+ULONG GTLibStorage::Release()
+{
+ ULONG cRefs;
+
+ DebAssert(m_cRefs > 0, "Release");
+ cRefs = --m_cRefs;
+ if (cRefs == 0) {
+ this->GTLibStorage::~GTLibStorage();
+ MemFree(this);
+ }
+
+ return cRefs;
+}
+#pragma code_seg()
+
+
+/***
+* LookupStream - Map a stream name to the info structure for that stream.
+*
+* Inputs:
+* pwcsName - The name of the desired stream.
+* Outputs:
+* If found, returns a pointer to the matching element of m_rgstrminfo.
+* Otherwise, returns NULL.
+*
+* Implementation:
+* Binary search, which assumes that m_rgstrminfo is sorted by name.
+* I decided against a hashing algorithm because it seems overly complex
+* (to do it right, which would involve a variable-size hash table due
+* to the extreme differences in stream counts between different typelibs)
+* for very little gain. Note that this function will almost always be
+* followed very quickly by a disk hit (either a seek or a read or both).
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+StreamInfo FAR *GTLibStorage::LookupStream(const char FAR* pwcsName)
+{
+ int i;
+ int istrminfoLow, istrminfoHigh, istrminfoCur;
+
+ // Perform a case-insensitive binary search of the streaminfo array.
+
+ istrminfoLow = 0;
+ istrminfoHigh = (int)m_cstrminfo-1;
+
+ while (istrminfoLow <= istrminfoHigh) {
+
+ // Check halfway between high and low possibilities.
+ istrminfoCur = (istrminfoLow+istrminfoHigh)/2;
+
+ // Compare the current guess against the desired string.
+ i = xstrcmp((LPSTR)pwcsName, m_rgstrminfo[istrminfoCur].szName);
+
+ // If the names match, then return the found StreamInfo entry.
+ if (i == 0)
+ return m_rgstrminfo+istrminfoCur;
+
+ // If desired name is lower than the guess, update the upper bound
+ // to be one lower than the current guess.
+ else if (i < 0)
+ istrminfoHigh = istrminfoCur-1;
+
+ // If desired name is higher than the guess, update the lower bound
+ // to be one higher than the current guess.
+ else
+ istrminfoLow = istrminfoCur+1;
+ }
+
+ // The requested name was not found, so return NULL.
+ return NULL;
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_INIT)
+HRESULT GTLibStorage::OpenStream(const OLECHAR FAR* pwcsName, void FAR *reserved1, DWORD grfMode, DWORD reserved2, IStreamA FAR *FAR *ppstm)
+{
+ StreamInfo *pstrminfo;
+ HRESULT hresult;
+#if FV_UNICODE_OLE
+ CHAR FAR* pwcsNameA;
+
+ IfOleErrRet(ConvertStringToA(pwcsName, &pwcsNameA));
+#else //FV_UNICODE_OLE
+ #define pwcsNameA pwcsName
+#endif //FV_UNICODE_OLE
+
+ // If we're trying to open stream with write permissions, make sure
+ // it was the most recently created stream, that we're in the process
+ // creating a new storage, and that the stream being opened has not
+ // yet been written to.
+ if (grfMode & (STGM_READ | STGM_READWRITE | STGM_WRITE)) {
+ if (m_szNameFirst == NULL || xstrcmp(m_szNameFirst, (LPSTR)pwcsNameA) != 0) {
+ DebHalt("OpenStream");
+ hresult = HresultOfScode(STG_E_INVALIDFUNCTION);
+ goto Done;
+ }
+
+ DebAssert(m_istrminfoOpen == -1, "OpenStream");
+
+ // Only one stream to be open at a time when writing streams.
+ if (m_istrminfoOpen != -1) {
+ hresult = HresultOfScode(STG_E_INVALIDFUNCTION);
+ goto Done;
+ }
+
+ m_istrminfoOpen = m_cstrminfo-1;
+
+ DebAssert(m_rgstrminfo[m_istrminfoOpen].szName == m_szNameFirst, "OpenStream");
+
+ // Instantiate the GTLibStream.
+ hresult = GTLibStream::Create(m_plockbytes, m_ulOffsetNext, this, ppstm);
+ goto Done;
+ }
+
+ // Look up the StreamInfo corresponding to pwcsName.
+ // If it isn't found, return FILENOTFOUND, just like the docfile
+ // implementation does.
+ if ((pstrminfo = LookupStream(pwcsNameA)) == NULL) {
+ hresult = HresultOfScode(STG_E_FILENOTFOUND);
+ goto Done;
+ }
+
+ // Create the GTLibStream with the plockbytes, offset and size.
+ hresult = GTLibStream::Open(m_plockbytes, pstrminfo->ulOffset, pstrminfo->ulCb, ppstm);
+
+Done:
+#if FV_UNICODE_OLE
+ ConvertStringFree(pwcsNameA);
+#endif //FV_UNICODE_OLE
+
+ return hresult;
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_INIT)
+HRESULT GTLibStorage::Stat(STATSTGA FAR *pstatstg, DWORD grfStatFlag)
+{
+ pstatstg->pwcsName = NULL;
+ pstatstg->type = STGTY_STORAGE;
+ ULISet32(pstatstg->cbSize, 0);
+ pstatstg->mtime.dwLowDateTime = pstatstg->mtime.dwHighDateTime = 0;
+ pstatstg->ctime.dwLowDateTime = pstatstg->ctime.dwHighDateTime = 0;
+ pstatstg->atime.dwLowDateTime = pstatstg->atime.dwHighDateTime = 0;
+ pstatstg->grfMode = STGM_READ | STGM_SHARE_DENY_WRITE;
+ pstatstg->grfLocksSupported = 0;
+ pstatstg->clsid = m_guid;
+ pstatstg->grfStateBits = 0;
+ pstatstg->reserved = 0;
+ return NOERROR;
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_CREATE)
+HRESULT
+GTLibStorage::Create(
+ ILockBytesA FAR *plockbytes,
+ UINT cstreamMax,
+ IStorageA FAR* FAR* ppstg)
+{
+ ULARGE_INTEGER uli;
+ GTLibStorage *pgtlstg;
+ UINT cbHdrData;
+ HRESULT hresult;
+
+ if ((pgtlstg = MemNew(GTLibStorage)) == NULL)
+ return HresultOfScode(E_OUTOFMEMORY);
+
+ ::new (pgtlstg) GTLibStorage;
+
+ pgtlstg->m_cRefs = 1;
+
+ plockbytes->AddRef();
+ pgtlstg->m_plockbytes = plockbytes;
+
+ // If you change this formula, you must also change the inverse used
+ // in GTLibStorage::Commit.
+ cbHdrData = cstreamMax*(sizeof(StreamInfo)+CB_GTLIBSTREAM_NAME_MAX);
+
+ pgtlstg->m_ulOffsetNext = sizeof(GTLibStgHdr)+cstreamMax*(sizeof(SerStreamInfo)+CB_GTLIBSTREAM_NAME_MAX);
+ DebAssert(pgtlstg->m_ulOffsetNext <= (ULONG)cbHdrData+sizeof(GTLibStgHdr), "Create");
+
+ // alloc the buffer to the larger of cbHdrData (what we need) and
+ // m_ulOffsetNext (what we are using to fill the header region of the file
+ // with zeros).
+ if ((pgtlstg->m_pvHdrData = MemZalloc((size_t)max(cbHdrData, pgtlstg->m_ulOffsetNext))) == NULL) {
+ hresult = HresultOfScode(E_OUTOFMEMORY);
+ }
+
+ // Initialize the header region of the file with zeros.
+ uli.HighPart = uli.LowPart = 0;
+ IfOleErrGo(plockbytes->WriteAt(uli, pgtlstg->m_pvHdrData, pgtlstg->m_ulOffsetNext, NULL));
+
+ // Initialize the allocation heap of StreamInfos, which starts at
+ // m_pvHdrData and grow up.
+ pgtlstg->m_rgstrminfo = (StreamInfo *)pgtlstg->m_pvHdrData;
+
+ // Initialize the allocation heap of stream names, which starts at
+ // the top of m_pvHdrData and grows down.
+ pgtlstg->m_szNameFirst = ((char *)pgtlstg->m_pvHdrData)+cbHdrData;
+ pgtlstg->m_szNameLim = pgtlstg->m_szNameFirst;
+
+ *ppstg = pgtlstg;
+ return NOERROR;
+
+Error:
+ pgtlstg->Release();
+ return hresult;
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_CREATE)
+HRESULT
+GTLibStorage::CreateStream(
+ const OLECHAR FAR* pwcsName,
+ DWORD grfMode,
+ DWORD reserved1,
+ DWORD reserved2,
+ IStreamA FAR *FAR *ppstm)
+{
+ LPSTR szName;
+ HRESULT hresult;
+#if FV_UNICODE_OLE
+ CHAR FAR* pwcsNameA;
+#endif //FV_UNICODE_OLE
+
+ DebAssert(m_istrminfoOpen == -1, "CreateStream");
+
+ // Only one stream to be open at a time when creating streams.
+ if (m_istrminfoOpen != -1)
+ return HresultOfScode(STG_E_INVALIDFUNCTION);
+
+#if FV_UNICODE_OLE
+ IfOleErrRet(ConvertStringToA(pwcsName, &pwcsNameA));
+#endif //FV_UNICODE_OLE
+
+ // Update the stream count and record the open stream. This implicitly
+ // allocates a new strminfo structure from pvHdrData (the m_rgstrminfo
+ // grows up from the bottom of pvHdrData).
+ m_istrminfoOpen = m_cstrminfo++;
+
+ // Allocate the stream name from pvHdrData. The name table grows down
+ // from the top of pvHdrData.
+ szName = m_szNameFirst-xstrblen0(pwcsNameA);
+
+ // If the name collided with the stream directory table, we've tried
+ // to open too many streams with names that were too long.
+ if (szName < (LPSTR)(m_rgstrminfo+m_cstrminfo)) {
+ hresult = HresultOfScode(STG_E_TOOMANYOPENFILES);
+ goto Error;
+ }
+
+ // Copy the name into the allocated space and point the streaminfo at it.
+ xstrcpy(szName, pwcsNameA);
+ m_rgstrminfo[m_istrminfoOpen].szName = szName;
+ m_rgstrminfo[m_istrminfoOpen].ulCb = 0;
+
+ // Finally, instantiate the GTLibStream.
+ IfOleErrGo(GTLibStream::Create(m_plockbytes, m_ulOffsetNext, this, ppstm));
+
+ m_szNameFirst = szName;
+#if FV_UNICODE_OLE
+ ConvertStringFree(pwcsNameA);
+#endif //FV_UNICODE_OLE
+ return NOERROR;
+
+Error:
+ m_cstrminfo--;
+ m_istrminfoOpen = (UINT)-1;
+#if FV_UNICODE_OLE
+ ConvertStringFree(pwcsNameA);
+#endif //FV_UNICODE_OLE
+ return hresult;
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_CREATE)
+void GTLibStorage::NotifyStreamClosed(ULONG ulCb)
+{
+ DebAssert(m_istrminfoOpen >= 0 && m_istrminfoOpen < m_cstrminfo, "NotifyStreamClosed");
+ m_rgstrminfo[m_istrminfoOpen].ulCb = ulCb;
+ m_ulOffsetNext += ulCb;
+ m_istrminfoOpen = (UINT)-1;
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_CREATE)
+/***
+*SwapStreamInfos() - Swaps two StreamInfos -- used by SortStreamInfo.
+***********************************************************************/
+void GTLibStorage::SwapStreamInfos(StreamInfo *pstrminfo1, StreamInfo *pstrminfo2)
+{
+ ULONG ulCbTmp;
+ LPSTR szNameTmp;
+ USHORT istrminfoTmp;
+
+ // Swap only the ulCb, szName, and istrminfoCur fields.
+ ulCbTmp = pstrminfo1->ulCb;
+ szNameTmp = pstrminfo1->szName;
+ istrminfoTmp = pstrminfo1->map.istrminfoCur;
+ pstrminfo1->ulCb = pstrminfo2->ulCb;
+ pstrminfo1->szName = pstrminfo2->szName;
+ pstrminfo1->map.istrminfoCur = pstrminfo2->map.istrminfoCur;
+ pstrminfo2->ulCb = ulCbTmp;
+ pstrminfo2->szName = szNameTmp;
+ pstrminfo2->map.istrminfoCur = istrminfoTmp;
+
+ // Update the affected istrminfoOrg fields in rgstrminfo so that
+ // we maintain the invariant that the ith element's istrminfoOrg contains
+ // the index of the element that was the ith element before sorting.
+ // In other words, we are tracking the movement of elements so we can
+ // easily walk the elements in the original order once sorting is done.
+ m_rgstrminfo[(int)pstrminfo1->map.istrminfoCur].map.istrminfoOrg = (USHORT)(pstrminfo1-m_rgstrminfo);
+ m_rgstrminfo[(int)pstrminfo2->map.istrminfoCur].map.istrminfoOrg = (USHORT)(pstrminfo2-m_rgstrminfo);
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*void SortStreamInfo - Sorts a StreamInfo array by name using quicksort.
+***********************************************************************/
+void GTLibStorage::SortStreamInfo(StreamInfo *rgstrminfo, UINT uCount)
+{
+ LPSTR szNameMid;
+ UINT iLow=0, iHigh=uCount-1;
+
+ if (uCount <= 1)
+ return;
+
+ // Get the middle element as the value for partition.
+ szNameMid = rgstrminfo[uCount/2].szName;
+
+ while (iLow < iHigh) {
+ while ((xstrcmp(rgstrminfo[iLow].szName,szNameMid) < 0) && (iLow < iHigh))
+ iLow++;
+
+ while ((xstrcmp(rgstrminfo[iHigh].szName,szNameMid) >= 0) && (iLow < iHigh))
+ iHigh--;
+
+ if (iLow < iHigh) {
+ // swap the StreamInfos
+ SwapStreamInfos(rgstrminfo+iLow, rgstrminfo+iHigh);
+ } // if
+ } // while
+
+
+ DebAssert(iLow == iHigh, "Terminating condition");
+
+ // Take care of all the termination conditions. iLow and iHigh are
+ // pointing to the same location. Adjust these so that it points to the
+ // end of the subarrays.
+ if (iHigh == uCount-1) {
+ // all elements were < or = to ulMid.
+ //
+ // if the last element is ulMid then dec. iLow
+ // i.e. reduce the array size if possible.
+ if (xstrcmp(rgstrminfo[iHigh].szName, szNameMid) < 0) {
+ // swap the middle element with the last element.
+ SwapStreamInfos(rgstrminfo+uCount/2, rgstrminfo+iHigh);
+ }
+ iLow--;
+ }
+
+ else if (iLow == 0) {
+ // all elements were > or = to ulMid
+ //
+ // if the last element is ulMid then inc. iHigh
+ // i.e. reduce the array size if possible.
+ if (xstrcmp(rgstrminfo[iHigh].szName, szNameMid) > 0) {
+ // swap the middle element with the first element.
+ SwapStreamInfos(rgstrminfo, rgstrminfo+uCount/2);
+ }
+ iHigh++;
+ }
+
+ else {
+ // Adjust iLow and iHigh so that these points to the right place
+ if (xstrcmp(rgstrminfo[iHigh].szName, szNameMid) > 0)
+ iLow--;
+ else
+ iHigh++;
+ }
+
+ // Sort the lower sub array
+ SortStreamInfo(rgstrminfo, (UINT)iLow+1);
+
+ // Sort the upper sub array
+ SortStreamInfo(rgstrminfo+iLow+1, (UINT)(uCount-iLow-1));
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_CREATE)
+HRESULT GTLibStorage::Commit(DWORD grfCommitFlags)
+{
+ GTLibStgHdr gtlhdr;
+ SerStreamInfo serstrminfo;
+ ULARGE_INTEGER uli;
+ HRESULT hresult;
+ UINT istrminfo, cstreamMax;
+
+ // We don't need the ulOffset fields anymore, so record the current
+ // sort order in that field.
+ for (istrminfo = 0; istrminfo < m_cstrminfo; istrminfo++) {
+ m_rgstrminfo[istrminfo].map.istrminfoOrg =
+ m_rgstrminfo[istrminfo].map.istrminfoCur = istrminfo;
+ }
+
+ // Sort m_rgstrminfo by name, preserving the original sort order
+ // in the istrminfoOrg fields. This allows us to easily construct the
+ // list (sorted by stream offset) of the SERSTREAMINFOs.
+ SortStreamInfo(m_rgstrminfo, m_cstrminfo);
+
+ // Note that this is the inverse calculation performed to compute
+ // the size of the buffer initially. If you change that, this must
+ // also be changed.
+ cstreamMax = (((BYTE *)m_szNameLim)-((BYTE *)m_pvHdrData))/
+ (sizeof(StreamInfo)+CB_GTLIBSTREAM_NAME_MAX);
+
+ gtlhdr.ulSignature = GTLIBSTORAGE_SIGNATURE;
+ gtlhdr.wCStrm = m_cstrminfo;
+ gtlhdr.wCbExtra = ((BYTE *)m_szNameFirst)-(BYTE *)(m_rgstrminfo+m_cstrminfo);
+ gtlhdr.wCbExtra -= (cstreamMax-m_cstrminfo)*(sizeof(StreamInfo)-sizeof(SerStreamInfo));
+ gtlhdr.wCbNameTable = (USHORT)((m_szNameLim - m_szNameFirst)*sizeof(*m_szNameFirst));
+ gtlhdr.wStreamFirst = m_rgstrminfo[0].map.istrminfoOrg;
+ gtlhdr.guid = m_guid;
+
+ // Write out the header info at the beginning of the file.
+ uli.HighPart = uli.LowPart = 0;
+#if HP_BIGENDIAN
+ SwapStruct(&gtlhdr, SZ_GTLibStgHdr_Swap);
+#endif // HP_BIGENDIAN
+ IfOleErrRet(m_plockbytes->WriteAt(uli, &gtlhdr, sizeof(gtlhdr), NULL));
+#if HP_BIGENDIAN
+ // Swap the header structure back because we later use parts of it.
+ SwapStruct(&gtlhdr, SZ_GTLibStgHdr_Swap);
+#endif // HP_BIGENDIAN
+
+ uli.LowPart += sizeof(gtlhdr);
+
+ // Write out the streaminfo table.
+ for (istrminfo = 0; istrminfo < m_cstrminfo; istrminfo++) {
+ serstrminfo.ulCb = m_rgstrminfo[istrminfo].ulCb;
+ serstrminfo.wOffsetName = m_rgstrminfo[istrminfo].szName - m_szNameFirst;
+ serstrminfo.wNextStream = m_rgstrminfo[istrminfo].map.istrminfoCur;
+ if (serstrminfo.wNextStream != m_cstrminfo-1)
+ serstrminfo.wNextStream = m_rgstrminfo[serstrminfo.wNextStream+1].map.istrminfoOrg;
+ else
+ serstrminfo.wNextStream = (USHORT)-1;
+#if HP_BIGENDIAN
+ SwapStruct(&serstrminfo, SZ_SerStreamInfo_Swap);
+#endif // HP_BIGENDIAN
+ IfOleErrRet(m_plockbytes->WriteAt(uli, &serstrminfo, sizeof(serstrminfo), NULL));
+ uli.LowPart += sizeof(serstrminfo);
+ }
+
+ // Finally, write out the name table, if there's any name to write out.
+ // Do NOT write out a 0-length name table because that will truncate the
+ // file.
+ if (gtlhdr.wCbNameTable != 0)
+ return m_plockbytes->WriteAt(uli, m_szNameFirst, gtlhdr.wCbNameTable, NULL);
+ else
+ return NOERROR;
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_RARE)
+HRESULT GTLibStorage::CreateStorage(const OLECHAR FAR* pwcsName, DWORD grfMode, DWORD reserved1, DWORD reserved2, IStorageA FAR *FAR *ppstg)
+{
+ DebHalt("Method not implemented");
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT GTLibStorage::OpenStorage(const OLECHAR FAR* pwcsName, IStorageA FAR *pstgPriority, DWORD grfMode, SNBA snbExclude, DWORD reserved, IStorageA FAR *FAR *ppstg)
+{
+ DebHalt("Method not implemented");
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT GTLibStorage::CopyTo(DWORD ciidExclude, IID const FAR *rgiidExclude, SNBA snbExclude, IStorageA FAR *pstgDest)
+{
+ DebHalt("Method not implemented");
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT GTLibStorage::MoveElementTo(OLECHAR const FAR* lpszName, IStorageA FAR *pstgDest, OLECHAR const FAR* lpszNewName, DWORD grfFlags)
+{
+ DebHalt("Method not implemented");
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT GTLibStorage::Revert()
+{
+ DebHalt("Method not implemented");
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT GTLibStorage::EnumElements(DWORD reserved1, void FAR *reserved2, DWORD reserved3, IEnumSTATSTGA FAR *FAR *ppenm)
+{
+ DebHalt("Method not implemented");
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT GTLibStorage::DestroyElement(const OLECHAR FAR* pwcsName)
+{
+ DebHalt("Method not implemented");
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT GTLibStorage::RenameElement(const OLECHAR FAR* pwcsOldName, const OLECHAR FAR* pwcsNewName)
+{
+ DebHalt("Method not implemented");
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT GTLibStorage::SetElementTimes(const OLECHAR FAR *lpszName, FILETIME const FAR *pctime, FILETIME const FAR *patime, FILETIME const FAR *pmtime)
+{
+ DebHalt("Method not implemented");
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT GTLibStorage::SetStateBits(DWORD grfStateBits, DWORD grfMask)
+{
+ DebHalt("Method not implemented");
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+#pragma code_seg()
+
+HRESULT GTLibStorage::SetClass(REFCLSID clsid)
+{
+ m_guid = clsid;
+ return NOERROR;
+}
+
+/////////////////////////////////////////////////////////////////////////////
+// Implementation of GTLibStream
+/////////////////////////////////////////////////////////////////////////////
+
+
+#pragma code_seg(CS_INIT)
+GTLibStream::GTLibStream()
+{
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_INIT)
+GTLibStream::~GTLibStream()
+{
+ ULARGE_INTEGER uli;
+
+ if (m_pgtlstgContainer != NULL) {
+ m_pgtlstgContainer->NotifyStreamClosed(m_ulCb);
+ uli.HighPart = 0;
+ uli.LowPart = m_ulOffsetStart+m_ulCb;
+ (void)(m_plockbytes->WriteAt(uli, NULL, 0, NULL));
+ }
+
+ if (m_plockbytes != NULL)
+ m_plockbytes->Release();
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_INIT)
+HRESULT GTLibStream::Open(ILockBytesA FAR *plockbytes, ULONG ulOffset, ULONG ulCb, IStreamA FAR * FAR *ppstm)
+{
+ GTLibStream FAR *pstm;
+
+ if ((pstm = MemNew(GTLibStream)) == NULL)
+ return HresultOfScode(E_OUTOFMEMORY);
+
+ ::new (pstm) GTLibStream;
+
+ pstm->m_cRefs = 1;
+
+ plockbytes->AddRef();
+ pstm->m_plockbytes = plockbytes;
+
+ pstm->m_ulOffsetStart = ulOffset;
+ pstm->m_ulOffsetCur = 0;
+ pstm->m_ulCb = ulCb;
+ pstm->m_pgtlstgContainer = NULL;
+
+ *ppstm = pstm;
+ return NOERROR;
+}
+#pragma code_seg()
+
+HRESULT GTLibStream::QueryInterface(REFIID riid, LPVOID FAR *ppvObj)
+{
+ if (riid == IID_IStreamA) {
+ AddRef();
+ *ppvObj = this;
+ return S_OK;
+ }
+ else {
+ *ppvObj = NULL;
+ return HresultOfScode(E_NOINTERFACE);
+ }
+}
+
+#pragma code_seg(CS_INIT)
+ULONG GTLibStream::AddRef()
+{
+ return ++m_cRefs;
+}
+
+ULONG GTLibStream::Release()
+{
+ ULONG cRefs;
+
+ DebAssert(m_cRefs > 0, "Release");
+ cRefs = --m_cRefs;
+ if (cRefs == 0) {
+ this->GTLibStream::~GTLibStream();
+ MemFree(this);
+ }
+
+ return cRefs;
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_INIT)
+HRESULT GTLibStream::Read(void HUGEP *pv, ULONG cb, ULONG FAR *pcbRead)
+{
+ ULARGE_INTEGER uli;
+
+ // Compute the position from which the read is to take place.
+ uli.HighPart = 0;
+ uli.LowPart = m_ulOffsetStart+m_ulOffsetCur;
+
+ // Truncate the read if it is an attempt to go beyond the end of the
+ // the stream.
+ if (m_ulOffsetCur + cb > m_ulCb)
+ cb = m_ulCb-m_ulOffsetCur;
+
+ // Update m_ulOffsetCur to the new seek position.
+ m_ulOffsetCur += cb;
+
+ return m_plockbytes->ReadAt(uli, pv, cb, pcbRead);
+}
+#pragma code_seg()
+
+HRESULT GTLibStream::Seek(LARGE_INTEGER dlibMove, DWORD dwOrigin, ULARGE_INTEGER FAR *plibNewPosition)
+{
+ DebAssert(dlibMove.HighPart == 0 || (dlibMove.HighPart == -1 && (dlibMove.LowPart & 0x80000000)), "ReadAt");
+
+ switch (dwOrigin) {
+ case STREAM_SEEK_SET:
+ // Don't allow a seek before the beginning of the stream.
+ if (dlibMove.HighPart == -1)
+ goto Error;
+
+ m_ulOffsetCur = dlibMove.LowPart;
+ break;
+
+ case STREAM_SEEK_CUR:
+ // Don't allow a seek before the beginning of the stream.
+ if ((m_ulOffsetCur + dlibMove.LowPart) & 0x80000000)
+ goto Error;
+
+ m_ulOffsetCur += dlibMove.LowPart;
+ break;
+
+ case STREAM_SEEK_END:
+ // Don't allow a seek before the beginning of the stream.
+ if (dlibMove.LowPart > m_ulCb)
+ goto Error;
+
+ m_ulOffsetCur = m_ulCb-dlibMove.LowPart;
+ break;
+
+ default:
+Error:
+ DebHalt("Seek");
+ return HresultOfScode(STG_E_INVALIDPARAMETER);
+ }
+
+ if (plibNewPosition != NULL) {
+ plibNewPosition->HighPart = 0;
+ plibNewPosition->LowPart = m_ulOffsetCur;
+ }
+ return NOERROR;
+}
+
+
+#pragma code_seg(CS_CREATE)
+HRESULT
+GTLibStream::Create(
+ ILockBytesA FAR *plockbytes,
+ ULONG ulOffset,
+ GTLibStorage FAR *pgtlstgContainer,
+ IStreamA FAR * FAR *ppstm)
+{
+ GTLibStream FAR *pstm;
+
+ if ((pstm = MemNew(GTLibStream)) == NULL)
+ return HresultOfScode(E_OUTOFMEMORY);
+
+ ::new (pstm) GTLibStream;
+
+ pstm->m_cRefs = 1;
+
+ plockbytes->AddRef();
+ pstm->m_plockbytes = plockbytes;
+
+ pstm->m_ulOffsetStart = ulOffset;
+ pstm->m_ulOffsetCur = 0;
+ pstm->m_pgtlstgContainer = pgtlstgContainer;
+
+ DebAssert(pgtlstgContainer != NULL && pgtlstgContainer->m_istrminfoOpen != -1, "Create");
+ pstm->m_ulCb = pgtlstgContainer->m_rgstrminfo[pgtlstgContainer->m_istrminfoOpen].ulCb;
+
+ *ppstm = pstm;
+ return NOERROR;
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_CREATE)
+HRESULT GTLibStream::Write(void const HUGEP *pv, ULONG cb, ULONG FAR *pcbWritten)
+{
+ ULARGE_INTEGER uli;
+
+ // Compute the position from which the read is to take place.
+ uli.HighPart = 0;
+ uli.LowPart = m_ulOffsetStart+m_ulOffsetCur;
+
+ // Update m_ulOffsetCur to the new seek position.
+ m_ulOffsetCur += cb;
+
+ // If the new offset is greater than the current length of the stream,
+ // update the length to the new offset.
+ if (m_ulOffsetCur > m_ulCb)
+ m_ulCb = m_ulOffsetCur;
+
+ // Perform the write.
+ return m_plockbytes->WriteAt(uli, pv, cb, pcbWritten);
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_CREATE)
+HRESULT GTLibStream::Commit(DWORD grfCommitFlags)
+{
+ return NOERROR;
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_RARE)
+HRESULT GTLibStream::SetSize(ULARGE_INTEGER libNewSize)
+{
+ DebHalt("Method not implemented");
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT GTLibStream::CopyTo(IStreamA FAR *pstm, ULARGE_INTEGER cb, ULARGE_INTEGER FAR *pcbRead, ULARGE_INTEGER FAR *pcbWritten)
+{
+ DebHalt("Method not implemented");
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT GTLibStream::Revert()
+{
+ DebHalt("Method not implemented");
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT GTLibStream::LockRegion(ULARGE_INTEGER libOffset, ULARGE_INTEGER cb, DWORD dwLockType)
+{
+ DebHalt("Method not implemented");
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT GTLibStream::UnlockRegion(ULARGE_INTEGER libOffset, ULARGE_INTEGER cb, DWORD dwLockType)
+{
+ DebHalt("Method not implemented");
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT GTLibStream::Stat(STATSTGA FAR *pstatstg, DWORD grfStatFlag)
+{
+ DebHalt("Method not implemented");
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT GTLibStream::Clone(IStreamA FAR * FAR *ppstm)
+{
+ DebHalt("Method not implemented");
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+#pragma code_seg()
+
+/////////////////////////////////////////////////////////////////////////////
+// Implementation of FileLockBytes
+/////////////////////////////////////////////////////////////////////////////
+
+class FileLockBytes : public ILockBytesA
+{
+friend HRESULT OpenFileLockBytes(BOOL isNew,
+ LPOLESTR szFile,
+ ILockBytesA FAR* FAR* pplockbytes);
+friend HRESULT CreateFileLockBytesOnHFILE(int hfile,
+ BOOL isNew,
+ ULONG oStart,
+ ULONG cbData,
+ ILockBytesA FAR* FAR* pplockbytes);
+
+public:
+
+ // Methods implemented for IUnknown.
+ STDMETHOD(QueryInterface)(REFIID riid, LPVOID FAR *ppvObj);
+ STDMETHOD_(ULONG, AddRef)(void);
+ STDMETHOD_(ULONG, Release)(void);
+
+ // Methods implemented for ILockBytes.
+ STDMETHOD(ReadAt)(ULARGE_INTEGER uliOffset,
+ void HUGEP *pv,
+ ULONG cb,
+ ULONG FAR *pcbRead);
+ STDMETHOD(WriteAt)(ULARGE_INTEGER uliOffset,
+ void const HUGEP *pv,
+ ULONG cb,
+ ULONG FAR *pcbWritten);
+ STDMETHOD(Flush)(void);
+ STDMETHOD(SetSize)(ULARGE_INTEGER uliCb);
+ STDMETHOD(LockRegion)(ULARGE_INTEGER uliOffset,
+ ULARGE_INTEGER uliCb,
+ DWORD dwLockType);
+ STDMETHOD(UnlockRegion)(ULARGE_INTEGER uliOffset,
+ ULARGE_INTEGER uliCb,
+ DWORD dwLockType);
+ STDMETHOD(Stat)(STATSTGA FAR *pstatstg, DWORD grfStatFlag);
+
+protected:
+ FileLockBytes();
+ ~FileLockBytes();
+
+ ULONG m_cRefs; // The reference count.
+
+ int m_hfile; // The DOS file handle on windows
+ // The wings sopen file handle on the mac.
+ // -1 if the file is not open.
+
+ ULONG m_oStart;
+};
+
+#if OE_WIN32
+class FileLockBytesMemory : public ILockBytesA
+{
+friend HRESULT CreateFileLockBytesOnHFILE(int hfile,
+ BOOL isNew,
+ ULONG oStart,
+ ULONG cbData,
+ ILockBytesA FAR* FAR* pplockbytes);
+
+public:
+
+ // Methods implemented for IUnknown.
+ STDMETHOD(QueryInterface)(REFIID riid, LPVOID FAR *ppvObj);
+ STDMETHOD_(ULONG, AddRef)(void);
+ STDMETHOD_(ULONG, Release)(void);
+
+ // Methods implemented for ILockBytes.
+ STDMETHOD(ReadAt)(ULARGE_INTEGER uliOffset,
+ void HUGEP *pv,
+ ULONG cb,
+ ULONG FAR *pcbRead);
+ STDMETHOD(WriteAt)(ULARGE_INTEGER uliOffset,
+ void const HUGEP *pv,
+ ULONG cb,
+ ULONG FAR *pcbWritten);
+ STDMETHOD(Flush)(void);
+ STDMETHOD(SetSize)(ULARGE_INTEGER uliCb);
+ STDMETHOD(LockRegion)(ULARGE_INTEGER uliOffset,
+ ULARGE_INTEGER uliCb,
+ DWORD dwLockType);
+ STDMETHOD(UnlockRegion)(ULARGE_INTEGER uliOffset,
+ ULARGE_INTEGER uliCb,
+ DWORD dwLockType);
+ STDMETHOD(Stat)(STATSTGA FAR *pstatstg, DWORD grfStatFlag);
+
+protected:
+ FileLockBytesMemory();
+ ~FileLockBytesMemory();
+
+ ULONG m_cRefs; // The reference count.
+
+ int m_hfile; // The DOS file handle on windows
+ // The wings sopen file handle on the mac.
+ // -1 if the file is not open.
+
+ HANDLE m_hmapping; // The file-mapping handle
+ // NULL if the file is not open.
+
+ LPVOID m_pvmappingBase; // pointer to the file mapping
+ LPVOID m_pvmapping; // pointer to the file mapping, with offset to ILockBytes start added
+ ULONG m_ulEOF; // offset of end-of-file
+};
+#endif //OE_WIN32
+
+
+#pragma code_seg(CS_INIT)
+HRESULT OpenFileLockBytes(BOOL isNew, LPOLESTR szFile, ILockBytesA **pplockbytes)
+{
+ int hfile;
+ HRESULT hresult;
+
+#if OE_MAC
+ int omode, smode;
+
+ if(isNew){
+ omode = (_O_CREAT | _O_BINARY | _O_RDWR);
+ smode = _SH_DENYRW;
+ }else{
+ omode = (_O_BINARY | _O_RDONLY);
+ smode = _SH_DENYNO;
+ }
+ if((hfile = _sopen(szFile, omode, smode, (_S_IWRITE | _S_IREAD))) == -1){
+ // "too many files" on sopen sets errno, but not _macerrno
+ if (_macerrno == 0 && errno == EMFILE)
+ _macerrno = tmfoErr;
+ hresult = HresultOfTiperr(TiperrOfOSErr((OSErr)_macerrno));
+ goto Error;
+ }
+#else // OE_MAC
+ // The win16 and win32 implementation.
+ OFSTRUCT ofstruct;
+
+ hfile = oOpenFile(szFile,
+ &ofstruct,
+ isNew
+ ? (OF_CREATE | OF_WRITE | OF_SHARE_EXCLUSIVE)
+ : (OF_READ));
+
+ if (hfile == HFILE_ERROR) {
+ hresult = HresultOfTiperr(TiperrOfOFErr(ofstruct.nErrCode));
+ goto Error;
+ }
+#endif // OE_MAC
+
+ IfFailGoTo(CreateFileLockBytesOnHFILE(hfile, isNew, 0L, 0L, pplockbytes), Error);
+ return NOERROR;
+
+Error:;
+#if OE_MAC
+ _close(hfile);
+#else
+ _lclose(hfile);
+#endif
+ return hresult;
+}
+
+HRESULT
+CreateFileLockBytesOnHFILE(int hfile, BOOL isNew, ULONG oStart, ULONG cbData, ILockBytesA **pplockbytes)
+{
+
+ FileLockBytes *plockbytes;
+
+#if OE_WIN32
+ if (isNew) {
+MappedFileFailed:
+#endif //OE_WIN32
+
+ if ((plockbytes = MemNew(FileLockBytes)) == NULL)
+ return HresultOfScode(E_OUTOFMEMORY);
+ ::new (plockbytes) FileLockBytes;
+ plockbytes->m_hfile = hfile;
+ plockbytes->m_oStart = oStart;
+ *pplockbytes = plockbytes;
+
+#if OE_WIN32
+ } else {
+ // use memory-mapped file I/O for read-only typelibs
+
+ HANDLE h;
+ LPVOID lpv;
+ FileLockBytesMemory *plockmem;
+ DWORD ulEOFLow, ulEOFHigh;
+ SYSTEM_INFO si;
+ ULONG oMappedStart;
+ static DWORD dwAllocationGranularity=0;
+
+ // get the length of the file as a 64-bit int
+ ulEOFLow = GetFileSize((HANDLE)hfile, &ulEOFHigh);
+ if (ulEOFLow == 0xffffffff && GetLastError()) {
+ goto MappedFileFailed; // use the old I/O code
+ }
+
+ DebAssert(ulEOFHigh == 0, "Don't support files >4GB");
+ ulEOFLow -= oStart;
+
+ h = CreateFileMapping((HANDLE)hfile, // handle of file to map
+ NULL, // security attributes pointer
+ PAGE_READONLY, // fdwProtect
+ 0, // dwMaximumSizeHigh
+ 0, // dwMaximumSizeLow
+ NULL // lpszMapName (create with no name)
+ );
+ if (h == NULL) {
+ goto MappedFileFailed; // use the old I/O code
+ }
+
+ // look up and cache information about the allocation granularity
+ if (dwAllocationGranularity == 0) {
+ GetSystemInfo(&si);
+ dwAllocationGranularity = si.dwAllocationGranularity;
+ }
+
+ // The file offset passed to MapViewOfFile() must be aligned on the
+ // machine's allocation granularity (typically 64K)
+ oMappedStart = oStart % dwAllocationGranularity;
+ oStart -= oMappedStart;
+ if (cbData) {
+ // if the caller only wants a specific part of the file mapped in,
+ // we may have to map more in so that the start of the mapping is
+ // properly aligned
+ cbData+=oMappedStart;
+ }
+
+ lpv = MapViewOfFile(h, // hMapObject
+ FILE_MAP_READ, // fdwAccess
+ 0, // dwFileOffsetHigh
+ oStart, // dwFileOffsetLow
+ cbData // cbMap (0 = entire file)
+ );
+ if (lpv == NULL) {
+ CloseHandle(h);
+ goto MappedFileFailed; // possibly out of memory for the mapping
+ }
+
+ if ((plockmem = MemNew(FileLockBytesMemory)) == NULL) {
+ UnmapViewOfFile(lpv);
+ CloseHandle(h);
+ return HresultOfScode(E_OUTOFMEMORY);
+ }
+ ::new (plockmem) FileLockBytesMemory;
+ plockmem->m_hfile = hfile;
+ plockmem->m_hmapping = h;
+ plockmem->m_pvmappingBase = lpv;
+ plockmem->m_pvmapping = ((char *)lpv)+oMappedStart;
+ plockmem->m_ulEOF = ulEOFLow;
+ *pplockbytes = plockmem;
+ }
+#endif //OE_WIN32
+
+ return NOERROR;
+}
+
+#pragma code_seg()
+
+#pragma code_seg(CS_INIT)
+FileLockBytes::FileLockBytes()
+{
+ m_cRefs = 1;
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_INIT)
+FileLockBytes::~FileLockBytes()
+{
+#if OE_MAC
+ if (m_hfile != -1)
+ _close(m_hfile);
+#else // OE_MAC
+ // Close the DOS file handle on the DLL, if it's open.
+ if (m_hfile != -1)
+ _lclose(m_hfile);
+#endif // OE_MAC
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_INIT)
+ULONG FileLockBytes::AddRef()
+{
+ return ++m_cRefs;
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_INIT)
+ULONG FileLockBytes::Release()
+{
+ ULONG cRefs;
+
+ DebAssert(m_cRefs > 0, "Release");
+
+ cRefs = --m_cRefs;
+ if (cRefs == 0) {
+ this->FileLockBytes::~FileLockBytes();
+ MemFree(this);
+ }
+ return cRefs;
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_INIT)
+HRESULT
+FileLockBytes::ReadAt(
+ ULARGE_INTEGER uliOffset,
+ void HUGEP *pv,
+ ULONG cb,
+ ULONG FAR *pcbRead)
+{
+ UINT cbRead;
+ DebAssert(m_hfile != -1, "ReadAt");
+ DebAssert(uliOffset.HighPart == 0, "ReadAt");
+
+#if !OE_MAC
+ // Ensure that cb fits in a WORD for _lread.
+ if ((cb & 0xffff0000) != 0) {
+ return HresultOfTiperr(TIPERR_ReadFault);
+ }
+#endif // !OE_MAC
+
+ // Seek to the specified location, relative to the start of the resource.
+ if (_llseek(m_hfile, uliOffset.LowPart + m_oStart, SEEK_SET) == -1L) {
+ return HresultOfScode(STG_E_SEEKERROR);
+ }
+
+#if OE_MAC
+ cbRead = _read(m_hfile, pv, cb);
+
+ if (cbRead == -1) {
+ return HresultOfScode(STG_E_READFAULT);
+ }
+#else // OE_MAC
+ cbRead = _lread(m_hfile, (LPSTR)pv, (WORD)cb);
+
+ if (cbRead == HFILE_ERROR) {
+ return HresultOfScode(STG_E_READFAULT);
+ }
+#endif // OE_MAC
+
+ if (pcbRead != NULL)
+ *pcbRead = cbRead;
+
+ return NOERROR;
+}
+#pragma code_seg()
+
+HRESULT FileLockBytes::QueryInterface(REFIID riid, LPVOID FAR *ppvObj)
+{
+ if (riid == IID_ILockBytesA) {
+ AddRef();
+ *ppvObj = (ILockBytesA *)this;
+ return S_OK;
+ }
+ else {
+ *ppvObj = NULL;
+ return HresultOfScode(E_NOINTERFACE);
+ }
+}
+
+#pragma code_seg(CS_CREATE)
+HRESULT
+FileLockBytes::WriteAt(
+ ULARGE_INTEGER uliOffset,
+ void const HUGEP *pv,
+ ULONG cb,
+ ULONG FAR *pcbWritten)
+{
+ UINT cbWritten;
+ DebAssert(m_hfile != -1, "WriteAt");
+ DebAssert(uliOffset.HighPart == 0, "WriteAt");
+
+#if !OE_MAC
+ // Ensure that cb fits in a WORD for _lwrite.
+ if ((cb & 0xffff0000) != 0) {
+ return HresultOfTiperr(TIPERR_WriteFault);
+ }
+#endif // !OE_MAC
+
+ // Seek to the specified location, relative to the start of the resource.
+ if (_llseek(m_hfile, uliOffset.LowPart, SEEK_SET) == -1L) {
+ return HresultOfScode(STG_E_SEEKERROR);
+ }
+
+#if OE_MAC
+ cbWritten = _write(m_hfile, pv, cb);
+
+ if (cbWritten == -1) {
+ return HresultOfScode(STG_E_WRITEFAULT);
+ }
+#else // OE_MAC
+ cbWritten = _lwrite(m_hfile, (LPSTR)pv, (WORD)cb);
+
+ if (cbWritten == HFILE_ERROR) {
+ return HresultOfScode(STG_E_WRITEFAULT);
+ }
+#endif // OE_MAC
+
+ if (pcbWritten != NULL)
+ *pcbWritten = cbWritten;
+
+ return S_OK;
+}
+
+HRESULT FileLockBytes::Flush()
+{
+ // Since _lwrite is unbuffered, this does nothing.
+ return S_OK;
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_RARE)
+HRESULT FileLockBytes::SetSize(ULARGE_INTEGER uliCb)
+{
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT FileLockBytes::LockRegion(ULARGE_INTEGER uliOffset, ULARGE_INTEGER uliCb, DWORD dwLockType)
+{
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT FileLockBytes::UnlockRegion(ULARGE_INTEGER uliOffset, ULARGE_INTEGER uliCb, DWORD dwLockType)
+{
+ // Locks are never necessary, so don't bother.
+ return S_OK;
+}
+
+HRESULT FileLockBytes::Stat(STATSTGA FAR *pstatstg, DWORD grfStatFlag)
+{
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+#pragma code_seg()
+
+
+
+#if OE_WIN32 //FileLockBytesMemory is Win32-only
+FileLockBytesMemory::FileLockBytesMemory()
+{
+ m_cRefs = 1;
+}
+
+FileLockBytesMemory::~FileLockBytesMemory()
+{
+ // Close the DOS file handle on the DLL, if it's open.
+ if (m_hfile != -1)
+ _lclose(m_hfile);
+ if (m_pvmappingBase)
+ UnmapViewOfFile(m_pvmappingBase);
+ if (m_hmapping)
+ CloseHandle(m_hmapping);
+}
+
+ULONG FileLockBytesMemory::AddRef()
+{
+ return ++m_cRefs;
+}
+
+ULONG FileLockBytesMemory::Release()
+{
+ ULONG cRefs;
+
+ DebAssert(m_cRefs > 0, "Release");
+
+ cRefs = --m_cRefs;
+ if (cRefs == 0) {
+ this->FileLockBytesMemory::~FileLockBytesMemory();
+ MemFree(this);
+ }
+ return cRefs;
+}
+
+HRESULT
+FileLockBytesMemory::ReadAt(
+ ULARGE_INTEGER uliOffset,
+ void HUGEP *pv,
+ ULONG cb,
+ ULONG FAR *pcbRead)
+{
+ DebAssert(m_hfile != -1, "ReadAt");
+ DebAssert(uliOffset.HighPart == 0, "ReadAt");
+
+ // make sure the seek is within the file
+ if (uliOffset.LowPart > m_ulEOF)
+ return HresultOfScode(STG_E_SEEKERROR);
+
+ if (uliOffset.LowPart+cb >= m_ulEOF)
+ cb = uliOffset.LowPart-m_ulEOF;
+
+ // use structured exception handling to cope with read errors
+ // during the file I/O
+ __try {
+
+ memcpy(pv, ((char *)m_pvmapping)+uliOffset.LowPart, cb);
+
+ } __except(EXCEPTION_EXECUTE_HANDLER) {
+
+ return HresultOfScode(STG_E_READFAULT);
+
+ }
+
+ if (pcbRead != NULL)
+ *pcbRead = cb;
+
+ return NOERROR;
+}
+
+HRESULT FileLockBytesMemory::QueryInterface(REFIID riid, LPVOID FAR *ppvObj)
+{
+ if (riid == IID_ILockBytesA) {
+ AddRef();
+ *ppvObj = (ILockBytesA *)this;
+ return S_OK;
+ }
+ else {
+ *ppvObj = NULL;
+ return HresultOfScode(E_NOINTERFACE);
+ }
+}
+
+HRESULT
+FileLockBytesMemory::WriteAt(
+ ULARGE_INTEGER uliOffset,
+ void const HUGEP *pv,
+ ULONG cb,
+ ULONG FAR *pcbWritten)
+{
+ DebAssert(FALSE, "Memory-mapped files are only used for READ");
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT FileLockBytesMemory::Flush()
+{
+ // Since the file is open for read-only, this is a no-op
+ return S_OK;
+}
+
+HRESULT FileLockBytesMemory::SetSize(ULARGE_INTEGER uliCb)
+{
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT FileLockBytesMemory::LockRegion(ULARGE_INTEGER uliOffset, ULARGE_INTEGER uliCb, DWORD dwLockType)
+{
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+
+HRESULT FileLockBytesMemory::UnlockRegion(ULARGE_INTEGER uliOffset, ULARGE_INTEGER uliCb, DWORD dwLockType)
+{
+ // Locks are never necessary, so don't bother.
+ return S_OK;
+}
+
+HRESULT FileLockBytesMemory::Stat(STATSTGA FAR *pstatstg, DWORD grfStatFlag)
+{
+ return HresultOfScode(STG_E_UNIMPLEMENTEDFUNCTION);
+}
+#endif //OE_WIN32
+
+#if OE_MAC
+#pragma code_seg(CS_INIT)
+#endif
diff --git a/private/oleauto/src/typelib/gtlibstg.hxx b/private/oleauto/src/typelib/gtlibstg.hxx
new file mode 100644
index 000000000..558dfa4e3
--- /dev/null
+++ b/private/oleauto/src/typelib/gtlibstg.hxx
@@ -0,0 +1,208 @@
+/***
+*gtlibstg.hxx - Light-weight implementations of IStorage and IStream.
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This is used in IE_OLE build only as the default underlying IStorage
+* and IStream implementations for serializing ITypeLib.
+*
+*Revision History:
+* [00] Sept-01-93 mikewo: Created
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#ifndef GTLIBSTG_HXX_INCLUDED
+#define GTLIBSTG_HXX_INCLUDED
+
+
+#define GTLIBSTORAGE_SIGNATURE 0x47544c53
+
+struct GTLibStgHdr {
+ ULONG ulSignature; // The signature at the beginning of the file.
+ USHORT wCStrm; // The number of streams.
+ USHORT wCbExtra; // The number of bytes between the name table
+ // and the first stream. This is generally a
+ // small multiple of 8.
+ USHORT wCbNameTable; // The number of bytes in the name table.
+ USHORT wStreamFirst; // The first SerStreamInfo in the linked list
+ // which is sorted by order of the actual stream
+ // data in the file.
+ GUID guid; // The guid associated with this IStorage.
+};
+
+
+HRESULT
+OpenFileLockBytes(BOOL isNew,
+ LPOLESTR szFile,
+ ILockBytesA **pplockbytes);
+
+HRESULT
+CreateFileLockBytesOnHFILE(int hfile,
+ BOOL isNew,
+ ULONG oStart,
+ ULONG cbData,
+ ILockBytesA **plockbytes);
+
+struct StreamInfo;
+class GTLibStream;
+
+class GTLibStorage : public IStorageA
+{
+friend class GTLibStream;
+
+public:
+ static HRESULT Create(ILockBytesA FAR *plockbytes,
+ UINT cstreamMax,
+ IStorageA FAR * FAR *ppstg);
+ static HRESULT OpenForReadOnly(ILockBytesA FAR *plockbytes,
+ IStorageA FAR * FAR *ppstg);
+
+ // Methods implemented for IUnknown.
+ STDMETHOD(QueryInterface)(REFIID riid, LPVOID FAR *ppvObj);
+ STDMETHOD_(ULONG, AddRef)(void);
+ STDMETHOD_(ULONG, Release)(void);
+
+ // Methods implemented for IStorage.
+ STDMETHOD(CreateStream)(const OLECHAR FAR* pwcsName,
+ DWORD grfMode,
+ DWORD reserved1,
+ DWORD reserved2,
+ IStreamA FAR *FAR *ppstm);
+ STDMETHOD(OpenStream)(const OLECHAR FAR* pwcsName,
+ void FAR *reserved1,
+ DWORD grfMode,
+ DWORD reserved2,
+ IStreamA FAR *FAR *ppstm);
+ STDMETHOD(CreateStorage)(const OLECHAR FAR* pwcsName,
+ DWORD grfMode,
+ DWORD reserved1,
+ DWORD reserved2,
+ IStorageA FAR *FAR *ppstg);
+ STDMETHOD(OpenStorage)(const OLECHAR FAR* pwcsName,
+ IStorageA FAR *pstgPriority,
+ DWORD grfMode,
+ SNBA snbExclude,
+ DWORD reserved,
+ IStorageA FAR *FAR *ppstg);
+ STDMETHOD(CopyTo)(DWORD ciidExclude,
+ IID const FAR *rgiidExclude,
+ SNBA snbExclude,
+ IStorageA FAR *pstgDest);
+ STDMETHOD(MoveElementTo)(OLECHAR const FAR* lpszName,
+ IStorageA FAR *pstgDest,
+ OLECHAR const FAR* lpszNewName,
+ DWORD grfFlags);
+ STDMETHOD(Commit)(DWORD grfCommitFlags);
+ STDMETHOD(Revert)(void);
+ STDMETHOD(EnumElements)(DWORD reserved1,
+ void FAR *reserved2,
+ DWORD reserved3,
+ IEnumSTATSTGA FAR *FAR *ppenm);
+ STDMETHOD(DestroyElement)(const OLECHAR FAR* pwcsName);
+ STDMETHOD(RenameElement)(const OLECHAR FAR* pwcsOldName,
+ const OLECHAR FAR* pwcsNewName);
+ STDMETHOD(SetElementTimes)(const OLECHAR FAR *lpszName,
+ FILETIME const FAR *pctime,
+ FILETIME const FAR *patime,
+ FILETIME const FAR *pmtime);
+ STDMETHOD(SetClass)(REFCLSID clsid);
+ STDMETHOD(SetStateBits)(DWORD grfStateBits, DWORD grfMask);
+ STDMETHOD(Stat)(STATSTGA FAR *pstatstg, DWORD grfStatFlag);
+
+protected:
+ GTLibStorage(); // No external client should directly construct
+ ~GTLibStorage();// or destruct an instance of this class.
+
+ // Used by OpenStream.
+ nonvirt StreamInfo FAR *LookupStream(const char FAR* pwcsName);
+
+ // Used by GTLibStream destructor after we're done writing a stream.
+ nonvirt void NotifyStreamClosed(ULONG ulCb);
+ VOID SortStreamInfo(StreamInfo *rgstrminfo, UINT uCount);
+ VOID SwapStreamInfos(StreamInfo *pstrminfo1, StreamInfo *pstrminfo2);
+
+ ULONG m_cRefs; // The reference count.
+ GUID m_guid; // The guid;
+ ILockBytesA FAR *m_plockbytes; // The underlying ILockBytes instance.
+ StreamInfo FAR *m_rgstrminfo; // The array of info about each stream,
+ // sorted alphabetically by name.
+ // This points into m_pvHdrData.
+ LPVOID m_pvHdrData; // The raw header data read from the file.
+ ULONG m_ulOffsetNext; // The offset of the next stream to be
+ // created. Used only in write mode.
+ LPSTR m_szNameFirst; // The pointer (into m_pvHdrData) to the
+ // most recent name allocated. The name
+ // grows down from the top of m_pvHdrData.
+ // Used only in write mode.
+ LPSTR m_szNameLim; // Marks the end of the name table heap.
+ // Used only in write mode.
+ UINT m_istrminfoOpen; // The index (into m_rgstrminfo) of the
+ // currently open stream, or -1 if none.
+ // Used only in write mode.
+ UINT m_cstrminfo; // The number of entries in m_rgstrminfo.
+};
+
+
+class GTLibStream : public IStreamA
+{
+public:
+ static HRESULT Create(ILockBytesA FAR *plockbytes,
+ ULONG ulOffset,
+ GTLibStorage FAR *pgtlstgContainer,
+ IStreamA FAR * FAR *ppstm);
+ static HRESULT Open(ILockBytesA FAR *plockbytes,
+ ULONG ulOffset,
+ ULONG ulCb,
+ IStreamA FAR* FAR* ppstm);
+
+ // Methods implemented for IUnknown.
+ virtual HRESULT STDMETHODCALLTYPE QueryInterface(REFIID riid, LPVOID FAR *ppvObj);
+ virtual ULONG STDMETHODCALLTYPE AddRef();
+ virtual ULONG STDMETHODCALLTYPE Release();
+
+ // Methods implemented for IStream.
+ virtual HRESULT STDMETHODCALLTYPE Read(VOID HUGEP *pv,
+ ULONG cb, ULONG FAR *pcbRead);
+ virtual HRESULT STDMETHODCALLTYPE Write(VOID const HUGEP *pv,
+ ULONG cb,
+ ULONG FAR *pcbWritten);
+ virtual HRESULT STDMETHODCALLTYPE Seek(LARGE_INTEGER dlibMove,
+ DWORD dwOrigin,
+ ULARGE_INTEGER FAR *plibNewPosition);
+ virtual HRESULT STDMETHODCALLTYPE SetSize(ULARGE_INTEGER libNewSize);
+ virtual HRESULT STDMETHODCALLTYPE CopyTo(IStreamA FAR *pstm,
+ ULARGE_INTEGER cb,
+ ULARGE_INTEGER FAR *pcbRead,
+ ULARGE_INTEGER FAR *pcbWritten);
+ virtual HRESULT STDMETHODCALLTYPE Commit(DWORD grfCommitFlags);
+ virtual HRESULT STDMETHODCALLTYPE Revert();
+ virtual HRESULT STDMETHODCALLTYPE LockRegion(ULARGE_INTEGER libOffset,
+ ULARGE_INTEGER cb,
+ DWORD dwLockType);
+ virtual HRESULT STDMETHODCALLTYPE UnlockRegion(ULARGE_INTEGER libOffset,
+ ULARGE_INTEGER cb,
+ DWORD dwLockType);
+ virtual HRESULT STDMETHODCALLTYPE Stat(STATSTGA FAR *pstatstg, DWORD grfStatFlag);
+ virtual HRESULT STDMETHODCALLTYPE Clone(IStreamA FAR * FAR *ppstm);
+
+protected:
+ GTLibStream(); // No external client should directly construct
+ ~GTLibStream(); // or destruct an instance of this class.
+
+ ULONG m_cRefs; // The reference count.
+ ILockBytesA FAR *m_plockbytes; // The underlying ILockBytes instance.
+ ULONG m_ulCb; // The length of the stream in bytes.
+ ULONG m_ulOffsetStart; // The offset (in the lockbytes) of the
+ // start of the stream.
+ ULONG m_ulOffsetCur; // The current seek position (from start
+ // of the stream).
+ GTLibStorage FAR *m_pgtlstgContainer; // The containing storage, if it
+ // needs to be notified on closure.
+};
+
+
+#endif // GTLIBSTG_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/impmgr.cxx b/private/oleauto/src/typelib/impmgr.cxx
new file mode 100644
index 000000000..2b80ef62b
--- /dev/null
+++ b/private/oleauto/src/typelib/impmgr.cxx
@@ -0,0 +1,1502 @@
+/***
+*impmgr.cxx - Import Manager
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* The Import Manager for a Type manages references to other Types.
+*
+*Owner:
+* AlanC
+*
+*Implementation Notes:
+* The IMPTYPE entries are represented using two parallel arrays.
+* Qimptype(himptype) returns a pointer to the entry in the IMPTYPE
+* array for that import entry.
+* Qubimptype(himptype) returns a pointer to the entry in the UB_IMPTYPE
+* array for the import entry.
+* When an impory entry's reference count goes to zero it is added to
+* the free list. This implies that the arrays are sparse in that free
+* array elements may be inter-mixed with allocated elements.
+* When a new import entry must be allocated and the free list is empty
+* then cimptypeGrow entries are added to the free list.
+*
+* The import manager distinguishes between four types of references
+* to TypeInfos:
+* - a self-referential import entry references the module itself
+* This case is explicitly checked for by testing whether the TypeInfo
+* pointer associated with the entry is equal to the pointer to
+* the TypeInfo which contains the import manager
+* - references to nested TypeInfos (record TypeInfos in same module)
+* The import entries which reference record TypeInfos in this module
+* do not 'bump' the reference count of the record TypeInfos in any way
+* Such references are indicated by m_depkind == DEP_Nested
+* - references to other TypeInfos in the same library.
+* Import entries of this type maintain an internal reference to the
+* TypeInfo
+* Such references are indicated by m_isInternalRef == TRUE
+* - references to TypeInfos in other libraries
+* These maintain a normal external reference.
+*
+* Note that references to record TypeInfos defined in other modules are not
+* distinguished from references to other TypeInfos except for the case
+* where an external reference to the record TypeInfo is needed because
+* it is defined by a TypeInfo contained in the same library as this
+* TypeInfo. It is necessary to explicitly test for this situation in
+* order to add an internal reference to the RecTypeInfo since there is no
+* common protocol that introduces the AddInternal method.
+*
+* UNDONE OA95: When the impmgr is saved or when it drops a reference to a
+* ITypeInfo then it should update its copy of the ITypeInfo's TYPEID
+*
+*
+*Revision History:
+* 26-Aug-91 ilanc: Ripped asserts in Init
+* 27-Nov-91 ilanc: Ripped const cast away of this in
+* DebCheckState and DebShowState.
+* 03-Apr-92 martinc: added explicit casts from bitfield to enum (for cfront)
+* 18-Jun-92 w-peterh: changes to debshowstate
+* 10-Jul-92 w-peterh: added SetTypeInfoAndDepKind()
+* 26-Aug-92 rajivk : wrapped all the DePrintf with ID_TEST and ID_DEBUG
+* 17-Sep-92 rajivk: added functions for editing modules. Edit & Continue
+* 15-Nov-92 rajivk: CheckLaoutDep verifies the project id.
+* 12-Feb-93 w-peterh: GetContainingTypeLib returns HRESULT
+* 12-Mar-93 rajivk: Support for Byte swapping.
+*
+*
+*****************************************************************************/
+
+#include "silver.hxx"
+#include "typelib.hxx"
+#include <new.h>
+#include "sheapmgr.hxx"
+#include "impmgr.hxx"
+#include "xstring.h"
+#include "gdtinfo.hxx"
+#include "clutil.hxx"
+#include "nammgr.hxx"
+#include "exbind.hxx" // for EXBIND -- BindTypeDefn needs it.
+
+//#if !OE_REALMODE
+//#include "genproj.hxx"
+//#endif
+
+#include <stdlib.h>
+
+#pragma hdrstop(RTPCHNAME)
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+char szOleImpmgrCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleImpmgrCxx
+#else
+static char szImpmgrCxx[] = __FILE__;
+#define SZ_FILE_NAME szImpmgrCxx
+#endif
+#endif
+
+//this is a table used to map runtime function ordinals to the address of the function
+//on the Mac.
+#if OE_MAC
+#define RTORDINAL_FIRST 512
+#define RTORDINAL_LAST 685 // rtErrObj
+#define RTORDINAL_BAD ((WORD)0xFFFF) //bad ordinal value
+extern "C" void *rgMacStrdcl[]; //generated by build process in strdcl.c
+#endif
+
+// Define static class constants
+#pragma code_seg(CS_INIT)
+BYTE IMPMGR::bFirstSerByte = 0;
+BYTE IMPMGR::bCurVersion = 0;
+#define cimptypeGrow 1
+#pragma code_seg(CS_INIT)
+
+
+/***
+*PUBLIC IMPMGR constructor
+*Purpose:
+* need to initialize const/static class members
+* since cfront is buggy and we have no ctor linker.
+*
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+IMPMGR::IMPMGR()
+{
+ if (bFirstSerByte == 0) {
+ bFirstSerByte = 'I' * 2 + 'M';
+ }
+
+ m_fCheckRemainingDepCalled = TRUE;
+
+ m_lPosOfDeps = 0;
+}
+#pragma code_seg()
+
+/***
+*PUBLIC IMPMGR::Init - import manager initialization method
+*Purpose:
+* initialize import manager.
+*
+*Entry:
+* psheapmgr - pointer to SHEAP_MGR.
+* pbdTimptype - pointer to BLK_DESC of Timptype table
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+#pragma code_seg( CS_CORE2 )
+TIPERROR IMPMGR::Init(SHEAP_MGR * psheapmgr,
+ BLK_DESC * pbdTimptype,
+ BLK_DESC * pbdTimpaddr,
+ DYN_TYPEROOT *pdtroot)
+{
+ UINT i;
+ TIPERROR err;
+
+ IfErrRet( m_bdTubimptype.Init(psheapmgr, 0) );
+
+ // Save pointer to bdTimptype and bdTimpaddr
+ m_pbdTimptype = pbdTimptype;
+
+ DebAssert(pbdTimptype->CbSize() == 0, "IMPMGR::Init bdTimptype not empty");
+ DebAssert(pbdTimptype->IsValid(), "IMPMGR::Init bdTimptype not valid");
+
+ // Initialize the bucket table
+ for (i = 0; i < IMPMGR_cBuckets; i++) {
+ m_rghimptypeBucket[i] = (sHIMPTYPE) HIMPTYPE_Nil;
+ }
+
+ m_himptypeFreeList = (sHIMPTYPE) HIMPTYPE_Nil;
+
+
+ m_fCheckRemainingDepCalled = TRUE;
+ m_lPosOfDeps = 0;
+#if OE_RISC
+ m_ptlbtempl = NULL;
+#endif //OE_RISC
+
+ m_pdtroot = pdtroot;
+
+ // Note: the destructor checks to see if the bmData block is valid to
+ // determine whether or not initialization succeeded
+ IfErrRet(m_bmData.Init(psheapmgr));
+
+ return TIPERR_None;
+}
+#pragma code_seg( )
+
+
+/***
+*PRIVATE IMPMGR::Rqimptype - returns pointer to timptype
+*Purpose:
+* Returns pointer to array of pointers to TypeInfo's
+*
+*Entry:
+* none
+*
+*Exit:
+* return pointer to timptype
+*
+***********************************************************************/
+
+inline IMPTYPE* IMPMGR::Rqimptype() const
+{
+ return (IMPTYPE *)(m_pbdTimptype->QtrOfBlock());
+}
+
+
+/***
+*PRIVATE IMPMGR::Rqubimptype - returns pointer to tubimptype
+*Purpose:
+* Returns pointer to tubimptype
+*
+*Entry:
+* none
+*
+*Exit:
+* return pointer to tubimptype
+*
+***********************************************************************/
+
+inline UB_IMPTYPE *IMPMGR::Rqubimptype() const
+{
+ return (UB_IMPTYPE *)(m_bdTubimptype.QtrOfBlock());
+}
+
+
+/***
+*PRIVATE IMPMGR::Himptype - return handle for import entry given qubimptype
+*Purpose:
+* return handle for import entry given qubimptype
+* Causes no heap movement.
+*
+*Entry:
+* qubimptype - pointer to UB_IMPTYPE entry
+*
+*Exit:
+* return handle for import entry
+*
+***********************************************************************/
+
+inline HIMPTYPE IMPMGR::Himptype(UB_IMPTYPE *qubimptype) const
+{
+ return (qubimptype - Rqubimptype()) * sizeof(IMPTYPE);
+}
+
+
+
+
+/***
+*PRIVATE IMPMGR::ReleasePtinfo
+*Purpose:
+* Release the typeinfo pointer owned by an import entry.
+* If the pointer is null on entry do nothing.
+* Sets the pointer to null before exiting.
+*
+*Entry:
+* himptype - handle of import entry whose ptinfo is to be released
+*
+*Exit:
+* None
+***********************************************************************/
+
+#pragma code_seg(CS_CORE2)
+VOID IMPMGR::ReleasePtinfo(HIMPTYPE himptype)
+{
+ ITypeInfoA *ptinfo = ((ITypeInfoA *)(ULONG) Qimptype(himptype)->m_ptinfo);
+
+ // If the pointer is NULL of if the import entry references the
+ // container TypeInfo then don't release it
+ // 21-Aug-92 ilanc: don't do this for nested types (was == Nested)
+ // 24-Aug-92 ilanc: do this for nested types --
+ // but make it internal release.
+ // 24-Aug-92 ilanc: if this is nested type contained w/in
+ // this type -- do nothing as well.
+ // 24-Aug-92 ilanc: commented out DEP_Nested conjunct.
+ // 25-Aug-92 ilanc: reintroduced DEP_Nested conjunct since
+ // it's only ever set for nested types
+ // of this module and SetNestedTypeInfo
+ // doesn't an int/ext refcount.
+ //
+ if (ptinfo != NULL &&
+ ptinfo != m_pdtroot->Pgdtinfo()) {
+
+ if (Qubimptype(himptype)->m_depkind != DEP_Nested) {
+
+ // If this is a reference to a TypeInfo in the same library then
+ // release its internal reference; otherwise do a normal release
+ if (Qubimptype(himptype)->m_isInternalRef) {
+ // Note that we know the truetype of the typeinfo in this case
+ // since ptinfo must point into this impmgr's containing typelib.
+ // That truetype supports the ole implementation of STL_TYPEINFO
+ // even though we can't QueryInterface to STL_TYPEINFO.
+ ((STL_TYPEINFO *)ptinfo)->RelInternalRef();
+ }
+ else
+ ptinfo->Release();
+ }
+ Qimptype(himptype)->m_ptinfo = NULL;
+ }
+}
+#pragma code_seg()
+
+
+/***
+*PRIVATE IMPMGR::SetPtinfo
+*Purpose:
+* Set m_ptinfo of the import entry to the passed in TypeInfo
+* SetPtinfo changes the internal/external reference status of the
+* passed in TypeInfo as needed to account for the addition of
+* a reference to that TypeInfo from the import entry.
+*
+*Entry:
+* himptype - handle of import entry whose ptinfo is to be released
+* ptinfo - pointer to TypeInfo
+*
+*Exit:
+* None
+***********************************************************************/
+
+TIPERROR IMPMGR::SetPtinfo(HIMPTYPE himptype, ITypeInfoA *ptinfo, BOOL fDepBeingRead)
+{
+ TIPERROR err;
+ ITypeLibA *ptlib1, *ptlib2;
+
+
+ // Store the reference
+ Qimptype(himptype)->m_ptinfo = ptinfo;
+
+ // Avoid adding a reference to the typeinfo which contains
+ // the import manager so that there is not a circular reference problem
+ if (ptinfo == m_pdtroot->Pgdtinfo())
+ return TIPERR_None;
+
+ // Assume that an external reference will be needed.
+ ptinfo->AddRef();
+
+ // Check whether the referenced TypeInfo is in the same library.
+ // If it is then release the external reference and add an internal
+ // reference to the TypeInfo instead.
+ // Have to deal with the REC_TYPEINFO and STL_TYPEINFO cases separately
+ // since there is no protocol that contains the AddInternalRef function
+
+ // First get a pointer to the containing TypeLib
+ err = TiperrOfHresult(m_pdtroot->Pgdtinfo()->GetContainingTypeLib(&ptlib2, NULL));
+ DebAssert(err == TIPERR_None, "SetPtinfo - no container");
+ ptlib2->Release();
+
+ // If ptinfo is contained in the same library as this impmgr's typeinfo,
+ // then change the reference to internal.
+ err = TiperrOfHresult(ptinfo->GetContainingTypeLib(&ptlib1, NULL));
+ DebAssert(err == TIPERR_None, "SetPtinfo - no container");
+
+ ptlib1->Release();
+ if (ptlib1 == ptlib2) {
+ ((STL_TYPEINFO *)ptinfo)->AddInternalRef();
+ ptinfo->Release();
+ Qubimptype(himptype)->m_isInternalRef = TRUE;
+ }
+ return TIPERR_None;
+}
+
+
+/***
+*PRIVATE IMPMGR::HimptypeAlloc
+*Purpose:
+* Allocate an imptype entry. Grows free list if its empty.
+*
+*Entry:
+* phimptype - Return parameter for himptype
+*
+*Exit:
+* himptype - handle for allocated import entry
+*
+*CONSIDER: it may not be worth the extra code to grow the free list
+*CONSIDER: 10 at a time since the SHEAPMGR will be changed to buffer
+*CONSIDER: the heap entries
+***********************************************************************/
+
+TIPERROR IMPMGR::HimptypeAlloc(sHIMPTYPE *phimptype)
+{
+ UB_IMPTYPE *qubimptype, *qubimptypeEmpty;
+ IMPTYPE *qimptype;
+ UINT cbSize;
+ HIMPTYPE himptype;
+ TIPERROR err;
+
+ if (m_himptypeFreeList == (sHIMPTYPE) HIMPTYPE_Nil) {
+
+ // Add cimptypeGrow Imptype enties to free list
+
+ // Increase size of Timptype array by cimptype entries
+ // and initialize each entry to NULL
+ // Note that the constructor of the IMPTYPE entries is never called
+ cbSize = m_pbdTimptype->CbSize();
+ IfErrRet( m_pbdTimptype->Realloc(cbSize +
+ cimptypeGrow*sizeof(IMPTYPE)) );
+ qimptype = (IMPTYPE *)(((BYTE *)Rqimptype()) + cbSize);
+ if (cimptypeGrow == 1)
+ ::new (qimptype) IMPTYPE;
+ else
+ ::new (qimptype) IMPTYPE[cimptypeGrow];
+
+ // Grow the Tubimptype array by cimptypeGrow elements
+ cbSize = m_bdTubimptype.CbSize();
+
+ if (err = m_bdTubimptype.Realloc(cbSize +
+ cimptypeGrow*sizeof(UB_IMPTYPE)) ) {
+ // Undo growing the Timptype table
+ m_pbdTimptype->Realloc(m_pbdTimptype->CbSize() -
+ cimptypeGrow*sizeof(IMPTYPE));
+ return err;
+ }
+
+ // Initialize entries and link them into the free list
+ // qubimptypeEmpty points to front of free list when loop exited
+ qubimptypeEmpty = (UB_IMPTYPE *)(((BYTE *)Rqubimptype()) + cbSize);
+ himptype = m_himptypeFreeList;
+ for (qubimptype = qubimptypeEmpty + cimptypeGrow - 1;
+ qubimptype >= qubimptypeEmpty;
+ qubimptype--) {
+
+ // call the Constructor to initialize the UB_IMPTYPE instance.
+ ::new (qubimptype) UB_IMPTYPE;
+
+ qubimptype->m_himptypeNext = (sHIMPTYPE) himptype;
+
+ himptype = Himptype(qubimptype);
+ }
+
+ }
+ else {
+ qubimptypeEmpty = Qubimptype((HIMPTYPE) m_himptypeFreeList);
+ DebAssert(qubimptypeEmpty->m_cRefs == 0 &&
+ qubimptypeEmpty->m_isInternalRef == FALSE &&
+ qubimptypeEmpty->m_isExcodeRef == FALSE &&
+ qubimptypeEmpty->m_isDeclRef == FALSE &&
+ qubimptypeEmpty->m_refkind == REF_NoName &&
+ qubimptypeEmpty->m_depkind == DEP_None, " The way things should be ");
+ }
+
+
+#if ID_DEBUG
+ // Set up head of free list and check state of the IMPMGR
+ m_himptypeFreeList = (sHIMPTYPE) Himptype(qubimptypeEmpty);
+ DebCheckState(1);
+#endif
+
+ // qubimptypeEmpty points to the head of the free list
+ // Update the m_himptypeFreeList to point to the second element
+ // in the free list and return the old head.
+ m_himptypeFreeList = (sHIMPTYPE) qubimptypeEmpty->m_himptypeNext;
+
+ // Reset the NEXT pointer of the entry we're returning
+ qubimptypeEmpty->m_himptypeNext = (sHIMPTYPE) HIMPTYPE_Nil;
+
+ *phimptype = Himptype(qubimptypeEmpty);
+ return TIPERR_None;
+}
+
+
+/***
+*PRIVATE IMPMGR::NewEntry - allocate a new IMPTYPE entry
+*Purpose:
+* Allocates and initializes a new IMPTYPE entry.
+* Links the new entry into the front of the bucket list.
+*
+*Entry:
+* pqubimptype - returns pointer to UB_IMPTYPE of the new entry
+* phimptype - returns the himptype of the new entry
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+TIPERROR IMPMGR::NewEntry(UB_IMPTYPE **pqubimptype,
+ sHIMPTYPE *phimptype)
+{
+ TIPERROR err;
+ UB_IMPTYPE *qubimptype;
+
+ IfErrRet( HimptypeAlloc(phimptype) );
+
+ // Initialize the new entry
+ Qimptype(*phimptype)->m_ptinfo = NULL;
+ qubimptype = *pqubimptype = Qubimptype(*phimptype);
+
+ // Following assertions are true because the entry was previously free
+ DebAssert( qubimptype->m_cRefs == 0 &&
+ qubimptype->m_isExcodeRef == FALSE,
+ "IMPMGR::NewEntry: entry incorrectly initialized");
+
+ qubimptype->m_refkind = REF_Name; // Set to this so that the entry
+ // can be passed to Free without
+ // additional initialization
+ qubimptype->m_depkind = DEP_None;
+
+ return TIPERR_None;
+}
+
+
+/***
+*PRIVATE IBucket - hash function for hlnam
+*Purpose:
+* Map hlnam to a bucket index.
+*Entry:
+* hlnam
+*
+*Exit:
+* bucket index
+*
+***********************************************************************/
+
+inline UINT IMPMGR::IBucket(HLNAM hlnam)
+{
+ return (hlnam >> 3) % IMPMGR_cBuckets;
+}
+
+
+/***
+*PRIVATE IMPMGR::IBucket - hash function for qualified name
+*Purpose:
+* Map a qualified name to the index of the bucket in which an import
+* entry with that name should be stored.
+*
+*Entry:
+* cName - number of names in qualified name
+* rghlnam - array of local name handles
+*
+*Exit:
+* bucket index
+*
+***********************************************************************/
+
+inline UINT IMPMGR::IBucket(UINT cName, sHLNAM rghlnam[])
+{
+ // Hash based on the last name
+ return IBucket(rghlnam[cName - 1]);
+}
+
+
+
+
+
+
+
+/***
+*PUBLIC IMPMGR::GetHimptype - return Himptype given pointer to TypeInfo
+*Purpose:
+* Returns handle of ImpType entry associated with passed in TypeInfo.
+* Adds new entry if there is none and assigns it depkind.
+* Always increments the reference count of the import entry.
+*
+*Entry:
+* ptinfo - pointer to TypeInfo
+* depkind - specifies to what level decompilation is needed if can't
+* refind the TypeInfo.
+* phimptype - parameter for returning HIMPTYPE
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR IMPMGR::GetHimptype(ITypeInfoA *ptinfo,
+ DEPEND_KIND depkind,
+ sHIMPTYPE *phimptype)
+{
+ UB_IMPTYPE *qubimptype;
+ TIPERROR err;
+ UINT cImpType = m_pbdTimptype->CbSize() / sizeof(IMPTYPE);
+ UB_IMPTYPE *rqubimptype = Rqubimptype();
+ IMPTYPE *rqimptype = Rqimptype();
+ BOOL fNew = FALSE;
+
+ *phimptype = GetHimptypeIfExists( ptinfo );
+ if ( *phimptype != HIMPTYPE_Nil) {
+ qubimptype = Qubimptype(*phimptype);
+ }
+ else {
+ // No matching entry found --- allocate a new one
+ // Note that the new entry is not linked into the hash table
+ IfErrRet (NewEntry(&qubimptype, phimptype));
+
+ qubimptype->m_refkind = (depkind == DEP_Base) ? REF_Base :
+ REF_NoName;
+ fNew = TRUE;
+ }
+
+ // Set the depend kind to MAX_OF(qubimptype->m_depkind and depkind)
+ qubimptype->m_depkind = max(qubimptype->m_depkind, depkind);
+ qubimptype->m_cRefs++;
+
+ if (fNew)
+ IfErrRet(SetPtinfo(*phimptype, ptinfo));
+
+ return TIPERR_None;
+}
+
+
+
+
+/***
+*PUBLIC IMPMGR::GetHimptypeIfExists - return Himptype, given a pointer to TypeInfo
+*Purpose:
+* It returns the corresponding himptype for given typeinfo.
+* If there is no import entry for this typeinfo then HIMPTYPE_Nil
+* is returned.
+*
+*Entry:
+* ptinfo - pointer to TypeInfo
+*
+*
+*Exit:
+* HIMPTYPE
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+HIMPTYPE IMPMGR::GetHimptypeIfExists(ITypeInfoA *ptinfo)
+{
+ UINT i;
+ UINT cImpType = m_pbdTimptype->CbSize() / sizeof(IMPTYPE);
+ UB_IMPTYPE *rqubimptype = Rqubimptype();
+ IMPTYPE *rqimptype = Rqimptype();
+
+ // Does a linear search on ImpAddr to find a matching TypeInfo pointer.
+ // CONSIDER: building a non-persistant hash table to make this faster
+ for (i = 0; i < cImpType; i++)
+ if (!rqubimptype[i].isFree() && // if not a free entry
+ rqimptype[i].m_ptinfo == ptinfo) { // and TypeInfo ptr matches
+
+ return HimptypeOfIndex(i);
+ }
+
+ return HIMPTYPE_Nil;
+
+}
+#pragma code_seg( )
+
+
+
+#if ID_DEBUG
+/***
+*PUBLIC GetName
+*Purpose:
+* Retrieves the array of names for an ImpType entry. The
+* returned pointer may become invalid after invoking other
+* methods on the import manager.
+*
+*Entry:
+* himptype - handle for import entry whose name is to be retrieved
+* pcName - returns the number of names
+* prghlnam - returns pointer to array of names
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+VOID IMPMGR::GetName(HIMPTYPE himptype, UINT *pcName, sHLNAM *prghlnam[])
+{
+ UB_IMPTYPE *qubimptype = Qubimptype(himptype);
+ USHORT *qus;
+
+ if (qubimptype->m_refkind == REF_Name) {
+ *pcName = 1;
+ *prghlnam = &(qubimptype->m_hlnam);
+ }
+ else {
+ DebAssert(qubimptype->m_refkind == REF_QualName, "");
+ qus = (USHORT *)m_bmData.QtrOfHandle(qubimptype->m_hrghlnam);
+ *pcName = *qus;
+ *prghlnam = (sHLNAM *)(qus + 1);
+ }
+}
+#endif //EI_OB || ID_DEBUG
+
+
+
+
+/***
+*PUBLIC IMPMGR::GetTypeInfo - returns pointer to TypeInfo of import entry
+*Purpose:
+* Returns pointer to TYPEINFO of import entry.
+*
+*Entry:
+* himptype - handle for ImpType entry
+* pptinfo - returns pointer to ITypeInfo
+*
+*Exit:
+* TIPERROR
+* If TIPERROR = TIPERR_None then *pptinfo returns a pointer to the
+* TYPEINFO. This reference must be released by the caller.
+*
+***********************************************************************/
+
+TIPERROR IMPMGR::GetTypeInfo(HIMPTYPE himptype,
+ DEPEND_KIND depkind,
+ ITypeInfoA **pptinfo)
+{
+ TIPERROR err;
+
+ // We don't care what depkind is set to by this call.
+ IfErrRet( CheckRemainingDep( &depkind ) );
+ *pptinfo = Qimptype(himptype)->m_ptinfo;
+ DebAssert(*pptinfo != NULL, "IMPMGR::GetTypeInfo: m_ptinfo null");
+
+ // Add a reference to account for the TypeInfo pointer being returned
+ (*pptinfo)->AddRef();
+ return TIPERR_None;
+}
+
+
+
+#if 0 //Dead Code
+/***
+*PUBLIC IMPMGR::AddrefHimptype - add reference to an import entry
+*Purpose:
+* Increments reference count of import entry
+*
+*Entry:
+* himptype - handle for ImpType entry
+*
+*Exit:
+* none
+*
+***********************************************************************/
+
+void IMPMGR::AddrefHimptype(HIMPTYPE himptype)
+{
+ UB_IMPTYPE *qubimptype;
+
+ if (himptype==HIMPTYPE_Nil) return;
+
+ qubimptype = Qubimptype(himptype);
+ qubimptype->m_cRefs++;
+}
+#endif //0
+
+
+/***
+*PUBLIC IMPMGR::Unref - unreference an import entry
+*Purpose:
+* Decrements reference count of import entry
+*
+*Entry:
+* himptype - handle for ImpType entry
+*
+*Exit:
+* none
+*
+***********************************************************************/
+
+void IMPMGR::Unref(HIMPTYPE himptype)
+{
+ UB_IMPTYPE *qubimptype;
+
+ if (himptype==HIMPTYPE_Nil) return;
+
+ qubimptype = Qubimptype(himptype);
+
+ DebAssert(qubimptype->m_cRefs > 0, "IMPMGR::Unref: m_cRefs <= 0");
+
+ qubimptype->m_cRefs--;
+
+ // Assert that if the ref count is zero and the entry is not
+ // going to be freed, then the NEXT field does not contain a
+ // valid HIMPTYPE.
+ //
+ DebAssert( qubimptype->m_cRefs != 0
+ || qubimptype->isFree()
+ || qubimptype->m_himptypeNext == (sHIMPTYPE)HIMPTYPE_Nil,
+ "Next field is not Nil");
+
+ DebAssert (!(Qubimptype(himptype)->isFree()), "typelib import entries aren't ever freed");
+}
+
+
+/***
+*PUBLIC IMPMGR::HimptypeFirst - return first Himptype in sequence
+*Purpose:
+* Returns first Himptype in sequence.
+* Subsequent elements of the sequence are generated by HimptypeNext
+* Used by clients who need to iterate over all valid Himptype's
+*
+*Entry:
+* None
+*
+*Exit:
+* return first Himptype or HIMPTYPE_Nil if no Himptype's
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+HIMPTYPE IMPMGR::HimptypeFirst() const
+{
+ // The above becomes greatly simplified in the OLE case, where
+ // import entries are never freed (isFree() always returns FALSE).
+ // I chose to do this by hand instead of counting on the C optimizer,
+ // because this routine is called a lot.
+ if (m_pbdTimptype->CbSize()) {
+ return 0;
+ }
+ return HIMPTYPE_Nil;
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC IMPMGR::HimptypeNext - return next Himptype in sequence
+*Purpose:
+* Return the Himptype in the sequence which follows HimptypeNext.
+* Note that the ordering of elements in the sequence is irrelevant as
+* long as all Himptypes are in the sequence exactly once.
+* Used by clients who need to iterate over all valid Himptype's
+*
+*Entry:
+* Himptype
+*
+*Exit:
+* return next Himptype in sequence or HIMPTYPE_Nil if no more elements
+* in the sequence
+*
+***********************************************************************/
+
+HIMPTYPE IMPMGR::HimptypeNext(HIMPTYPE himptype) const
+{
+ // The above becomes greatly simplified in the OLE case, where
+ // import entries are never freed (isFree() always returns FALSE).
+ // I chose to do this by hand instead of counting on the C optimizer,
+ // because this routine is called a lot.
+ if ((himptype+sizeof(IMPTYPE)) < m_pbdTimptype->CbSize()) {
+ return himptype+sizeof(IMPTYPE);
+ }
+ return HIMPTYPE_Nil;
+}
+
+
+
+
+
+
+//
+// Import Address Support
+//
+
+
+/***
+*PUBLIC IMPMGR ::RegisterDeclRefDep
+*Purpose: Registers a dependency of the typeinfo (of this impmgr) on Ptinfo.
+* The dependency registered is of type declref.
+*
+*Entry:
+* ptinfo : typeinfo on which this typeinfo depends on.
+*
+*Exit:
+* TIPERROR
+*
+*
+***********************************************************************/
+TIPERROR IMPMGR::RegisterDeclRefDep(ITypeInfoA *ptinfo)
+{
+ TIPERROR err=TIPERR_None;
+ sHIMPTYPE himptype;
+ DEPEND_KIND depkind;
+
+ depkind = m_pdtroot->CompState() < CS_DECLARED ? DEP_Layout : DEP_Code;
+
+ IfErrRet(GetHimptype(ptinfo, depkind, &himptype));
+
+ // Set the DeclRef flag and unref the
+ // himptype to decrement the reference added by GetHimptype.
+
+ Qubimptype(himptype)->m_isDeclRef = TRUE;
+ Unref(himptype);
+
+ DebAssert(himptype != HIMPTYPE_Nil, " Bad Himptype ");
+
+ return err;
+}
+
+
+
+/***
+*PUBLIC IMPMGR::CheckRemainingDep - read import typeids for
+* dependncy that are not of DEP_KIND (DEP_Layout).
+*Purpose:
+* Read previously serialized Typeids from stream.
+* Does modify Timptype table.
+*
+*Entry:
+* pdepkindFail: used for return value. Represents the dependency type that
+* failed.
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+#pragma code_seg( CS_CORE2 )
+TIPERROR IMPMGR::CheckRemainingDep(DEPEND_KIND *pdepkindFail)
+{
+ TIPERROR err = TIPERR_None;
+
+ BYTE b;
+ UINT cEntries;
+ UB_IMPTYPE *qubimptype;
+ IMPTYPE *qimptype, *qimptypeLimit;
+ LPOLESTR szTypeId=NULL;
+ ITypeInfoA *ptinfo;
+ HIMPTYPE himptype;
+ STREAM *pstrm;
+ GenericTypeLibOLE *pgtlibole;
+
+ *pdepkindFail = DEP_None;
+ if ( m_fCheckRemainingDepCalled ) {
+ return TIPERR_None;
+ }
+
+
+ // open the stream
+ IfErrRet(m_pdtroot->Pgdtinfo()->OpenStream(&pstrm, SOM_Read));
+
+ // Set the flag indicating that this function has been called.
+ m_fCheckRemainingDepCalled = TRUE;
+
+ // set the position of the head to read the typeinfos.
+ IfErrGo(pstrm->SetPos( m_lPosOfDeps ));
+
+ // Lock the block desc so that the memory does not move
+ m_bdTubimptype.Lock();
+ m_pbdTimptype->Lock();
+
+ qimptype = Rqimptype();
+ qubimptype = Rqubimptype();
+
+ // Read in the TypeId associated with each TypeInfo when the IMPMGR
+ // was saved. Convert it to a pointer to the TypeInfo.
+ cEntries = m_bdTubimptype.CbSize() / sizeof(UB_IMPTYPE);
+
+ pgtlibole = m_pdtroot->Pgdtinfo()->PgtlibOleContaining();
+
+ qimptypeLimit = Rqimptype() + cEntries;
+ for (; qimptype < qimptypeLimit; qimptype++, qubimptype++) {
+ if ( qubimptype->isFree() == FALSE ) {
+
+ // Read in the typeid.
+ IfErrGo(pstrm->ReadSz(&szTypeId));
+
+ // Map TypeId to the associated TypeInfo
+ err = pgtlibole->TypeInfoFromCompressedTypeId(szTypeId, &ptinfo);
+
+ // Free the szTypeId
+ MemFree(szTypeId);
+ szTypeId = NULL;
+
+ IfErrGo(err);
+
+ // Convert the qimptype to an Himptype
+ himptype = (BYTE *)qimptype - m_pbdTimptype->QtrOfBlock();
+
+ err = SetPtinfo(himptype, (TYPEINFO *)ptinfo);
+ // fall through ...
+
+ // Release the reference added by the TypeInfoFromCompressedTypeId
+ ptinfo->Release();
+
+ IfErrGo(err);
+ } // if
+ } // for
+
+ // Ensure that we have read in all the TypeIds
+ IfErrGo( pstrm->ReadByte(&b) );
+
+ if (b != bFirstSerByte) {
+ err = TIPERR_InvDataRead;
+ goto Error;
+ }
+
+Error:
+ // UnLock the block desc(s)
+ m_bdTubimptype.Unlock();
+ m_pbdTimptype->Unlock();
+
+ if (szTypeId)
+ MemFree(szTypeId);
+
+ // If there was an error then we want to flag that remaining dep(s)
+ // were not read in.
+ if (err) {
+ // Set the flag indicating that this function has not been called.
+ m_fCheckRemainingDepCalled = FALSE;
+ }
+
+ // Release the STREAM;
+ pstrm->Release();
+
+#if ID_DEBUG
+ // Check the state
+ if ((!err) && (*pdepkindFail == DEP_None))
+ DebCheckState(1);
+#endif
+
+ return err;
+}
+#pragma code_seg( )
+
+
+
+/***
+*PUBLIC IMPMGR::Read - read import manager from stream
+*Purpose:
+* Read previously serialized IMPMGR from stream.
+* Does not modify Timptype table.
+*
+*Entry:
+* pstrm - stream from which IMPMGR is read
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR IMPMGR::Read(STREAM *pstrm)
+{
+ BYTE b;
+ BYTE bVersion;
+ UINT cEntries;
+ TIPERROR err;
+ IMPTYPE *qimptype, *qimptypeLimit;
+ HIMPTYPE himptype;
+
+ IfErrRet( pstrm->ReadByte(&b) );
+
+ if (b != bFirstSerByte || DebErrorNow(TIPERR_InvDataRead)) {
+ return TIPERR_InvDataRead;
+ }
+
+ IfErrRet( pstrm->ReadByte(&bVersion) );
+
+ if (bVersion != bCurVersion || DebErrorNow(TIPERR_UnsupFormat)) {
+ return TIPERR_UnsupFormat;
+ }
+
+
+ // Read in head of free list and bucket table
+ IfErrRet( pstrm->ReadUShort(&m_himptypeFreeList));
+
+ IfErrRet( pstrm->Read(&m_rghimptypeBucket, sizeof(m_rghimptypeBucket)));
+
+#if HP_BIGENDIAN
+ // For big endian swap the bytes back after reading
+ SwapShortArray(m_rghimptypeBucket, IMPMGR_cBuckets);
+#endif
+
+
+ IfErrRet( m_bdTubimptype.Read(pstrm) );
+
+#if HP_BIGENDIAN
+ SwapStructArray(m_bdTubimptype.QtrOfBlock(),
+ m_bdTubimptype.CbSize() / sizeof(UB_IMPTYPE),
+ UB_IMPTYPE_Layout);
+#endif
+
+
+ IfErrRet( m_bmData.Read(pstrm) );
+
+#if HP_BIGENDIAN
+ SwapbmData(TRUE);
+#endif
+
+ cEntries = m_bdTubimptype.CbSize() / sizeof(UB_IMPTYPE);
+ IfErrRet( m_pbdTimptype->Realloc(cEntries * sizeof(IMPTYPE)) );
+ qimptype = Rqimptype();
+
+ qimptypeLimit = Rqimptype() + cEntries;
+
+ for (; qimptype < qimptypeLimit; qimptype++) {
+ // Convert the qimptype to an Himptype
+ // Initialize each pointer of imptype to NULL;
+ himptype = (BYTE *)qimptype - m_pbdTimptype->QtrOfBlock();
+ // Initialize to NULL
+ Qimptype(himptype)->m_ptinfo = NULL;
+ }
+
+ // Initialize the flags indicating that the CheckRemainingDep and
+ // CheckLayoutDep has not yet been read.
+ m_fCheckRemainingDepCalled = FALSE;
+
+
+ // save the position to the beginning of the typeids
+ pstrm->GetPos( &m_lPosOfDeps );
+
+
+ return TIPERR_None;
+}
+
+
+/***
+*PUBLIC IMPMGR::Write - write import manager from stream
+*Purpose:
+* Serialize IMPMGR to stream.
+* Does not serialize Timptype since that is separately serialized.
+*
+*Entry:
+* pstrm - stream to which IMPMGR is written
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR IMPMGR::Write(STREAM *pstrm)
+{
+ TIPERROR err;
+
+ // Write out identification byte and version number
+ IfErrRet( pstrm->WriteByte(bFirstSerByte) );
+ IfErrRet( pstrm->WriteByte(bCurVersion) );
+
+
+ // Write out head of free list and bucket table
+ IfErrRet( pstrm->WriteUShort(m_himptypeFreeList));
+
+
+#if HP_BIGENDIAN
+ // For big endian swap the bytes before writing out and then swap back
+ SwapShortArray(m_rghimptypeBucket, IMPMGR_cBuckets);
+#endif
+
+ err = pstrm->Write(m_rghimptypeBucket, sizeof(m_rghimptypeBucket));
+
+#if HP_BIGENDIAN
+ // For big endian swap the bytes before writing out and then swap back
+ SwapShortArray(m_rghimptypeBucket, (UINT)IMPMGR_cBuckets);
+#endif
+
+ IfErrRet(err);
+
+
+#if HP_BIGENDIAN
+ SwapStructArray(m_bdTubimptype.QtrOfBlock(),
+ m_bdTubimptype.CbSize() / sizeof(UB_IMPTYPE),
+ UB_IMPTYPE_Layout);
+#endif
+
+ // Write out tubimptype
+ err = m_bdTubimptype.Write(pstrm);
+
+#if HP_BIGENDIAN
+ SwapStructArray(m_bdTubimptype.QtrOfBlock(),
+ m_bdTubimptype.CbSize() / sizeof(UB_IMPTYPE),
+ UB_IMPTYPE_Layout);
+#endif
+
+ IfErrRet(err);
+
+#if HP_BIGENDIAN
+ SwapbmData(FALSE);
+#endif
+ err = m_bmData.Write(pstrm);
+
+#if HP_BIGENDIAN
+ SwapbmData(TRUE);
+#endif
+
+ IfErrRet(err);
+
+
+ // For OLE libraries we don't need to verify the project ID and
+ // we WriteLayoutEntries is called only once to write out the TypeIds
+ // for all referenced TypeInfos.
+ // write the type info for which the depend kind is not DEP_Layout kind
+ IfErrRet(WriteLayoutEntries(pstrm, FALSE));
+
+
+ // Write out identification byte in the end so that it is verified in
+ // CheckRemainingDep that we are in sync.
+ IfErrRet( pstrm->WriteByte(bFirstSerByte));
+
+ return TIPERR_None;
+
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC IMPMGR::WriteLayoutEntries - write import manager's TYPEID to stream
+*Purpose:
+* Writes out the typeids.
+*Entry:
+* pstrm - stream to which IMPMGR is written
+* isLayoutDep - True if entries for layout dep has to be written
+* False if the remaining dep has to be written
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+#pragma code_seg(CS_CREATE)
+TIPERROR IMPMGR::WriteLayoutEntries( STREAM *pstrm, BOOL isLayoutDep )
+{
+ TIPERROR err = TIPERR_None;
+ IMPTYPE *qimptype, *qimptypeEnd;
+ UB_IMPTYPE *qubimptype;
+ GenericTypeLibOLE *pgtlibole;
+
+ pgtlibole = m_pdtroot->Pgdtinfo()->PgtlibOleContaining();
+
+ // Lock the block desc so that the memory does not move
+ m_bdTubimptype.Lock();
+ m_pbdTimptype->Lock();
+
+ qubimptype = Rqubimptype();
+ qimptype = Rqimptype();
+ qimptypeEnd = Rqimptype() + (m_bdTubimptype.CbSize() / sizeof(UB_IMPTYPE));
+
+ for(; qimptype < qimptypeEnd; qimptype++, qubimptype++) {
+ if ( qubimptype->isFree() == FALSE ) {
+ IfErrGo(pgtlibole->WriteTypeId(pstrm, qimptype->m_ptinfo));
+ }
+ }
+
+Error:
+ // Unlock the block desc
+ m_bdTubimptype.Unlock();
+ m_pbdTimptype->Unlock();
+
+ return err;
+}
+#pragma code_seg()
+
+
+
+
+/***
+*PUBLIC IMPMGR::~IMPMGR - IMPMGR destructor
+*Purpose:
+* release resources of IMPMGR instance
+*Entry:
+* psstrm - stream to which IMPMGR is written
+*
+*Exit:
+* none
+*
+***********************************************************************/
+#pragma code_seg( CS_CORE )
+IMPMGR::~IMPMGR()
+{
+ HIMPTYPE himptype;
+
+ // Check to ensure that initialization was successful
+ if (m_bdTubimptype.IsValid() && m_bmData.IsValid()) {
+
+ // Walk the Timptype array and release every TypeInfo
+ for (himptype = HimptypeFirst();
+ himptype != HIMPTYPE_Nil;
+ himptype = HimptypeNext(himptype))
+ ReleasePtinfo(himptype);
+
+ // Shrink space usage back to minimum
+ m_pbdTimptype->Realloc(0);
+
+ //the destructor for member m_pbdTubimptype will release its space
+ }
+
+
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC IMPMGR::RemoveInternalRefs() - Removes internal references.
+*Purpose:
+* This function nulls out the pointer to the referenced typeinfo
+* if this reference is to an internal module. This is done so that
+* in case of a cycle there is no dangling pointer reference.
+* This is called from GEN_DTINFO::RemoveInternalRefs();
+*
+* WARNING :: This should only be called from GEN_DTINFO::RemoveInternalRefs()
+* Which is called from STAT_TYPELIBs desctructor. Never call this
+* function unless you are sure what this does as it will create
+* leaks if the type infos are not deleted explicitly.
+*
+*Entry:
+* None.
+*
+*Exit:
+* none
+*
+***********************************************************************/
+#pragma code_seg( CS_CORE )
+VOID IMPMGR::RemoveInternalRefs()
+{
+ HIMPTYPE himptype;
+
+ DebAssert(m_bdTubimptype.IsValid() && m_bmData.IsValid(), "");
+
+ // Walk the Timptype array and release every TypeInfo
+ for (himptype = HimptypeFirst();
+ himptype != HIMPTYPE_Nil;
+ himptype = HimptypeNext(himptype)) {
+
+ if ( Qubimptype(himptype)->m_isInternalRef )
+ Qimptype(himptype)->m_ptinfo = NULL;
+ }
+}
+#pragma code_seg( )
+
+
+
+
+#if HP_BIGENDIAN
+/***
+*PRIVATE IMPMGR::SwapbmData
+*Purpose:
+* Swaps the array(s) of sHLNAM(s) stored in the BLK_MGR (m_bmData)
+*
+*Entry:
+* fSwapFirst == TRUE if we're un-swapping (i.e. we must swap any
+* data first before we look at it)
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_CORE2)
+VOID IMPMGR::SwapbmData(BOOL fSwapFirst) const
+{
+ UINT cEntries;
+ UINT i;
+ UB_IMPTYPE *rqubimptype = Rqubimptype();
+ sHCHUNK hchunk;
+ USHORT cHlnam;
+ HLNAM *qhlnam;
+
+
+ // Count the number of UB_IMPTYPE
+ cEntries = m_bdTubimptype.CbSize() / sizeof(UB_IMPTYPE);
+
+ for (i=0; i < cEntries; i++, rqubimptype++) {
+
+ if (rqubimptype->m_refkind == REF_QualName) {
+ hchunk = rqubimptype->m_hrghlnam;
+
+ qhlnam = (HLNAM *)m_bmData.QtrOfHandle(hchunk);
+
+ // Get the count of HLNAM(s)
+ cHlnam = *(USHORT *)qhlnam;
+
+ if (fSwapFirst) // if un-swapping, must unswap
+ SwapStruct(&cHlnam, "s"); // this before we use it
+ // (otherwise we trash a TON
+ // of memory -- trust me :) )
+
+ // Swap the array of SHORT(s) stored at hchunk.
+ // +1 is for the count of the HLNAM(s)
+ SwapShortArray(qhlnam, cHlnam +1);
+ }
+ }
+}
+#pragma code_seg()
+#endif //HP_BIGENDIAN
+
+
+
+
+
+#if ID_DEBUG
+#pragma code_seg(CS_DEBUG)
+/***
+*PUBLIC IMPMGR::DebCheckState
+*Purpose:
+* Check internal state of IMPMGR.
+*
+*Entry:
+* uLevel
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+nonvirt void IMPMGR::DebCheckState(UINT uLevel) const
+{
+ UINT cbTubimptype = m_bdTubimptype.CbSize();
+ UINT cbSize = m_pbdTimptype->CbSize();
+ UB_IMPTYPE *qubimptype;
+ NAMMGR *pnammgr;
+ USHORT *qus;
+ UINT i;
+ HIMPTYPE himptype;
+ UINT cEntries = 0;
+
+ //
+ // First check the ImpType tables
+ //
+ DebAssert(cbTubimptype / sizeof(UB_IMPTYPE) ==
+ cbSize / sizeof(IMPTYPE),
+ "IMPMGR::DebCheckState: table sizes inconsistent");
+ DebAssert(m_pbdTimptype->IsValid(),
+ "IMPMGR::DebCheckState bdTimptype not valid");
+ DebAssert(m_bdTubimptype.IsValid(),
+ "IMPMGR::DebCheckState bdTubimptype not valid");
+
+ DebAssert(m_pdtroot->GetNamMgr(&pnammgr) == TIPERR_None, "");
+ for (himptype = HimptypeFirst();
+ himptype != HIMPTYPE_Nil;
+ himptype = HimptypeNext(himptype)) {
+ cEntries++;
+ qubimptype = Qubimptype(himptype);
+ if ((qubimptype->m_depkind != DEP_None) &&
+ (qubimptype->m_depkind != DEP_Nested) &&
+ (qubimptype->m_refkind != REF_Name) &&
+ (qubimptype->m_refkind != REF_QualName))
+ DebAssert(Qimptype(himptype)->m_ptinfo != NULL,
+ "IMPMGR::DebCheckState: Ptinfo should be set. ");
+
+ if (qubimptype->m_refkind == REF_Name)
+ pnammgr->DebCheckHlnam(qubimptype->m_hlnam);
+ else if (qubimptype->m_refkind == REF_QualName) {
+ qus = (USHORT *)m_bmData.QtrOfHandle(qubimptype->m_hrghlnam);
+ for (i = *qus++; i > 0; i--)
+ pnammgr->DebCheckHlnam(*(sHLNAM *)qus++);
+ }
+ else
+ DebAssert(qubimptype->m_refkind == REF_Base ||
+ qubimptype->m_refkind == REF_NoName,
+ "IMPMGR::DebChkState: invalid RefKind");
+
+ }
+
+ // In Ole there is nothing in the free list. All entries are valid
+ // entries
+
+ //
+ DebAssert(cbSize / sizeof(IMPTYPE) == cEntries,
+ "IMPMGR::DebCheckState: Free list messed up");
+
+}
+#pragma code_seg()
+
+
+
+
+/***
+*PUBLIC IMPMGR::DebChkHimptype
+*Purpose:
+* Check whether an himptype is valid
+*
+*Entry:
+* himptype
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+void IMPMGR::DebChkHimptype(HIMPTYPE himptype) const
+{
+
+DebAssert( (himptype < m_pbdTimptype->CbSize() &&
+ (himptype % sizeof(IMPTYPE)) == 0 ) ||
+ ( m_fCheckRemainingDepCalled == FALSE ),
+ "DebChkHimptype: invalid import entry");
+}
+
+
+/***
+*PUBLIC IMPMGR::DebChkHimpaddr
+*Purpose:
+* Check whether an himpaddr is valid
+*
+*Entry:
+* himpaddr
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+void IMPMGR::DebChkHimpaddr(HIMPADDR himpaddr) const
+{
+}
+#pragma code_seg()
+
+#endif
+
+
+
+// catches compiler generated code for static construction.
+#pragma code_seg(CS_INIT)
diff --git a/private/oleauto/src/typelib/impmgr.hxx b/private/oleauto/src/typelib/impmgr.hxx
new file mode 100644
index 000000000..043358f69
--- /dev/null
+++ b/private/oleauto/src/typelib/impmgr.hxx
@@ -0,0 +1,490 @@
+/**
+*impmgr.hxx - IMPMGR header file
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Declaration of IMPMGR class.
+*
+*Revision History:
+*
+* 05-Mar-91 alanc: Created.
+* 27-Nov-91 ilanc: Made SzOfHsz const (to avoid const castaway).
+* 10-Jul-92 w-peterh: added SetTypeInfoAndDepKind()
+* 18-Aug-92 w-peterh: moved IMPADDR def to cltypes.hxx
+* 17-Sep-92 rajivk: Edit & Continue support ( Check LayoutDep and RemainingDep)
+* 17-Sep-92 rajivk: Suport for saving all the edits. ( GetHimpType ).
+* 12-Feb-93 w-peterh: added HimpTypeOfIndex()
+* 09-Jun-93 RajivK : Remove impaddr from typelib.dll and cleanup language dep code.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#ifndef IMPMGR_HXX_INCLUDED
+#define IMPMGR_HXX_INCLUDED
+
+#include "sheapmgr.hxx"
+#include "cltypes.hxx"
+#include "stream.hxx"
+#include "blkmgr.hxx"
+#include "gdtinfo.hxx"
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szIMPMGR_HXX)
+#define SZ_FILE_NAME g_szIMPMGR_HXX
+#endif
+
+const UINT IMPMGR_cBuckets = 32;
+
+class TINFO;
+#if OE_RISC
+class TLB_TEMPLATE;
+#endif //OE_RISC
+
+// The higher the number the more decompilation is required to
+// remove that dependency. For example DEP_Layout has the highest
+// number since it requires the type to be decompiled to CS_UNDECLARED
+// when the referenced type's interface changes.
+enum DEPEND_KIND
+{
+ DEP_None,
+ DEP_Code,
+ DEP_Frame,
+ DEP_Layout,
+ DEP_Nested,
+ DEP_Base
+};
+
+enum REF_KIND
+{
+ REF_Name = 0,
+ REF_QualName = 1,
+ REF_NoName = 2,
+ REF_Base = 3
+};
+
+
+/***
+*class UB_IMPTYPE: Element of TUBIMPTYPE array.
+*Purpose:
+* Structure containing the unbound description of an Import entry.
+*
+*NOTE:- If the struture's layout changes then change
+* UB_IMPTYPE_Layout also for correct serialization
+***********************************************************************/
+
+class UB_IMPTYPE
+{
+public:
+ BOOL isFree() const;
+
+ USHORT m_cRefs;
+
+ // all of the following are packed into a single USHORT
+ USHORT m_refkind:6; //(REF_KIND)
+ USHORT m_isDeclRef:1; //(BOOL) set if this entry was created (or would have
+ // been created if it didn't already exist) as
+ // part of the process of getting to Declared state.
+ // Such an entry is created for the containing
+ // modules of nested types referenced by this module.
+ USHORT m_isExcodeRef:1; //(BOOL)set if this entry is refd from the excode table
+ USHORT m_depkind:6; //(DEPEND_KIND)describes how THIS class depends upon imported class.
+ USHORT m_isInternalRef:1; //(BOOL) set if this is a reference to a TypeInfo
+ // in the same library
+
+ sHIMPTYPE m_himptypeNext;
+
+ union {
+ sHLNAM m_hlnam;
+ sHCHUNK m_hrghlnam; //first word of chunk contains count followed
+ //by 1-n words containing sHLNAM's
+ };
+
+ UB_IMPTYPE() {
+ m_cRefs = 0;
+ m_isInternalRef = FALSE;
+ m_isExcodeRef = FALSE;
+ m_isDeclRef = FALSE;
+ m_refkind = REF_NoName;
+ m_depkind = DEP_None;
+ m_himptypeNext = HIMPTYPE_Nil;
+ }
+
+};
+
+// Defines the UB_IMPTYPE structure layout
+#define UB_IMPTYPE_Layout "ssss"
+
+
+
+/***
+*PUBLIC UB_IMPTYPE::isFree - test whether the import entry is free
+*Purpose:
+* Method to test whether this import entry is free
+*
+***********************************************************************/
+
+inline BOOL UB_IMPTYPE::isFree() const
+{
+ return FALSE; // In typelib import entries are never freed
+ // in the typelib.dll implementation.
+}
+
+
+/***
+*CLASS IMPTYPE - element of TIMPTYPE array
+*Purpose:
+* An IMPTYPE entry and its correponding UB_IMPTYPEENTRY contains the
+* complete description of an import entry.
+*
+***********************************************************************/
+
+class IMPTYPE
+{
+public:
+ inline IMPTYPE() {m_ptinfo = NULL;}
+ ITypeInfoA *m_ptinfo;
+};
+
+
+class IMPSTATUS; //needed for friend declaration below
+class COMPILETIME_SEG;
+
+
+/***
+*CLASS IMPMGR - 'impmgr': Import Manager
+*Purpose:
+* The Import Manager for a Type manages references to other Types.
+*
+***********************************************************************/
+
+class IMPMGR
+{
+friend void CheckImpMgrStatus(IMPSTATUS rgimpstatus[],
+ IMPMGR *pimpmgr,
+ NAMMGR *pnammgr);
+
+friend COMPILETIME_SEG;
+
+public:
+
+ IMPMGR(); //called by GEN_DTINFO::GetImpMgr
+ ~IMPMGR();
+ nonvirt TIPERROR Init(SHEAP_MGR * psheapmgr,
+ BLK_DESC * pbdTimptype,
+ BLK_DESC * pbdTimpaddr,
+ DYN_TYPEROOT *pdtroot);
+ HIMPTYPE HimptypeOfIndex(UINT i);
+ UINT IndexOfHimptype(HIMPTYPE himptype);
+
+ nonvirt HIMPTYPE GetHimptypeIfExists(ITypeInfoA *ptinfo);
+ nonvirt TIPERROR GetHimptype(UINT cName,
+ sHLNAM *rghlnam,
+ sHIMPTYPE *phimptype);
+ nonvirt TIPERROR GetHimptype(HLNAM hlnam, sHIMPTYPE *phimptype);
+ nonvirt TIPERROR GetHimptype(UINT cName,
+ sHLNAM *rghlnam,
+ ITypeInfoA *ptinfo,
+ sHIMPTYPE *phimptype);
+ nonvirt TIPERROR GetHimptype(ITypeInfoA *ptinfo,
+ DEPEND_KIND depkind,
+ sHIMPTYPE *phimptype);
+ nonvirt VOID GetName(HIMPTYPE himptype, UINT *pcName, sHLNAM *prghlnam[]);
+
+ nonvirt TIPERROR GetTypeInfo(HIMPTYPE himptype,
+ DEPEND_KIND depkind,
+ TYPEINFO **pptinfo);
+ nonvirt TIPERROR GetTypeInfo(HIMPTYPE himptype,
+ DEPEND_KIND depkind,
+ ITypeInfoA **pptinfo);
+#if 0
+ nonvirt void AddrefHimptype(HIMPTYPE himptype);
+#endif
+ nonvirt void Unref(HIMPTYPE himptype);
+ nonvirt TIPERROR CheckRemainingDep( DEPEND_KIND *pdepkindFail);
+ nonvirt TIPERROR CheckLayoutDep();
+ nonvirt TIPERROR RegisterDeclRefDep(ITypeInfoA *ptinfo);
+ nonvirt TIPERROR RegisterCodeRefDep(ITypeInfoA *ptinfo);
+ nonvirt DEPEND_KIND DepKind(HIMPTYPE himptype);
+
+ nonvirt BOOL IsEmpty();
+
+ nonvirt VOID BindImpTypes();
+ // Method to remove cycle problem within a project.
+ nonvirt VOID RemoveInternalRefs();
+ nonvirt TIPERROR ReadEntireImpMgr();
+ nonvirt TIPERROR WriteLayoutEntries( STREAM *pstrm, BOOL isLayoutDep );
+
+ HIMPTYPE HimptypeFirst() const;
+ HIMPTYPE HimptypeNext(HIMPTYPE himptype) const;
+
+ TIPERROR Read(STREAM *pstrm );
+ TIPERROR Write(STREAM *pstrm);
+
+ // OB specific functions
+
+ nonvirt UINT GetSize();
+
+ nonvirt UINT GetImpTypeSize();
+
+#if ID_DEBUG
+ nonvirt void DebCheckState(UINT uLevel) const;
+ nonvirt void DebShowState(UINT uLevel) const;
+ nonvirt void DebChkHimptype(HIMPTYPE himptype) const;
+ nonvirt void DebChkHimpaddr(HIMPADDR himpaddr) const;
+ nonvirt UINT DebShowSize();
+#else //!ID_DEBUG
+ nonvirt void DebCheckState(UINT uLevel) const {}
+ nonvirt void DebShowState(UINT uLevel) const {}
+ nonvirt void DebChkHimptype(HIMPTYPE himptype) const {}
+ nonvirt void DebChkHimpaddr(HIMPADDR himpaddr) const {}
+ nonvirt void DebShowSize() {}
+#endif
+
+private:
+ nonvirt TIPERROR BindTypeInfo(HIMPTYPE himptype, ITypeInfoA **pptinfo);
+ nonvirt TIPERROR BindTypeInfoOfHlnam(sHLNAM hlnam, ITypeInfoA **pptinfo);
+ nonvirt TIPERROR BindTypeInfoOfRghlnam(UINT chlnam,
+ sHLNAM *rghlnam,
+ ITypeInfoA **pptinfo);
+ nonvirt TIPERROR NewEntry(UB_IMPTYPE **pqubimptype,
+ sHIMPTYPE *phimptype);
+ nonvirt UINT IBucket(HLNAM hlnam);
+ nonvirt UINT IBucket(UINT cName, sHLNAM rghlnam[]);
+ nonvirt UINT IBucketOfHimptype(HIMPTYPE himptype);
+ nonvirt BOOL HasQualName(HIMPTYPE himptype, UINT cName, sHLNAM *rghlnam);
+ nonvirt UB_IMPTYPE* Qubimptype(TYPEID tid);
+ nonvirt UB_IMPTYPE* Qubimptype(HIMPTYPE himptype) const;
+ nonvirt HIMPTYPE Himptype(UB_IMPTYPE *qubimptype) const;
+ nonvirt IMPTYPE* Qimptype(HIMPTYPE himptype) const;
+ nonvirt TIPERROR HimptypeAlloc(sHIMPTYPE *phimptype);
+ nonvirt VOID HimptypeDelete(HIMPTYPE himptype);
+ nonvirt UB_IMPTYPE* Rqubimptype() const; //return tubimptype
+ nonvirt IMPTYPE* Rqimptype() const; //return timptype
+ TIPERROR SetPtinfo(HIMPTYPE himptype, ITypeInfoA *ptinfo, BOOL fDepBeingRead=FALSE);
+ VOID ReleasePtinfo(HIMPTYPE himptype);
+ LPSTR LqstrOfHsz(HCHUNK hsz) const;
+ UINT ChlnamQual(HIMPTYPE himptype) const;
+ sHLNAM *RqhlnamQual(HIMPTYPE himptype) const;
+ VOID SwapbmData(BOOL fSwapFirst) const;
+
+ // ImpAddr functions; only required for OB.
+
+
+ // Data Members
+ static USHORT cimptypeGrow;
+ static BYTE bFirstSerByte; // First byte of serialization
+ static BYTE bCurVersion; // Serialization format version number
+
+ // Data members for checking dependencies.
+ BOOL m_fCheckRemainingDepCalled;
+
+ // Datamember to record the address from where the typeids are.
+ // For the types where the dependecy is not Layout dependency.
+ LONG m_lPosOfDeps;
+
+
+
+ DYN_TYPEROOT *m_pdtroot;
+
+ //BLK_DESC for tubimptype
+ BLK_DESC m_bdTubimptype;
+
+ //pointer to BLK_DESC of timptype
+ BLK_DESC *m_pbdTimptype;
+
+ sHIMPTYPE m_rghimptypeBucket[IMPMGR_cBuckets];
+ sHIMPTYPE m_himptypeFreeList;
+
+ BLK_MGR m_bmData;
+#if OE_RISC
+ TLB_TEMPLATE *m_ptlbtempl;
+#endif // OE_RISC
+
+ // Impaddrs not required for OLE
+
+};
+
+
+
+/***
+*PRIVATE IMPMGR::Qubimptype - return pointer to UB_IMPTYPE of import entry
+*Purpose:
+* Returns pointer to UB_IMPTYPE entry associated with given himptype
+*
+*Entry:
+* himptype - imptype handle
+*
+*Exit:
+* return pointer to UB_IMPTYPE entry associated with himptype
+*
+***********************************************************************/
+
+inline UB_IMPTYPE* IMPMGR::Qubimptype(HIMPTYPE himptype) const
+{
+ DebChkHimptype(himptype);
+
+ return (UB_IMPTYPE *)(m_bdTubimptype.QtrOfBlock()) +
+ himptype/sizeof(IMPTYPE);
+}
+
+
+/***
+* IMPMGR::DepKind - Returns the dependency kind
+*Purpose:
+* Get the Dependency Kind for the given himptype
+*
+*Entry:
+* himptype - imptype handle
+*
+*Exit:
+* return DEPEND_KIND
+*
+***********************************************************************/
+
+inline DEPEND_KIND IMPMGR::DepKind(HIMPTYPE himptype)
+{
+ DebChkHimptype(himptype);
+
+ return (DEPEND_KIND) Qubimptype(himptype)->m_depkind;
+}
+
+
+
+/***
+*PUBLIC IMPMGR::HimptypeOfIndex
+*Purpose:
+* Returns the Himptype of an index into the import arrays.
+*
+*Entry:
+* index into timptype and tubimptype
+*
+*Exit:
+* himptype - imptype handle
+*
+***********************************************************************/
+
+inline HIMPTYPE IMPMGR::HimptypeOfIndex(UINT i)
+{
+ DebChkHimptype(i * sizeof(IMPTYPE));
+ return i * sizeof(IMPTYPE);
+}
+
+
+/***
+*PUBLIC IMPMGR::IndexOfHimptype
+*Purpose:
+* Returns the index of an himptype into the import arrays.
+*
+*Entry:
+* index into timptype and tubimptype
+*
+*Exit:
+* index
+*
+***********************************************************************/
+
+inline UINT IMPMGR::IndexOfHimptype(HIMPTYPE himptype)
+{
+ DebChkHimptype(himptype);
+ return ((UINT) himptype) / sizeof(IMPTYPE);
+}
+
+ // These functions are not available for OLE
+
+/***
+*PRIVATE IMPMGR::Qimptype - return pointer to IMPTYPE of import entry
+*Purpose:
+* Returns pointer to IMPTYPE entry associated with given himptype
+*
+*Entry:
+* himptype - imptype handle
+*
+*Exit:
+* return pointer to IMPTYPE entry associated with himptype
+*
+***********************************************************************/
+
+inline IMPTYPE* IMPMGR::Qimptype(HIMPTYPE himptype) const
+{
+ return (IMPTYPE *)(m_pbdTimptype->QtrOfBlock() + himptype);
+}
+
+
+
+
+
+
+/***
+*PUBLIC IMPMGR::LqstrOfHsz
+*
+***********************************************************************/
+
+inline LPSTR IMPMGR::LqstrOfHsz(HCHUNK hsz) const
+{
+ return (char *)m_bmData.QtrOfHandle(hsz);
+}
+
+
+/***
+*PUBLIC IMPMGR::GetTypeInfo - returns pointer to TypeInfo of import entry
+*Purpose:
+* Returns pointer to TYPEINFO of import entry.
+*
+*Entry:
+* himptype - handle for ImpType entry
+* pptinfo - returns pointer to TYPEINFO
+*
+*Exit:
+* TIPERROR
+* If TIPERROR = TIPERR_None then *pptinfo returns a pointer to the
+* TYPEINFO. This reference must be released by the caller.
+*
+***********************************************************************/
+
+inline TIPERROR IMPMGR::GetTypeInfo(HIMPTYPE himptype,
+ DEPEND_KIND depkind,
+ TYPEINFO **pptinfo)
+{
+ return GetTypeInfo(himptype,
+ depkind,
+ (ITypeInfoA **)pptinfo);
+}
+
+/***
+*PUBLIC IMPMGR::IsEmpty -
+*Purpose:
+* Returns TRUE if there is nothing in the the import manager
+* to serialize.
+*
+*Entry:
+*
+*Exit:
+* BOOL : returns TRUE if the import manager is empty. Else returns FALSE.
+***********************************************************************/
+inline BOOL IMPMGR::IsEmpty()
+{
+ return (m_bdTubimptype.CbSize() == 0);
+}
+
+/***
+*PUBLIC IMPMGR::GetImpTypeSize
+*Purpose:
+* Returns the size of the IMPTYPE table.
+*
+*Entry:
+*
+*Exit:
+* UINT
+***********************************************************************/
+inline UINT IMPMGR::GetImpTypeSize()
+{
+ return m_bdTubimptype.CbSize();
+}
+
+
+#endif // ! IMPMGR_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/machine.hxx b/private/oleauto/src/typelib/machine.hxx
new file mode 100644
index 000000000..da6ddec10
--- /dev/null
+++ b/private/oleauto/src/typelib/machine.hxx
@@ -0,0 +1,222 @@
+/***
+*machine.hxx - Helpers for dealing with machine dependencies.
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file contains helper functions for dealing with machine
+* dependencies. For example, inline function sin this file do
+* efficient reading and write words and longs to unaligned addresses.
+*
+* The macros used the HP_* symbols to find out the characteristics
+* of the current machine.
+*
+*Revision History:
+*
+* [00] 15-Mar-91 petergo: Created.
+*
+*****************************************************************************/
+
+#ifndef MACHINE_HXX_INCLUDED
+#define MACHINE_HXX_INCLUDED
+
+#include <limits.h>
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szMACHINE_HXX)
+#define SZ_FILE_NAME g_szMACHINE_HXX
+#endif
+
+
+// This file requires 8-bit bytes, 16-bit shorts, 32-bit longs.
+#if CHAR_BIT != 8 || USHRT_MAX != 0xffff || ULONG_MAX != 0xffffffff
+#error Fundemental types have unexpected sizes.
+#endif
+
+
+
+
+/***
+*ReadUnaligned() - read data type from unaligned address
+*Purpose:
+* Reads the value of a data type from a possibly unaligned address.
+*
+*Entry:
+* p - address to read from
+* type - type of value to read
+*
+*Exit:
+* Reads the value read. The value returned is of the correct type.
+*
+***********************************************************************/
+
+#define ReadUnaligned(p, type) \
+ ((type) ReadUnalignedHelper((p), sizeof(type)))
+
+
+
+/***
+*ReadUnalignedHelper - read unaligned value
+*Purpose:
+* Reads a value from a possible unaligned address.
+* On processors that can efficiently read from unaligned addresses,
+* we just do the read. Otherwise we assemble the value from
+* bytes.
+*
+*Entry:
+* pb - pointer to value to read.
+* cb - number of bytes to read.
+*
+*Exit:
+* Value read.
+*
+***********************************************************************/
+
+inline ULONG ReadUnalignedHelper(void * pv, UINT cb)
+{
+#if HP_MUSTALIGNSHORT && HP_BIGENDIAN
+
+ BYTE * pb = (BYTE *) pv; // to eliminate annoying casts.
+
+ if (cb == 1)
+ return pb[0];
+ else if (cb == 2)
+ return (pb[0] << 8) + (pb[1]);
+ else if (cb == 4)
+ return ((ULONG) pb[0] << 24) + ((ULONG) pb[1] << 16) +
+ ((ULONG) pb[2] << 8) + ((ULONG) pb[3]);
+ else
+ { DebHalt("ReadUnaligned: bad data type size"); return 0;}
+
+#elif HP_MUSTALIGNSHORT && !HP_BIGENDIAN
+
+ BYTE * pb = (BYTE *) pv; // to eliminate annoying casts.
+
+ if (cb == 1)
+ return pb[0];
+ else if (cb == 2)
+ return (pb[0]) + (pb[1] << 8);
+ else if (cb == 4)
+ return ((ULONG) pb[0]) + ((ULONG) pb[1] << 8) +
+ ((ULONG) pb[2] << 16) + ((ULONG) pb[3] << 24);
+ else
+ { DebHalt("ReadUnaligned: bad data type size"); return 0;}
+
+#else // ! HP_MUSTALIGNSHORT
+
+ if (cb == 1)
+ return * (BYTE *) pv;
+ else if (cb == 2)
+ return * (USHORT *) pv;
+ else if (cb == 4)
+ return * (ULONG *) pv;
+ else
+ { DebHalt("ReadUnaligned: bad data type size"); return 0;}
+
+#endif // ! HP_MUSTALIGNSHORT
+}
+
+
+/***
+*WriteUnaligned - write an unaligned value.
+*Purpose:
+* Writes the value of a data type to a possibly unaligned address.
+*
+*Entry:
+* p - address to write to
+* val - value to write
+* type - type of value to write
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#define WriteUnaligned(p, val, type) \
+ (WriteUnalignedHelper((p), (ULONG) (val), sizeof(type)))
+
+
+/***
+*WriteUnalignedHelper - write unaligned value
+*Purpose:
+* Writes a value to a possible unaligned address.
+* On processors that can efficiently write to unaligned addresses,
+* we just do the write. Otherwise we split the value into bytes.
+*
+*Entry:
+* pb - pointer to location to write at.
+* ul - value to write
+* cb - number of bytes to write.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+inline void WriteUnalignedHelper(void * pv, ULONG ul, UINT cb)
+{
+#if HP_MUSTALIGNSHORT && HP_BIGENDIAN
+
+ BYTE * pb = (BYTE *) pv; // to eliminate annoying casts.
+
+ if (cb == 1)
+ *pb = (BYTE) ul;
+ else if (cb == 2) {
+ pb[1] = (BYTE) (ul);
+ pb[0] = (BYTE) (ul >> 8);
+ }
+ else if (cb == 4) {
+ pb[3] = (BYTE) (ul);
+ ul >>= 8;
+ pb[2] = (BYTE) (ul);
+ ul >>= 8;
+ pb[1] = (BYTE) (ul);
+ ul >>= 8;
+ pb[0] = (BYTE) (ul);
+ }
+ else {
+ DebHalt("WriteUnaligned: bad data type size");
+ }
+
+
+#elif HP_MUSTALIGNSHORT && !HP_BIGENDIAN
+
+ BYTE * pb = (BYTE *) pv; // to eliminate annoying casts.
+
+ if (cb == 1)
+ *pb = (BYTE) ul;
+ else if (cb == 2) {
+ pb[0] = (BYTE) (ul);
+ pb[1] = (BYTE) (ul >> 8);
+ }
+ else if (cb == 4) {
+ pb[0] = (BYTE) (ul);
+ ul >>= 8;
+ pb[1] = (BYTE) (ul);
+ ul >>= 8;
+ pb[2] = (BYTE) (ul);
+ ul >>= 8;
+ pb[3] = (BYTE) (ul);
+ }
+ else {
+ DebHalt("WriteUnaligned: bad data type size");
+ }
+
+#else // ! HP_MUSTALIGNSHORT
+
+ if (cb == 1)
+ * (BYTE *) pv = (BYTE) ul;
+ else if (cb == 2)
+ * (USHORT *) pv = (USHORT) ul;
+ else if (cb == 4)
+ * (ULONG *) pv = (ULONG) ul;
+ else
+ DebHalt("WriteUnaligned: bad data type size");
+
+#endif // ! HP_MUSTALIGNSHORT
+}
+
+
+#endif // MACHINE_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/macros.hxx b/private/oleauto/src/typelib/macros.hxx
new file mode 100644
index 000000000..dac97ca8e
--- /dev/null
+++ b/private/oleauto/src/typelib/macros.hxx
@@ -0,0 +1,276 @@
+/***
+*macros.hxx - Utility macros for Silver
+*
+* Copyright (C) 1990, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Contains useful utility macros for Silver.
+*
+* Macros defined here:
+* OOB_MAKEULONG
+* OOB_MAKELONG
+* OOB_MAKEP
+* OOB_SELECTOROF
+* OOB_OFFSETOF
+* PURE
+* RoundUp
+* RoundDown
+* NOTUSED
+* OOB_DELETE
+* MEMFREE
+* RELEASE
+*
+*Revision History:
+*
+* 14-Feb-91 ilanc: Created
+* [01] 28-Feb-91 ilanc: Prefix all macros with SILVER_
+* [02] 01-Mar-91 ilanc: No, prefix them all with OOB_
+* [03] 11-Mar-91 ilanc: define PURE (AFX no longers uses it).
+* [04] 25-Mar-91 petergo: Added RoundUp and RoundDown.
+* [05] 18-Jul-91 mikewo: Added NOTUSED macro (to declare unused formals).
+* [06] 05-Sep-91 ilanc: Added DELETE/MEMFREE (reset pointers to NULL).
+* [07] 11-Sep-91 ilanc: DELETE -> OOB_DELETE (WIN32 has its own DELETE).
+* [08] 01-Nov-91 ilanc: Added RELEASE.
+*
+*****************************************************************************/
+
+#ifndef MACROS_HXX_INCLUDED
+#define MACROS_HXX_INCLUDED
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szMACROS_HXX)
+#define SZ_FILE_NAME g_szMACROS_HXX
+#endif
+
+/*** Useful Helper Macros */
+
+// These are better than the standard OS2DEF.H versions since
+// allow you to manipulate a non-lvalue pointer -- in particular THIS.
+
+/* Combine l & h to form a 32 bit quantity. */
+#define OOB_MAKEULONG(l, h) ((ULONG)(((USHORT)(l)) | ((ULONG)((USHORT)(h))) << 16))
+#define OOB_MAKELONG(l, h) ((LONG)OOB_MAKEULONG(l, h))
+
+/* Create untyped far pointer from selector and offset */
+#define OOB_MAKEP(sel, off) ((VOID *)OOB_MAKEULONG(off, sel))
+
+/* Extract selector or offset from far pointer */
+#define OOB_SELECTOROF(p) ((USHORT) ((ULONG) (p) >> 16))
+
+// #define OFFSETOF(p) ((USHORT) ((ULONG) p & USHRT_MAX))
+#define OOB_OFFSETOF(p) ((USHORT) (ULONG) (p))
+
+
+// NOTUSED - this macro "declares" formal parameters that are not used in
+// their function. This prevents compiler warnings from being
+// generated. Only one formal can be declared at a time.
+// Usage is:
+// NOTUSED parm1;
+// NOTUSED parm2;
+// ...
+#define NOTUSED (void)
+
+
+// Evaluates to the number of elements in the given array.
+//
+#define DIM(X) (sizeof(X) / (sizeof((X)[0])))
+
+
+/***
+*operator new - supports placement syntax
+*Purpose:
+* Support placement syntax
+*
+*Entry:
+* size_t - ignored
+* pv - address
+*
+*Exit:
+* Returns pv
+*
+***********************************************************************/
+
+inline void *operator new(size_t, void* pv)
+{
+ return pv;
+}
+
+
+// OOB_DELETE
+//
+// This macro deletes an object (previously allocated with new)
+// via a pointer to said object and resets the pointer to NULL.
+//
+#define OOB_DELETE(pobject) (delete pobject, pobject = NULL)
+
+
+// MEMFREE
+//
+// This macro frees an object (previously allocated with MemAlloc)
+// via a pointer to said object and resets the pointer to NULL.
+//
+#define MEMFREE(pobject) (MemFree(pobject), pobject = NULL)
+
+
+// RELEASE
+//
+// This macro releases an object (previously constructed)
+// with its class's Release method and resets the object
+// pointer to null.
+//
+//
+#define RELEASE(pobject) \
+ if ((pobject) != NULL) { \
+ (pobject)->Release(); \
+ pobject = NULL; \
+ }
+
+
+/***
+*RoundUp - round up uint to a multiply of a power of two.
+*Purpose:
+* Rounds a value up.
+*
+*Entry:
+* u - value to round
+* uPower2 - round to multiple of this, must be a power of two.
+*
+*Exit:
+* Returns smallest multiple of uPower2 not less than u.
+*
+***********************************************************************/
+
+inline UINT RoundUp(UINT u, UINT uPower2)
+{
+ DebAssert((uPower2 & (uPower2 - 1)) == 0,
+ "RoundUp: not a power of two");
+
+ return (u + (uPower2 - 1)) & ~(uPower2 - 1);
+}
+
+#ifndef ID_INT_IS_LONG
+inline ULONG RoundUp(ULONG u, ULONG uPower2)
+{
+ DebAssert((uPower2 & (uPower2 - 1)) == 0,
+ "RoundUp: not a power of two");
+
+ return (u + (uPower2 - 1)) & ~(uPower2 - 1);
+}
+#endif
+
+/***
+*RoundDown - round down uint to a multiply of a power of two.
+*Purpose:
+* Rounds a value down.
+*
+*Entry:
+* u - value to round
+* uPower2 - round to multiple of this, must be a power of two.
+*
+*Exit:
+* Returns largest multiple of uPower2 not greater than u.
+*
+***********************************************************************/
+
+inline UINT RoundDown(UINT u, UINT uPower2)
+{
+ DebAssert((uPower2 & (uPower2 - 1)) == 0,
+ "RoundUp: not a power of two");
+
+ return u & ~(uPower2 - 1);
+}
+
+#ifndef ID_INT_IS_LONG
+inline ULONG RoundDown(ULONG u, ULONG uPower2)
+{
+ DebAssert((uPower2 & (uPower2 - 1)) == 0,
+ "RoundUp: not a power of two");
+
+ return u & ~(uPower2 - 1);
+}
+#endif
+
+/************************************************************
+* ODD and EVEN
+*********/
+inline BOOL ODD(UINT u)
+{
+ return((u&1) != 0);
+}
+
+inline BOOL EVEN(UINT u)
+{
+ return(!ODD(u));
+}
+
+
+#if 0
+# define ASSERTONERROR() DebAssert(!getenv("ASSERTONERR"), "Error detected")
+#else
+# define ASSERTONERROR()
+#endif
+
+//
+// The following are the correct/current OLE failure code macros
+//
+#define IfFailRet(s) { \
+ hresult = (s); \
+ if(FAILED(GetScode(hresult))){ \
+ ASSERTONERROR(); \
+ return hresult; }}
+#define IfFailRetTiperr(s) IfFailRet(s)
+#define IfFailGo(s) { \
+ hresult = (s); \
+ if(FAILED(GetScode(hresult))){ \
+ ASSERTONERROR(); \
+ goto Error; }}
+#define IfFailGoTo(s, label) { \
+ hresult = (s); \
+ if(FAILED(GetScode(hresult))){ \
+ ASSERTONERROR(); \
+ goto label; }}
+
+#define IfOleErrRet(s) IfFailRet(s)
+#define IfOleErrRetTiperr(s) IfFailRet(s)
+#define IfOleErrGo(s) IfFailGo(s)
+#define IfOleErrGoTo(s,label) IfFailGoTo(s, label)
+
+#define IfErrRet(s) { \
+ err = (s); \
+ if(FAILED(GetScode(err))){ \
+ ASSERTONERROR(); \
+ return err; }}
+#define IfErrRetHresult(s) IfErrRet(s)
+#define IfErrGo(s) { \
+ err = (s); \
+ if(FAILED(GetScode(err))){ \
+ ASSERTONERROR(); \
+ goto Error; }}
+#define IfErrGoTo(s, label) { \
+ err = (s); \
+ if(FAILED(GetScode(err))){ \
+ ASSERTONERROR(); \
+ goto label; }}
+
+#define IfNullRet(s) { \
+ if (!(s)) { \
+ ASSERTONERROR(); \
+ return HresultOfScode(E_OUTOFMEMORY); }}
+#define IfNullGo(s) { \
+ if (!(s)) { \
+ ASSERTONERROR(); \
+ goto Error; }}
+#define IfNullGoTo(s, label) { \
+ if (!(s)) { \
+ ASSERTONERROR(); \
+ goto label; }}
+#define IfNullMemErr(s) { \
+ if (!(s)) { \
+ ASSERTONERROR(); \
+ err = HresultOfScode(E_OUTOFMEMORY); goto Error;}}
+
+
+#endif // !MACROS_HXX_INCLUDED
+
diff --git a/private/oleauto/src/typelib/mbstring.cxx b/private/oleauto/src/typelib/mbstring.cxx
new file mode 100644
index 000000000..c1e32ac4f
--- /dev/null
+++ b/private/oleauto/src/typelib/mbstring.cxx
@@ -0,0 +1,667 @@
+/***
+*mbstring.c
+*
+* Copyright (C) 1993-1994, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Defines various functions that support Multi Bytes Code System.
+*
+*Revision History:
+*
+* [00] 07-Mar-93 kazusy: Created.
+*
+*Implementation Notes:
+*
+*
+*****************************************************************************/
+
+#include "silver.hxx"
+#include "typelib.hxx" // Redefine DebAssertFailed to ODebAssertFailed
+ // in the statically linked Mac TYPELIB.LIB
+#include <stdlib.h>
+#include <string.h>
+
+#include "debug.h"
+
+#pragma hdrstop(RTPCHNAME)
+
+#include "mbstring.h"
+
+#if OE_MAC
+#include <script.h>
+#endif //OE_MAC
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+static CHAR szMbString[] = __FILE__;
+#define SZ_FILE_NAME szMbString
+#endif
+
+
+
+// CONSIDER: move the IsSBCS macro into a header file.
+BOOL g_fSBCS = FALSE; // true if the system is SBCS -- be conservative
+ // because InitMbString (called by InitAppData)
+ // isn't always called on entry to every
+ // typelib API.
+#define IsSBCS() (g_fSBCS)
+
+
+/***
+*
+* InitMbString()
+*
+*Purpose:
+*
+*Create a lookup table which allows a small, fast isleadbyte() implementation,
+*and set up fJapan, fKorea, and fTaiwan macros.
+*
+****************************************************************************/
+
+char FAR g_rgchLeadByteTable[256];
+#pragma code_seg(CS_QUERY) // called from LibMain for OE_WIN16 and OE_WIN32
+void InitMbString(void)
+{
+#if OE_WIN
+
+ BYTE ctr;
+
+ // need to set up g_fSBCS.
+ g_fSBCS=TRUE; // assume SBCS
+ memset(g_rgchLeadByteTable, 0, 256);
+ // stop at 128 since there aren't any lead bytes under that
+ for (ctr = 255; ctr>127; ctr--) {
+ if (IsDBCSLeadByte(ctr)) {
+ g_rgchLeadByteTable[ctr] = -1;
+ g_fSBCS=FALSE; // must be DBCS
+ }
+ }
+
+#else //OE_MAC
+
+ // preserve the old font in the current grafPort
+ short fontSave = qd.thePort->txFont;
+
+ // then set the grafPort font to 1 (Application Default) because
+ // ParseTable uses qd.thePort->txFont to determine the currect script,
+ // which in turn determines the lead byte table. We want the application
+ // default table. OB Bug #3858
+ TextFont(1);
+
+ memset(g_rgchLeadByteTable, 0, 256);
+
+ // fill in the table. If the function fails, the table is already 0-filled
+ ParseTable(g_rgchLeadByteTable);
+
+ // restore the old font
+ TextFont(fontSave);
+
+ // for OE_MAC, FJapan is #defined to 1, so skip setting g_SystemLangId.
+ // UNDONE: (dougf) how to figure out if we can set g_fSBCS=FALSE on
+ // UNDONE: the MAC? Supposedly, GetUserDefaultLangID can't be used
+ // UNDONE: to do the check.
+
+#endif //OE_MAC
+}
+#pragma code_seg()
+
+
+#define _MBCS_OS
+
+#ifdef _MBCS_OS
+/***
+*
+* _mbascii
+*
+*Purpose:
+* Disable MB ASCII support (set _mbascii flag to 0).
+*
+* The _mbascii flag indicates whether the lib routines and
+* macros should operate on MB ASCII characters (i.e., the
+* double-byte versions of the ASCII characters that exist
+* in certain MBCS representations such as Kanji).
+*
+* In some cases, people want these to be worked on by the
+* various MB is/to/cmp routines. However, in most cases,
+* you do NOT want to do this (e.g., when modifying filenames,
+* you do NOT want to change the case of the MB ASCII chars
+* even though you DO want to change the case of the SB
+* ASCII chars.)
+*
+*******************************************************************************/
+
+unsigned int _mbascii = 0; /* 0 = do NOT operate on MB ASCII chars */
+
+#endif //_MBCS_OS
+
+#define _ISLEADBYTE(c) g_rgchLeadByteTable[(BYTE)c]
+
+/***
+* _mbschr - Multibyte implementation of strchr
+*******************************************************************************/
+#pragma code_seg(CS_INIT)
+unsigned char * __cdecl _mbschr( const unsigned char *pchSrc, const unsigned short ch)
+{
+ const unsigned char *p;
+
+ if (IsSBCS())
+ return (unsigned char *) strchr( (CHAR *) pchSrc, ch );
+
+ DebAssert( pchSrc != NULL, "_mbschr: null string is assigned.");
+
+ if (ch < 256) {
+ DebAssert(_ISLEADBYTE(ch) == 0, "_mbschr: invalid character is specified.");
+ for (p = pchSrc ; *p ; ) {
+ if (*p == ch)
+ break;
+ if (_ISLEADBYTE(*p)) {
+ p++;
+ if (*p == '\0')
+ break;
+ }
+ p++;
+ }
+ return (unsigned char *) (*p == ch ? p : NULL);
+ }
+ else {
+ for (p = pchSrc ; *p ; ) {
+ if (*p == (ch >> 8) ) {
+ if (*(p+1) == (ch & 0xFF))
+ break;
+ if (*++p == '\0')
+ break;
+ p++;
+ }
+ else {
+ if (_ISLEADBYTE(*p)) {
+ p++;
+ if (*p == '\0')
+ break;
+ }
+ p++;
+ }
+ }
+ return (unsigned char *) (*p? p : NULL);
+ }
+
+ return (NULL); // to satisfy compiler
+}
+#pragma code_seg()
+
+/***
+* _mbsrchr - Multibyte implementation of strrchr
+*******************************************************************************/
+#pragma code_seg(CS_INIT)
+unsigned char * __cdecl _mbsrchr( const unsigned char *pchSrc, const unsigned short ch)
+{
+ unsigned char *p;
+ unsigned char *pchFind = NULL;
+
+ if (IsSBCS())
+ return (unsigned char *) strrchr( (CHAR *) pchSrc, ch );
+
+ DebAssert( pchSrc != NULL, "_mbschr: null string is assigned.");
+
+ if (ch < 256) {
+ DebAssert(_ISLEADBYTE(ch) == 0, "_mbschr: invalid character is specified.");
+ for (p = (unsigned char *)pchSrc ; *p ; ) {
+ if (*p == ch)
+ pchFind = p;
+ if (_ISLEADBYTE(*p)) {
+ p++;
+ if (*p == '\0')
+ break;
+ }
+ p++;
+ }
+ return pchFind;
+ }
+ else {
+ for (p = (unsigned char *)pchSrc ; *p ; ) {
+ if (*p == (ch >> 8) ) {
+ if (*(p+1) == (ch & 0xFF))
+ pchFind = p;
+ if (*++p == '\0')
+ break;
+ p++;
+ }
+ else {
+ if (_ISLEADBYTE(*p)) {
+ p++;
+ if (*p == '\0')
+ break;
+ }
+ p++;
+ }
+ }
+ return pchFind;
+ }
+}
+#pragma code_seg()
+
+
+#if 0 //Dead Code
+unsigned char * __cdecl _mbsinc(const unsigned char *pchStr)
+{
+ DebAssert( !IsSBCS(), "_mbsinc called in SBCS environment." );
+
+ DebAssert(*pchStr != '\0', "_mbsinc: end of string");
+ if (_ISLEADBYTE(*pchStr)) {
+ pchStr++;
+ DebAssert(*pchStr != '\0', "_mbsinc: 2nd byte is null");
+ }
+ pchStr++;
+ return (unsigned char *)pchStr;
+}
+#endif //0
+
+
+#if 0 //Dead Code
+int __cdecl _ismbblead(unsigned char c)
+{
+ return _ISLEADBYTE(c);
+}
+#endif //0
+
+
+/***
+* _mbslen - Multibyte implementation of strclen
+*******************************************************************************/
+unsigned int __cdecl _mbslen(const unsigned char *pchStr)
+{
+ int nCnt = 0;
+ unsigned char ch;
+
+ if (IsSBCS())
+ return strlen((CHAR *) pchStr );
+
+
+ while (ch = *pchStr++) {
+ if (_ISLEADBYTE(ch)) {
+ if (*pchStr++ == '\0')
+ break;
+ }
+ nCnt++;
+ }
+ return nCnt;
+}
+
+
+#if 0 //Dead Code
+unsigned int __cdecl __mbblen(const unsigned char *pchStr)
+{
+ int nCnt = 0;
+
+ while (*pchStr) {
+ if (_ISLEADBYTE(*pchStr)) {
+ if (*++pchStr == '\0')
+ break;
+ nCnt++;
+ }
+ pchStr++;
+ nCnt++;
+ }
+ return nCnt;
+}
+#endif //0
+
+
+#if !OE_WIN32
+/***
+* _mbsnbcpy - Copy one string to another, n bytes only (MBCS strncpy)
+*
+*Purpose:
+* Copies exactly cnt bytes from src to dst. If strlen(src) < cnt, the
+* remaining character are padded with null bytes. If strlen >= cnt, no
+* terminating null byte is added. 2-byte MBCS characters are handled
+* correctly.
+*
+*Entry:
+* unsigned char *dst = destination for copy
+* unsigned char *src = source for copy
+* int cnt = number of characters to copy
+*
+*Exit:
+* returns dst = destination of copy
+*
+*Exceptions:
+*
+*******************************************************************************/
+
+unsigned char * __cdecl _mbsnbcpy(unsigned char *dst, const unsigned char *src, size_t cnt)
+{
+
+ unsigned char *start = dst;
+ size_t i;
+
+ if (IsSBCS())
+ return (unsigned char *) strncpy((CHAR *) dst, (CHAR *) src, cnt );
+
+ for (i = 0; i < cnt; i++) {
+
+ if (_ISLEADBYTE(*src)) {
+ *dst++ = *src++;
+ i++;
+ if (i==cnt) {
+ dst[-1] = '\0';
+ break;
+ }
+ if ((*dst++ = *src++) == '\0') {
+ dst[-2] = '\0';
+ break;
+ }
+ }
+
+ else
+ if ((*dst++ = *src++) == '\0')
+ break;
+
+ }
+
+ /* pad with nulls as needed */
+
+ while (++i < cnt)
+ *dst++ = '\0';
+
+ return(start);
+}
+#endif //!OE_WIN32
+
+
+#if !OE_WIN32
+/***
+*int _mbsncmp(s1, s2, n) - Compare n characters of two MBCS strings (strncmp)
+*
+*Purpose:
+* Compares up to n characters of two strings for lexical order.
+* Strings are compared on a character basis, not a byte basis.
+*
+*Entry:
+* unsigned char *s1, *s2 = strings to compare
+* size_t n = maximum number of characters to compare
+*
+*Exit:
+* returns <0 if s1 < s2
+* returns 0 if s1 == s2
+* returns >0 if s1 > s2
+*
+*Exceptions:
+*
+*******************************************************************************/
+
+int __cdecl _mbsncmp( const unsigned char *s1, const unsigned char *s2, size_t n)
+{
+ unsigned short c1, c2;
+
+ if (IsSBCS())
+ return strncmp( (CHAR *) s1, (CHAR *) s2, n );
+
+ if (n==0)
+ return(0);
+
+ while (n--) {
+
+ c1 = *s1++;
+ if (_ISLEADBYTE(c1))
+ c1 = ( (*s1 == '\0') ? 0 : ((c1<<8) | *s1++) );
+
+ c2 = *s2++;
+ if (_ISLEADBYTE(c2))
+ c2 = ( (*s2 == '\0') ? 0 : ((c2<<8) | *s2++) );
+
+ if (c1 != c2)
+ return( (c1 > c2) ? 1 : -1);
+
+ if (c1 == 0)
+ return(0);
+ }
+
+ return(0);
+}
+#endif //!OE_WIN32
+
+#define _MBSSPNP(p,s) _mbsspnp(p,s)
+#define _MBSPBRK(q,s) _mbspbrk(q,s);
+
+/***
+* _mbsicmp - Case-insensitive string comparision routine (MBCS lstrcmpi)
+*
+*Purpose:
+* Compares two strings for lexical order without regard to case.
+* Strings are compared on a character basis, not a byte basis.
+*
+*Entry:
+* char *s1, *s2 = strings to compare
+*
+*Exit:
+* returns <0 if s1 < s2
+* returns 0 if s1 == s2
+* returns >0 if s1 > s2
+*
+*Exceptions:
+*
+*******************************************************************************/
+
+#if !OE_WIN32
+int __cdecl _mbsicmp(const unsigned char *s1, const unsigned char *s2)
+{
+ unsigned short c1, c2;
+
+ if (IsSBCS()) {
+#if OE_WIN
+ return lstrcmpi( (CHAR *) s1, (CHAR *) s2 );
+#else //OE_WIN
+ // UNDONE: (dougf) shouldn't it always be this instead? lstrcmpi is
+ // UNDONE: win.ini sensitive, and we may not want that.
+ return stricmp( (XCHAR *) s1, (XCHAR *) s2 );
+#endif //OE_WIN
+ }
+
+ for (;;) {
+
+ c1 = *s1++;
+ if (_ISLEADBYTE(c1)) {
+ if (*s1 == '\0')
+ c1 = 0;
+ else {
+ c1 = ((c1<<8) | *s1++);
+#ifndef _MBCS_OS
+ if ( (_mbascii) &&
+ ((c1 >= _MBLOWERLOW) && (c1 <= _MBLOWERHIGH))
+ )
+ c1 -= _MBCASEDIFF;
+#endif
+ }
+ }
+ else
+ c1 = toupper(c1);
+
+ c2 = *s2++;
+ if (_ISLEADBYTE(c2)) {
+ if (*s2 == '\0')
+ c2 = 0;
+ else {
+ c2 = ((c2<<8) | (unsigned char)*s2++);
+#ifndef _MBCS_OS
+ if ( (_mbascii) &&
+ ((c2 >= _MBLOWERLOW) && (c2 <= _MBLOWERHIGH))
+ )
+ c2 -= _MBCASEDIFF;
+#endif
+ }
+ }
+ else
+ c2 = toupper(c2);
+
+ if (c1 != c2)
+ return( (c1 > c2) ? 1 : -1);
+ if (c1 == 0)
+ return(0);
+
+ }
+
+}
+#endif //!OE_WIN32
+
+/***
+* _mbscmp - Compare MBCS strings (strcmp)
+*
+*Purpose:
+* Compares two strings for lexical order. Strings
+* are compared on a character basis, not a byte basis.
+*
+*Entry:
+* char *s1, *s2 = strings to compare
+*
+*Exit:
+* returns <0 if s1 < s2
+* returns 0 if s1 == s2
+* returns >0 if s1 > s2
+*
+*Exceptions:
+*
+*******************************************************************************/
+int __cdecl _mbscmp( const unsigned char *s1, const unsigned char *s2)
+{
+ unsigned short c1, c2;
+
+ if (IsSBCS())
+ return strcmp( (CHAR *) s1, (CHAR *) s2 );
+
+ for (;;) {
+ c1 = *s1++;
+ if (_ISLEADBYTE(c1))
+ c1 = ( (*s1 == '\0') ? 0 : ((c1<<8) | *s1++) );
+
+ c2 = *s2++;
+ if (_ISLEADBYTE(c2))
+ c2 = ( (*s2 == '\0') ? 0 : ((c2<<8) | *s2++) );
+
+ if (c1 != c2)
+ return( (c1 > c2) ? 1 : -1);
+ if (c1 == 0)
+ return(0);
+ }
+
+}
+
+
+#if !OE_WIN32 //Dead Code for Win32
+/***
+* XCHAR *xstrdec(XCHAR *pxchStart, XCHAR *pxch)
+*
+* Purpose:
+* This is used to find the previous character in a
+* double byte string.
+*
+* Entry:
+* pxchFirst = pointer to the beginning of the string
+* pxchCur = pointer to a character in the string. Must not
+* point to the beginning of the string. Also, must not
+* point to the middle of a character.
+*
+* Exit:
+* returns a pointer to the character preceding the one
+* pointed to by pxchCur
+***********************************************************************/
+XCHAR *xstrdec(XCHAR *pxchFirst, XCHAR *pxchCur)
+{
+ XCHAR *pxch = pxchCur;
+
+ if (IsSBCS())
+ return pxchCur-1;
+
+
+ DebAssert(pxch > pxchFirst, "invalid pointers");
+ pxch--;
+
+ // Optimization: If the last byte is a lead byte, then
+ // we know that the last character is a double byte character.
+ // That is, we know that the last byte is not functioning as
+ // a lead byte (because it has no trail byte after it), and
+ // therefore, it must itself be a trail byte. Remember that
+ // when xislead returns TRUE, it means that the byte *may* be
+ // a lead byte, but it may also be a trail byte.
+ //
+ if (xislead(*pxch)) {
+ DebAssert(pxch > pxchFirst, "string of length one cannot contain lead byte");
+ return pxch-1;
+ }
+
+ if (pxch == pxchFirst) {
+ return pxchFirst;
+ }
+
+ // Now, we search along the string until either we hit
+ // the beginning of the string, or we find a non-lead byte.
+ //
+ while (--pxch >= pxchFirst && xislead(*pxch)) {}
+
+ // At this point, pxch + 1 is either equal to pxchFirst,
+ // or else it is pointing to a character just past
+ // a non-lead byte. In either case, we know that
+ // pxch points to the beginning of a character.
+
+ // We also know that everything between pxch + 1 and the
+ // last byte of the string must be lead bytes, and therefore
+ // must consist of double byte characters. Therefore, depending
+ // on whether there are an odd or even number of lead bytes,
+ // we can deduce whether the last byte was a trail byte or not:
+ return pxchCur - 1 - ((pxchCur - pxch) & 1);
+}
+#endif //!OE_WIN32
+
+
+#if 0 //Dead Code
+/***
+*XCHAR *PxchFindPrevCharOrBeginOfChar(XSZ xszStart, XCHAR *pxchCur)
+*Purpose:
+* This finds the first character in the string xszStart which
+* begins at an address lower than pxchCur. This is used
+* to move backwards in a string possibly containing double
+* byte characters.
+*
+* Unlike xstrdec, this may be called in the case where
+* pxchCur may point into the middle of a character. (If
+* pxchCur does happen to point into the middle of a character,
+* then this returns a pointer to the beginning of that character.
+* (Hence the long name for this function.))
+*
+* If you are sure that pxchCur doesn't point into the middle
+* of a double byte character, you should call xstrdec.
+*
+***********************************************************************/
+XCHAR *PxchFindPrevCharOrBeginOfChar(XCHAR *pxchFirst, XCHAR *pxchCur)
+{
+ XCHAR *pxch = pxchCur;
+
+ DebAssert(pxch > pxchFirst, "invalid pointers");
+ pxch--;
+
+ // We search along the string until either we hit
+ // the beginning of the string, or we find a non-lead byte.
+ //
+ while (--pxch >= pxchFirst && xislead(*pxch)) {}
+
+ // At this point, pxch + 1 is either equal to pxchFirst,
+ // or else it is pointing to a character just past
+ // a non-lead byte. In either case, we know that
+ // pxch points to the beginning of a character.
+
+ // We also know that everything between pxch + 1 and the
+ // last byte of the string must be lead bytes, and therefore
+ // must consist of double byte characters. Therefore, depending
+ // on whether there are an odd or even number of lead bytes,
+ // we can deduce whether the last byte was a trail byte or not:
+ return pxchCur - 1 - ((pxchCur - pxch) & 1);
+}
+#endif //0
+
+
+
+
+#if OE_MAC
+#pragma code_seg(CS_INIT)
+#endif
diff --git a/private/oleauto/src/typelib/mbstring.h b/private/oleauto/src/typelib/mbstring.h
new file mode 100644
index 000000000..8ae9f3fc5
--- /dev/null
+++ b/private/oleauto/src/typelib/mbstring.h
@@ -0,0 +1,46 @@
+/***
+*mbstring.h - declarations for string manipulation functions for MBCS
+*
+* Copyright (C) 1993, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file contains the function declarations for the string
+* manipulation functions of MBCS version.
+*
+*Revision History:
+*
+* [01] 08-Mar-93 kazusy: Created.
+*
+*****************************************************************************/
+
+#ifndef MBSTRING_H_INCLUDED
+#define MBSTRING_H_INCLUDED
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+void InitMbString(void);
+unsigned char * __cdecl _mbschr(const unsigned char *, const unsigned short);
+unsigned char * __cdecl _mbsrchr(const unsigned char *, const unsigned short);
+unsigned int __cdecl _mbslen(const unsigned char *);
+int __cdecl _mbscmp(const unsigned char *, const unsigned char *);
+
+#if !OE_WIN32
+unsigned char * __cdecl _mbsnbcpy(unsigned char *, const unsigned char *, size_t);
+int __cdecl _mbsncmp(const unsigned char *, const unsigned char *, size_t);
+int __cdecl _mbsicmp(const unsigned char *, const unsigned char *);
+#endif //!OE_WIN32
+
+#if 0 //Dead Code
+unsigned char * __cdecl _mbsinc(const unsigned char *);
+int __cdecl _ismbblead(unsigned char);
+unsigned int __cdecl __mbblen(const unsigned char *);
+#endif //0
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif // MBSTRING_H_INCLUDED
diff --git a/private/oleauto/src/typelib/mem.cxx b/private/oleauto/src/typelib/mem.cxx
new file mode 100644
index 000000000..1acc149c6
--- /dev/null
+++ b/private/oleauto/src/typelib/mem.cxx
@@ -0,0 +1,417 @@
+/***
+*mem.cxx - implementation of the simple memory allocation routines.
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file contains the implementations of the simple memory allocators,
+* MemAlloc(), MemZalloc, and MemRealloc().
+*
+*Revision History:
+*
+* [00] 19-Feb-91 mikewo: Created.
+* [01] 15-Mar-91 ilanc: Added segment mm for Win and Os/2.
+* [02] 12-Apr-91 ilanc: Added exception handling.
+* [03] 16-May-91 alanc: Added SZ functions
+* [04] 08-Oct-91 ilanc: LStrFree is NOP if arg is NULL.
+* [05] 23-Oct-91 stevenl: Fixed MemRealloc for shrinking blocks.
+* [06] 19-Dec-91 mattsh: Fixed MemFree
+* [07] 06-Apr-92 martinc: Mac-specific changes
+* [08] 20-Apr-92 martinc: restored file i/o for OE_MAC
+* [09] 27-May-92 petergo: LStr routine now defer to BStr routines
+* [10] 13-Nov-92 bradlo: moved LStr wrappers to separate file
+* [11] 18-Feb-93 RajivK: Changed the implementation of MemAlloc/Free/ReAlloc
+*
+*Implementation Notes:
+* Include os2.h/windows.h *after* silver.hxx
+*
+*****************************************************************************/
+
+#include <limits.h>
+
+// Include some Silver stuff that defines some symbols needed
+// immediately.
+//
+#include "switches.hxx"
+#include "typelib.hxx"
+#include "version.hxx"
+#include "silver.hxx"
+#include "mem.hxx"
+#include "clutil.hxx"
+#include "bstr.h"
+#include "xstring.h"
+
+#pragma hdrstop(RTPCHNAME)
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+char szOleMemCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleMemCxx
+#else
+static char szMemCxx[] = __FILE__;
+#define SZ_FILE_NAME szMemCxx
+#endif
+#endif
+
+#if ID_DEBUG
+// This variables can used to find out the memory USAGE. g_cbHeapAllocdMax
+// is the Max memory allocate by OB during the execution.
+ULONG g_cbHeapAllocd, g_cbHeapAllocdMax;
+#endif
+
+/***
+*void *MemAlloc - Allocates memory from the global heap.
+*Purpose:
+* This method allocates memory from the global heap, just like the
+* standard C library routine, malloc().
+*
+*Implementation Notes: Defer to OLE's IMalloc interface to allocate memory.
+*
+*Entry:
+* cb - The number of bytes to allocate.
+*
+*Exit:
+* Returns a pointer to the allocated memory. THIS CAN RETURN NULL.
+*
+*Errors:
+* Returns NULL in case of error
+*
+****************************************************************/
+#pragma code_seg(CS_INIT)
+#if ID_DEBUG
+void *MemAlloc(ULONG cb)
+#else // !ID_DEBUG
+void *MemAlloc(size_t cb)
+#endif // !ID_DEBUG
+{
+ void *pvRet;
+
+
+ DebAssert(cb <= USHRT_MAX, "Block will overflow.");
+
+ DebHeapChk();
+
+#if ID_DEBUG
+ if (DebErrorNow(TIPERR_OutOfMemory))
+ return NULL;
+#endif // ID_DEBUG
+
+ // Allocate Memory using OLE interface
+ APP_DATA FAR* pappdata;
+
+#if OE_WIN32
+ if (FAILED(GetAppData(&pappdata))) {
+ return NULL;
+ }
+
+ pvRet = pappdata->m_pimalloc->Alloc(cb);
+#else // !OE_WIN32
+ IMalloc FAR* pmalloc;
+
+ // If the APP_DATA hasn't yet been initialized, get the
+ // IMalloc from CoGetMalloc directly.
+ if ((pappdata = Pappdata()) == NULL) {
+ if (CoGetMalloc(MEMCTX_TASK, &pmalloc))
+ return NULL;
+ pvRet = pmalloc->Alloc(cb);
+ pmalloc->Release();
+ }
+ else
+ pvRet = pappdata->m_pimalloc->Alloc(cb);
+#endif // !OE_WIN32
+
+#if ID_DEBUG
+ if (pvRet == NULL)
+ return NULL;
+
+ g_cbHeapAllocd += cb;
+ if (g_cbHeapAllocd > g_cbHeapAllocdMax)
+ g_cbHeapAllocdMax = g_cbHeapAllocd;
+#endif
+
+ return(pvRet);
+}
+#pragma code_seg()
+
+/***
+*void *MemZalloc - Allocates 0-initialized memory from the global heap.
+*Purpose:
+* This is the same as MemAlloc(), except the returned memory block is
+* initialized to 0.
+*
+*Entry:
+* cb - The number of bytes to allocate.
+*
+*Implementation Notes: Defer to OLE's IMalloc interface to allocate memory
+*
+*Exit:
+* Returns a pointer to the allocated memory, which is initialized to hold
+* all zeros. THIS CAN RETURN NULL.
+*
+*Errors:
+* OutOfMemory
+*
+****************************************************************/
+#pragma code_seg(CS_INIT)
+#if ID_DEBUG
+void *MemZalloc(ULONG cb)
+#else // !ID_DEBUG
+void *MemZalloc(size_t cb)
+#endif // !ID_DEBUG
+{
+ void *pvRet;
+
+ DebAssert(cb <= USHRT_MAX, "Block will overflow.");
+
+ DebHeapChk();
+
+ // Allocate Memory using MemAlloc
+ if (DebErrorNow(TIPERR_OutOfMemory) || ((pvRet = MemAlloc(cb)) == NULL)) {
+ return NULL;
+ }
+
+#if ID_DEBUG
+ g_cbHeapAllocd += cb;
+ if (g_cbHeapAllocd > g_cbHeapAllocdMax)
+ g_cbHeapAllocdMax = g_cbHeapAllocd;
+#endif
+
+ // IMalloc does not provide interface for zero initialized memory
+ // allocation , so we need to initialize the memory.
+ memset(pvRet, 0, (size_t)cb);
+
+ return(pvRet);
+}
+#pragma code_seg()
+
+#if OE_MAC || OE_RISC || OE_WIN32
+/***
+*void *MemRealloc - Resizes a previously allocated block of memory.
+*Purpose:
+* This function changes the size of a block of memory previously allocated
+* with MemAlloc(), MemZalloc(), or MemRealloc(), just like the standard
+* C library function realloc().
+*
+*Entry:
+* pvOld - The memory block whose size should be changed.
+* cbNew - The new size of the memory block.
+*
+*Exit:
+* Returns a pointer to the reallocated memory block, which may not be
+* the same as pvOld. If the allocation fails, NULL is returned and the
+* original block of memory (pvOld) is NOT deallocated.
+*
+*Errors;
+* OutOfMemory
+*
+****************************************************************/
+#pragma code_seg(CS_INIT)
+#pragma PCODE_OFF
+#if ID_DEBUG
+void *MemRealloc(void *pvOld, ULONG cbNew)
+#else // !ID_DEBUG
+void *MemRealloc(void *pvOld, size_t cbNew)
+#endif // !ID_DEBUG
+{
+ void *pvRet;
+#if ID_DEBUG
+ size_t cbOld;
+#endif
+
+ DebAssert(cbNew <= USHRT_MAX, "Block will overflow.");
+
+ DebHeapChk();
+
+
+ // save size of old block
+
+
+#if ID_DEBUG
+ // We should only fail if we're trying to increase the
+ // size of a block.
+ //
+ cbOld = (pvOld == NULL) ? 0 : (size_t)MemSize(pvOld);
+ if (cbNew > cbOld && DebErrorNow(TIPERR_OutOfMemory))
+ return NULL;
+#endif // ID_DEBUG
+
+ APP_DATA FAR* pappdata;
+
+ // Call IMalloc's Realloc
+#if OE_WIN32
+ if (FAILED(GetAppData(&pappdata))) {
+ return NULL;
+ }
+
+ pvRet = pappdata->m_pimalloc->Realloc(pvOld, cbNew);
+#else // !OE_WIN32
+ IMalloc FAR* pmalloc;
+
+ // If the APP_DATA hasn't yet been initialized, get the
+ // IMalloc from CoGetMalloc directly.
+ if ((pappdata = Pappdata()) == NULL) {
+ if (CoGetMalloc(MEMCTX_TASK, &pmalloc))
+ return NULL;
+ pvRet = pmalloc->Realloc(pvOld, cbNew);
+ pmalloc->Release();
+ }
+ else
+ pvRet = pappdata->m_pimalloc->Realloc(pvOld, cbNew);
+#endif // !OE_WIN32
+
+ return(pvRet);
+}
+#pragma PCODE_ON
+#pragma code_seg()
+#endif //EI_OB || OE_MAC || OE_RISC || OE_WIN32
+
+/***
+*void MemFree - Frees memory allocated by MemAlloc/MemZalloc/MemRealloc
+*Purpose:
+* Frees memory allocated by MemAlloc/MemZalloc/MemRealloc
+*
+*Entry:
+* pv - pointer to memory block to be deallocated
+*
+*Exit:
+* None.
+****************************************************************/
+#if !OE_MAC
+#pragma code_seg(CS_QUERY)
+#else
+#pragma code_seg(CS_INIT)
+#endif
+#pragma PCODE_OFF
+void MemFree(void *pv)
+{
+ if ( pv==NULL )
+ return;
+
+#if ID_DEBUG
+ g_cbHeapAllocd -= MemSize(pv);
+#endif // ID_DEBUG
+
+ // Call IMalloc's Free to free the memory pointed by pv
+#if OE_WIN32 && 0 // can't rely on appdata being there
+ // because bad apps may end up releasing
+ // things after calling OleUninitialize.
+ DebAssert(Pappdata(), "How'd we alloc without IMalloc?");
+
+ Pappdata()->m_pimalloc->Free(pv);
+#else // !OE_WIN32
+ APP_DATA FAR* pappdata;
+ IMalloc FAR* pmalloc;
+
+ // If the APP_DATA hasn't yet been initialized (or has been
+ // initialized and then thrown away), get the
+ // IMalloc from CoGetMalloc directly.
+ if ((pappdata = Pappdata()) == NULL) {
+ if (CoGetMalloc(MEMCTX_TASK, &pmalloc))
+ return;
+ pmalloc->Free(pv);
+ pmalloc->Release();
+ }
+ else
+ pappdata->m_pimalloc->Free(pv);
+#endif // !OE_WIN32
+
+ DebHeapChk();
+}
+#pragma PCODE_ON
+#pragma code_seg()
+
+/***
+*void
+*Purpose:
+* Returns the Size, in bytes, of the memory block pointed by pv
+*
+*Entry:
+* pv - pointer to memory block whose size is requested
+*
+*Exit:
+* None.
+****************************************************************/
+#if ID_DEBUG
+#pragma code_seg( CS_CORE )
+ULONG MemSize(void *pv)
+{
+ ULONG cbSize;
+
+ // Get the Size of the memory block
+#if OE_WIN32 && 0 // can't rely on appdata being there
+ // because bad apps may end up releasing
+ // things after calling OleUninitialize.
+ DebAssert(Pappdata(), "How'd we alloc without IMalloc?");
+ cbSize = Pappdata()->m_pimalloc->GetSize(pv);
+#else // !OE_WIN32
+ IMalloc FAR* pmalloc;
+ APP_DATA FAR* pappdata;
+
+ // If the APP_DATA hasn't yet been initialized, get the
+ // IMalloc from CoGetMalloc directly.
+ if ((pappdata = Pappdata()) == NULL) {
+ if (CoGetMalloc(MEMCTX_TASK, &pmalloc))
+ return 0;
+ cbSize = pmalloc->GetSize(pv);
+ pmalloc->Release();
+ }
+ else
+ cbSize = pappdata->m_pimalloc->GetSize(pv);
+#endif // !OE_WIN32
+
+ return cbSize;
+}
+#pragma code_seg( )
+#endif //ID_DEBUG
+
+
+
+
+#if OE_MAC
+// CONSIDER: (dougf) Tune the size of this sucker (it's huge -- 1K). It's only
+// CONSIDER: used by gtlibole.cxx to hold a libid, which
+// CONSIDER: shouldn't require a 1K static buffer!
+MEMPOOL NEAR g_mempool;
+
+#if ID_DEBUG
+
+void NEAR *GetMemPool(int i)
+{
+ switch (i) {
+ case 0:
+ DebAssert(!g_mempool.is1024n0InUse, "GetMemPool");
+ g_mempool.is1024n0InUse = 1;
+ return g_mempool.rgb1024n0;
+
+ default:
+ DebHalt("GetMemPool");
+ }
+ return NULL;
+}
+
+void FreeMemPool(void *pmv)
+{
+ if (pmv == g_mempool.rgb1024n0) {
+ DebAssert(g_mempool.is1024n0InUse, "MemPool Already Free");
+ g_mempool.is1024n0InUse = 0;
+ }
+ else {
+ DebHalt("Bad pointer to FreeMemPool");
+ }
+}
+
+int MemPoolSize(int i)
+{
+ switch (i) {
+ case 0:
+ return sizeof(g_mempool.rgb1024n0);
+ default:
+ DebHalt("MemPoolSize");
+ }
+ return 0;
+}
+
+#endif // ID_DEBUG
+#endif //OE_MAC
diff --git a/private/oleauto/src/typelib/mem.hxx b/private/oleauto/src/typelib/mem.hxx
new file mode 100644
index 000000000..f97d9599a
--- /dev/null
+++ b/private/oleauto/src/typelib/mem.hxx
@@ -0,0 +1,174 @@
+/***
+*mem.hxx - Prototypes for simple memory allocation/freeing
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This header file contains the declarations of the simple memory
+* allocation functions, MemAlloc, MemZalloc, MemRealloc, and MemFree.
+* These functions are identical to their standard C library counterparts,
+* except they raise an OOM (out of memory) exception on failure.
+*
+* Note that
+*
+*Revision History:
+*
+* [00] 19-Feb-91 mikewo: Created.
+* [01] 14-Mar-91 ilanc: Added global segment mm for Win and Os/2.
+* [02] 01-Jul-91 ilanc: Move segment stuff to sheapmgr.
+* [03] 02-Dec-91 ilanc: no longer include cltypes.hxx (no need -- get
+* TIPERROR from types.h now).
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#ifndef MEM_HXX_INCLUDED
+#define MEM_HXX_INCLUDED
+
+#include <malloc.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#if OE_MAC
+// MEMPOOL routines
+//////////////////////////////
+
+typedef struct MEMPOOL {
+ char rgb1024n0[1024];
+#if ID_DEBUG
+ BOOL is1024n0InUse;
+#endif // ID_DEBUG
+} MEMPOOL;
+
+extern MEMPOOL NEAR g_mempool;
+
+#if ID_DEBUG
+
+#define MEMPOOL_1024_0 0
+void NEAR *GetMemPool(int i);
+void FreeMemPool(void *pmv);
+int MemPoolSize(int i);
+
+#else // ID_DEBUG
+
+#define MEMPOOL_1024_0 rgb1024n0
+#define GetMemPool(i) (g_mempool.i)
+#define FreeMemPool(pmv)
+#define MemPoolSize(i) (sizeof(g_mempool.i))
+
+#endif // ID_DEBUG
+#endif //OE_MAC
+
+
+// Base Allocation routines
+//////////////////////////////
+
+#if ID_DEBUG
+// Pass in a ULONG so we can assert that the size of the block being
+// allocated is < 64K.
+//
+LPVOID MemAlloc(ULONG cb);
+LPVOID MemZalloc(ULONG cb);
+LPVOID MemRealloc(LPVOID pvOld, ULONG cbNew);
+#else // !ID_DEBUG
+LPVOID MemAlloc(size_t cb);
+LPVOID MemZalloc(size_t cb);
+LPVOID MemRealloc(LPVOID pvOld, size_t cbNew);
+#endif // !ID_DEBUG
+
+void MemFree(LPVOID pv);
+ULONG MemSize(void *pv);
+
+#if 0 //Dead Code
+VOID hmemmove(VOID *pvDest, VOID *pvSrc, ULONG ulSize);
+VOID *HugeMemAlloc(ULONG ulSize);
+VOID *HugeMemRealloc(VOID *pvOld, ULONG ulSizeNew);
+VOID HugeMemFree(VOID *pv);
+#endif //0
+
+// SZ allocating functions
+//
+TIPERROR CreateXsz(XSZ FAR *psz, XSZ_CONST sz);
+TIPERROR ErrCopy(XSZ_CONST sz, XSZ szBuf, UINT cMax);
+
+#ifdef __cplusplus
+}
+
+#if !(OE_MAC && OE_DLL)
+// gets dup def warnings if included into the mac ole applet, and none of
+// our typelib code is *SUPPOSED* to call it, so it's safe to remove it.
+
+/***
+*operator new
+*Purpose:
+* Redefines standard new operator to invoke MemAlloc
+*
+*Entry:
+* size_t - size of instance to be allocated
+*
+*Exit:
+* Returns allocated memory block or NULL if OutOfMemory
+*
+***********************************************************************/
+
+inline LPVOID operator new(size_t cbSize)
+{
+// In non-OLE builds, this is just MemAlloc.
+#if FV_UNICODE_OLE || OE_MACPPC
+ return MemAlloc(cbSize);
+
+// In debug builds, force a divide-by-0 trap.
+#elif ID_DEBUG
+ int i = 0;
+ return (LPVOID)(1/i);
+
+// The compiler disallows the divide-by-0 attempt in the retail builds,
+// so just return NULL to simulate an out-of-memory condition.
+#else
+ return NULL;
+#endif // EI_OB
+}
+#endif // !(OE_MAC && EI_OLE && OE_DLL)
+
+/***
+*MemNew - Use this instead of the new operator in OLE code to allocate memory.
+****************************************************************************/
+#define MemNew(type) ((type FAR *)MemAlloc(sizeof(type)))
+
+
+/***
+*operator delete
+*Purpose:
+* Redefines standard operator delete to invoke MemFree
+*
+*Entry:
+* pv - address
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#if !(OE_MAC && OE_DLL)
+// gets dup def warnings if included into the mac ole applet, and none of
+// our typelib code is *SUPPOSED* to call it, so it's safe to remove it.
+
+inline void operator delete(LPVOID pv)
+{
+#if FV_UNICODE_OLE || OE_MACPPC
+ MemFree(pv);
+// In debug builds, force a divide-by-0 trap.
+#elif ID_DEBUG
+ int i = 0;
+ i = 1 / i;
+// The compiler disallows the divide-by-0 attempt in the retail builds
+#endif // EI_OB
+}
+#endif // !(OE_MAC && EI_OLE && OE_DLL)
+
+#endif // cplusplus
+#endif // MEM_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/namemacs.h b/private/oleauto/src/typelib/namemacs.h
new file mode 100644
index 000000000..7a574c6a7
--- /dev/null
+++ b/private/oleauto/src/typelib/namemacs.h
@@ -0,0 +1,1305 @@
+ #undef StgCreateDocfile
+ #undef StgCreateDocfileOnILockBytes
+ #undef StgOpenStorage
+ #undef StgOpenStorageOnILockBytes
+ #undef StgIsStorageFile
+ #undef StgIsStorageILockBytes
+ #undef StgSetTimes
+ #undef StgSetTimesMac
+ #undef StgSetTimesFSp
+ #undef DllGetClassObject
+ #undef StgCreateDocfileFSp
+ #undef StgOpenStorageFSp
+ #undef StgCreateDocfileMac
+ #undef StgOpenStorageMac
+ #undef StgIsStorageFileMac
+ #undef StgIsStorageFileFSp
+ #undef StgGetFSpFromIStorage
+ #undef StgGetFRefFromIStorage
+ #undef OleregOpenRegistration
+ #undef OleregCloseRegistration
+ #undef OleregGetValue
+ #undef OleregSetValue
+ #undef OleregRemoveKey
+ #undef OleGlobalAddAtom
+ #undef OleGlobalDuplicateAtom
+ #undef OleGlobalDeleteAtom
+ #undef OleGlobalFindAtom
+ #undef OleGlobalGetAtomName
+ #undef OleGlobalAlloc
+ #undef OleGlobalCompact
+ #undef OleGlobalFree
+ #undef OleGlobalHandle
+ #undef OleGlobalLock
+ #undef OleGlobalReAlloc
+ #undef OleGlobalSize
+ #undef OleGlobalUnlock
+ #undef RegQueryValue
+ #undef RegOpenKey
+ #undef RegSetValue
+ #undef RegEnumKey
+ #undef RegEnumProgID
+ #undef RegDeleteKey
+ #undef RegCreateKey
+ #undef RegCloseKey
+ #undef RegInitialize
+ #undef InitUserData
+ #undef SendHighLevelEvent
+ #undef OleWinExec
+ #undef InitDB
+ #undef CloseDB
+ #undef OleGetCurrentTask
+ #undef OleGetProcAddress
+ #undef OleLoadLibrary
+ #undef OleFreeLibrary
+ #undef OutputDebugString
+ #undef SoftAssert
+ #undef FnAssert
+ #undef IsValidInterface
+ #undef IsValidIid
+ #undef IsValidHandle
+ #undef EnterOLEApi
+ #undef ExitOLEApi
+ #undef FnAssertOn
+ #undef GlobalFreePtr
+ #undef GlobalAllocPtr
+ #undef UserInitialize
+ #undef UserUninitialize
+ #undef IsValidInPtr
+ #undef IsValidOutPtr
+ #undef RegQueryValueEx
+ #undef RegFlush
+ #undef RegDeleteValue
+ #undef RegSetValueEx
+ #undef RegEnumValue
+ #undef OLEInitDBCSCountry
+ #undef IAnsiNext
+ #undef IAnsiPrev
+ #undef OleMakeFSSpec
+ #undef OleFullPathFromFSSpec
+ #undef OleGetFSSpecInfo
+ #undef DllGetClassObject
+ #undef SysAllocString
+ #undef SysReAllocString
+ #undef SysAllocStringLen
+ #undef SysReAllocStringLen
+ #undef SysFreeString
+ #undef SysStringLen
+ #undef VariantInit
+ #undef VariantClear
+ #undef VariantCopy
+ #undef VariantCopyInd
+ #undef VariantChangeType
+ #undef VarI2FromI4
+ #undef VarI2FromR4
+ #undef VarI2FromR8
+ #undef VarI2FromCy
+ #undef VarI2FromDate
+ #undef VarI2FromStr
+ #undef VarI2FromDisp
+ #undef VarI2FromBool
+ #undef VarI4FromI2
+ #undef VarI4FromR4
+ #undef VarI4FromR8
+ #undef VarI4FromCy
+ #undef VarI4FromDate
+ #undef VarI4FromStr
+ #undef VarI4FromDisp
+ #undef VarI4FromBool
+ #undef VarR4FromI2
+ #undef VarR4FromI4
+ #undef VarR4FromR8
+ #undef VarR4FromCy
+ #undef VarR4FromDate
+ #undef VarR4FromStr
+ #undef VarR4FromDisp
+ #undef VarR4FromBool
+ #undef VarR8FromI2
+ #undef VarR8FromI4
+ #undef VarR8FromR4
+ #undef VarR8FromCy
+ #undef VarR8FromDate
+ #undef VarR8FromStr
+ #undef VarR8FromDisp
+ #undef VarR8FromBool
+ #undef VarDateFromI2
+ #undef VarDateFromI4
+ #undef VarDateFromR4
+ #undef VarDateFromR8
+ #undef VarDateFromCy
+ #undef VarDateFromStr
+ #undef VarDateFromDisp
+ #undef VarDateFromBool
+ #undef VarCyFromI2
+ #undef VarCyFromI4
+ #undef VarCyFromR4
+ #undef VarCyFromR8
+ #undef VarCyFromDate
+ #undef VarCyFromStr
+ #undef VarCyFromDisp
+ #undef VarCyFromBool
+ #undef VarBstrFromI2
+ #undef VarBstrFromI4
+ #undef VarBstrFromR4
+ #undef VarBstrFromR8
+ #undef VarBstrFromCy
+ #undef VarBstrFromDate
+ #undef VarBstrFromDisp
+ #undef VarBstrFromBool
+ #undef VarBoolFromI2
+ #undef VarBoolFromI4
+ #undef VarBoolFromR4
+ #undef VarBoolFromR8
+ #undef VarBoolFromDate
+ #undef VarBoolFromCy
+ #undef VarBoolFromStr
+ #undef VarBoolFromDisp
+ #undef SafeArrayCreate
+ #undef SafeArrayDestroy
+ #undef SafeArrayGetDim
+ #undef SafeArrayGetElemsize
+ #undef SafeArrayGetUBound
+ #undef SafeArrayGetLBound
+ #undef SafeArrayLock
+ #undef SafeArrayUnlock
+ #undef SafeArrayAccessData
+ #undef SafeArrayUnaccessData
+ #undef SafeArrayGetElement
+ #undef SafeArrayPutElement
+ #undef SafeArrayCopy
+ #undef SafeArrayAllocDescriptor
+ #undef SafeArrayAllocData
+ #undef SafeArrayDestroyDescriptor
+ #undef SafeArrayDestroyData
+ #undef SafeArrayRedim
+ #undef VariantTimeToDosDateTime
+ #undef DosDateTimeToVariantTime
+ #undef DispGetParam
+ #undef DispGetIDsOfNames
+ #undef DispInvoke
+ #undef CreateDispTypeInfo
+ #undef CreateStdDispatch
+ #undef RegisterActiveObject
+ #undef RevokeActiveObject
+ #undef GetActiveObject
+ #undef DoInvokeMethod
+ #undef VariantChangeTypeEx
+ #undef SafeArrayPtrOfIndex
+ #undef MPWVarFromR4
+ #undef MPWVarFromR8
+ #undef MPWR4FromVar
+ #undef MPWR8FromVar
+ #undef CreateTypeLib
+ #undef LoadTypeLib
+ #undef LoadRegTypeLib
+ #undef RegisterTypeLib
+ #undef LHashValOfNameSys
+ #undef QueryPathOfRegTypeLib
+ #undef LoadTypeLibFSp
+ #undef RegisterTypeLibFolder
+ #undef QueryTypeLibFolder
+ #undef OleBuildVersion
+ #undef OleInitialize
+ #undef OleUninitialize
+ #undef DllGetClassObject
+ #undef OleQueryLinkFromData
+ #undef OleQueryCreateFromData
+ #undef OleCreateFromData
+ #undef OleCreateLinkFromData
+ #undef OleCreate
+ #undef OleCreateLink
+ #undef OleLoad
+ #undef OleSave
+ #undef OleRun
+ #undef OleIsRunning
+ #undef OleLockRunning
+ #undef ReadClassStg
+ #undef WriteClassStg
+ #undef ReadClassStm
+ #undef WriteClassStm
+ #undef BindMoniker
+ #undef MkParseDisplayName
+ #undef OleSaveToStream
+ #undef OleLoadFromStream
+ #undef CreateBindCtx
+ #undef CreateItemMoniker
+ #undef CreateFileMoniker
+ #undef CreateGenericComposite
+ #undef GetRunningObjectTable
+ #undef OleGetMalloc
+ #undef ReleaseStgMedium
+ #undef ReadStringStream
+ #undef WriteStringStream
+ #undef RegisterDragDrop
+ #undef RevokeDragDrop
+ #undef DoDragDrop
+ #undef CreateOleAdviseHolder
+ #undef CreateDataAdviseHolder
+ #undef OpenOrCreateStream
+ #undef CreateAntiMoniker
+ #undef CreatePointerMoniker
+ #undef MonikerRelativePathTo
+ #undef MonikerCommonPrefixWith
+ #undef OleSetClipboard
+ #undef OleGetClipboard
+ #undef OleDuplicateData
+ #undef CreateILockBytesOnHGlobal
+ #undef GetHGlobalFromILockBytes
+ #undef GetClassFile
+ #undef OleDraw
+ #undef OleCreateDefaultHandler
+ #undef OleCreateEmbeddingHelper
+ #undef OleConvertIStorageToOLESTREAMEx
+ #undef OleConvertOLESTREAMToIStorageEx
+ #undef SetDocumentBitStg
+ #undef GetDocumentBitStg
+ #undef WriteOleStg
+ #undef ReadOleStg
+ #undef OleCreateFromFile
+ #undef OleCreateLinkToFile
+ #undef CreateDataCache
+ #undef OleConvertIStorageToOLESTREAM
+ #undef OleConvertOLESTREAMToIStorage
+ #undef ReadFmtUserTypeStg
+ #undef WriteFmtUserTypeStg
+ #undef OleFlushClipboard
+ #undef OleIsCurrentClipboard
+ #undef OleTranslateAccelerator
+ #undef OleDoAutoConvert
+ #undef OleGetAutoConvert
+ #undef OleSetAutoConvert
+ #undef GetConvertStg
+ #undef SetConvertStg
+ #undef CreateStreamOnHGlobal
+ #undef GetHGlobalFromStream
+ #undef OleDuplicateMedium
+ #undef OleSetContainedObject
+ #undef OleNoteObjectVisible
+ #undef OleCreateStaticFromData
+ #undef OleRegGetUserType
+ #undef OleRegGetMiscStatus
+ #undef OleRegEnumFormatEtc
+ #undef OleRegEnumVerbs
+ #undef OleGetEnumFormatEtc
+ #undef OleSetEnumFormatEtc
+ #undef OleRemoveEnumFormatEtc
+ #undef OleSendLLE
+ #undef OleSetInPlaceWindow
+ #undef OleUnSetInPlaceWindow
+ #undef OleClipWindow
+ #undef OleClipWindows
+ #undef OleInsertMenus
+ #undef OleHashMenuID
+ #undef OleUnhashMenuID
+ #undef OlePatchGetMHandle
+ #undef OleUnpatchGetMHandle
+ #undef OleAddMBarMenu
+ #undef OleSetInPlaceRects
+ #undef OleMaskMouse
+ #undef OleMoveWindow
+ #undef OleSizeParentWindow
+ #undef OleSizeObjectWindow
+ #undef OleDragParentWindow
+ #undef OleDragObjectWindow
+ #undef OleGrowParentWindow
+ #undef OleGrowObjectWindow
+ #undef OleNewMBar
+ #undef OleDisposeMBar
+ #undef OleProcessDdeAE
+ #undef OleProcessClipboardAE
+ #undef InitializeClipboard
+ #undef UnInitializeClipboard
+ #undef OleIsClipboardFormatAvailable
+ #undef OleGetClipboardData
+ #undef OleSetClipboardData
+ #undef OleEnumClipboardFormats
+ #undef StoreClap
+ #undef OleCountClipboardFormats
+ #undef OleCloseClipboard
+ #undef OleEmptyClipboard
+ #undef OleSetClipboardEx
+ #undef OleZoomParentWindow
+ #undef OleSetParentRgns
+ #undef CreateFileMonikerFSp
+ #undef OleCreateFromFSp
+ #undef OleCreateLinkToFSp
+ #undef OleGetCursor
+ #undef OleSetCursor
+ #undef OleUpdateCursor
+ #undef GetClassFSp
+ #undef ReadOle1FmtProgIDStgMac
+ #undef WriteOle1FmtProgIDStgMac
+ #undef OleGetIconOfFile
+ #undef OleGetIconOfClass
+ #undef OleGetIconOfFSp
+ #undef OlePictFromIconAndLabel
+ #undef OleGetIconFromIconSuite
+ #undef OleUIPictIconFree
+ #undef OleUIPictIconDraw
+ #undef OleUIPictExtractIcon
+ #undef OleUIPictExtractLabel
+ #undef OleUIPictExtractIconSource
+ #undef OleMetaFileToPict
+ #undef OleQueryCreateAll
+ #undef OleWhichGrowHandle
+ #undef MkGetMacNetInfo
+ #undef CoBuildVersion
+ #undef CoInitialize
+ #undef CoUninitialize
+ #undef CoGetMalloc
+ #undef CoRegisterClassObject
+ #undef CoRevokeClassObject
+ #undef CoGetClassObject
+ #undef CoMarshalInterface
+ #undef CoUnmarshalInterface
+ #undef CoLoadLibrary
+ #undef CoFreeLibrary
+ #undef CoFreeAllLibraries
+ #undef CoCreateInstance
+ #undef StringFromIID
+ #undef CoDisconnectObject
+ #undef CoReleaseMarshalData
+ #undef CoFreeUnusedLibraries
+ #undef IsEqualGUID
+ #undef StringFromCLSID
+ #undef CLSIDFromString
+ #undef RESULTFROMSCODE
+ #undef GETSCODE
+ #undef CoRegisterMessageFilter
+ #undef CoIsHandlerConnected
+ #undef CoMarshalHresult
+ #undef CoUnmarshalHresult
+ #undef CoGetCurrentProcess
+ #undef CoIsOle1Class
+ #undef CLSIDFromProgID
+ #undef ProgIDFromCLSID
+ #undef CoLockObjectExternal
+ #undef CoGetTreatAsClass
+ #undef CoTreatAsClass
+ #undef CoGetStandardMarshal
+ #undef PropagateResult
+ #undef IIDFromString
+ #undef CoCreateStandardMalloc
+ #undef CoCreateGuid
+ #undef StringFromGUID2
+ #undef CoGetClassExt
+ #undef Ole1ClassFromCLSID2
+ #undef CLSIDFromOle1Class
+ #undef CoOpenClassKey
+ #undef GUIDFromString
+ #undef CoFileTimeNow
+ #undef RemAllocOID
+ #undef RemFreeOID
+ #undef RemCreateRemoteHandler
+ #undef RemConnectToObject
+ #undef RemGetInfoForCid
+ #undef LrpcCall
+ #undef LrpcDispatch
+ #undef LrpcRegisterMonitor
+ #undef LrpcRevokeMonitor
+ #undef LrpcGetThreadWindow
+ #undef LookupEtask
+ #undef SetEtask
+ #undef RemLookupSHUnk
+ #undef CoMemctxOf
+ #undef CoMemAlloc
+ #undef CoMemFree
+ #undef CoRunModalLoop
+ #undef CoHandleIncomingCall
+ #undef CoSetAckState
+ #undef OleProcessLrpcAE
+ #undef CoFileTimeToMacDateTime
+ #undef CoMacDateTimeToFileTime
+ #undef InternalCoInitialize
+ #undef CoHandlePendingMessage
+ #undef DllGetClassObject
+ #undef CompareStringA
+ #undef LCMapStringA
+ #undef GetLocaleInfoA
+ #undef GetStringTypeA
+ #undef GetSystemDefaultLangID
+ #undef GetUserDefaultLangID
+ #undef GetSystemDefaultLCID
+ #undef GetUserDefaultLCID
+#if ID_MUNGE_STAT_NAMES
+#if ID_OLE_STAT_DOCFILE
+ #define StgCreateDocfile StaticStgCreateDocfile
+ #define StgCreateDocfileOnILockBytes StaticStgCreateDocfileOnILockBytes
+ #define StgOpenStorage StaticStgOpenStorage
+ #define StgOpenStorageOnILockBytes StaticStgOpenStorageOnILockBytes
+ #define StgIsStorageFile StaticStgIsStorageFile
+ #define StgIsStorageILockBytes StaticStgIsStorageILockBytes
+ #define StgSetTimes StaticStgSetTimes
+ #define StgSetTimesMac StaticStgSetTimesMac
+ #define StgSetTimesFSp StaticStgSetTimesFSp
+ #define DllGetClassObject StaticDllGetClassObject
+ #define StgCreateDocfileFSp StaticStgCreateDocfileFSp
+ #define StgOpenStorageFSp StaticStgOpenStorageFSp
+ #define StgCreateDocfileMac StaticStgCreateDocfileMac
+ #define StgOpenStorageMac StaticStgOpenStorageMac
+ #define StgIsStorageFileMac StaticStgIsStorageFileMac
+ #define StgIsStorageFileFSp StaticStgIsStorageFileFSp
+ #define StgGetFSpFromIStorage StaticStgGetFSpFromIStorage
+ #define StgGetFRefFromIStorage StaticStgGetFRefFromIStorage
+#endif // ID_OLE_STAT_DOCFILE
+#if ID_OLE_STAT_USER
+ #define OleregOpenRegistration StaticOleregOpenRegistration
+ #define OleregCloseRegistration StaticOleregCloseRegistration
+ #define OleregGetValue StaticOleregGetValue
+ #define OleregSetValue StaticOleregSetValue
+ #define OleregRemoveKey StaticOleregRemoveKey
+ #define OleGlobalAddAtom StaticOleGlobalAddAtom
+ #define OleGlobalDuplicateAtom StaticOleGlobalDuplicateAtom
+ #define OleGlobalDeleteAtom StaticOleGlobalDeleteAtom
+ #define OleGlobalFindAtom StaticOleGlobalFindAtom
+ #define OleGlobalGetAtomName StaticOleGlobalGetAtomName
+ #define OleGlobalAlloc StaticOleGlobalAlloc
+ #define OleGlobalCompact StaticOleGlobalCompact
+ #define OleGlobalFree StaticOleGlobalFree
+ #define OleGlobalHandle StaticOleGlobalHandle
+ #define OleGlobalLock StaticOleGlobalLock
+ #define OleGlobalReAlloc StaticOleGlobalReAlloc
+ #define OleGlobalSize StaticOleGlobalSize
+ #define OleGlobalUnlock StaticOleGlobalUnlock
+ #define RegQueryValue StaticRegQueryValue
+ #define RegOpenKey StaticRegOpenKey
+ #define RegSetValue StaticRegSetValue
+ #define RegEnumKey StaticRegEnumKey
+ #define RegEnumProgID StaticRegEnumProgID
+ #define RegDeleteKey StaticRegDeleteKey
+ #define RegCreateKey StaticRegCreateKey
+ #define RegCloseKey StaticRegCloseKey
+ #define RegInitialize StaticRegInitialize
+ #define InitUserData StaticInitUserData
+ #define SendHighLevelEvent StaticSendHighLevelEvent
+ #define OleWinExec StaticOleWinExec
+ #define InitDB StaticInitDB
+ #define CloseDB StaticCloseDB
+ #define OleGetCurrentTask StaticOleGetCurrentTask
+ #define OleGetProcAddress StaticOleGetProcAddress
+ #define OleLoadLibrary StaticOleLoadLibrary
+ #define OleFreeLibrary StaticOleFreeLibrary
+ #define OutputDebugString StaticOutputDebugString
+ #define SoftAssert StaticSoftAssert
+ #define FnAssert StaticFnAssert
+ #define IsValidInterface StaticIsValidInterface
+ #define IsValidIid StaticIsValidIid
+ #define IsValidHandle StaticIsValidHandle
+ #define EnterOLEApi StaticEnterOLEApi
+ #define ExitOLEApi StaticExitOLEApi
+ #define FnAssertOn StaticFnAssertOn
+ #define GlobalFreePtr StaticGlobalFreePtr
+ #define GlobalAllocPtr StaticGlobalAllocPtr
+ #define UserInitialize StaticUserInitialize
+ #define UserUninitialize StaticUserUninitialize
+ #define IsValidInPtr StaticIsValidInPtr
+ #define IsValidOutPtr StaticIsValidOutPtr
+ #define RegQueryValueEx StaticRegQueryValueEx
+ #define RegFlush StaticRegFlush
+ #define RegDeleteValue StaticRegDeleteValue
+ #define RegSetValueEx StaticRegSetValueEx
+ #define RegEnumValue StaticRegEnumValue
+ #define OLEInitDBCSCountry StaticOLEInitDBCSCountry
+ #define IAnsiNext StaticIAnsiNext
+ #define IAnsiPrev StaticIAnsiPrev
+ #define OleMakeFSSpec StaticOleMakeFSSpec
+ #define OleFullPathFromFSSpec StaticOleFullPathFromFSSpec
+ #define OleGetFSSpecInfo StaticOleGetFSSpecInfo
+#endif //ID_OLE_STAT_USER
+#if ID_OLE_STAT_OLE2DISP
+ #define DllGetClassObject StaticDllGetClassObject
+ #define SysAllocString StaticSysAllocString
+ #define SysReAllocString StaticSysReAllocString
+ #define SysAllocStringLen StaticSysAllocStringLen
+ #define SysReAllocStringLen StaticSysReAllocStringLen
+ #define SysFreeString StaticSysFreeString
+ #define SysStringLen StaticSysStringLen
+ #define VariantInit StaticVariantInit
+ #define VariantClear StaticVariantClear
+ #define VariantCopy StaticVariantCopy
+ #define VariantCopyInd StaticVariantCopyInd
+ #define VariantChangeType StaticVariantChangeType
+ #define VarI2FromI4 StaticVarI2FromI4
+ #define VarI2FromR4 StaticVarI2FromR4
+ #define VarI2FromR8 StaticVarI2FromR8
+ #define VarI2FromCy StaticVarI2FromCy
+ #define VarI2FromDate StaticVarI2FromDate
+ #define VarI2FromStr StaticVarI2FromStr
+ #define VarI2FromDisp StaticVarI2FromDisp
+ #define VarI2FromBool StaticVarI2FromBool
+ #define VarI4FromI2 StaticVarI4FromI2
+ #define VarI4FromR4 StaticVarI4FromR4
+ #define VarI4FromR8 StaticVarI4FromR8
+ #define VarI4FromCy StaticVarI4FromCy
+ #define VarI4FromDate StaticVarI4FromDate
+ #define VarI4FromStr StaticVarI4FromStr
+ #define VarI4FromDisp StaticVarI4FromDisp
+ #define VarI4FromBool StaticVarI4FromBool
+ #define VarR4FromI2 StaticVarR4FromI2
+ #define VarR4FromI4 StaticVarR4FromI4
+ #define VarR4FromR8 StaticVarR4FromR8
+ #define VarR4FromCy StaticVarR4FromCy
+ #define VarR4FromDate StaticVarR4FromDate
+ #define VarR4FromStr StaticVarR4FromStr
+ #define VarR4FromDisp StaticVarR4FromDisp
+ #define VarR4FromBool StaticVarR4FromBool
+ #define VarR8FromI2 StaticVarR8FromI2
+ #define VarR8FromI4 StaticVarR8FromI4
+ #define VarR8FromR4 StaticVarR8FromR4
+ #define VarR8FromCy StaticVarR8FromCy
+ #define VarR8FromDate StaticVarR8FromDate
+ #define VarR8FromStr StaticVarR8FromStr
+ #define VarR8FromDisp StaticVarR8FromDisp
+ #define VarR8FromBool StaticVarR8FromBool
+ #define VarDateFromI2 StaticVarDateFromI2
+ #define VarDateFromI4 StaticVarDateFromI4
+ #define VarDateFromR4 StaticVarDateFromR4
+ #define VarDateFromR8 StaticVarDateFromR8
+ #define VarDateFromCy StaticVarDateFromCy
+ #define VarDateFromStr StaticVarDateFromStr
+ #define VarDateFromDisp StaticVarDateFromDisp
+ #define VarDateFromBool StaticVarDateFromBool
+ #define VarCyFromI2 StaticVarCyFromI2
+ #define VarCyFromI4 StaticVarCyFromI4
+ #define VarCyFromR4 StaticVarCyFromR4
+ #define VarCyFromR8 StaticVarCyFromR8
+ #define VarCyFromDate StaticVarCyFromDate
+ #define VarCyFromStr StaticVarCyFromStr
+ #define VarCyFromDisp StaticVarCyFromDisp
+ #define VarCyFromBool StaticVarCyFromBool
+ #define VarBstrFromI2 StaticVarBstrFromI2
+ #define VarBstrFromI4 StaticVarBstrFromI4
+ #define VarBstrFromR4 StaticVarBstrFromR4
+ #define VarBstrFromR8 StaticVarBstrFromR8
+ #define VarBstrFromCy StaticVarBstrFromCy
+ #define VarBstrFromDate StaticVarBstrFromDate
+ #define VarBstrFromDisp StaticVarBstrFromDisp
+ #define VarBstrFromBool StaticVarBstrFromBool
+ #define VarBoolFromI2 StaticVarBoolFromI2
+ #define VarBoolFromI4 StaticVarBoolFromI4
+ #define VarBoolFromR4 StaticVarBoolFromR4
+ #define VarBoolFromR8 StaticVarBoolFromR8
+ #define VarBoolFromDate StaticVarBoolFromDate
+ #define VarBoolFromCy StaticVarBoolFromCy
+ #define VarBoolFromStr StaticVarBoolFromStr
+ #define VarBoolFromDisp StaticVarBoolFromDisp
+ #define SafeArrayCreate StaticSafeArrayCreate
+ #define SafeArrayDestroy StaticSafeArrayDestroy
+ #define SafeArrayGetDim StaticSafeArrayGetDim
+ #define SafeArrayGetElemsize StaticSafeArrayGetElemsize
+ #define SafeArrayGetUBound StaticSafeArrayGetUBound
+ #define SafeArrayGetLBound StaticSafeArrayGetLBound
+ #define SafeArrayLock StaticSafeArrayLock
+ #define SafeArrayUnlock StaticSafeArrayUnlock
+ #define SafeArrayAccessData StaticSafeArrayAccessData
+ #define SafeArrayUnaccessData StaticSafeArrayUnaccessData
+ #define SafeArrayGetElement StaticSafeArrayGetElement
+ #define SafeArrayPutElement StaticSafeArrayPutElement
+ #define SafeArrayCopy StaticSafeArrayCopy
+ #define SafeArrayAllocDescriptor StaticSafeArrayAllocDescriptor
+ #define SafeArrayAllocData StaticSafeArrayAllocData
+ #define SafeArrayDestroyDescriptor StaticSafeArrayDestroyDescriptor
+ #define SafeArrayDestroyData StaticSafeArrayDestroyData
+ #define SafeArrayRedim StaticSafeArrayRedim
+ #define VariantTimeToDosDateTime StaticVariantTimeToDosDateTime
+ #define DosDateTimeToVariantTime StaticDosDateTimeToVariantTime
+ #define DispGetParam StaticDispGetParam
+ #define DispGetIDsOfNames StaticDispGetIDsOfNames
+ #define DispInvoke StaticDispInvoke
+ #define CreateDispTypeInfo StaticCreateDispTypeInfo
+ #define CreateStdDispatch StaticCreateStdDispatch
+ #define RegisterActiveObject StaticRegisterActiveObject
+ #define RevokeActiveObject StaticRevokeActiveObject
+ #define GetActiveObject StaticGetActiveObject
+ #define DoInvokeMethod StaticDoInvokeMethod
+ #define VariantChangeTypeEx StaticVariantChangeTypeEx
+ #define SafeArrayPtrOfIndex StaticSafeArrayPtrOfIndex
+ #define MPWVarFromR4 StaticMPWVarFromR4
+ #define MPWVarFromR8 StaticMPWVarFromR8
+ #define MPWR4FromVar StaticMPWR4FromVar
+ #define MPWR8FromVar StaticMPWR8FromVar
+#endif //ID_OLE_STAT_OLE2DISP
+#if ID_OLE_STAT_TYPELIB
+ #define CreateTypeLib StaticCreateTypeLib
+ #define LoadTypeLib StaticLoadTypeLib
+ #define LoadRegTypeLib StaticLoadRegTypeLib
+ #define RegisterTypeLib StaticRegisterTypeLib
+ #define LHashValOfNameSys StaticLHashValOfNameSys
+ #define QueryPathOfRegTypeLib StaticQueryPathOfRegTypeLib
+ #define LoadTypeLibFSp StaticLoadTypeLibFSp
+ #define RegisterTypeLibFolder StaticRegisterTypeLibFolder
+ #define QueryTypeLibFolder StaticQueryTypeLibFolder
+#endif //ID_OLE_STAT_TYPELIB
+#if ID_OLE_STAT_DEF
+ #define OleBuildVersion StaticOleBuildVersion
+ #define OleInitialize StaticOleInitialize
+ #define OleUninitialize StaticOleUninitialize
+ #define DllGetClassObject StaticDllGetClassObject
+ #define OleQueryLinkFromData StaticOleQueryLinkFromData
+ #define OleQueryCreateFromData StaticOleQueryCreateFromData
+ #define OleCreateFromData StaticOleCreateFromData
+ #define OleCreateLinkFromData StaticOleCreateLinkFromData
+ #define OleCreate StaticOleCreate
+ #define OleCreateLink StaticOleCreateLink
+ #define OleLoad StaticOleLoad
+ #define OleSave StaticOleSave
+ #define OleRun StaticOleRun
+ #define OleIsRunning StaticOleIsRunning
+ #define OleLockRunning StaticOleLockRunning
+ #define ReadClassStg StaticReadClassStg
+ #define WriteClassStg StaticWriteClassStg
+ #define ReadClassStm StaticReadClassStm
+ #define WriteClassStm StaticWriteClassStm
+ #define BindMoniker StaticBindMoniker
+ #define MkParseDisplayName StaticMkParseDisplayName
+ #define OleSaveToStream StaticOleSaveToStream
+ #define OleLoadFromStream StaticOleLoadFromStream
+ #define CreateBindCtx StaticCreateBindCtx
+ #define CreateItemMoniker StaticCreateItemMoniker
+ #define CreateFileMoniker StaticCreateFileMoniker
+ #define CreateGenericComposite StaticCreateGenericComposite
+ #define GetRunningObjectTable StaticGetRunningObjectTable
+ #define OleGetMalloc StaticOleGetMalloc
+ #define ReleaseStgMedium StaticReleaseStgMedium
+ #define ReadStringStream StaticReadStringStream
+ #define WriteStringStream StaticWriteStringStream
+ #define RegisterDragDrop StaticRegisterDragDrop
+ #define RevokeDragDrop StaticRevokeDragDrop
+ #define DoDragDrop StaticDoDragDrop
+ #define CreateOleAdviseHolder StaticCreateOleAdviseHolder
+ #define CreateDataAdviseHolder StaticCreateDataAdviseHolder
+ #define OpenOrCreateStream StaticOpenOrCreateStream
+ #define CreateAntiMoniker StaticCreateAntiMoniker
+ #define CreatePointerMoniker StaticCreatePointerMoniker
+ #define MonikerRelativePathTo StaticMonikerRelativePathTo
+ #define MonikerCommonPrefixWith StaticMonikerCommonPrefixWith
+ #define OleSetClipboard StaticOleSetClipboard
+ #define OleGetClipboard StaticOleGetClipboard
+ #define OleDuplicateData StaticOleDuplicateData
+ #define CreateILockBytesOnHGlobal StaticCreateILockBytesOnHGlobal
+ #define GetHGlobalFromILockBytes StaticGetHGlobalFromILockBytes
+ #define GetClassFile StaticGetClassFile
+ #define OleDraw StaticOleDraw
+ #define OleCreateDefaultHandler StaticOleCreateDefaultHandler
+ #define OleCreateEmbeddingHelper StaticOleCreateEmbeddingHelper
+ #define OleConvertIStorageToOLESTREAMEx StaticOleConvertIStorageToOLESTREAMEx
+ #define OleConvertOLESTREAMToIStorageEx StaticOleConvertOLESTREAMToIStorageEx
+ #define SetDocumentBitStg StaticSetDocumentBitStg
+ #define GetDocumentBitStg StaticGetDocumentBitStg
+ #define WriteOleStg StaticWriteOleStg
+ #define ReadOleStg StaticReadOleStg
+ #define OleCreateFromFile StaticOleCreateFromFile
+ #define OleCreateLinkToFile StaticOleCreateLinkToFile
+ #define CreateDataCache StaticCreateDataCache
+ #define OleConvertIStorageToOLESTREAM StaticOleConvertIStorageToOLESTREAM
+ #define OleConvertOLESTREAMToIStorage StaticOleConvertOLESTREAMToIStorage
+ #define ReadFmtUserTypeStg StaticReadFmtUserTypeStg
+ #define WriteFmtUserTypeStg StaticWriteFmtUserTypeStg
+ #define OleFlushClipboard StaticOleFlushClipboard
+ #define OleIsCurrentClipboard StaticOleIsCurrentClipboard
+ #define OleTranslateAccelerator StaticOleTranslateAccelerator
+ #define OleDoAutoConvert StaticOleDoAutoConvert
+ #define OleGetAutoConvert StaticOleGetAutoConvert
+ #define OleSetAutoConvert StaticOleSetAutoConvert
+ #define GetConvertStg StaticGetConvertStg
+ #define SetConvertStg StaticSetConvertStg
+ #define CreateStreamOnHGlobal StaticCreateStreamOnHGlobal
+ #define GetHGlobalFromStream StaticGetHGlobalFromStream
+ #define OleDuplicateMedium StaticOleDuplicateMedium
+ #define OleSetContainedObject StaticOleSetContainedObject
+ #define OleNoteObjectVisible StaticOleNoteObjectVisible
+ #define OleCreateStaticFromData StaticOleCreateStaticFromData
+ #define OleRegGetUserType StaticOleRegGetUserType
+ #define OleRegGetMiscStatus StaticOleRegGetMiscStatus
+ #define OleRegEnumFormatEtc StaticOleRegEnumFormatEtc
+ #define OleRegEnumVerbs StaticOleRegEnumVerbs
+ #define OleGetEnumFormatEtc StaticOleGetEnumFormatEtc
+ #define OleSetEnumFormatEtc StaticOleSetEnumFormatEtc
+ #define OleRemoveEnumFormatEtc StaticOleRemoveEnumFormatEtc
+ #define OleSendLLE StaticOleSendLLE
+ #define OleSetInPlaceWindow StaticOleSetInPlaceWindow
+ #define OleUnSetInPlaceWindow StaticOleUnSetInPlaceWindow
+ #define OleClipWindow StaticOleClipWindow
+ #define OleClipWindows StaticOleClipWindows
+ #define OleInsertMenus StaticOleInsertMenus
+ #define OleHashMenuID StaticOleHashMenuID
+ #define OleUnhashMenuID StaticOleUnhashMenuID
+ #define OlePatchGetMHandle StaticOlePatchGetMHandle
+ #define OleUnpatchGetMHandle StaticOleUnpatchGetMHandle
+ #define OleAddMBarMenu StaticOleAddMBarMenu
+ #define OleSetInPlaceRects StaticOleSetInPlaceRects
+ #define OleMaskMouse StaticOleMaskMouse
+ #define OleMoveWindow StaticOleMoveWindow
+ #define OleSizeParentWindow StaticOleSizeParentWindow
+ #define OleSizeObjectWindow StaticOleSizeObjectWindow
+ #define OleDragParentWindow StaticOleDragParentWindow
+ #define OleDragObjectWindow StaticOleDragObjectWindow
+ #define OleGrowParentWindow StaticOleGrowParentWindow
+ #define OleGrowObjectWindow StaticOleGrowObjectWindow
+ #define OleNewMBar StaticOleNewMBar
+ #define OleDisposeMBar StaticOleDisposeMBar
+ #define OleProcessDdeAE StaticOleProcessDdeAE
+ #define OleProcessClipboardAE StaticOleProcessClipboardAE
+ #define InitializeClipboard StaticInitializeClipboard
+ #define UnInitializeClipboard StaticUnInitializeClipboard
+ #define OleIsClipboardFormatAvailable StaticOleIsClipboardFormatAvailable
+ #define OleGetClipboardData StaticOleGetClipboardData
+ #define OleSetClipboardData StaticOleSetClipboardData
+ #define OleEnumClipboardFormats StaticOleEnumClipboardFormats
+ #define StoreClap StaticStoreClap
+ #define OleCountClipboardFormats StaticOleCountClipboardFormats
+ #define OleCloseClipboard StaticOleCloseClipboard
+ #define OleEmptyClipboard StaticOleEmptyClipboard
+ #define OleSetClipboardEx StaticOleSetClipboardEx
+ #define OleZoomParentWindow StaticOleZoomParentWindow
+ #define OleSetParentRgns StaticOleSetParentRgns
+ #define CreateFileMonikerFSp StaticCreateFileMonikerFSp
+ #define OleCreateFromFSp StaticOleCreateFromFSp
+ #define OleCreateLinkToFSp StaticOleCreateLinkToFSp
+ #define OleGetCursor StaticOleGetCursor
+ #define OleSetCursor StaticOleSetCursor
+ #define OleUpdateCursor StaticOleUpdateCursor
+ #define GetClassFSp StaticGetClassFSp
+ #define ReadOle1FmtProgIDStgMac StaticReadOle1FmtProgIDStgMac
+ #define WriteOle1FmtProgIDStgMac StaticWriteOle1FmtProgIDStgMac
+ #define OleGetIconOfFile StaticOleGetIconOfFile
+ #define OleGetIconOfClass StaticOleGetIconOfClass
+ #define OleGetIconOfFSp StaticOleGetIconOfFSp
+ #define OlePictFromIconAndLabel StaticOlePictFromIconAndLabel
+ #define OleGetIconFromIconSuite StaticOleGetIconFromIconSuite
+ #define OleUIPictIconFree StaticOleUIPictIconFree
+ #define OleUIPictIconDraw StaticOleUIPictIconDraw
+ #define OleUIPictExtractIcon StaticOleUIPictExtractIcon
+ #define OleUIPictExtractLabel StaticOleUIPictExtractLabel
+ #define OleUIPictExtractIconSource StaticOleUIPictExtractIconSource
+ #define OleMetaFileToPict StaticOleMetaFileToPict
+ #define OleQueryCreateAll StaticOleQueryCreateAll
+ #define OleWhichGrowHandle StaticOleWhichGrowHandle
+ #define MkGetMacNetInfo StaticMkGetMacNetInfo
+#endif //ID_OLE_STAT_DEF
+#if ID_OLE_STAT_COMPOBJ
+ #define CoBuildVersion StaticCoBuildVersion
+ #define CoInitialize StaticCoInitialize
+ #define CoUninitialize StaticCoUninitialize
+ #define CoGetMalloc StaticCoGetMalloc
+ #define CoRegisterClassObject StaticCoRegisterClassObject
+ #define CoRevokeClassObject StaticCoRevokeClassObject
+ #define CoGetClassObject StaticCoGetClassObject
+ #define CoMarshalInterface StaticCoMarshalInterface
+ #define CoUnmarshalInterface StaticCoUnmarshalInterface
+ #define CoLoadLibrary StaticCoLoadLibrary
+ #define CoFreeLibrary StaticCoFreeLibrary
+ #define CoFreeAllLibraries StaticCoFreeAllLibraries
+ #define CoCreateInstance StaticCoCreateInstance
+ #define StringFromIID StaticStringFromIID
+ #define CoDisconnectObject StaticCoDisconnectObject
+ #define CoReleaseMarshalData StaticCoReleaseMarshalData
+ #define CoFreeUnusedLibraries StaticCoFreeUnusedLibraries
+ #define IsEqualGUID StaticIsEqualGUID
+ #define StringFromCLSID StaticStringFromCLSID
+ #define CLSIDFromString StaticCLSIDFromString
+ #define RESULTFROMSCODE StaticRESULTFROMSCODE
+ #define GETSCODE StaticGETSCODE
+ #define CoRegisterMessageFilter StaticCoRegisterMessageFilter
+ #define CoIsHandlerConnected StaticCoIsHandlerConnected
+ #define CoMarshalHresult StaticCoMarshalHresult
+ #define CoUnmarshalHresult StaticCoUnmarshalHresult
+ #define CoGetCurrentProcess StaticCoGetCurrentProcess
+ #define CoIsOle1Class StaticCoIsOle1Class
+ #define CLSIDFromProgID StaticCLSIDFromProgID
+ #define ProgIDFromCLSID StaticProgIDFromCLSID
+ #define CoLockObjectExternal StaticCoLockObjectExternal
+ #define CoGetTreatAsClass StaticCoGetTreatAsClass
+ #define CoTreatAsClass StaticCoTreatAsClass
+ #define CoGetStandardMarshal StaticCoGetStandardMarshal
+ #define PropagateResult StaticPropagateResult
+ #define IIDFromString StaticIIDFromString
+ #define CoCreateStandardMalloc StaticCoCreateStandardMalloc
+ #define CoCreateGuid StaticCoCreateGuid
+ #define StringFromGUID2 StaticStringFromGUID2
+ #define CoGetClassExt StaticCoGetClassExt
+ #define Ole1ClassFromCLSID2 StaticOle1ClassFromCLSID2
+ #define CLSIDFromOle1Class StaticCLSIDFromOle1Class
+ #define CoOpenClassKey StaticCoOpenClassKey
+ #define GUIDFromString StaticGUIDFromString
+ #define CoFileTimeNow StaticCoFileTimeNow
+ #define RemAllocOID StaticRemAllocOID
+ #define RemFreeOID StaticRemFreeOID
+ #define RemCreateRemoteHandler StaticRemCreateRemoteHandler
+ #define RemConnectToObject StaticRemConnectToObject
+ #define RemGetInfoForCid StaticRemGetInfoForCid
+ #define LrpcCall StaticLrpcCall
+ #define LrpcDispatch StaticLrpcDispatch
+ #define LrpcRegisterMonitor StaticLrpcRegisterMonitor
+ #define LrpcRevokeMonitor StaticLrpcRevokeMonitor
+ #define LrpcGetThreadWindow StaticLrpcGetThreadWindow
+ #define LookupEtask StaticLookupEtask
+ #define SetEtask StaticSetEtask
+ #define RemLookupSHUnk StaticRemLookupSHUnk
+ #define CoMemctxOf StaticCoMemctxOf
+ #define CoMemAlloc StaticCoMemAlloc
+ #define CoMemFree StaticCoMemFree
+ #define CoRunModalLoop StaticCoRunModalLoop
+ #define CoHandleIncomingCall StaticCoHandleIncomingCall
+ #define CoSetAckState StaticCoSetAckState
+ #define OleProcessLrpcAE StaticOleProcessLrpcAE
+ #define CoFileTimeToMacDateTime StaticCoFileTimeToMacDateTime
+ #define CoMacDateTimeToFileTime StaticCoMacDateTimeToFileTime
+ #define InternalCoInitialize StaticInternalCoInitialize
+ #define CoHandlePendingMessage StaticCoHandlePendingMessage
+#endif //ID_OLE_STAT_COMPOBJ
+#if ID_OLE_STAT_PROXY
+ #define DllGetClassObject StaticDllGetClassObject
+#endif //ID_OLE_STAT_PROXY
+#if ID_OLE_STAT_OLE2NLS
+ #define CompareStringA StaticCompareStringA
+ #define LCMapStringA StaticLCMapStringA
+ #define GetLocaleInfoA StaticGetLocaleInfoA
+ #define GetStringTypeA StaticGetStringTypeA
+ #define GetSystemDefaultLangID StaticGetSystemDefaultLangID
+ #define GetUserDefaultLangID StaticGetUserDefaultLangID
+ #define GetSystemDefaultLCID StaticGetSystemDefaultLCID
+ #define GetUserDefaultLCID StaticGetUserDefaultLCID
+#endif //ID_OLE_STAT_OLE2NLS
+#endif //ID_MUNGE_STAT_NAMES
+#if ID_MUNGE_DLL_NAMES
+#if !ID_OLE_STAT_DOCFILE
+ #define StgCreateDocfile _DllStgCreateDocfile
+ #define StgCreateDocfileOnILockBytes _DllStgCreateDocfileOnILockBytes
+ #define StgOpenStorage _DllStgOpenStorage
+ #define StgOpenStorageOnILockBytes _DllStgOpenStorageOnILockBytes
+ #define StgIsStorageFile _DllStgIsStorageFile
+ #define StgIsStorageILockBytes _DllStgIsStorageILockBytes
+ #define StgSetTimes _DllStgSetTimes
+ #define StgSetTimesMac _DllStgSetTimesMac
+ #define StgSetTimesFSp _DllStgSetTimesFSp
+ #define DllGetClassObject _DllDllGetClassObject
+ #define StgCreateDocfileFSp _DllStgCreateDocfileFSp
+ #define StgOpenStorageFSp _DllStgOpenStorageFSp
+ #define StgCreateDocfileMac _DllStgCreateDocfileMac
+ #define StgOpenStorageMac _DllStgOpenStorageMac
+ #define StgIsStorageFileMac _DllStgIsStorageFileMac
+ #define StgIsStorageFileFSp _DllStgIsStorageFileFSp
+ #define StgGetFSpFromIStorage _DllStgGetFSpFromIStorage
+ #define StgGetFRefFromIStorage _DllStgGetFRefFromIStorage
+#endif // ID_OLE_STAT_DOCFILE
+#if !ID_OLE_STAT_USER
+ #define OleregOpenRegistration _DllOleregOpenRegistration
+ #define OleregCloseRegistration _DllOleregCloseRegistration
+ #define OleregGetValue _DllOleregGetValue
+ #define OleregSetValue _DllOleregSetValue
+ #define OleregRemoveKey _DllOleregRemoveKey
+ #define OleGlobalAddAtom _DllOleGlobalAddAtom
+ #define OleGlobalDuplicateAtom _DllOleGlobalDuplicateAtom
+ #define OleGlobalDeleteAtom _DllOleGlobalDeleteAtom
+ #define OleGlobalFindAtom _DllOleGlobalFindAtom
+ #define OleGlobalGetAtomName _DllOleGlobalGetAtomName
+ #define OleGlobalAlloc _DllOleGlobalAlloc
+ #define OleGlobalCompact _DllOleGlobalCompact
+ #define OleGlobalFree _DllOleGlobalFree
+ #define OleGlobalHandle _DllOleGlobalHandle
+ #define OleGlobalLock _DllOleGlobalLock
+ #define OleGlobalReAlloc _DllOleGlobalReAlloc
+ #define OleGlobalSize _DllOleGlobalSize
+ #define OleGlobalUnlock _DllOleGlobalUnlock
+ #define RegQueryValue _DllRegQueryValue
+ #define RegOpenKey _DllRegOpenKey
+ #define RegSetValue _DllRegSetValue
+ #define RegEnumKey _DllRegEnumKey
+ #define RegEnumProgID _DllRegEnumProgID
+ #define RegDeleteKey _DllRegDeleteKey
+ #define RegCreateKey _DllRegCreateKey
+ #define RegCloseKey _DllRegCloseKey
+ #define RegInitialize _DllRegInitialize
+ #define InitUserData _DllInitUserData
+ #define SendHighLevelEvent _DllSendHighLevelEvent
+ #define OleWinExec _DllOleWinExec
+ #define InitDB _DllInitDB
+ #define CloseDB _DllCloseDB
+ #define OleGetCurrentTask _DllOleGetCurrentTask
+ #define OleGetProcAddress _DllOleGetProcAddress
+ #define OleLoadLibrary _DllOleLoadLibrary
+ #define OleFreeLibrary _DllOleFreeLibrary
+ #define OutputDebugString _DllOutputDebugString
+ #define SoftAssert _DllSoftAssert
+ #define FnAssert _DllFnAssert
+ #define IsValidInterface _DllIsValidInterface
+ #define IsValidIid _DllIsValidIid
+ #define IsValidHandle _DllIsValidHandle
+ #define EnterOLEApi _DllEnterOLEApi
+ #define ExitOLEApi _DllExitOLEApi
+ #define FnAssertOn _DllFnAssertOn
+ #define GlobalFreePtr _DllGlobalFreePtr
+ #define GlobalAllocPtr _DllGlobalAllocPtr
+ #define UserInitialize _DllUserInitialize
+ #define UserUninitialize _DllUserUninitialize
+ #define IsValidInPtr _DllIsValidInPtr
+ #define IsValidOutPtr _DllIsValidOutPtr
+ #define RegQueryValueEx _DllRegQueryValueEx
+ #define RegFlush _DllRegFlush
+ #define RegDeleteValue _DllRegDeleteValue
+ #define RegSetValueEx _DllRegSetValueEx
+ #define RegEnumValue _DllRegEnumValue
+ #define OLEInitDBCSCountry _DllOLEInitDBCSCountry
+ #define IAnsiNext _DllIAnsiNext
+ #define IAnsiPrev _DllIAnsiPrev
+ #define OleMakeFSSpec _DllOleMakeFSSpec
+ #define OleFullPathFromFSSpec _DllOleFullPathFromFSSpec
+ #define OleGetFSSpecInfo _DllOleGetFSSpecInfo
+#endif //ID_OLE_STAT_USER
+#if !ID_OLE_STAT_OLE2DISP
+ #define DllGetClassObject _DllDllGetClassObject
+ #define SysAllocString _DllSysAllocString
+ #define SysReAllocString _DllSysReAllocString
+ #define SysAllocStringLen _DllSysAllocStringLen
+ #define SysReAllocStringLen _DllSysReAllocStringLen
+ #define SysFreeString _DllSysFreeString
+ #define SysStringLen _DllSysStringLen
+ #define VariantInit _DllVariantInit
+ #define VariantClear _DllVariantClear
+ #define VariantCopy _DllVariantCopy
+ #define VariantCopyInd _DllVariantCopyInd
+ #define VariantChangeType _DllVariantChangeType
+ #define VarI2FromI4 _DllVarI2FromI4
+ #define VarI2FromR4 _DllVarI2FromR4
+ #define VarI2FromR8 _DllVarI2FromR8
+ #define VarI2FromCy _DllVarI2FromCy
+ #define VarI2FromDate _DllVarI2FromDate
+ #define VarI2FromStr _DllVarI2FromStr
+ #define VarI2FromDisp _DllVarI2FromDisp
+ #define VarI2FromBool _DllVarI2FromBool
+ #define VarI4FromI2 _DllVarI4FromI2
+ #define VarI4FromR4 _DllVarI4FromR4
+ #define VarI4FromR8 _DllVarI4FromR8
+ #define VarI4FromCy _DllVarI4FromCy
+ #define VarI4FromDate _DllVarI4FromDate
+ #define VarI4FromStr _DllVarI4FromStr
+ #define VarI4FromDisp _DllVarI4FromDisp
+ #define VarI4FromBool _DllVarI4FromBool
+ #define VarR4FromI2 _DllVarR4FromI2
+ #define VarR4FromI4 _DllVarR4FromI4
+ #define VarR4FromR8 _DllVarR4FromR8
+ #define VarR4FromCy _DllVarR4FromCy
+ #define VarR4FromDate _DllVarR4FromDate
+ #define VarR4FromStr _DllVarR4FromStr
+ #define VarR4FromDisp _DllVarR4FromDisp
+ #define VarR4FromBool _DllVarR4FromBool
+ #define VarR8FromI2 _DllVarR8FromI2
+ #define VarR8FromI4 _DllVarR8FromI4
+ #define VarR8FromR4 _DllVarR8FromR4
+ #define VarR8FromCy _DllVarR8FromCy
+ #define VarR8FromDate _DllVarR8FromDate
+ #define VarR8FromStr _DllVarR8FromStr
+ #define VarR8FromDisp _DllVarR8FromDisp
+ #define VarR8FromBool _DllVarR8FromBool
+ #define VarDateFromI2 _DllVarDateFromI2
+ #define VarDateFromI4 _DllVarDateFromI4
+ #define VarDateFromR4 _DllVarDateFromR4
+ #define VarDateFromR8 _DllVarDateFromR8
+ #define VarDateFromCy _DllVarDateFromCy
+ #define VarDateFromStr _DllVarDateFromStr
+ #define VarDateFromDisp _DllVarDateFromDisp
+ #define VarDateFromBool _DllVarDateFromBool
+ #define VarCyFromI2 _DllVarCyFromI2
+ #define VarCyFromI4 _DllVarCyFromI4
+ #define VarCyFromR4 _DllVarCyFromR4
+ #define VarCyFromR8 _DllVarCyFromR8
+ #define VarCyFromDate _DllVarCyFromDate
+ #define VarCyFromStr _DllVarCyFromStr
+ #define VarCyFromDisp _DllVarCyFromDisp
+ #define VarCyFromBool _DllVarCyFromBool
+ #define VarBstrFromI2 _DllVarBstrFromI2
+ #define VarBstrFromI4 _DllVarBstrFromI4
+ #define VarBstrFromR4 _DllVarBstrFromR4
+ #define VarBstrFromR8 _DllVarBstrFromR8
+ #define VarBstrFromCy _DllVarBstrFromCy
+ #define VarBstrFromDate _DllVarBstrFromDate
+ #define VarBstrFromDisp _DllVarBstrFromDisp
+ #define VarBstrFromBool _DllVarBstrFromBool
+ #define VarBoolFromI2 _DllVarBoolFromI2
+ #define VarBoolFromI4 _DllVarBoolFromI4
+ #define VarBoolFromR4 _DllVarBoolFromR4
+ #define VarBoolFromR8 _DllVarBoolFromR8
+ #define VarBoolFromDate _DllVarBoolFromDate
+ #define VarBoolFromCy _DllVarBoolFromCy
+ #define VarBoolFromStr _DllVarBoolFromStr
+ #define VarBoolFromDisp _DllVarBoolFromDisp
+ #define SafeArrayCreate _DllSafeArrayCreate
+ #define SafeArrayDestroy _DllSafeArrayDestroy
+ #define SafeArrayGetDim _DllSafeArrayGetDim
+ #define SafeArrayGetElemsize _DllSafeArrayGetElemsize
+ #define SafeArrayGetUBound _DllSafeArrayGetUBound
+ #define SafeArrayGetLBound _DllSafeArrayGetLBound
+ #define SafeArrayLock _DllSafeArrayLock
+ #define SafeArrayUnlock _DllSafeArrayUnlock
+ #define SafeArrayAccessData _DllSafeArrayAccessData
+ #define SafeArrayUnaccessData _DllSafeArrayUnaccessData
+ #define SafeArrayGetElement _DllSafeArrayGetElement
+ #define SafeArrayPutElement _DllSafeArrayPutElement
+ #define SafeArrayCopy _DllSafeArrayCopy
+ #define SafeArrayAllocDescriptor _DllSafeArrayAllocDescriptor
+ #define SafeArrayAllocData _DllSafeArrayAllocData
+ #define SafeArrayDestroyDescriptor _DllSafeArrayDestroyDescriptor
+ #define SafeArrayDestroyData _DllSafeArrayDestroyData
+ #define SafeArrayRedim _DllSafeArrayRedim
+ #define VariantTimeToDosDateTime _DllVariantTimeToDosDateTime
+ #define DosDateTimeToVariantTime _DllDosDateTimeToVariantTime
+ #define DispGetParam _DllDispGetParam
+ #define DispGetIDsOfNames _DllDispGetIDsOfNames
+ #define DispInvoke _DllDispInvoke
+ #define CreateDispTypeInfo _DllCreateDispTypeInfo
+ #define CreateStdDispatch _DllCreateStdDispatch
+ #define RegisterActiveObject _DllRegisterActiveObject
+ #define RevokeActiveObject _DllRevokeActiveObject
+ #define GetActiveObject _DllGetActiveObject
+ #define DoInvokeMethod _DllDoInvokeMethod
+ #define VariantChangeTypeEx _DllVariantChangeTypeEx
+ #define SafeArrayPtrOfIndex _DllSafeArrayPtrOfIndex
+ #define MPWVarFromR4 _DllMPWVarFromR4
+ #define MPWVarFromR8 _DllMPWVarFromR8
+ #define MPWR4FromVar _DllMPWR4FromVar
+ #define MPWR8FromVar _DllMPWR8FromVar
+#endif //ID_OLE_STAT_OLE2DISP
+#if !ID_OLE_STAT_TYPELIB
+ #define CreateTypeLib _DllCreateTypeLib
+ #define LoadTypeLib _DllLoadTypeLib
+ #define LoadRegTypeLib _DllLoadRegTypeLib
+ #define RegisterTypeLib _DllRegisterTypeLib
+ #define LHashValOfNameSys _DllLHashValOfNameSys
+ #define QueryPathOfRegTypeLib _DllQueryPathOfRegTypeLib
+ #define LoadTypeLibFSp _DllLoadTypeLibFSp
+ #define RegisterTypeLibFolder _DllRegisterTypeLibFolder
+ #define QueryTypeLibFolder _DllQueryTypeLibFolder
+#endif //ID_OLE_STAT_TYPELIB
+#if !ID_OLE_STAT_DEF
+ #define OleBuildVersion _DllOleBuildVersion
+ #define OleInitialize _DllOleInitialize
+ #define OleUninitialize _DllOleUninitialize
+ #define DllGetClassObject _DllDllGetClassObject
+ #define OleQueryLinkFromData _DllOleQueryLinkFromData
+ #define OleQueryCreateFromData _DllOleQueryCreateFromData
+ #define OleCreateFromData _DllOleCreateFromData
+ #define OleCreateLinkFromData _DllOleCreateLinkFromData
+ #define OleCreate _DllOleCreate
+ #define OleCreateLink _DllOleCreateLink
+ #define OleLoad _DllOleLoad
+ #define OleSave _DllOleSave
+ #define OleRun _DllOleRun
+ #define OleIsRunning _DllOleIsRunning
+ #define OleLockRunning _DllOleLockRunning
+ #define ReadClassStg _DllReadClassStg
+ #define WriteClassStg _DllWriteClassStg
+ #define ReadClassStm _DllReadClassStm
+ #define WriteClassStm _DllWriteClassStm
+ #define BindMoniker _DllBindMoniker
+ #define MkParseDisplayName _DllMkParseDisplayName
+ #define OleSaveToStream _DllOleSaveToStream
+ #define OleLoadFromStream _DllOleLoadFromStream
+ #define CreateBindCtx _DllCreateBindCtx
+ #define CreateItemMoniker _DllCreateItemMoniker
+ #define CreateFileMoniker _DllCreateFileMoniker
+ #define CreateGenericComposite _DllCreateGenericComposite
+ #define GetRunningObjectTable _DllGetRunningObjectTable
+ #define OleGetMalloc _DllOleGetMalloc
+ #define ReleaseStgMedium _DllReleaseStgMedium
+ #define ReadStringStream _DllReadStringStream
+ #define WriteStringStream _DllWriteStringStream
+ #define RegisterDragDrop _DllRegisterDragDrop
+ #define RevokeDragDrop _DllRevokeDragDrop
+ #define DoDragDrop _DllDoDragDrop
+ #define CreateOleAdviseHolder _DllCreateOleAdviseHolder
+ #define CreateDataAdviseHolder _DllCreateDataAdviseHolder
+ #define OpenOrCreateStream _DllOpenOrCreateStream
+ #define CreateAntiMoniker _DllCreateAntiMoniker
+ #define CreatePointerMoniker _DllCreatePointerMoniker
+ #define MonikerRelativePathTo _DllMonikerRelativePathTo
+ #define MonikerCommonPrefixWith _DllMonikerCommonPrefixWith
+ #define OleSetClipboard _DllOleSetClipboard
+ #define OleGetClipboard _DllOleGetClipboard
+ #define OleDuplicateData _DllOleDuplicateData
+ #define CreateILockBytesOnHGlobal _DllCreateILockBytesOnHGlobal
+ #define GetHGlobalFromILockBytes _DllGetHGlobalFromILockBytes
+ #define GetClassFile _DllGetClassFile
+ #define OleDraw _DllOleDraw
+ #define OleCreateDefaultHandler _DllOleCreateDefaultHandler
+ #define OleCreateEmbeddingHelper _DllOleCreateEmbeddingHelper
+ #define OleConvertIStorageToOLESTREAMEx _DllOleConvertIStorageToOLESTREAMEx
+ #define OleConvertOLESTREAMToIStorageEx _DllOleConvertOLESTREAMToIStorageEx
+ #define SetDocumentBitStg _DllSetDocumentBitStg
+ #define GetDocumentBitStg _DllGetDocumentBitStg
+ #define WriteOleStg _DllWriteOleStg
+ #define ReadOleStg _DllReadOleStg
+ #define OleCreateFromFile _DllOleCreateFromFile
+ #define OleCreateLinkToFile _DllOleCreateLinkToFile
+ #define CreateDataCache _DllCreateDataCache
+ #define OleConvertIStorageToOLESTREAM _DllOleConvertIStorageToOLESTREAM
+ #define OleConvertOLESTREAMToIStorage _DllOleConvertOLESTREAMToIStorage
+ #define ReadFmtUserTypeStg _DllReadFmtUserTypeStg
+ #define WriteFmtUserTypeStg _DllWriteFmtUserTypeStg
+ #define OleFlushClipboard _DllOleFlushClipboard
+ #define OleIsCurrentClipboard _DllOleIsCurrentClipboard
+ #define OleTranslateAccelerator _DllOleTranslateAccelerator
+ #define OleDoAutoConvert _DllOleDoAutoConvert
+ #define OleGetAutoConvert _DllOleGetAutoConvert
+ #define OleSetAutoConvert _DllOleSetAutoConvert
+ #define GetConvertStg _DllGetConvertStg
+ #define SetConvertStg _DllSetConvertStg
+ #define CreateStreamOnHGlobal _DllCreateStreamOnHGlobal
+ #define GetHGlobalFromStream _DllGetHGlobalFromStream
+ #define OleDuplicateMedium _DllOleDuplicateMedium
+ #define OleSetContainedObject _DllOleSetContainedObject
+ #define OleNoteObjectVisible _DllOleNoteObjectVisible
+ #define OleCreateStaticFromData _DllOleCreateStaticFromData
+ #define OleRegGetUserType _DllOleRegGetUserType
+ #define OleRegGetMiscStatus _DllOleRegGetMiscStatus
+ #define OleRegEnumFormatEtc _DllOleRegEnumFormatEtc
+ #define OleRegEnumVerbs _DllOleRegEnumVerbs
+ #define OleGetEnumFormatEtc _DllOleGetEnumFormatEtc
+ #define OleSetEnumFormatEtc _DllOleSetEnumFormatEtc
+ #define OleRemoveEnumFormatEtc _DllOleRemoveEnumFormatEtc
+ #define OleSendLLE _DllOleSendLLE
+ #define OleSetInPlaceWindow _DllOleSetInPlaceWindow
+ #define OleUnSetInPlaceWindow _DllOleUnSetInPlaceWindow
+ #define OleClipWindow _DllOleClipWindow
+ #define OleClipWindows _DllOleClipWindows
+ #define OleInsertMenus _DllOleInsertMenus
+ #define OleHashMenuID _DllOleHashMenuID
+ #define OleUnhashMenuID _DllOleUnhashMenuID
+ #define OlePatchGetMHandle _DllOlePatchGetMHandle
+ #define OleUnpatchGetMHandle _DllOleUnpatchGetMHandle
+ #define OleAddMBarMenu _DllOleAddMBarMenu
+ #define OleSetInPlaceRects _DllOleSetInPlaceRects
+ #define OleMaskMouse _DllOleMaskMouse
+ #define OleMoveWindow _DllOleMoveWindow
+ #define OleSizeParentWindow _DllOleSizeParentWindow
+ #define OleSizeObjectWindow _DllOleSizeObjectWindow
+ #define OleDragParentWindow _DllOleDragParentWindow
+ #define OleDragObjectWindow _DllOleDragObjectWindow
+ #define OleGrowParentWindow _DllOleGrowParentWindow
+ #define OleGrowObjectWindow _DllOleGrowObjectWindow
+ #define OleNewMBar _DllOleNewMBar
+ #define OleDisposeMBar _DllOleDisposeMBar
+ #define OleProcessDdeAE _DllOleProcessDdeAE
+ #define OleProcessClipboardAE _DllOleProcessClipboardAE
+ #define InitializeClipboard _DllInitializeClipboard
+ #define UnInitializeClipboard _DllUnInitializeClipboard
+ #define OleIsClipboardFormatAvailable _DllOleIsClipboardFormatAvailable
+ #define OleGetClipboardData _DllOleGetClipboardData
+ #define OleSetClipboardData _DllOleSetClipboardData
+ #define OleEnumClipboardFormats _DllOleEnumClipboardFormats
+ #define StoreClap _DllStoreClap
+ #define OleCountClipboardFormats _DllOleCountClipboardFormats
+ #define OleCloseClipboard _DllOleCloseClipboard
+ #define OleEmptyClipboard _DllOleEmptyClipboard
+ #define OleSetClipboardEx _DllOleSetClipboardEx
+ #define OleZoomParentWindow _DllOleZoomParentWindow
+ #define OleSetParentRgns _DllOleSetParentRgns
+ #define CreateFileMonikerFSp _DllCreateFileMonikerFSp
+ #define OleCreateFromFSp _DllOleCreateFromFSp
+ #define OleCreateLinkToFSp _DllOleCreateLinkToFSp
+ #define OleGetCursor _DllOleGetCursor
+ #define OleSetCursor _DllOleSetCursor
+ #define OleUpdateCursor _DllOleUpdateCursor
+ #define GetClassFSp _DllGetClassFSp
+ #define ReadOle1FmtProgIDStgMac _DllReadOle1FmtProgIDStgMac
+ #define WriteOle1FmtProgIDStgMac _DllWriteOle1FmtProgIDStgMac
+ #define OleGetIconOfFile _DllOleGetIconOfFile
+ #define OleGetIconOfClass _DllOleGetIconOfClass
+ #define OleGetIconOfFSp _DllOleGetIconOfFSp
+ #define OlePictFromIconAndLabel _DllOlePictFromIconAndLabel
+ #define OleGetIconFromIconSuite _DllOleGetIconFromIconSuite
+ #define OleUIPictIconFree _DllOleUIPictIconFree
+ #define OleUIPictIconDraw _DllOleUIPictIconDraw
+ #define OleUIPictExtractIcon _DllOleUIPictExtractIcon
+ #define OleUIPictExtractLabel _DllOleUIPictExtractLabel
+ #define OleUIPictExtractIconSource _DllOleUIPictExtractIconSource
+ #define OleMetaFileToPict _DllOleMetaFileToPict
+ #define OleQueryCreateAll _DllOleQueryCreateAll
+ #define OleWhichGrowHandle _DllOleWhichGrowHandle
+ #define MkGetMacNetInfo _DllMkGetMacNetInfo
+#endif //ID_OLE_STAT_DEF
+#if !ID_OLE_STAT_COMPOBJ
+ #define CoBuildVersion _DllCoBuildVersion
+ #define CoInitialize _DllCoInitialize
+ #define CoUninitialize _DllCoUninitialize
+ #define CoGetMalloc _DllCoGetMalloc
+ #define CoRegisterClassObject _DllCoRegisterClassObject
+ #define CoRevokeClassObject _DllCoRevokeClassObject
+ #define CoGetClassObject _DllCoGetClassObject
+ #define CoMarshalInterface _DllCoMarshalInterface
+ #define CoUnmarshalInterface _DllCoUnmarshalInterface
+ #define CoLoadLibrary _DllCoLoadLibrary
+ #define CoFreeLibrary _DllCoFreeLibrary
+ #define CoFreeAllLibraries _DllCoFreeAllLibraries
+ #define CoCreateInstance _DllCoCreateInstance
+ #define StringFromIID _DllStringFromIID
+ #define CoDisconnectObject _DllCoDisconnectObject
+ #define CoReleaseMarshalData _DllCoReleaseMarshalData
+ #define CoFreeUnusedLibraries _DllCoFreeUnusedLibraries
+ #define IsEqualGUID _DllIsEqualGUID
+ #define StringFromCLSID _DllStringFromCLSID
+ #define CLSIDFromString _DllCLSIDFromString
+ #define RESULTFROMSCODE _DllRESULTFROMSCODE
+ #define GETSCODE _DllGETSCODE
+ #define CoRegisterMessageFilter _DllCoRegisterMessageFilter
+ #define CoIsHandlerConnected _DllCoIsHandlerConnected
+ #define CoMarshalHresult _DllCoMarshalHresult
+ #define CoUnmarshalHresult _DllCoUnmarshalHresult
+ #define CoGetCurrentProcess _DllCoGetCurrentProcess
+ #define CoIsOle1Class _DllCoIsOle1Class
+ #define CLSIDFromProgID _DllCLSIDFromProgID
+ #define ProgIDFromCLSID _DllProgIDFromCLSID
+ #define CoLockObjectExternal _DllCoLockObjectExternal
+ #define CoGetTreatAsClass _DllCoGetTreatAsClass
+ #define CoTreatAsClass _DllCoTreatAsClass
+ #define CoGetStandardMarshal _DllCoGetStandardMarshal
+ #define PropagateResult _DllPropagateResult
+ #define IIDFromString _DllIIDFromString
+ #define CoCreateStandardMalloc _DllCoCreateStandardMalloc
+ #define CoCreateGuid _DllCoCreateGuid
+ #define StringFromGUID2 _DllStringFromGUID2
+ #define CoGetClassExt _DllCoGetClassExt
+ #define Ole1ClassFromCLSID2 _DllOle1ClassFromCLSID2
+ #define CLSIDFromOle1Class _DllCLSIDFromOle1Class
+ #define CoOpenClassKey _DllCoOpenClassKey
+ #define GUIDFromString _DllGUIDFromString
+ #define CoFileTimeNow _DllCoFileTimeNow
+ #define RemAllocOID _DllRemAllocOID
+ #define RemFreeOID _DllRemFreeOID
+ #define RemCreateRemoteHandler _DllRemCreateRemoteHandler
+ #define RemConnectToObject _DllRemConnectToObject
+ #define RemGetInfoForCid _DllRemGetInfoForCid
+ #define LrpcCall _DllLrpcCall
+ #define LrpcDispatch _DllLrpcDispatch
+ #define LrpcRegisterMonitor _DllLrpcRegisterMonitor
+ #define LrpcRevokeMonitor _DllLrpcRevokeMonitor
+ #define LrpcGetThreadWindow _DllLrpcGetThreadWindow
+ #define LookupEtask _DllLookupEtask
+ #define SetEtask _DllSetEtask
+ #define RemLookupSHUnk _DllRemLookupSHUnk
+ #define CoMemctxOf _DllCoMemctxOf
+ #define CoMemAlloc _DllCoMemAlloc
+ #define CoMemFree _DllCoMemFree
+ #define CoRunModalLoop _DllCoRunModalLoop
+ #define CoHandleIncomingCall _DllCoHandleIncomingCall
+ #define CoSetAckState _DllCoSetAckState
+ #define OleProcessLrpcAE _DllOleProcessLrpcAE
+ #define CoFileTimeToMacDateTime _DllCoFileTimeToMacDateTime
+ #define CoMacDateTimeToFileTime _DllCoMacDateTimeToFileTime
+ #define InternalCoInitialize _DllInternalCoInitialize
+ #define CoHandlePendingMessage _DllCoHandlePendingMessage
+#endif //ID_OLE_STAT_COMPOBJ
+#if !ID_OLE_STAT_PROXY
+ #define DllGetClassObject _DllDllGetClassObject
+#endif //ID_OLE_STAT_PROXY
+#if !ID_OLE_STAT_OLE2NLS
+ #define CompareStringA _DllCompareStringA
+ #define LCMapStringA _DllLCMapStringA
+ #define GetLocaleInfoA _DllGetLocaleInfoA
+ #define GetStringTypeA _DllGetStringTypeA
+ #define GetSystemDefaultLangID _DllGetSystemDefaultLangID
+ #define GetUserDefaultLangID _DllGetUserDefaultLangID
+ #define GetSystemDefaultLCID _DllGetSystemDefaultLCID
+ #define GetUserDefaultLCID _DllGetUserDefaultLCID
+#endif //ID_OLE_STAT_OLE2NLS
+#endif //ID_MUNGE_DLL_NAMES
diff --git a/private/oleauto/src/typelib/nammgr.cxx b/private/oleauto/src/typelib/nammgr.cxx
new file mode 100644
index 000000000..8c8b2825e
--- /dev/null
+++ b/private/oleauto/src/typelib/nammgr.cxx
@@ -0,0 +1,1521 @@
+/***
+*nammgr.cxx - Name manager
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* The Name Manager handles the hashing and storing of names. Each
+* class has its own name manager. See \silver\doc\ic\nammgr.doc for
+* information on the name manager.
+*
+*Revision History:
+*
+* 22-Jan-91 petergo: Created.
+* [01] 25-Feb-91 petergo: Now uses heap/block manager for mem mgt.
+* [02] 13-Jun-91 petergo: Updated for new AFX-less protocols.
+* [03] 02-Dec-91 ilanc: Used IfErrRet in Write
+* [04] 12-Mar-92 ilanc: Added DebDeleteGlobalDefault()
+* [05] 15-May-92 w-peterh: added CaseChange parameters to HlnamOfStr()
+* [06] 15-Nov-92 RajivK: added isStrDef() for Edit & Continue stuff
+* [07] 19-Nov-92 RajivK: added CbOfHlnam() and CchOfHgnam();
+* [08] 31-Dec-92 RajivK: Support for code page conversion.
+* [09] 08-Jan-93 RajivK: Fixed some undone(s)
+* [10] 12-Feb-93 w-peterh: removed Undone in IsStrDef
+* [11] 12-Feb-93 rajivk: added GetLcid() and SetLcid() and StriCmp()
+*
+*Implementation Notes:
+*
+* The name table is stored in an expandable buffer, managed by deriving
+* from the BUF class. This buffer is structure in two parts: the first
+* part is the bucket table. The bucket table allows a mapping from the
+* hash value low bits to the offset first name in that bucket. The bucket
+* table occupies sizeof(sHLNAM)*NM_cBuckets bytes. Following the bucket
+* table the names are stored, one after another. Each name is stored in 2
+* parts. The first part NAM_INFO contains all the information related to a
+* name. The second part NAM_STR only contains the string/name.
+* These 2 are stored in different sheap. This is done purely for
+* capacity reasons.
+*
+* Starting with the name pointed to by the bucket table, all of the names
+* which fall into a given bucket are stored in a binary tree, ordered by
+* the full 16-bit hash value. Thus, searching for a given name involves
+*
+* 1) Hashing to get 16-bit hash value
+* 2) Go name at root of bucket (bucket is low bits of hash)
+* 3) Search for hash value in binary tree
+* 4) Compare each name with the same 16-bit hash value to find it.
+*
+*****************************************************************************/
+
+#define NAMMGR_VTABLE // export nam mgr vtable
+
+#include "silver.hxx"
+#include "typelib.hxx"
+#include <stddef.h>
+#include "xstring.h"
+#include <stdlib.h>
+#include <new.h>
+#include "cltypes.hxx"
+#include "stream.hxx"
+#include "blkmgr.hxx"
+
+
+#include "nammgr.hxx"
+#include "clutil.hxx"
+#include "tls.h"
+
+#pragma hdrstop(RTPCHNAME)
+
+#undef tolower
+#undef toupper // Don't use unsafe macro forms
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+char szOleNammgrCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleNammgrCxx
+#else
+static char szNammgrCxx[] = __FILE__;
+#define SZ_FILE_NAME szNammgrCxx
+#endif
+#endif
+
+
+#define CHAR_SET_SIZE 256
+
+
+/***
+*PUBLIC NAMMGR::NAMMGR - constructor
+*Purpose:
+* This is private -- used by Create only.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+NAMMGR::NAMMGR()
+{
+ m_fInit = FALSE;
+ m_fSortKeys = FALSE;
+ m_fOLBKwordInit = FALSE;
+
+ m_pbmNamInfo = NULL;
+
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC NAMMGR::~NAMMGR - destructor
+*Purpose:
+* Destroys a name manager.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+NAMMGR::~NAMMGR()
+{
+
+ // Release the sheap containing the names and the overhead
+ BLK_MGR::FreeStandalone(m_pbmNamInfo);
+
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC NAMMGR::Init - initialize the name manager
+*Purpose:
+* Initializes the name manager.
+*
+* Note: we are careful in this routine that if an error occurs
+* when we try to allocate memory, we aren't in a bad state. In particular;
+* we don't link ourselves onto the list of name managers until our
+* construction is complete.
+*
+*Entry:
+* psheapmgr - pointer to SHEAP_MGR to place in.
+* pdtroot : pointer to DYN_TYPEROOT ( is a default parameter );
+*
+*Exit:
+* *pnammgr - pointer to new name manager.
+* Return TIPERROR indicating success/failure.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR NAMMGR::Init(SHEAP_MGR * psheapmgr, DYN_TYPEROOT *pdtroot)
+{
+ UINT cbBuckets; // number of bytes in bucket table.
+ UINT i;
+ TIPERROR err;
+ HCHUNK hchunk;
+
+ DebAssert(m_fInit == FALSE, "NAMMGR::Init: table already initialized");
+
+ // Initialize the block manager. Could return error: do first.
+ IfErrRet(m_bm.Init(psheapmgr));
+
+ // Create bucket table
+ cbBuckets = NM_cBuckets * sizeof(sHLNAM);
+ IfErrRet(m_bm.AllocChunk(&hchunk, cbBuckets));
+
+ m_hchunkBucketTbl = hchunk;
+
+ // Initialize bucket table to all empty.
+ for (i = 0; i < NM_cBuckets; ++i)
+ SetBucketOfHash(i, HLNAM_Nil);
+
+
+ // Create the sheap that will contain name overhead (NAM_INFO)
+ IfErrGo(BLK_MGR::CreateStandalone(&m_pbmNamInfo, FALSE));
+
+
+ m_fInit = TRUE;
+ return TIPERR_None;
+
+
+Error:
+ // Free the table we allocate earlier
+ m_bm.FreeChunk(m_hchunkBucketTbl, cbBuckets);
+ return err;
+
+}
+#pragma code_seg()
+
+/***
+*SetGtlibole()
+*Purpose:
+* set the pointer to the project that owns this nammgr.
+*
+*Entry:
+*
+*Exit:
+*
+******************************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR NAMMGR::SetGtlibole(GenericTypeLibOLE *pgtlibole)
+{
+
+ m_pgtlibole = pgtlibole;
+ return TIPERR_None;
+
+}
+#pragma code_seg()
+
+
+
+/***
+*GetBucketOfHash() - get the number stored in the bucket
+*Purpose:
+* Given a hash value, gets the value in the bucket corresponding
+* to that hash value.
+*
+* Before calling this function make sure there are no police
+* or customs agents around.
+*
+*Entry:
+* uHash - hash value
+*
+*Exit:
+* Returns the hlnam stored in that bucket.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+HLNAM NAMMGR::GetBucketOfHash(UINT uHash) const
+{
+ return RqhlnamBucketTbl()[uHash % NM_cBuckets];
+}
+#pragma code_seg( )
+
+
+/***
+*SetBucketOfHash - set the number stored in the bucket
+*Purpose:
+* Given a hash value, sets the value in the bucket corresponding
+* to that hash value.
+*
+*Entry:
+* uHash - hash value
+* hlnam - value to set
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+void NAMMGR::SetBucketOfHash(UINT uHash, HLNAM hlnam)
+{
+ DebCheckHlnam(hlnam);
+
+ RqhlnamBucketTbl()[uHash % NM_cBuckets] = hlnam;
+}
+#pragma code_seg()
+
+/***
+*NAMMGR::Read - read presistant representation.
+*Purpose:
+* Reads in the persistant representation of the name table from
+* a stream. The global name handles are all removed, since they
+* do not persist.
+*
+*Entry:
+* psstrm - stream to read from.
+*
+*Exit:
+* Returns TIPERROR.
+* If an error occurs, you can only call Read again or destroy it.
+*
+***********************************************************************/
+
+TIPERROR NAMMGR::Read(STREAM * psstrm)
+{
+ TIPERROR err;
+
+ if ((err = m_bm.Read(psstrm)) ||
+ (err = psstrm->ReadUShort(&m_hchunkBucketTbl)) ||
+ // In ole we have only one sheap to store both the structures.
+ // In OB we have different sheaps to allocate NAM_INFO and NAM_STR structs
+ (err = m_pbmNamInfo->Read(psstrm)))
+ {
+ return err;
+ }
+
+#if HP_BIGENDIAN
+ // Swap bytes on Big-Endian machine.
+ SwapBytesBack();
+#else // !HP_BIGENDIAN
+#endif // !HP_BIGENDIAN
+
+
+ DebCheckState(1); // arg=1 forces blkmgrs to be checked.
+ return TIPERR_None;
+}
+
+
+#if HP_BIGENDIAN
+
+/***
+*NAMMGR::SwapHlnamBytes - swap bytes in an hlnam
+*Purpose:
+* Swaps the bytes in the structure corresponding to an HLNAM.
+*
+*Entry:
+* hlnam - hlnam
+*
+*Exit:
+* None.
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+void NAMMGR::SwapHlnamBytes(HLNAM hlnam)
+{
+ NAM_INFO * qnam;
+
+ qnam = QnamOfHlnam(hlnam);
+ DebAssert(IsTextName(qnam), "Bad name");
+ SwapStruct(qnam, NM_NamInfoLayout);
+}
+#pragma code_seg( )
+
+/***
+*NAMMGR::SwapBytes - swaps bytes for Mac serialization
+*Purpose:
+* This function swaps bytes in place for serialization and deserialization
+* on different platforms. Swaps from valid ordering for this platform,
+* to reverse ordering.
+*
+*Entry:
+* None.
+*Exit:
+* None.
+***********************************************************************/
+
+void NAMMGR::SwapBytes()
+{
+ sHLNAM * rqhlnam;
+
+ // Swap bytes in the name chunks
+ ForEachName(SwapHlnamBytes, TRUE);
+
+ // Swap bytes in the bucket table.
+ rqhlnam = RqhlnamBucketTbl();
+ SwapShortArray(rqhlnam, NM_cBuckets);
+}
+
+/***
+*NAMMGR::SwapBytesBack - swaps bytes for Mac serialization
+*Purpose:
+* This function swaps bytes in place for serialization and deserialization
+* on different platforms. Swaps from invalid ordering for this platform,
+* to valid ordering.
+*
+*Entry:
+*
+*Exit:
+* None.
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+void NAMMGR::SwapBytesBack()
+{
+ sHLNAM * rqhlnam;
+
+ // Swap bytes in the bucket table.
+ rqhlnam = RqhlnamBucketTbl();
+ SwapShortArray(rqhlnam, NM_cBuckets);
+
+ // Swap bytes in the name chunks
+ ForEachName(SwapHlnamBytes, FALSE);
+}
+#pragma code_seg( )
+
+#endif //HP_BIGENDIAN
+
+/***
+*Write - write persistant representation.
+*Purpose:
+* Writes the persistant representation of the name table from
+* a stream.
+*
+*Entry:
+* psstrm - stream to read from.
+*
+*Exit:
+* Returns TIPERROR.
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR NAMMGR::Write(STREAM * psstrm)
+{
+ TIPERROR err;
+
+ DebCheckState(1); // arg=1 forces blkmgrs to be checked.
+
+ // For Big Endian: Must byte swap to write, then swap back.
+#if HP_BIGENDIAN
+ SwapBytes();
+#endif //HP_BIGENDIAN
+
+ IfErrGo(m_bm.Write(psstrm));
+ IfErrGo(psstrm->WriteUShort(m_hchunkBucketTbl));
+ IfErrGo(m_pbmNamInfo->Write(psstrm));
+
+
+Error:
+#if HP_BIGENDIAN
+ SwapBytesBack();
+#endif //HP_BIGENDIAN
+
+ return err;
+}
+#pragma code_seg()
+
+
+/***
+*ForEachName - call function for each name in the nam mgr
+*Purpose:
+* This function calls its argument (a pointer to a member of NAMMGR)
+* and passes it an HLNAM for every name in the name table. This
+* is used for rebinding localized names, serialization, and
+* other fun stuff.
+*
+*Entry:
+* pfn - pointer to member function of NAMMGR to call
+* fBefore - TRUE if child handles should be fetched before swapping,
+* FALSE if after.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#if HP_BIGENDIAN
+#pragma code_seg( CS_CORE2 )
+void NAMMGR::ForEachName(void (NAMMGR::*pfn)(HLNAM), BOOL fBefore)
+{
+ UINT i;
+ HLNAM hlnam;
+
+ for (i = 0; i < NM_cBuckets; ++i) {
+ hlnam = GetBucketOfHash(i);
+ if (hlnam != HLNAM_Nil)
+ ForEachDescendant(hlnam, pfn, fBefore);
+ }
+}
+#pragma code_seg( )
+#endif //HP_BIGENDIAN
+
+/***
+*ForEachDescendant - call function for name and its descendants
+*Purpose:
+* This function calls its argument (a pointer to a member of NAMMGR)
+* and passes it an HLNAM for the HLNAM passed and all its descendants in
+* the binary tree.
+*
+*Entry:
+* hlnam - name at root of names to process.
+* pfn - pointer to member function of NAMMGR to call
+* fBefore - TRUE if child handles should be fetched before swapping,
+* FALSE if after. (Needed for byte swapping support.)
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+void NAMMGR::ForEachDescendant(HLNAM hlnamRoot, void (NAMMGR::*pfn)(HLNAM),
+ BOOL fBefore)
+{
+ NAM_INFO * qnam;
+ HLNAM hlnamLeft, hlnamRight;
+
+ DebCheckHlnam(hlnamRoot);
+ DebAssert(hlnamRoot != HLNAM_Nil, "ForEachDescendant: HLNAM_Nil passed");
+
+ if (fBefore) {
+ qnam = QnamOfHlnam(hlnamRoot);
+ hlnamLeft = qnam->m_hlnamLeft;
+ hlnamRight = qnam->m_hlnamRight;
+ }
+
+ (this->*pfn)(hlnamRoot); // call function on this one.
+
+ if (!fBefore) {
+ qnam = QnamOfHlnam(hlnamRoot);
+ hlnamLeft = qnam->m_hlnamLeft;
+ hlnamRight = qnam->m_hlnamRight;
+ }
+
+ if (QnamOfHlnam(hlnamRoot)->m_hlnamLeft != HLNAM_Nil)
+ ForEachDescendant(hlnamLeft, pfn, fBefore);
+ if (QnamOfHlnam(hlnamRoot)->m_hlnamRight != HLNAM_Nil)
+ ForEachDescendant(hlnamRight, pfn, fBefore);
+}
+#pragma code_seg( )
+
+
+/***
+*NAMMGR::AddEntry - link a new table entry into the correct tree
+*Purpose:
+* Takes a new table entry that has just been created, but not
+* linked into the table bucket and binary tree, and puts it in
+* the correct place. The entry must be new and not a duplicate; this
+* isn't checked by this routine.
+*
+*Entry:
+* hlnam - offset of new entry to add.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+void NAMMGR::AddEntry(HLNAM hlnamNew)
+{
+ HLNAM hlnam; // current position in tree.
+ HLNAM hlnamChild; // child of current position.
+ UINT uHashNew; // hash value of the hlnamNew
+ UINT uHash; // hash value of hlnam.
+
+ DebCheckHlnam(hlnamNew);
+ DebAssert(hlnamNew != HLNAM_Nil, "AddEntry: nil hlnam");
+
+ uHashNew = WHashValOfLHashVal(HashOfHlnam(hlnamNew));
+
+ // Check the bucket to see if any names in this bucket
+ hlnam = GetBucketOfHash(uHashNew);
+ if (hlnam == HLNAM_Nil) {
+ // No entries in this bucket. Make this the root of the bucket.
+ SetBucketOfHash(uHashNew, hlnamNew);
+ }
+ else {
+ // Traverse the tree until we hit one without a child, and put
+ // the new entry as that child.
+ for (;;) {
+ DebCheckHlnam(hlnam);
+ uHash = WHashValOfLHashVal(HashOfHlnam(hlnam));
+
+ if (uHashNew < uHash) {
+ hlnamChild = QnamOfHlnam(hlnam)->m_hlnamLeft;
+ if (hlnamChild == HLNAM_Nil) {
+ // hit the end of the tree -- put new entry here.
+ QnamOfHlnam(hlnam)->m_hlnamLeft = hlnamNew;
+ return;
+ }
+ }
+ else {
+ hlnamChild = QnamOfHlnam(hlnam)->m_hlnamRight;
+ if (hlnamChild == HLNAM_Nil) {
+ // hit the end of the tree -- put new entry here.
+ QnamOfHlnam(hlnam)->m_hlnamRight = hlnamNew;
+ return;
+ }
+ }
+
+ hlnam = hlnamChild;
+ }
+ }
+}
+#pragma code_seg( )
+
+
+#if 0 //Dead Code
+/***
+*NAMMGR::CleanNames
+*Purpose:
+* Clear the name manager optimizations from the name
+* manager entries.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+void NAMMGR::CleanNames()
+{
+ // Clear the optimizations for all entries
+ ForEachName(CleanHlnam, TRUE);
+}
+
+
+/***
+*NAMMGR::CleanHlnam
+*Purpose:
+* Clear the optimization in this name manager entry.
+*
+*Entry:
+* hlnam - the name to clean
+*
+*Exit:
+*
+***********************************************************************/
+void NAMMGR::CleanHlnam(HLNAM hlnam)
+{
+ NAM_INFO *qnam;
+
+ qnam = (NAM_INFO *)QnamOfHlnam(hlnam);
+ DebAssert(IsTextName(qnam), "Bad name");
+
+ // Clear the optimizations
+
+ // initialize other bits to 0
+ qnam->m_fGlobal = 0;
+ qnam->m_fMultiple = 0;
+ qnam->m_fAmbiguous = 0;
+ qnam->m_fNonParam = 0;
+
+ // Make sure that the ityp is invalid
+ qnam->m_ityp = NM_InvalidItyp;
+}
+#endif //0
+
+/***
+*NAMMGR::FindHash - find a hash value in this table.
+*Purpose:
+* Tries to find a given hash value in the binary tree starting
+* at hlnam.
+*
+*Entry:
+* uHashFind - the hash value to find
+* hlnam - starting hlnam to look at. Can be HLNAM_Nil, in which
+* case HLNAM_Nil is immediately returned again.
+*
+*Exit:
+* Returns the HLNAM of the first entry with this hash value found,
+* or HLNAM_Nil if it isn't in this table.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+HLNAM NAMMGR::FindHash(UINT uHashFind, HLNAM hlnam) const
+{
+ UINT uHash; // hash value of hlnam
+
+ // Traverse the binary tree until we find the hash value.
+ for (;;) {
+ DebCheckHlnam(hlnam);
+
+ if (hlnam == HLNAM_Nil)
+ return HLNAM_Nil; // Didn't find the name.
+
+ uHash = WHashValOfLHashVal(((NAMMGR *)this)->HashOfHlnam(hlnam));
+
+ if (uHashFind == uHash)
+ return hlnam;
+ else if (uHashFind < uHash)
+ hlnam = QnamOfHlnam(hlnam)->m_hlnamLeft;
+ else
+ hlnam = QnamOfHlnam(hlnam)->m_hlnamRight;
+ }
+}
+#pragma code_seg( )
+
+
+/***
+*NAMMGR::FindTextNam - Find a text name in the hash table.
+*Purpose:
+* Tries to find a given text name in the name table. Only unlocalized
+* text names are searched.
+*
+*Entry:
+* xsz - string to find
+* uHash - hash value of string -- a parameter to avoid recomputation.
+* fChangeCase - if TRUE then an existing string of differing case
+* will be overwritten with the new case only if the name
+* stored is not imported from a referenced typelib.
+*
+*Exit:
+* Returns the HLNAM of the string if it's in the table, or HLNAM_Nil
+* if it isn't in the table.
+* *pfCaseChanged - whetheror not the case of the string has been changed
+* if pfCaseChanged is NULL then it is ignored
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+HLNAM NAMMGR::FindTextNam(XSZ_CONST xsz, UINT uHash,
+ BOOL fChangeCase, BOOL *pfCaseChanged,
+ BOOL fPreserveCase)
+{
+ HLNAM hlnam;
+ NAM_INFO * qnam;
+ NAM_STR *qnamstr;
+
+ DebAssert(uHash == WHashValOfLHashVal(LHashValOfNameSysA(Pgtlibole()->GetSyskind(),
+ Pgtlibole()->GetLcid(),
+ (LPSTR) xsz)),
+ "FindTextNam: incorrect uHash parameter");
+
+ if (pfCaseChanged) {
+ *pfCaseChanged = FALSE; // assume we're not changing case
+ }
+ // Search the binary tree at the bucket for the given hash value, until
+ // we have checked all nodes with that hash value and none are the
+ // actual string.
+
+ hlnam = GetBucketOfHash(uHash);
+
+ while ((hlnam = FindHash(uHash, hlnam)) != HLNAM_Nil) {
+ // Found a node with the given hash value. Check to see if
+ // string is there.
+ qnam = QnamOfHlnam(hlnam);
+
+ qnamstr = QnamstrOfHlnam(hlnam);
+
+ if ( IsTextName(qnam) &&
+ (StriEq(xsz, (((NAM_STR *) qnamstr)->m_xsz)) == 0)) {
+ // Found the string, so we're done. However, if the case
+ // spelling is different, we need to store the new version;
+ // the lengths better be the same to change in place.
+ // Also note that we won't change the case if the "sticky bit"
+ // (m_fPreserveCase) is set, unless we want to override the name
+ // with another m_fPreserveCase name, in which case fPreserveCase
+ // will be TRUE.
+ //
+
+ qnam->m_fPreserveCase = fPreserveCase || qnam->m_fPreserveCase;
+
+ // If we have 2 DBCS strings of different length, don't overwrite the string.
+ if (xstrblen(qnamstr->m_xsz) != xstrblen(xsz))
+ return hlnam;
+
+
+ if (fChangeCase && xstrcmp(xsz, (((NAM_STR *) qnamstr)->m_xsz)) &&
+ ((!((NAM_INFO *)qnam)->m_fPreserveCase) || fPreserveCase)) {
+
+ xstrcpy((((NAM_STR *) qnamstr)->m_xsz), xsz);
+
+ if (pfCaseChanged) {
+ *pfCaseChanged = TRUE;
+ }
+ } // changed case
+
+ return hlnam;
+ }
+
+ // didn't find the string at this node, continue on to the
+ // right child (by convention, equal hash values sort to the
+ // right) and keep looking.
+ hlnam = qnam->m_hlnamRight;
+ }
+ return HLNAM_Nil;
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC NAMMGR::HlnamOfStrIfExist - get hlnam of string
+*Purpose:
+* Looks up the string in the name table.
+*
+*Entry:
+* xsz - string to look up
+*
+*Exit:
+* *phlnam - name handle
+* Return TIPERROR.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+HLNAM NAMMGR::HlnamOfStrIfExist(XSZ_CONST xsz)
+{
+ UINT uHash;
+
+ DebCheckState(0);
+
+ // Hash the string.
+ uHash = (UINT)WHashValOfLHashVal(LHashValOfNameSysA(Pgtlibole()->GetSyskind(),
+ Pgtlibole()->GetLcid(),
+ (LPSTR) xsz));
+
+ // Search the binary tree for the name.
+ return FindTextNam(xsz, uHash, FALSE, NULL, FALSE);
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC NAMMGR::HlnamOfStr - get hlnam of string, adding if necessary
+*Purpose:
+* Looks up the string in the name table, adding it if its
+* not there.
+*
+*Entry:
+* xsz - string to look up
+* fChangeCase - change the case of the xsz in the name table if it
+* already exists
+* bFlagsInitial - used to initialize qnam->m_bFlags
+*
+*Exit:
+* *phlnam - name handle
+* *pfCaseChanged - whether the case ogf the xsz for this name changed
+* if NULL then ignore
+* Return TIPERROR.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+
+#if OE_WIN32
+TIPERROR NAMMGR::HlnamOfStrW(const OLECHAR FAR* lpstrW, HLNAM * phlnam,
+ BOOL fChangeCase, BOOL *pfCaseChanged,
+ BOOL fPreserveCase, BOOL fAppToken)
+{
+ HRESULT hresult;
+ TIPERROR err;
+ LPSTR lpstrA;
+
+ if ((hresult = ConvertStringToA(lpstrW, &lpstrA)) != NOERROR) {
+ return TiperrOfHresult(hresult);
+ }
+ err = HlnamOfStr(lpstrA, phlnam, fChangeCase, pfCaseChanged, fPreserveCase, fAppToken);
+ ConvertStringFree(lpstrA);
+ return err;
+}
+#endif //OE_WIN32
+
+
+TIPERROR NAMMGR::HlnamOfStr(XSZ_CONST xsz, HLNAM * phlnam,
+ BOOL fChangeCase, BOOL *pfCaseChanged,
+ BOOL fPreserveCase, BOOL fAppToken)
+{
+ UINT uHash;
+ HLNAM hlnam;
+ HNAMSTR hnamstr;
+ UINT cbStr;
+ NAM_INFO * qnam;
+ NAM_STR * qnamstr;
+ TIPERROR err = TIPERR_None;
+ #define szCopy xsz // for OLE, we don't change the case,
+ // so we don't need to make a copy
+ BOOL fCaseChanged = FALSE;
+
+ DebCheckState(0);
+
+ // Hash the string.
+ uHash = (UINT)WHashValOfLHashVal(LHashValOfNameSysA(Pgtlibole()->GetSyskind(),
+ Pgtlibole()->GetLcid(),
+ (LPSTR) xsz));
+
+ // Search the binary tree for the name.
+ hlnam = FindTextNam(xsz, uHash, fChangeCase,
+ pfCaseChanged, fPreserveCase);
+
+ if (hlnam == HLNAM_Nil) {
+ // Not in the table: we must create a new table entry,
+ // and place it in the table.
+
+ // Unless we're creating this type library, we should NEVER end
+ // up adding a name to the typelib's name table. Typelib's that
+ // we're in the process of creating should have the modified bit set,
+ // and those that we're reading won't have the bit set.
+ DebAssert(m_pgtlibole->IsModified(), "Name allocated by lookup");
+
+
+ // cb has the number of bytes in this string.
+ cbStr = xstrblen0(szCopy);
+
+ // In Typelib we allocate the space for both the structures in the same
+ // segment. We allocate 1 chunk for both the logical structures.
+ // Note that phsyically they are in the same structure (NAM_INFO).
+
+ // Allocate new chunk for the name overhead.
+ IfErrGo(m_pbmNamInfo->AllocChunk(&hlnam, sizeof(NAM_INFO) + cbStr));
+
+ // hnammstr in typelib is same as hlnam
+ hnamstr = hlnam;
+
+
+
+ // Fill in the string entry.
+ qnam = (NAM_INFO *) QnamOfHlnam(hlnam);
+ qnam->m_uHash = uHash;
+ qnam->m_hlnamLeft = HLNAM_Nil;
+ qnam->m_hlnamRight = HLNAM_Nil;
+
+ // Get the pointer to the NAM_STR. We need to copy the string there.
+ qnamstr = QnamstrOfHlnam(hlnam);
+
+ xstrcpy(qnamstr->m_xsz, szCopy);
+
+ qnam->m_fAppToken = fAppToken;
+
+ // if the name was found in the typelib then set the Imported name bit
+ // to denote that this name is imported and hence should not change.
+ // Also if the fPreserveCase flag is set then we set the ImpNam bit
+ // so that we will preserve the case of this name. Note that the
+ // fCaseChanged flag is not the same as *pfCaseChanged which is an
+ // argument to this function.
+ //
+ qnam->m_fPreserveCase = (fCaseChanged || fPreserveCase);
+
+ // VBA2: need a constructor for NAM_INFO/NAM_STR.
+ // initialize other bits to 0
+ qnam->m_fGlobal = 0;
+ qnam->m_fMultiple = 0;
+ qnam->m_fAmbiguous = 0;
+ qnam->m_fNonParam = 0;
+
+ // Make sure that the ityp is invalid
+ qnam->m_ityp = NM_InvalidItyp;
+
+ // And add the string entry into the table.
+ AddEntry(hlnam); // (may invalidate qnam)
+
+ // return CaseChanged flag if asked for
+ if (pfCaseChanged)
+ *pfCaseChanged = fCaseChanged;
+
+
+Error:
+ ;
+
+ } // if hlnam == HLNAM_Nil
+
+ // Done.
+ *phlnam = hlnam;
+
+ return err;
+}
+#pragma code_seg( )
+
+
+
+
+
+/***
+*NAMMGR::StrOfHlnam - get a string from the name table
+*Purpose:
+* Returns the string associated with a given name.
+* The hlnam must be valid (won't return error for invalid hlnam)
+*
+*Entry:
+* hlnam - name to get
+* xsz - buffer to store name
+* cchMax - max chars to store (include terminator)
+*
+*Exit:
+* String stored into xsz.
+* Returns TIPERR_BufferToSmall if buffer was too small.
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CORE2)
+TIPERROR NAMMGR::StrOfHlnam(HLNAM hlnam, XSZ xsz, UINT cbMax) const
+{
+ NAM_STR *qnamstr;
+ UINT cbStr;
+
+ DebCheckState(0);
+ DebCheckHlnam(hlnam);
+
+
+ qnamstr = (NAM_STR *) QnamstrOfHlnam(hlnam);
+
+ cbStr = xstrblen0(qnamstr->m_xsz);
+ if (cbMax < cbStr)
+ return TIPERR_BufferTooSmall;
+
+ xstrcpy(xsz, qnamstr->m_xsz);
+
+ return TIPERR_None;
+}
+
+
+#if 0 //Dead Code: OE_WIN32
+TIPERROR NAMMGR::StrOfHlnamW(HLNAM hlnam, LPOLESTR xsz, UINT cchMax) const
+{
+ NAM_STR *qnamstr;
+ UINT cbStr;
+ int cchUnicode;
+
+ DebCheckState(0);
+ DebCheckHlnam(hlnam);
+
+
+ qnamstr = (NAM_STR *) QnamstrOfHlnam(hlnam);
+
+ cbStr = xstrblen0(qnamstr->m_xsz);
+
+ cchUnicode = MultiByteToWideChar(CP_ACP, 0, qnamstr->m_xsz, cbStr, xsz, cchMax);
+
+ if (cchUnicode == 0) // MBTWC failed
+ return TIPERR_BufferTooSmall; //CONSIDER: is this the right error for all cases?
+
+ return TIPERR_None;
+}
+#endif //OE_WIN32
+
+#pragma code_seg()
+
+
+/***
+*NAMMGR::GetHgnamOfStrLhash
+*Purpose:
+*
+*Entry:
+*
+*Exit:
+* phgnam :
+* TIPERROR : Error
+*
+***********************************************************************/
+TIPERROR NAMMGR::GetHgnamOfStrLhash(LPSTR szNameBuf,
+ ULONG lHashVal,
+ HGNAM *phgnam)
+{
+ ULONG lHashValSample;
+ HLNAM hlnam;
+ TIPERROR err = TIPERR_None;
+
+ lHashValSample = m_pgtlibole->GetSampleHashVal();
+ if (!IsHashValCompatible(lHashValSample, lHashVal)) {
+ // need to recalc hashval
+ lHashVal = LHashValOfNameSysA(Pgtlibole()->GetSyskind(),
+ Pgtlibole()->GetLcid(),
+ szNameBuf);
+ }
+ hlnam = FindTextNam(szNameBuf,
+ WHashValOfLHashVal(lHashVal),
+ FALSE,
+ NULL,
+ FALSE);
+
+ if (hlnam != HLNAM_Nil) {
+ IfErrRet(HgnamOfHlnam(hlnam, phgnam));
+ }
+ else {
+ *phgnam = HGNAM_Nil;
+ }
+ return err;
+}
+
+
+/***
+*NAMMGR::IsName - is this name defined in this nammgr.
+*Purpose:
+* Tests whether name is defined in library. Returns true if the passed
+* is name matches the name of any type, member name, or parameter name.
+* If a matching name is found then the szNameBuf is modified to so that
+* characters are cased according to how they appear in the library.
+*
+*Entry:
+* szNameBuf : String that needs to be searched.
+* wHashVal : Hashvalue of the string that needs to be searched.
+*
+*Exit:
+* pfName : True is the name was found in the Lib. else false.
+* TIPERROR : Error
+*
+***********************************************************************/
+TIPERROR NAMMGR::IsName(LPSTR szNameBuf, ULONG lHashVal, BOOL FAR *pfName)
+{
+ HLNAM hlnam;
+ USHORT wHashVal;
+ NAM_INFO *qnam;
+ NAM_STR *qnamstr;
+ TIPERROR err = TIPERR_None;
+
+ *(UNALIGNED BOOL FAR *)pfName = FALSE;
+
+ DebAssert(IsHashValCompatible(lHashVal, m_pgtlibole->GetSampleHashVal()),
+ " Hash value is not compatible ");
+
+
+ // The "0" param means don't look for application tokens.
+ // (These have NM_fAppToken set.)
+ //
+ wHashVal = WHashValOfLHashVal(lHashVal);
+
+ hlnam = FindTextNam(szNameBuf, wHashVal, FALSE, NULL, FALSE);
+
+ // if string was found then copy the string in szNameBuf
+ if (hlnam != HLNAM_Nil) {
+ qnam = QnamOfHlnam(hlnam);
+ qnamstr = QnamstrOfHlnam(hlnam);
+
+
+ // If this name is only a paramter, then pretend we didn't find it.
+ if (qnam->m_fNonParam) {
+ *(UNALIGNED BOOL FAR *)pfName = TRUE;
+
+ // DBCS strings can be of different lengths and still match.
+ // (as crazy as it sounds)
+ // If this is true, don't modify szNameBuf.
+ if(xstrblen(szNameBuf) != xstrblen(qnamstr->m_xsz))
+ return TIPERR_None;
+
+ xstrcpy(szNameBuf, qnamstr->m_xsz);
+ }
+ }
+
+ return TIPERR_None;
+}
+
+
+/***
+*NAMMGR::BstrOfHlnam - get a bstr from the name table
+*Purpose:
+* Returns a BSTR copy of the string associated with a given name.
+* The hlnam must be valid (won't return error for invalid hlnam)
+*
+*Entry:
+* hlnam - name to get
+* cchMax - max chars to store (include terminator)
+*
+*Exit:
+* Returns TIPERR_None and sets *pbstr to a copy of the string if
+* successful. Otherwise, returns TIPERR_OutOfMemory.
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR NAMMGR::BstrOfHlnam(HLNAM hlnam, BSTRA *pbstr) const
+{
+ BSTRA bstr;
+
+ DebCheckState(0);
+ DebCheckHlnam(hlnam);
+
+ bstr = AllocBstrA(((NAM_STR *)QnamstrOfHlnam(hlnam))->m_xsz);
+ if (bstr == NULL)
+ return TIPERR_OutOfMemory;
+
+ *pbstr = bstr;
+ return TIPERR_None;
+}
+
+#if OE_WIN32
+TIPERROR NAMMGR::BstrWOfHlnam(HLNAM hlnam, BSTR *pbstr) const
+{
+ BSTR bstr;
+ int cchUnicode;
+ char *sz;
+ int cbAnsi;
+
+ DebCheckState(0);
+ DebCheckHlnam(hlnam);
+
+ sz = ((NAM_STR *)QnamstrOfHlnam(hlnam))->m_xsz;
+ cbAnsi = xstrblen(sz);
+
+ cchUnicode = MultiByteToWideChar(CP_ACP, 0, sz, cbAnsi, NULL, 0);
+ if (cchUnicode == 0 && cbAnsi != 0)
+ return TIPERR_OutOfMemory;
+
+ bstr = AllocBstrLen(NULL, cchUnicode);
+ if (bstr == NULL)
+ return TIPERR_OutOfMemory;
+
+ cchUnicode = MultiByteToWideChar(CP_ACP, 0, sz, cbAnsi, bstr, cchUnicode);
+ DebAssert(cchUnicode || cbAnsi == 0, "translation failed");
+
+ *pbstr = bstr;
+ return TIPERR_None;
+}
+#endif //OE_WIN32
+
+#pragma code_seg( )
+
+
+#if 0 //Dead Code
+/***
+*NAMMGR::CbOfHlnam - Returns size (# of bytes) of string(nam).
+*Purpose:
+* Returns the size of the string associated with a given name.
+* The hlnam must be valid (won't return error for invalid hlnam)
+*
+*Entry:
+* hlnam - name whose size is to be returned
+*
+*Exit:
+* Returns size of the string
+*
+***********************************************************************/
+#pragma code_seg(CS_CORE2)
+UINT NAMMGR::CbOfHlnam(HLNAM hlnam) const
+{
+ return (UINT) (xstrblen0((QnamstrOfHlnam(hlnam))->m_xsz));
+}
+#pragma code_seg()
+#endif //0
+
+
+
+
+
+/***
+*PUBLIC NAMMGR::HgnamOfHlnam - get hgnam from an hlnam
+*Purpose:
+* Gets a global per-process name handle from a local name handle
+* to use for comparing name entries across class boundaries.
+*
+*Entry:
+* hlnam - hlnam to get hgnam of
+*
+*Exit:
+* *phgnam the hgnam corresponding to this local name. It can be
+* relied upon that hgnam & 0xFFFF == HashOfHlnam(hlnam).
+*
+*
+***********************************************************************/
+#pragma code_seg( CS_CORE2 )
+TIPERROR NAMMGR::HgnamOfHlnam(HLNAM hlnam, HGNAM * phgnam)
+{
+ NAM_INFO * qnam;
+ UINT uHash; // hash value being searched for.
+
+ DebCheckState(0);
+
+ // Make sure we're dealing with an unlocalized name.
+ qnam = QnamOfHlnam(hlnam);
+
+ uHash = WHashValOfLHashVal(HashOfHlnam(hlnam));
+
+ *phgnam = ((HGNAM) ((USHORT)hlnam) << 16) + uHash;
+ return TIPERR_None;
+}
+#pragma code_seg( )
+
+/***
+*PUBLIC NAMMGR::LpstrOfHgnam - get pointer to the text associated with an HGNAM.
+*Purpose:
+* Returns the string associated with an HGNAM.
+*
+*Implementaion Notes:
+* Returns a pointer directly into the name table.
+* DANGEROUS -- Callers must guarantee that heap movement won't occur
+* before this pointer is used.
+*
+*Entry:
+* hgnam - hgnam to look up. Must be a hgnam earlier returned.
+*
+*Exit:
+* returns the pointer to the string data (WARNING -- SHORT TERM!)
+*
+***********************************************************************/
+LPSTR NAMMGR::LpstrOfHgnam(HGNAM hgnam) const
+{
+
+ return (LPSTR) QnamstrOfHlnam(HlnamOfHgnam(hgnam))->m_xsz;
+}
+
+
+
+
+
+
+
+/***
+*PUBLIC HgnamOfStr - make HGNAM from a string.
+*Purpose:
+* This function makes a HGNAM directly from a string. It is provided
+* for class providers which don't use a local name table. It works
+* by using the static name table NAMMGR::m_nmGlobalDefault to store
+* the name.
+*
+*Note:
+* This function is a friend of NAMMGR.
+*
+*Entry:
+* xsz - string to convert to HGNAM
+*
+*Exit:
+* *phgnam - the name of the string.
+* Returns SCODE;
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR NAMMGR::HgnamOfStr(LPSTR szName, HGNAM FAR * phgnam)
+{
+ TIPERROR err;
+ HLNAM hlnam;
+
+ // Add as hlnam, convert to hgnam.
+ if ((err = HlnamOfStr(szName, &hlnam, FALSE, NULL)) ||
+ (err = HgnamOfHlnam(hlnam, phgnam))) {
+ return err;
+ }
+
+ return TIPERR_None;
+}
+#pragma code_seg( )
+
+
+
+
+
+
+
+/***
+*PUBLIC StrCmp(LPSTR szStr1, LPSTR szStr2)
+*Purpose: Compares two character strings of the same locale according to the
+* LCID stored .
+*Note : locale-specific string equality (only)
+* case-insensitive, according to codepage/locale specified.
+*
+*
+*Entry
+* szStr1, szStr2 strings that needs to be compared.
+*
+*Exit:
+* returns 0 if equal,
+*
+* Note:- This routine needs to be really fast.
+***********************************************************************/
+#pragma code_seg( CS_CORE2 )
+INT NAMMGR::StriEq(XSZ_CONST szStr1, XSZ_CONST szStr2)
+{
+ if(!m_pgtlibole->IsProjectDBCS()) {
+
+ UINT uCount;
+
+ // Make sure the sort keys have been generated
+ if (!m_fSortKeys) {
+ TIPERROR err;
+
+ // This should never fail.
+ err = GenerateSortKey();
+ DebAssert(err == TIPERR_None, "Bad error.");
+ }
+
+ // compare strings based on the the sort key cached in m_rgchTable.
+ if ((uCount = strlen(szStr1)) != xstrlen(szStr2))
+ return 1;
+
+ for(;
+ ((*(m_rguSortKeys + (0x00ff & (*szStr1))) ==
+ *(m_rguSortKeys + (0x00ff & (*szStr2)))) && uCount);
+
+ szStr1++, szStr2++, uCount--);
+ // END of FOR loop
+
+ // if all the characters matched(i.e. uCount == 0) then return 0
+ // (i.e. both strings are equal).
+ if (uCount)
+ return 1;
+ else
+ return 0;
+
+ INT nRetCode = 0;
+
+ } else {
+ return !(CompareStringA(m_pgtlibole->GetLcid(),
+ NORM_IGNORECASE |
+ NORM_IGNOREWIDTH |
+ NORM_IGNOREKANATYPE,
+ (LPSTR)szStr1,
+ -1,
+ (LPSTR)szStr2, -1)
+ == 2);
+ }
+}
+#pragma code_seg( )
+
+
+
+/***
+*PUBLIC GenerateSortKey()
+*Purpose: Initialize the table for Accent insensitive comparision.
+*
+*Entry
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_CORE2)
+TIPERROR NAMMGR::GenerateSortKey()
+{
+ BYTE rgch[256];
+ UINT i;
+
+ GetInsensitiveCompTbl(m_pgtlibole->GetLcid(), m_pgtlibole->GetSyskind(), (LPSTR)rgch );
+
+ for (i = 0; i < 256; m_rguSortKeys[i] = (UINT)rgch[i], i++);
+
+ // Mark the table as having been built.
+ m_fSortKeys = TRUE;
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC HashOfHlnam - retrieve hash value stored in the hlnam entry
+*Purpose:
+* Returns the the hash value that is stored in the name entry corresponding
+* to this hlnam. Actually we store only the whashVal for space optimization.
+*
+*Entry:
+* hlnam - name to get hash value of
+*
+*Exit:
+* Returns the hash value this name has.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+ULONG NAMMGR::HashOfHlnam(HLNAM hlnam)
+{
+ return (ULONG) ( (ULONG) (m_pgtlibole->GetSampleHashVal() & 0xffff0000) |
+ (ULONG) ((USHORT)QnamOfHlnam(hlnam)->m_uHash) ) ;
+}
+#pragma code_seg( )
+
+
+
+
+
+
+/////////////////////////////////////////////////////////
+// BELOW HERE IS DEBUGGING CODE ONLY!
+/////////////////////////////////////////////////////////
+
+#if ID_DEBUG
+
+/***
+*DebCheckState() - check state of this table.
+*Purpose:
+* Checks the current state of the table.
+*
+*Entry:
+* uLevel - 0 - quick check
+* 1 - recursive check all entries too.
+*
+*Exit:
+* None. Asserts if things are wrong.
+*
+***********************************************************************/
+
+void NAMMGR::DebCheckState(UINT uLevel) const
+{
+ UINT i;
+
+ DebAssert(m_fInit, "NAMMGR::DebCheckState: not initialized");
+
+ // Check the blkmgrs.
+ m_bm.DebCheckState(uLevel);
+ m_pbmNamInfo->DebCheckState(uLevel);
+
+ if (uLevel > 0) {
+ for (i = 0; i < NM_cBuckets; ++i) {
+ DebCheckHlnamRecurse(GetBucketOfHash(i));
+ }
+ }
+}
+
+
+
+
+
+/***
+*DebCheckHlnam - check that an hlnam is valid.
+*Purpose:
+* Checks to see that an hlnam is valid. HLNAM_Nil is a valid
+* value for this function.
+*
+*Entry:
+* hlnam - name handle to check
+*
+*Exit:
+* None. Assert if hlnam is invalid.
+*
+***********************************************************************/
+
+void NAMMGR::DebCheckHlnam(HLNAM hlnam) const
+{
+
+ DebAssert(hlnam == HLNAM_Nil || m_pbmNamInfo->QtrOfHandle(hlnam) != NULL,
+ "DebCheckHlnam: invalid hlnam");
+ if (hlnam == HLNAM_Nil) {
+ return;
+ }
+}
+
+
+/***
+*DebCheckHlnamRecurse - check that an hlnam is valid, and its descendants.
+*Purpose:
+* Checks to see that an hlnam is valid. HLNAM_Nil is a valid
+* value for this function. The descendants of this hlnam are checked also.
+*
+*Entry:
+* hlnam - name handle to check
+*
+*Exit:
+* None. Assert if hlnam is invalid.
+*
+***********************************************************************/
+
+void NAMMGR::DebCheckHlnamRecurse(HLNAM hlnam) const
+{
+ DebCheckHlnam(hlnam);
+
+ if (hlnam != HLNAM_Nil) {
+ DebCheckHlnamRecurse(QnamOfHlnam(hlnam)->m_hlnamLeft);
+ DebCheckHlnamRecurse(QnamOfHlnam(hlnam)->m_hlnamRight);
+ }
+}
+
+
+#endif // ID_DEBUG
+
+// catch global constructors and destructors
+#pragma code_seg(CS_INIT)
diff --git a/private/oleauto/src/typelib/nammgr.hxx b/private/oleauto/src/typelib/nammgr.hxx
new file mode 100644
index 000000000..8925b8a08
--- /dev/null
+++ b/private/oleauto/src/typelib/nammgr.hxx
@@ -0,0 +1,621 @@
+/***
+*nammgr.hxx - Name Manager
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* The Name Manager handles the hashing and storing of names. Each
+* class has its own name manager. See \silver\doc\ic\nammgr.doc for
+* information on the name manager.
+*
+*Revision History:
+*
+* 22-Jan-91 petergo: Created.
+* [01] 25-Feb-91 petergo: Now uses heap/block manager for mem mgt.
+* [02] 13-Jun-91 petergo: Updated for new protocols.
+* [03] 18-Mar-92 ilanc: Fixed release def of DebDeleteGlobalDefault()
+* [04] 15-May-92 w-peterh: added case change parameters to HlnamOfStr
+* [05] 15-Nov-92 RajivK: added isStrDef() for Edit & Continue stuff
+* [06] 19-Nov-92 RajivK: added CbOfHlnam() and CchOfHgnam();
+* [07] 31-Dec-92 RajivK: Support for code page conversion.
+* [08] 08-Jan-93 RajivK: Support for Code Resource on Mac
+* [09] 08-Jan-93 RajivK: Fixed some undone(s)
+* [10] 27-Feb-93 RajivK: added the data member m_lcid
+* [11] 01-Oct-93 StevenL: Don't make different hlnams for bracketed ids
+*
+*Implementation Notes:
+* See nammgr.cxx.
+*
+*****************************************************************************/
+
+#ifndef NAMMGR_HXX_INCLUDED
+#define NAMMGR_HXX_INCLUDED
+
+#include "cltypes.hxx"
+
+class STREAM;
+class GEN_PROJECT;
+class GenericTypeLibOLE;
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szNAMMGR_HXX)
+#define SZ_FILE_NAME g_szNAMMGR_HXX
+#endif
+
+
+// This constant defines the number of buckets used in the hash
+// table. Each bucket uses 2 bytes.
+// For testing purposes, it is useful to set this number very
+// low to force many bucket collisions.
+const UINT NM_cBuckets = 256;
+
+class DYN_TYPEROOT;
+
+
+
+// These structs define the layout of name structure which can
+// be stored in the name table. The following 2 struct(s) are logically
+// one struct. We have split it into two structs to separate the strings that
+// from the rest of the NamMgr information. This was done to increase the
+// capacity of the name table.
+
+// Over head of storing a name.
+// Name :- nam. Size: 10 bytes.
+struct NAM_INFO
+{
+ USHORT m_uHash; // Hash value of the string.
+ // NOTE:- we only cache the low 2 bytes. When we
+ // have to return a hash value then we form
+ // the 4 byte hash value and return it.
+ sHLNAM m_hlnamLeft; // Left child in binary tree
+ sHLNAM m_hlnamRight; // Right child in binary tree
+
+
+ USHORT m_fAppToken:1; // Used as a dirty bit--we set it if the
+ // name has ever been used as an app token.
+ USHORT m_fPreserveCase:1; // Don't change the case of this name
+ USHORT m_fGlobal:1; // This name can be bound to in an unqualified way
+ USHORT m_fMultiple:1; // There are multiple instances of this name
+ USHORT m_fAmbiguous:1; // There exists two global instances of this name
+ USHORT m_fNonParam:1; // There exists a non-parameter instance of name
+ USHORT m_ityp:10; // this name's index into the typeinfos
+
+};
+// Unlocalized text name
+struct NAM_STR : public NAM_INFO
+{
+ CHAR m_xsz[1]; // the name -- variable length extending beyond
+ // this structure.
+};
+
+
+// This is an invalid value of ityp
+#define NM_InvalidItyp 0x03FF
+
+// This defines the layout out a NAM_INFO for serialization;
+// It must be updated if new members are added to the structures.
+#define NM_NamInfoLayout "ssss"
+
+
+class NAMMGR;
+
+/***
+*class NAMMGR - 'nammgr': Name manager
+*Purpose:
+* The class implements the name manager. Each project has its own
+* name manager, which is created and owned by GTLIBOLE .
+*
+***********************************************************************/
+
+class NAMMGR
+{
+public:
+ NAMMGR();
+ ~NAMMGR();
+
+ TIPERROR Init(SHEAP_MGR * psheapmgr, DYN_TYPEROOT *pdtroot=NULL);
+ nonvirt TIPERROR HgnamOfStr(LPSTR szName, HGNAM FAR * phgnam);
+ nonvirt TIPERROR HlnamOfStr(XSZ_CONST sz, HLNAM *phlnam,
+ BOOL fChangeCase, BOOL *pfCaseChanged,
+ BOOL fPreserveCase = FALSE,
+ BOOL fAppToken = FALSE);
+#if OE_WIN32
+ nonvirt TIPERROR HlnamOfStrW(const OLECHAR FAR* lpstrW, HLNAM *phlnam,
+ BOOL fChangeCase, BOOL *pfCaseChanged,
+ BOOL fPreserveCase = FALSE,
+ BOOL fAppToken = FALSE);
+#else //OE_WIN32
+ #define HlnamOfStrW HlnamOfStr
+#endif //OE_WIN32
+ nonvirt HLNAM HlnamOfStrIfExist(XSZ_CONST xsz);
+ nonvirt TIPERROR StrOfHlnam(HLNAM hlnam, XSZ sz, UINT cbMax) const;
+#if 0
+#if OE_WIN32
+ nonvirt TIPERROR StrOfHlnamW(HLNAM hlnam, LPOLESTR sz, UINT cbMax) const;
+#else
+ #define StrOfHlnamW StrOfHlnam
+#endif //OE_WIN32
+#endif //0
+ nonvirt TIPERROR BstrOfHlnam(HLNAM hlnam, BSTRA *pbstr) const;
+#if OE_WIN32
+ nonvirt TIPERROR BstrWOfHlnam(HLNAM hlnam, BSTR *pbstr) const;
+#else //OE_WIN32
+ #define BstrWOfHlnam BstrOfHlnam
+#endif //OE_WIN32
+ nonvirt TIPERROR HgnamOfHlnam(HLNAM hlnam, HGNAM *hgnam);
+ nonvirt HLNAM HlnamOfHgnam(HGNAM hgnam) const;
+ nonvirt ULONG HashOfHlnam(HLNAM hlnam);
+ nonvirt BOOL IsStrDef(XSZ_CONST xsz);
+ nonvirt TIPERROR Read(STREAM *psstrm);
+ nonvirt TIPERROR Write(STREAM *psstrm);
+#if 0
+ nonvirt UINT CbOfHlnam(HLNAM hlnam) const;
+#endif
+ nonvirt TIPERROR CchOfHgnam(HGNAM hgnam, UINT *pcchMax) const;
+ nonvirt TIPERROR IsName(LPSTR szNameBuf, ULONG lHashVal, BOOL FAR *pfName);
+
+ nonvirt BOOL IsAppToken(HLNAM hlnam) const;
+ nonvirt BOOL IsCasePreserved(HLNAM hlnam) const;
+ nonvirt BOOL IsGlobal(HLNAM hlnam) const;
+ nonvirt BOOL IsMultiple(HLNAM hlnam) const;
+ nonvirt BOOL IsAmbiguous(HLNAM hlnam) const;
+ nonvirt BOOL IsNonParam(HLNAM hlnam) const;
+
+ nonvirt void SetAppToken(HLNAM hlnam, BOOL fValue);
+ nonvirt void SetPreserveCase(HLNAM hlnam, BOOL fValue);
+ nonvirt void SetGlobal(HLNAM hlnam, BOOL fValue);
+ nonvirt void SetMultiple(HLNAM hlnam, BOOL fValue);
+ nonvirt void SetAmbiguous(HLNAM hlnam, BOOL fValue);
+ nonvirt void SetNonParam(HLNAM hlnam, BOOL fValue);
+
+ nonvirt BOOL IsValidItyp(HLNAM hlnam) const;
+ nonvirt UINT ItypOfHlnam(HLNAM hlnam) const;
+ nonvirt void SetItypOfHlnam(HLNAM hlnam, UINT ityp);
+ nonvirt UINT IndexOfHlnam(HLNAM hlnam) const;
+
+ TIPERROR StrOfHgnam(HGNAM hgnam, XSZ sz, UINT cchMax);
+ nonvirt LPSTR LpstrOfHgnam(HGNAM hgnam) const;
+
+ TIPERROR GetHgnamOfStrLhash(XSZ xsz, ULONG lHashVal, HGNAM *phgnam);
+
+ nonvirt ULONG GetSize();
+ // function for code page conversion
+ nonvirt TIPERROR ConvertCodePage();
+ nonvirt LCID GetLcid();
+ nonvirt INT StriEq(XSZ_CONST szStr1, XSZ_CONST szStr2);
+ nonvirt TIPERROR GenerateSortKey();
+
+ // Has nammgr been initialized?
+ nonvirt BOOL IsValid() const;
+ nonvirt TIPERROR SetGtlibole(GenericTypeLibOLE *pgtlibole);
+ nonvirt GenericTypeLibOLE * Pgtlibole();
+
+
+#if 0
+ // Clean up the nammgr entries
+ nonvirt void CleanNames();
+#endif
+
+#if ID_DEBUG
+ nonvirt void DebCheckState(UINT uLevel) const;
+ nonvirt void DebCheckHlnam(HLNAM hlnam) const;
+ nonvirt void DebCheckHlnamRecurse(HLNAM hlnam) const;
+#else
+ // Make check functions No-op in release version
+ inline void NAMMGR::DebCheckState(UINT uLevel) const {}
+ inline void NAMMGR::DebCheckHlnam(HLNAM hlnam) const {}
+ inline void NAMMGR::DebCheckHlnamRecurse(HLNAM hlnam) const {}
+#endif // ID_DEBUG
+
+
+#if ID_DEBUG
+ nonvirt ULONG DebShowSize();
+#else
+ nonvirt VOID DebShowSize() {}
+#endif
+
+protected:
+ nonvirt VOID RehashNodes(HLNAM hlnamRoot);
+
+private:
+
+ BLK_MGR m_bm; // the block manager to manage memory
+ BLK_MGR *m_pbmNamInfo; // to store the over head of each name.
+
+
+ sHCHUNK m_hchunkBucketTbl; // hchunk of the bucket table.
+
+ BOOL m_fInit:1; // Init() has been called?
+ BOOL m_fSortKeys:1; // Sort keys table generated?
+ BOOL m_fOLBKwordInit:1; // OLBKword table has been inited
+ // BOOL m_unused:13;
+
+
+ GenericTypeLibOLE *m_pgtlibole; // pointer to the containing Project
+
+
+ UINT m_rguSortKeys[256];
+
+ nonvirt BOOL IsTextName(NAM_INFO * pnam) const;
+ nonvirt NAM_INFO* QnamOfHlnam(HLNAM hlnam) const;
+ nonvirt NAM_STR* QnamstrOfHlnam(HLNAM hlnam) const;
+ nonvirt sHLNAM * RqhlnamBucketTbl() const;
+ nonvirt HLNAM GetBucketOfHash(UINT uHash) const;
+ nonvirt void SetBucketOfHash(UINT uHash, HLNAM hlnam);
+ nonvirt HLNAM FindHash(UINT uHashFind, HLNAM hlnam) const;
+ nonvirt HLNAM FindTextNam(XSZ_CONST sz, UINT uHash,
+ BOOL fChangeCase, BOOL *pfCaseChanged,
+ BOOL fPreserveCase);
+ nonvirt void AddEntry(HLNAM hlnamNew);
+#if 0
+ nonvirt void CleanHlnam(HLNAM hlnam);
+#endif
+ nonvirt void ForEachName(void (NAMMGR::*)(HLNAM), BOOL fBefore);
+ nonvirt void ForEachDescendant(HLNAM hlnamRoot,
+ void (NAMMGR::*pfn)(HLNAM),
+ BOOL fBefore);
+ TIPERROR GetInfoOfHgnam(HGNAM hgnam, XSZ sz, UINT *cchMax) const;
+
+#if HP_BIGENDIAN
+ nonvirt void SwapBytes();
+ nonvirt void SwapBytesBack();
+ nonvirt void SwapHlnamBytes(HLNAM hlnam);
+#endif //HP_BIGENDIAN
+
+#ifdef NAMMGR_VTABLE
+#pragma VTABLE_EXPORT
+#endif
+};
+
+
+
+
+/***
+*IsTextName - checks to see if name is normal text name
+*Purpose:
+* Determines if the give name structure refers to a text name
+* which is not a localized name.
+*
+*Entry:
+* NAM * pnam - points to base part of a name structure.
+*
+*Exit:
+* return TRUE if is a text name.
+*
+******************************************************************************/
+
+inline BOOL NAMMGR::IsTextName(NAM_INFO * pnam) const
+{
+ // Now have only text names!
+ return TRUE;
+}
+
+
+/***
+*IndexOfHlnam
+*Purpose:
+* Computes the index of the given hlnam in the name table. This is
+* primarily used to compute hash values for the various hash
+* tables.
+*
+*Entry:
+* hlnam - the hlnam to compute the index of.
+*
+*Exit:
+* return index.
+*
+******************************************************************************/
+
+inline UINT NAMMGR::IndexOfHlnam(HLNAM hlnam) const
+{
+ DebAssert(hlnam % 2 == 0, "Bad hlnam!");
+ return hlnam / 2; // We use only the upper 15 bits
+}
+
+
+
+#if 0
+/***
+*GetLcid()
+*Purpose:
+* returns pointer to local code for the nammgr/project
+*
+*Entry:
+*
+*Exit:
+* returns pointer to the DYN_TYPEROOT;
+*
+*
+******************************************************************************/
+inline LCID NAMMGR::GetLcid()
+{
+ return m_pgtlib->GetLcid();
+}
+#endif //0
+
+
+/***
+*Pgtlibole()
+*Purpose:
+* returns pointer to the project that owns this nammgr.
+*
+*Entry:
+*
+*Exit:
+*
+******************************************************************************/
+inline GenericTypeLibOLE * NAMMGR::Pgtlibole()
+{
+ return m_pgtlibole;
+}
+
+
+/***
+*RqhlnamBucketTbl() - Get pointer to bucket table
+*Purpose:
+* Returns a pointer to the bucket table of the name mgr.
+*
+*Entry:
+* None.
+*
+*Exit:
+* Returns a pointer to the bucket table. The pointer is only valid
+* for a short time.
+*
+***********************************************************************/
+
+inline sHLNAM * NAMMGR::RqhlnamBucketTbl() const
+{
+ return (sHLNAM *) m_bm.QtrOfHandle(m_hchunkBucketTbl);
+}
+
+
+
+/***
+*QnamOfHlnam - gets a pointer to the NAM_INFO instance from an hlnam
+*Purpose:
+* From an hlnam, gets a pointer to the NAM instance which that
+* hlnam refers to. Since hlnams are just offsets into the name
+* table, this is a simple conversion of an offset to pointer.
+*
+* Be careful! The pointer returned by this function will be invalidated
+* when any name is added to the name table, so don't hold on to
+* it too long.
+*
+*Entry:
+* hlnam - hlnam to get pointer to
+*
+*Exit:
+* Returns a pointer to the NAM_INFO structure associated with this hlnam.
+*
+***********************************************************************/
+
+inline NAM_INFO * NAMMGR::QnamOfHlnam(HLNAM hlnam) const
+{
+ DebCheckHlnam(hlnam);
+ DebAssert(hlnam != HLNAM_Nil, "QnamOfHlnam: nil hlnam");
+
+ return (NAM_INFO *) m_pbmNamInfo->QtrOfHandle(hlnam);
+}
+
+
+
+/***
+*QnamstrOfHlnam - gets a pointer to the NAM_STR instance for a hlnam
+*Purpose:
+* From an hlnam, gets a pointer to the NAM_STR.
+*
+* Be careful! The pointer returned by this function will be invalidated
+* when any name is added to the name table, so don't hold on to
+* it too long.
+*
+*NOTE:- For ole this is same as QnamOfHlnam();
+*
+*Entry:
+* hlnam - hlnam for which we have to return the pointer to the NAM_STR
+*
+*Exit:
+* Returns a pointer to the NAM_STR structure associated with this hlnam.
+*
+***********************************************************************/
+
+inline NAM_STR * NAMMGR::QnamstrOfHlnam(HLNAM hlnam) const
+{
+ return (NAM_STR *) QnamOfHlnam(hlnam);
+}
+
+/***
+*PUBLIC IsXXX - returns the value of the given flag
+*Purpose:
+* Returns the flags byte of the hlnam.
+*
+*Entry:
+* hlnam - name handle
+*
+*Exit:
+* returns flag.
+***********************************************************************/
+
+inline BOOL NAMMGR::IsAppToken(HLNAM hlnam) const
+{
+ DebAssert(IsTextName(QnamOfHlnam(hlnam)), "not a text name");
+ return ((NAM_INFO *)QnamOfHlnam(hlnam))->m_fAppToken;
+}
+
+inline BOOL NAMMGR::IsCasePreserved(HLNAM hlnam) const
+{
+ DebAssert(IsTextName(QnamOfHlnam(hlnam)), "not a text name");
+ return ((NAM_INFO *)QnamOfHlnam(hlnam))->m_fPreserveCase;
+}
+
+inline BOOL NAMMGR::IsGlobal(HLNAM hlnam) const
+{
+ DebAssert(IsTextName(QnamOfHlnam(hlnam)), "not a text name");
+ return ((NAM_INFO *)QnamOfHlnam(hlnam))->m_fGlobal;
+}
+
+inline BOOL NAMMGR::IsMultiple(HLNAM hlnam) const
+{
+ DebAssert(IsTextName(QnamOfHlnam(hlnam)), "not a text name");
+ return ((NAM_INFO *)QnamOfHlnam(hlnam))->m_fMultiple;
+}
+
+inline BOOL NAMMGR::IsAmbiguous(HLNAM hlnam) const
+{
+ DebAssert(IsTextName(QnamOfHlnam(hlnam)), "not a text name");
+ return ((NAM_INFO *)QnamOfHlnam(hlnam))->m_fAmbiguous;
+}
+
+inline BOOL NAMMGR::IsNonParam(HLNAM hlnam) const
+{
+ DebAssert(IsTextName(QnamOfHlnam(hlnam)), "not a text name");
+ return ((NAM_INFO *)QnamOfHlnam(hlnam))->m_fNonParam;
+}
+
+/***
+*PUBLIC SetXXX - set the value of the given flag
+*Purpose:
+* Set the value of the given flag
+*
+*Entry:
+* hlnam - name handle
+* fValue - what to set the flag to
+*
+*Exit:
+*
+***********************************************************************/
+
+inline void NAMMGR::SetAppToken(HLNAM hlnam, BOOL fValue)
+{
+ DebAssert(IsTextName(QnamOfHlnam(hlnam)), "not a text name");
+ ((NAM_INFO *)QnamOfHlnam(hlnam))->m_fAppToken = fValue;
+}
+
+inline void NAMMGR::SetPreserveCase(HLNAM hlnam, BOOL fValue)
+{
+ DebAssert(IsTextName(QnamOfHlnam(hlnam)), "not a text name");
+ ((NAM_INFO *)QnamOfHlnam(hlnam))->m_fPreserveCase = fValue;
+}
+
+inline void NAMMGR::SetGlobal(HLNAM hlnam, BOOL fValue)
+{
+ DebAssert(IsTextName(QnamOfHlnam(hlnam)), "not a text name");
+ ((NAM_INFO *)QnamOfHlnam(hlnam))->m_fGlobal = fValue;
+}
+
+inline void NAMMGR::SetMultiple(HLNAM hlnam, BOOL fValue)
+{
+ DebAssert(IsTextName(QnamOfHlnam(hlnam)), "not a text name");
+ ((NAM_INFO *)QnamOfHlnam(hlnam))->m_fMultiple = fValue;
+}
+
+inline void NAMMGR::SetAmbiguous(HLNAM hlnam, BOOL fValue)
+{
+ DebAssert(IsTextName(QnamOfHlnam(hlnam)), "not a text name");
+ ((NAM_INFO *)QnamOfHlnam(hlnam))->m_fAmbiguous = fValue;
+}
+
+inline void NAMMGR::SetNonParam(HLNAM hlnam, BOOL fValue)
+{
+ DebAssert(IsTextName(QnamOfHlnam(hlnam)), "not a text name");
+ ((NAM_INFO *)QnamOfHlnam(hlnam))->m_fNonParam = fValue;
+}
+
+
+/***
+*PUBLIC IsValidITyp - Returns whether the ityp is valid
+*Purpose:
+* Returns the ityp of the hlnam
+*
+*Entry:
+* hlnam - name handle
+*
+*Exit:
+* returns bool
+***********************************************************************/
+
+inline BOOL NAMMGR::IsValidItyp(HLNAM hlnam) const
+{
+ DebAssert(IsTextName(QnamOfHlnam(hlnam)), "not a text name");
+ return ((NAM_INFO *)QnamOfHlnam(hlnam))->m_ityp != NM_InvalidItyp;
+}
+
+/***
+*PUBLIC ItypOfHlnam - reads ityp of an hlnam
+*Purpose:
+* Returns the ityp of the hlnam
+*
+*Entry:
+* hlnam - name handle
+*
+*Exit:
+* returns ityp
+***********************************************************************/
+
+inline UINT NAMMGR::ItypOfHlnam(HLNAM hlnam) const
+{
+ DebAssert(IsTextName(QnamOfHlnam(hlnam)), "not a text name");
+ return (UINT)((NAM_INFO *)QnamOfHlnam(hlnam))->m_ityp;
+}
+
+/***
+*PUBLIC SetItypOfHlnam - Sets the ityp of the given hlnam
+*Purpose:
+* Set the ityp of the given hlnam
+*
+*Entry:
+* hlnam - name handle
+* ityp - the index to the TypeInfo
+*
+*Exit:
+* None.
+***********************************************************************/
+
+inline void NAMMGR::SetItypOfHlnam(HLNAM hlnam, UINT ityp)
+{
+ DebAssert(IsTextName(QnamOfHlnam(hlnam)), "not a text name");
+ DebAssert(ityp < NM_InvalidItyp, "ityp is too large");
+
+ ((NAM_INFO *)QnamOfHlnam(hlnam))->m_ityp = ityp;
+}
+
+/***
+*PUBLIC HlnamOfHgnam - extracts hlnam from hgnam
+*Purpose:
+* Extracts hlnam from hgnam. Guaranteed to be the hiword.
+*
+*Entry:
+*
+*Exit:
+* HLNAM
+*
+***********************************************************************/
+
+inline HLNAM NAMMGR::HlnamOfHgnam(HGNAM hgnam) const
+{
+ return (HLNAM)(USHORT)(hgnam >> 16);
+}
+
+
+/***
+*PUBLIC IsValid - tests if nammgr valid
+*Purpose:
+* Tests if nammgr valid, i.e. has been initialized.
+*
+*Entry:
+*
+*Exit:
+* TRUE if has been initialized, else false.
+*
+***********************************************************************/
+
+inline BOOL NAMMGR::IsValid() const
+{
+ return (BOOL)m_fInit;
+}
+
+
+#endif // ! NAMMGR_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/ncache.hxx b/private/oleauto/src/typelib/ncache.hxx
new file mode 100644
index 000000000..d06e5cf06
--- /dev/null
+++ b/private/oleauto/src/typelib/ncache.hxx
@@ -0,0 +1,287 @@
+/***
+*ncache.hxx - NAME_CACHE header file
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* NAME_CACHE class used for project-level binding
+*
+*Revision History:
+*
+* 01-Jun-92 ilanc: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#ifndef NAME_CACHE_HXX_INCLUDED
+#define NAME_CACHE_HXX_INCLUDED
+
+#include <limits.h> // for CHAR_BIT
+#include "xstring.h" // for memset
+#include "cltypes.hxx"
+// #include "clutil.hxx"
+
+
+// WARMING: this is really from clutil.hxx
+// but we include this explicitly because we don't
+// want header files to depend on clutil.hxx cos it
+// has the effect of requiring hxxtoinc to know about
+// any global symbols it (clutil.hxx) defines.
+//
+inline UINT HashOfHgnam(HGNAM hgnam);
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szNCACHE_HXX)
+#define SZ_FILE_NAME g_szNCACHE_HXX
+#endif
+
+// NAME_CACHE byte size
+#define NAMCACHE_cbSize 16
+
+/***
+*class NAME_CACHE - 'namcache': Project-level NAME_CACHE
+*Purpose:
+* The class defines the project-level NAME_CACHE
+*
+*Implementation Notes:
+* Only has non-virtual/static methods. instances of NAME_CACHE
+* are allocated in BLK_DESCs and thus must have no virtual
+* funcs.
+*
+***********************************************************************/
+
+class NAME_CACHE
+{
+ friend class GenericTypeLibOLE;
+
+private:
+ BYTE m_rgBitmap[NAMCACHE_cbSize];
+ USHORT m_isValid;
+ nonvirt VOID SetBit(UINT uBit);
+ nonvirt BOOL GetBit(UINT uBit) const;
+
+public:
+ NAME_CACHE();
+ nonvirt VOID Invalidate();
+ nonvirt BOOL IsValid() const;
+ nonvirt VOID SetValid();
+ nonvirt BOOL IsNameInCache(HGNAM hgnam) const;
+ nonvirt VOID AddNameToCache(HGNAM hgnam);
+
+#if ID_DEBUG
+ nonvirt VOID DebShowState(UINT uLevel) const;
+ nonvirt VOID DebCheckState(UINT uLevel) const;
+#else
+ nonvirt VOID DebShowState(UINT uLevel) const {}
+ nonvirt VOID DebCheckState(UINT uLevel) const {}
+#endif
+};
+
+
+/***
+*PUBLIC NAME_CACHE::Invalidate - Invalidates cache.
+*Purpose:
+* Invalidates cache -- sets all bits to zero.
+* NOTE: must precede ctor since referenced by ctor and inline
+* and cfront complains otherwise.
+*
+*Entry:
+*
+*Exit:
+* Sets m_isValid to FALSE and all bits in bitmap to zero.
+*
+***********************************************************************/
+
+inline VOID NAME_CACHE::Invalidate()
+{
+ m_isValid = (USHORT)FALSE;
+ memset(m_rgBitmap, (int)0, sizeof(m_rgBitmap));
+}
+
+
+/***
+*PRIVATE NAME_CACHE::NAME_CACHE - constructor
+*Purpose:
+* Constructor - invalidates cache.
+*
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+inline NAME_CACHE::NAME_CACHE()
+{
+ Invalidate();
+}
+
+
+/***
+*PRIVATE NAME_CACHE::IsValid - is cache valid
+*Purpose:
+* tests if cache is valid
+*
+*Entry:
+*
+*Exit:
+* TRUE if valid, FALSE otherwise
+*
+***********************************************************************/
+
+inline BOOL NAME_CACHE::IsValid() const
+{
+ return (BOOL)m_isValid;
+}
+
+
+/***
+*PRIVATE NAME_CACHE::SetValid - makes cache valid
+*Purpose:
+* Makes cache valid.
+*
+*Entry:
+*
+*Exit:
+* None
+*
+***********************************************************************/
+
+inline VOID NAME_CACHE::SetValid()
+{
+ m_isValid = (USHORT)TRUE;
+}
+
+
+/***
+*PRIVATE NAME_CACHE::GetBit - Gets bit in bitmap.
+*Purpose:
+* Indicates whether bit that hash value maps to is set in bitmap.
+* Doesn't require cache to be valid -- up to client
+* to validate/invalidate cache.
+*
+*Entry:
+* uHash - Hash value to map and test.
+*
+*Exit:
+* Returns TRUE if bit set otherwise FALSE.
+*
+***********************************************************************/
+
+inline BOOL NAME_CACHE::GetBit(UINT uHash) const
+{
+ UINT uBitsElem;
+ UINT uBit;
+
+ uBitsElem=sizeof(m_rgBitmap[0]) * CHAR_BIT;
+
+ // map hash value to bit
+ uBit = uHash % (sizeof(m_rgBitmap) * uBitsElem);
+
+ return m_rgBitmap[uBit/uBitsElem] & (1 << (uBit % uBitsElem));
+}
+
+
+/***
+*PRIVATE NAME_CACHE::SetBit - Sets bit in bitmap.
+*Purpose:
+* Sets bit that hash value maps to in bitmap.
+* Doesn't require cache to be valid -- up to client
+* to validate/invalidate cache.
+*
+*Entry:
+* uHash - Hash value to map and set.
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID NAME_CACHE::SetBit(UINT uHash)
+{
+ UINT uBitsElem;
+ UINT uBit;
+
+ uBitsElem=sizeof(m_rgBitmap[0]) * CHAR_BIT;
+
+ // map hash value to bit
+ uBit = uHash % (sizeof(m_rgBitmap) * uBitsElem);
+
+ m_rgBitmap[uBit/uBitsElem] |= (1 << (uBit % uBitsElem));
+}
+
+
+/***
+*PUBLIC NAME_CACHE::IsNameInCache
+*Purpose:
+* Tests if a given name is in cache.
+* Doesn't care if cache is valid -- up to clients
+* to validate/invalidate cache.
+*
+*Entry:
+* hgnam Global name handle to test for.
+
+*
+*Exit:
+* TRUE if name is in cache.
+* FALSE otherwise.
+*
+***********************************************************************/
+
+inline BOOL NAME_CACHE::IsNameInCache(HGNAM hgnam) const
+{
+ return GetBit(HashOfHgnam(hgnam));
+}
+
+
+/***
+*PUBLIC NAME_CACHE::AddNameToCache
+*Purpose:
+* Adds name to cache but setting appropriate bit in map.
+* Doesn't care if cache is valid -- up to clients
+* to validate/invalidate cache.
+*
+*Entry:
+* hgnam Global name handle to set bit for.
+*
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID NAME_CACHE::AddNameToCache(HGNAM hgnam)
+{
+ SetBit(HashOfHgnam(hgnam));
+}
+
+
+#if ID_DEBUG
+
+/***
+*PUBLIC NAME_CACHE::DebCheckState - NAME_CACHE state
+*Purpose:
+* Cache NAME_CACHE state
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+*Exceptions:
+* None.
+*
+***********************************************************************/
+
+inline VOID NAME_CACHE::DebCheckState(UINT uLevel) const
+{
+}
+
+#endif // ID_DEBUG
+
+
+#endif // NAME_CACHE_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/newexe.h b/private/oleauto/src/typelib/newexe.h
new file mode 100644
index 000000000..d4c0bee49
--- /dev/null
+++ b/private/oleauto/src/typelib/newexe.h
@@ -0,0 +1,387 @@
+/*static char *SCCSID = "@(#)newexe.h:2.9";*/
+/*
+ * Title
+ *
+ * newexe.h
+ * Pete Stewart
+ * Copyright (c) 1984-1993, Microsoft Corporation. All rights reserved.
+ * 17 August 1984
+ *
+ * Description
+ *
+ * Data structure definitions for the DOS 4.0/Windows 2.0
+ * executable file format.
+ *
+ * Modification History
+ *
+ * 84/08/17 Pete Stewart Initial version
+ * 84/10/17 Pete Stewart Changed some constants to match OMF
+ * 84/10/23 Pete Stewart Updates to match .EXE format revision
+ * 84/11/20 Pete Stewart Substantial .EXE format revision
+ * 85/01/09 Pete Stewart Added constants ENEWEXE and ENEWHDR
+ * 85/01/10 Steve Wood Added resource definitions
+ * 85/03/04 Vic Heller Reconciled Windows and DOS 4.0 versions
+ * 85/03/07 Pete Stewart Added movable entry count
+ * 85/04/01 Pete Stewart Segment alignment field, error bit
+ * 88/03/28 Craig Critchley Version 3.00 stuff
+ */
+
+#define EMAGIC 0x5A4D /* Old magic number */
+#define ENEWEXE sizeof(struct exe_hdr)
+ /* Value of E_LFARLC for new .EXEs */
+#define ENEWHDR 0x003C /* Offset in old hdr. of ptr. to new */
+#define ERESWDS 0x0010 /* No. of reserved words in header */
+#define ECP 0x0004 /* Offset in struct of E_CP */
+#define ECBLP 0x0002 /* Offset in struct of E_CBLP */
+#define EMINALLOC 0x000A /* Offset in struct of E_MINALLOC */
+
+struct exe_hdr /* DOS 1, 2, 3 .EXE header */
+ {
+ unsigned short e_magic; /* Magic number */
+ unsigned short e_cblp; /* Bytes on last page of file */
+ unsigned short e_cp; /* Pages in file */
+ unsigned short e_crlc; /* Relocations */
+ unsigned short e_cparhdr; /* Size of header in paragraphs */
+ unsigned short e_minalloc; /* Minimum extra paragraphs needed */
+ unsigned short e_maxalloc; /* Maximum extra paragraphs needed */
+ unsigned short e_ss; /* Initial (relative) SS value */
+ unsigned short e_sp; /* Initial SP value */
+ unsigned short e_csum; /* Checksum */
+ unsigned short e_ip; /* Initial IP value */
+ unsigned short e_cs; /* Initial (relative) CS value */
+ unsigned short e_lfarlc; /* File address of relocation table */
+ unsigned short e_ovno; /* Overlay number */
+ unsigned short e_res[ERESWDS]; /* Reserved words */
+ long e_lfanew; /* File address of new exe header */
+ };
+
+#define E_MAGIC(x) (x).e_magic
+#define E_CBLP(x) (x).e_cblp
+#define E_CP(x) (x).e_cp
+#define E_CRLC(x) (x).e_crlc
+#define E_CPARHDR(x) (x).e_cparhdr
+#define E_MINALLOC(x) (x).e_minalloc
+#define E_MAXALLOC(x) (x).e_maxalloc
+#define E_SS(x) (x).e_ss
+#define E_SP(x) (x).e_sp
+#define E_CSUM(x) (x).e_csum
+#define E_IP(x) (x).e_ip
+#define E_CS(x) (x).e_cs
+#define E_LFARLC(x) (x).e_lfarlc
+#define E_OVNO(x) (x).e_ovno
+#define E_RES(x) (x).e_res
+#define E_LFANEW(x) (x).e_lfanew
+
+#define NEMAGIC 0x454E /* New magic number */
+#define NERESBYTES 0
+
+struct new_exe /* New .EXE header */
+ {
+ unsigned short int ne_magic; /* Magic number NE_MAGIC */
+ char ne_ver; /* Version number */
+ char ne_rev; /* Revision number */
+ unsigned short int ne_enttab; /* Offset of Entry Table */
+ unsigned short int ne_cbenttab; /* Number of bytes in Entry Table */
+ long ne_crc; /* Checksum of whole file */
+ unsigned short int ne_flags; /* Flag word */
+ unsigned short int ne_autodata; /* Automatic data segment number */
+ unsigned short int ne_heap; /* Initial heap allocation */
+ unsigned short int ne_stack; /* Initial stack allocation */
+ long ne_csip; /* Initial CS:IP setting */
+ long ne_sssp; /* Initial SS:SP setting */
+ unsigned short int ne_cseg; /* Count of file segments */
+ unsigned short int ne_cmod; /* Entries in Module Reference Table */
+ unsigned short int ne_cbnrestab; /* Size of non-resident name table */
+ unsigned short int ne_segtab; /* Offset of Segment Table */
+ unsigned short int ne_rsrctab; /* Offset of Resource Table */
+ unsigned short int ne_restab; /* Offset of resident name table */
+ unsigned short int ne_modtab; /* Offset of Module Reference Table */
+ unsigned short int ne_imptab; /* Offset of Imported Names Table */
+ long ne_nrestab; /* Offset of Non-resident Names Table */
+ unsigned short int ne_cmovent; /* Count of movable entries */
+ unsigned short int ne_align; /* Segment alignment shift count */
+ unsigned short int ne_cres; /* Count of resource segments */
+ unsigned char ne_exetyp; /* Target operating system */
+ unsigned char ne_flagsother; /* Additional exe flags */
+ unsigned short int ne_gangstart; /* offset to gangload area */
+ unsigned short int ne_ganglength; /* length of gangload area */
+ unsigned short int ne_swaparea; /* Minimum code swap area size */
+ unsigned short int ne_expver; /* Expected Windows version number */
+ };
+
+#define NE_MAGIC(x) (x).ne_magic
+#define NE_VER(x) (x).ne_ver
+#define NE_REV(x) (x).ne_rev
+#define NE_ENTTAB(x) (x).ne_enttab
+#define NE_CBENTTAB(x) (x).ne_cbenttab
+#define NE_CRC(x) (x).ne_crc
+#define NE_FLAGS(x) (x).ne_flags
+#define NE_AUTODATA(x) (x).ne_autodata
+#define NE_HEAP(x) (x).ne_heap
+#define NE_STACK(x) (x).ne_stack
+#define NE_CSIP(x) (x).ne_csip
+#define NE_SSSP(x) (x).ne_sssp
+#define NE_CSEG(x) (x).ne_cseg
+#define NE_CMOD(x) (x).ne_cmod
+#define NE_CBNRESTAB(x) (x).ne_cbnrestab
+#define NE_SEGTAB(x) (x).ne_segtab
+#define NE_RSRCTAB(x) (x).ne_rsrctab
+#define NE_RESTAB(x) (x).ne_restab
+#define NE_MODTAB(x) (x).ne_modtab
+#define NE_IMPTAB(x) (x).ne_imptab
+#define NE_NRESTAB(x) (x).ne_nrestab
+#define NE_CMOVENT(x) (x).ne_cmovent
+#define NE_ALIGN(x) (x).ne_align
+#define NE_RES(x) (x).ne_res
+
+#define NE_USAGE(x) (WORD)*((WORD FAR *)(x)+1)
+#define NE_PNEXTEXE(x) (WORD)(x).ne_cbenttab
+#define NE_PAUTODATA(x) (WORD)(x).ne_crc
+#define NE_PFILEINFO(x) (WORD)((DWORD)(x).ne_crc >> 16)
+
+#ifdef DOS5
+#define NE_MTE(x) (x).ne_psegcsum /* DOS 5 MTE handle for this module */
+#endif
+
+
+/*
+ * Format of NE_FLAGS(x):
+ *
+ * p Not-a-process
+ * l Private Library
+ * e Errors in image
+ * xxxx Unused
+ * ww Uses PM API
+ * G Library GlobalAlloc above the line
+ * M Multiple Instance
+ * L Uses LIM 3.2
+ * P Runs in protected mode
+ * r Runs in real mode
+ * i Instance data
+ * s Solo data
+ */
+#define NENOTP 0x8000 /* Not a process */
+#define NEPRIVLIB 0x4000 /* Private Library */
+#define NENONC 0x4000 /* Non-conforming program */
+#define NEIERR 0x2000 /* Errors in image */
+#define NEWINAPI 0x0300 /* Uses PM API. For binary compat */
+#define NEEMSLIB 0x0040 /* Library GA above EMS line */
+#define NEMULTINST 0x0020 /* multiple instance flag */
+#define NELIM32 0x0010 /* LIM 32 expanded memory */
+#define NEPROT 0x0008 /* Runs in protected mode */
+#define NEREAL 0x0004 /* Runs in real mode */
+#define NEINST 0x0002 /* Instance data */
+#define NESOLO 0x0001 /* Solo data */
+
+/*
+ * Format of additional flags:
+ *
+ * xxxx
+ * p Preload area defined after seg table
+ * P 2.X supports protected mode
+ * F 2.X supports proportional font
+ * L Long file name support
+ */
+
+#define NEPRELOAD 0x08 /* preload segments */
+#define NEINPROT 0x04 /* protect mode */
+#define NEINFONT 0x02 /* prop. system font */
+#define NELONGNAMES 0x01 /* long file names */
+
+struct new_seg /* New .EXE segment table entry */
+ {
+ unsigned short ns_sector; /* File sector of start of segment */
+ unsigned short ns_cbseg; /* Number of bytes in file */
+ unsigned short ns_flags; /* Attribute flags */
+ unsigned short ns_minalloc; /* Minimum allocation in bytes */
+ };
+
+struct new_seg1 /* New .EXE segment table entry */
+ {
+ unsigned short ns_sector; /* File sector of start of segment */
+ unsigned short ns_cbseg; /* Number of bytes in file */
+ unsigned short ns_flags; /* Attribute flags */
+ unsigned short ns_minalloc; /* Minimum allocation in bytes */
+ unsigned short ns_handle; /* Handle of segment */
+ };
+
+#define NS_SECTOR(x) (x).ns_sector
+#define NS_CBSEG(x) (x).ns_cbseg
+#define NS_FLAGS(x) (x).ns_flags
+#define NS_MINALLOC(x) (x).ns_minalloc
+
+/*
+ * Format of NS_FLAGS(x):
+ *
+ * xxxx Unused
+ * DD 286 DPL bits
+ * d Segment has debug info
+ * r Segment has relocations
+ * e Execute/read only
+ * p Preload segment
+ * P Pure segment
+ * m Movable segment
+ * i Iterated segment
+ * ttt Segment type
+ */
+#define NSTYPE 0x0007 /* Segment type mask */
+#define NSCODE 0x0000 /* Code segment */
+#define NSDATA 0x0001 /* Data segment */
+#define NSITER 0x0008 /* Iterated segment flag */
+#define NSMOVE 0x0010 /* Movable segment flag */
+#define NSPURE 0x0020 /* Pure segment flag */
+#define NSPRELOAD 0x0040 /* Preload segment flag */
+#define NSEXRD 0x0080 /* Execute-only (code segment), or
+ * read-only (data segment)
+ */
+#define NSRELOC 0x0100 /* Segment has relocations */
+#define NSDEBUG 0x0200 /* Segment has debug info */
+#define NSDPL 0x0C00 /* 286 DPL bits */
+#define NSDISCARD 0x1000 /* Discard bit for segment */
+
+#define NSALIGN 9 /* Segment data aligned on 512 byte boundaries */
+
+struct new_segdata /* Segment data */
+ {
+ union
+ {
+ struct
+ {
+ unsigned short ns_niter; /* number of iterations */
+ unsigned short ns_nbytes; /* number of bytes */
+ char ns_iterdata; /* iterated data bytes */
+ } ns_iter;
+ struct
+ {
+ char ns_data; /* data bytes */
+ } ns_noniter;
+ } ns_union;
+ };
+
+struct new_rlcinfo /* Relocation info */
+ {
+ unsigned short nr_nreloc; /* number of relocation items that */
+ }; /* follow */
+
+struct new_rlc /* Relocation item */
+ {
+ char nr_stype; /* Source type */
+ char nr_flags; /* Flag byte */
+ unsigned short nr_soff; /* Source offset */
+ union
+ {
+ struct
+ {
+ char nr_segno; /* Target segment number */
+ char nr_res; /* Reserved */
+ unsigned short nr_entry; /* Target Entry Table offset */
+ } nr_intref; /* Internal reference */
+ struct
+ {
+ unsigned short nr_mod; /* Index into Module Reference Table */
+ unsigned short nr_proc; /* Procedure ordinal or name offset */
+ } nr_import; /* Import */
+ } nr_union; /* Union */
+ };
+
+#define NR_STYPE(x) (x).nr_stype
+#define NR_FLAGS(x) (x).nr_flags
+#define NR_SOFF(x) (x).nr_soff
+#define NR_SEGNO(x) (x).nr_union.nr_intref.nr_segno
+#define NR_RES(x) (x).nr_union.nr_intref.nr_res
+#define NR_ENTRY(x) (x).nr_union.nr_intref.nr_entry
+#define NR_MOD(x) (x).nr_union.nr_import.nr_mod
+#define NR_PROC(x) (x).nr_union.nr_import.nr_proc
+
+/*
+ * Format of NR_STYPE(x):
+ *
+ * xxxxx Unused
+ * sss Source type
+ */
+#define NRSTYP 0x07 /* Source type mask */
+#define NRSSEG 0x02 /* 16-bit segment */
+#define NRSPTR 0x03 /* 32-bit pointer */
+#define NRSOFF 0x05 /* 16-bit offset */
+
+/*
+ * Format of NR_FLAGS(x):
+ *
+ * xxxxx Unused
+ * a Additive fixup
+ * rr Reference type
+ */
+#define NRADD 0x04 /* Additive fixup */
+#define NRRTYP 0x03 /* Reference type mask */
+#define NRRINT 0x00 /* Internal reference */
+#define NRRORD 0x01 /* Import by ordinal */
+#define NRRNAM 0x02 /* Import by name */
+
+
+/* Resource type or name string */
+struct rsrc_string
+ {
+ char rs_len; /* number of bytes in string */
+ char rs_string[ 1 ]; /* text of string */
+ };
+
+#define RS_LEN( x ) (x).rs_len
+#define RS_STRING( x ) (x).rs_string
+
+/* Resource type information block */
+struct rsrc_typeinfo
+ {
+ unsigned short rt_id;
+ unsigned short rt_nres;
+ long rt_proc;
+ };
+
+#define RT_ID( x ) (x).rt_id
+#define RT_NRES( x ) (x).rt_nres
+#define RT_PROC( x ) (x).rt_proc
+
+/* Resource name information block */
+struct rsrc_nameinfo
+ {
+ /* The following two fields must be shifted left by the value of */
+ /* the rs_align field to compute their actual value. This allows */
+ /* resources to be larger than 64k, but they do not need to be */
+ /* aligned on 512 byte boundaries, the way segments are */
+ unsigned short rn_offset; /* file offset to resource data */
+ unsigned short rn_length; /* length of resource data */
+ unsigned short rn_flags; /* resource flags */
+ unsigned short rn_id; /* resource name id */
+ unsigned short rn_handle; /* If loaded, then global handle */
+ unsigned short rn_usage; /* Initially zero. Number of times */
+ /* the handle for this resource has */
+ /* been given out */
+ };
+
+#define RN_OFFSET( x ) (x).rn_offset
+#define RN_LENGTH( x ) (x).rn_length
+#define RN_FLAGS( x ) (x).rn_flags
+#define RN_ID( x ) (x).rn_id
+#define RN_HANDLE( x ) (x).rn_handle
+#define RN_USAGE( x ) (x).rn_usage
+
+#define RSORDID 0x8000 /* if high bit of ID set then integer id */
+ /* otherwise ID is offset of string from
+ the beginning of the resource table */
+
+ /* Ideally these are the same as the */
+ /* corresponding segment flags */
+#define RNMOVE 0x0010 /* Moveable resource */
+#define RNPURE 0x0020 /* Pure (read-only) resource */
+#define RNPRELOAD 0x0040 /* Preloaded resource */
+#define RNDISCARD 0x1000 /* Discard bit for resource */
+
+#define RNLOADED 0x0004 /* True if handler proc return handle */
+
+/* Resource table */
+struct new_rsrc
+ {
+ unsigned short rs_align; /* alignment shift count for resources */
+ struct rsrc_typeinfo rs_typeinfo;
+ };
+
+#define RS_ALIGN( x ) (x).rs_align
diff --git a/private/oleauto/src/typelib/ntimage.h b/private/oleauto/src/typelib/ntimage.h
new file mode 100644
index 000000000..43a9bd479
--- /dev/null
+++ b/private/oleauto/src/typelib/ntimage.h
@@ -0,0 +1,968 @@
+/*++ BUILD Version: 0004 // Increment this if a change has global effects
+
+Copyright (c) 1989-1993 Microsoft Corporation
+
+Module Name:
+
+ ntimage.h
+
+Abstract:
+
+ This is the include file that describes all image structures.
+
+Author:
+
+ Mike O'Leary (mikeol) 21-Mar-1991
+
+Revision History:
+
+--*/
+
+#ifndef _NTIMAGE_
+#define _NTIMAGE_
+
+//
+// Define the linker version number. This is temporary to aid
+// in debugging with people trying to load images built with
+// an older linker. This is not required in the final product.
+//
+
+#define IMAGE_MAJOR_LINKER_VERSION 2
+
+// begin_winnt
+
+
+//
+// Image Format
+//
+
+#ifndef RC_INVOKED
+#pragma pack (1)
+#endif // !RC_INVOKED
+
+#define IMAGE_DOS_SIGNATURE 0x5A4D // MZ
+#define IMAGE_OS2_SIGNATURE 0x454E // NE
+#define IMAGE_OS2_SIGNATURE_LE 0x454C // LE
+#define IMAGE_NT_SIGNATURE 0x00004550 // PE00
+
+typedef struct _IMAGE_DOS_HEADER { // DOS .EXE header
+ USHORT e_magic; // Magic number
+ USHORT e_cblp; // Bytes on last page of file
+ USHORT e_cp; // Pages in file
+ USHORT e_crlc; // Relocations
+ USHORT e_cparhdr; // Size of header in paragraphs
+ USHORT e_minalloc; // Minimum extra paragraphs needed
+ USHORT e_maxalloc; // Maximum extra paragraphs needed
+ USHORT e_ss; // Initial (relative) SS value
+ USHORT e_sp; // Initial SP value
+ USHORT e_csum; // Checksum
+ USHORT e_ip; // Initial IP value
+ USHORT e_cs; // Initial (relative) CS value
+ USHORT e_lfarlc; // File address of relocation table
+ USHORT e_ovno; // Overlay number
+ USHORT e_res[4]; // Reserved words
+ USHORT e_oemid; // OEM identifier (for e_oeminfo)
+ USHORT e_oeminfo; // OEM information; e_oemid specific
+ USHORT e_res2[10]; // Reserved words
+ LONG e_lfanew; // File address of new exe header
+ } IMAGE_DOS_HEADER, *PIMAGE_DOS_HEADER;
+
+typedef struct _IMAGE_OS2_HEADER { // OS/2 .EXE header
+ USHORT ne_magic; // Magic number
+ CHAR ne_ver; // Version number
+ CHAR ne_rev; // Revision number
+ USHORT ne_enttab; // Offset of Entry Table
+ USHORT ne_cbenttab; // Number of bytes in Entry Table
+ LONG ne_crc; // Checksum of whole file
+ USHORT ne_flags; // Flag word
+ USHORT ne_autodata; // Automatic data segment number
+ USHORT ne_heap; // Initial heap allocation
+ USHORT ne_stack; // Initial stack allocation
+ LONG ne_csip; // Initial CS:IP setting
+ LONG ne_sssp; // Initial SS:SP setting
+ USHORT ne_cseg; // Count of file segments
+ USHORT ne_cmod; // Entries in Module Reference Table
+ USHORT ne_cbnrestab; // Size of non-resident name table
+ USHORT ne_segtab; // Offset of Segment Table
+ USHORT ne_rsrctab; // Offset of Resource Table
+ USHORT ne_restab; // Offset of resident name table
+ USHORT ne_modtab; // Offset of Module Reference Table
+ USHORT ne_imptab; // Offset of Imported Names Table
+ LONG ne_nrestab; // Offset of Non-resident Names Table
+ USHORT ne_cmovent; // Count of movable entries
+ USHORT ne_align; // Segment alignment shift count
+ USHORT ne_cres; // Count of resource segments
+ UCHAR ne_exetyp; // Target Operating system
+ UCHAR ne_flagsothers; // Other .EXE flags
+ USHORT ne_pretthunks; // offset to return thunks
+ USHORT ne_psegrefbytes; // offset to segment ref. bytes
+ USHORT ne_swaparea; // Minimum code swap area size
+ USHORT ne_expver; // Expected Windows version number
+ } IMAGE_OS2_HEADER, *PIMAGE_OS2_HEADER;
+
+//
+// File header format.
+//
+
+typedef struct _IMAGE_FILE_HEADER {
+ USHORT Machine;
+ USHORT NumberOfSections;
+ ULONG TimeDateStamp;
+ ULONG PointerToSymbolTable;
+ ULONG NumberOfSymbols;
+ USHORT SizeOfOptionalHeader;
+ USHORT Characteristics;
+} IMAGE_FILE_HEADER, *PIMAGE_FILE_HEADER;
+
+#define IMAGE_SIZEOF_FILE_HEADER 20
+
+#define IMAGE_FILE_RELOCS_STRIPPED 0x0001 // Relocation info stripped from file.
+#define IMAGE_FILE_EXECUTABLE_IMAGE 0x0002 // File is executable (i.e. no unresolved externel references).
+#define IMAGE_FILE_LINE_NUMS_STRIPPED 0x0004 // Line nunbers stripped from file.
+#define IMAGE_FILE_LOCAL_SYMS_STRIPPED 0x0008 // Local symbols stripped from file.
+#define IMAGE_FILE_MINIMAL_OBJECT 0x0010 // Reserved.
+#define IMAGE_FILE_UPDATE_OBJECT 0x0020 // Reserved.
+#define IMAGE_FILE_16BIT_MACHINE 0x0040 // 16 bit word machine.
+#define IMAGE_FILE_BYTES_REVERSED_LO 0x0080 // Bytes of machine word are reversed.
+#define IMAGE_FILE_32BIT_MACHINE 0x0100 // 32 bit word machine.
+#define IMAGE_FILE_DEBUG_STRIPPED 0x0200 // Debugging info stripped from file in .DBG file
+#define IMAGE_FILE_PATCH 0x0400 // Reserved.
+#define IMAGE_FILE_SYSTEM 0x1000 // System File.
+#define IMAGE_FILE_DLL 0x2000 // File is a DLL.
+#define IMAGE_FILE_BYTES_REVERSED_HI 0x8000 // Bytes of machine word are reversed.
+
+#define IMAGE_FILE_MACHINE_UNKNOWN 0
+#define IMAGE_FILE_MACHINE_I386 0x14c // Intel 386.
+#define IMAGE_FILE_MACHINE_R3000 0x162 // MIPS little-endian, 0540 big-endian
+#define IMAGE_FILE_MACHINE_R4000 0x166 // MIPS little-endian
+#define IMAGE_FILE_MACHINE_ALPHA 0x184 // Alpha_AXP
+
+//
+// Directory format.
+//
+
+typedef struct _IMAGE_DATA_DIRECTORY {
+ ULONG VirtualAddress;
+ ULONG Size;
+} IMAGE_DATA_DIRECTORY, *PIMAGE_DATA_DIRECTORY;
+
+#define IMAGE_NUMBEROF_DIRECTORY_ENTRIES 16
+
+//
+// Optional header format.
+//
+
+typedef struct _IMAGE_OPTIONAL_HEADER {
+ //
+ // Standard fields.
+ //
+
+ USHORT Magic;
+ UCHAR MajorLinkerVersion;
+ UCHAR MinorLinkerVersion;
+ ULONG SizeOfCode;
+ ULONG SizeOfInitializedData;
+ ULONG SizeOfUninitializedData;
+ ULONG AddressOfEntryPoint;
+ ULONG BaseOfCode;
+ ULONG BaseOfData;
+
+ //
+ // NT additional fields.
+ //
+
+ ULONG ImageBase;
+ ULONG SectionAlignment;
+ ULONG FileAlignment;
+ USHORT MajorOperatingSystemVersion;
+ USHORT MinorOperatingSystemVersion;
+ USHORT MajorImageVersion;
+ USHORT MinorImageVersion;
+ USHORT MajorSubsystemVersion;
+ USHORT MinorSubsystemVersion;
+ ULONG Reserved1;
+ ULONG SizeOfImage;
+ ULONG SizeOfHeaders;
+ ULONG CheckSum;
+ USHORT Subsystem;
+ USHORT DllCharacteristics;
+ ULONG SizeOfStackReserve;
+ ULONG SizeOfStackCommit;
+ ULONG SizeOfHeapReserve;
+ ULONG SizeOfHeapCommit;
+ ULONG LoaderFlags;
+ ULONG NumberOfRvaAndSizes;
+ IMAGE_DATA_DIRECTORY DataDirectory[IMAGE_NUMBEROF_DIRECTORY_ENTRIES];
+} IMAGE_OPTIONAL_HEADER, *PIMAGE_OPTIONAL_HEADER;
+
+typedef struct _IMAGE_ROM_OPTIONAL_HEADER {
+ USHORT Magic;
+ UCHAR MajorLinkerVersion;
+ UCHAR MinorLinkerVersion;
+ ULONG SizeOfCode;
+ ULONG SizeOfInitializedData;
+ ULONG SizeOfUninitializedData;
+ ULONG AddressOfEntryPoint;
+ ULONG BaseOfCode;
+ ULONG BaseOfData;
+ ULONG BaseOfBss;
+ ULONG GprMask;
+ ULONG CprMask[4];
+ ULONG GpValue;
+} IMAGE_ROM_OPTIONAL_HEADER, *PIMAGE_ROM_OPTIONAL_HEADER;
+
+#define IMAGE_SIZEOF_ROM_OPTIONAL_HEADER 56
+#define IMAGE_SIZEOF_STD_OPTIONAL_HEADER 28
+#define IMAGE_SIZEOF_NT_OPTIONAL_HEADER 224
+
+#define IMAGE_NT_OPTIONAL_HDR_MAGIC 0x10b
+#define IMAGE_ROM_OPTIONAL_HDR_MAGIC 0x107
+
+typedef struct _IMAGE_NT_HEADERS {
+ ULONG Signature;
+ IMAGE_FILE_HEADER FileHeader;
+ IMAGE_OPTIONAL_HEADER OptionalHeader;
+} IMAGE_NT_HEADERS, *PIMAGE_NT_HEADERS;
+
+typedef struct _IMAGE_ROM_HEADERS {
+ IMAGE_FILE_HEADER FileHeader;
+ IMAGE_ROM_OPTIONAL_HEADER OptionalHeader;
+} IMAGE_ROM_HEADERS, *PIMAGE_ROM_HEADERS;
+
+#define IMAGE_FIRST_SECTION( ntheader ) ((PIMAGE_SECTION_HEADER) \
+ ((ULONG)ntheader + \
+ FIELD_OFFSET( IMAGE_NT_HEADERS, OptionalHeader ) + \
+ ((PIMAGE_NT_HEADERS)(ntheader))->FileHeader.SizeOfOptionalHeader \
+ ))
+
+
+// Subsystem Values
+
+#define IMAGE_SUBSYSTEM_UNKNOWN 0 // Unknown subsystem.
+#define IMAGE_SUBSYSTEM_NATIVE 1 // Image doesn't require a subsystem.
+#define IMAGE_SUBSYSTEM_WINDOWS_GUI 2 // Image runs in the Windows GUI subsystem.
+#define IMAGE_SUBSYSTEM_WINDOWS_CUI 3 // Image runs in the Windows character subsystem.
+#define IMAGE_SUBSYSTEM_OS2_CUI 5 // image runs in the OS/2 character subsystem.
+#define IMAGE_SUBSYSTEM_POSIX_CUI 7 // image run in the Posix character subsystem.
+
+// Dll Characteristics
+
+#define IMAGE_LIBRARY_PROCESS_INIT 1 // Dll has a process initialization routine.
+#define IMAGE_LIBRARY_PROCESS_TERM 2 // Dll has a thread termination routine.
+#define IMAGE_LIBRARY_THREAD_INIT 4 // Dll has a thread initialization routine.
+#define IMAGE_LIBRARY_THREAD_TERM 8 // Dll has a thread termination routine.
+
+//
+// Loader Flags
+//
+
+#define IMAGE_LOADER_FLAGS_BREAK_ON_LOAD 0x00000001
+#define IMAGE_LOADER_FLAGS_DEBUG_ON_LOAD 0x00000002
+
+
+// Directory Entries
+
+#define IMAGE_DIRECTORY_ENTRY_EXPORT 0 // Export Directory
+#define IMAGE_DIRECTORY_ENTRY_IMPORT 1 // Import Directory
+#define IMAGE_DIRECTORY_ENTRY_RESOURCE 2 // Resource Directory
+#define IMAGE_DIRECTORY_ENTRY_EXCEPTION 3 // Exception Directory
+#define IMAGE_DIRECTORY_ENTRY_SECURITY 4 // Security Directory
+#define IMAGE_DIRECTORY_ENTRY_BASERELOC 5 // Base Relocation Table
+#define IMAGE_DIRECTORY_ENTRY_DEBUG 6 // Debug Directory
+#define IMAGE_DIRECTORY_ENTRY_COPYRIGHT 7 // Description String
+#define IMAGE_DIRECTORY_ENTRY_GLOBALPTR 8 // Machine Value (MIPS GP)
+#define IMAGE_DIRECTORY_ENTRY_TLS 9 // TLS Directory
+#define IMAGE_DIRECTORY_ENTRY_LOAD_CONFIG 10 // Load Configuration Directory
+
+//
+// Section header format.
+//
+
+#define IMAGE_SIZEOF_SHORT_NAME 8
+
+typedef struct _IMAGE_SECTION_HEADER {
+ UCHAR Name[IMAGE_SIZEOF_SHORT_NAME];
+ union {
+ ULONG PhysicalAddress;
+ ULONG VirtualSize;
+ } Misc;
+ ULONG VirtualAddress;
+ ULONG SizeOfRawData;
+ ULONG PointerToRawData;
+ ULONG PointerToRelocations;
+ ULONG PointerToLinenumbers;
+ USHORT NumberOfRelocations;
+ USHORT NumberOfLinenumbers;
+ ULONG Characteristics;
+} IMAGE_SECTION_HEADER, *PIMAGE_SECTION_HEADER;
+
+#define IMAGE_SIZEOF_SECTION_HEADER 40
+
+#define IMAGE_SCN_TYPE_REGULAR 0x00000000 //
+#define IMAGE_SCN_TYPE_DUMMY 0x00000001 // Reserved.
+#define IMAGE_SCN_TYPE_NO_LOAD 0x00000002 // Reserved.
+#define IMAGE_SCN_TYPE_GROUPED 0x00000004 // Used for 16-bit offset code.
+#define IMAGE_SCN_TYPE_NO_PAD 0x00000008 // Reserved.
+#define IMAGE_SCN_TYPE_COPY 0x00000010 // Reserved.
+
+#define IMAGE_SCN_CNT_CODE 0x00000020 // Section contains code.
+#define IMAGE_SCN_CNT_INITIALIZED_DATA 0x00000040 // Section contains initialized data.
+#define IMAGE_SCN_CNT_UNINITIALIZED_DATA 0x00000080 // Section contains uninitialized data.
+
+#define IMAGE_SCN_LNK_OTHER 0x00000100 // Reserved.
+#define IMAGE_SCN_LNK_INFO 0x00000200 // Section contains comments or some other type of information.
+#define IMAGE_SCN_LNK_OVERLAY 0x00000400 // Section contains an overlay.
+#define IMAGE_SCN_LNK_REMOVE 0x00000800 // Section contents will not become part of image.
+#define IMAGE_SCN_LNK_COMDAT 0x00001000 // Section contents comdat.
+
+#define IMAGE_SCN_ALIGN_1BYTES 0x00100000 //
+#define IMAGE_SCN_ALIGN_2BYTES 0x00200000 //
+#define IMAGE_SCN_ALIGN_4BYTES 0x00300000 //
+#define IMAGE_SCN_ALIGN_8BYTES 0x00400000 //
+#define IMAGE_SCN_ALIGN_16BYTES 0x00500000 // Default alignment if no others are specified.
+#define IMAGE_SCN_ALIGN_32BYTES 0x00600000 //
+#define IMAGE_SCN_ALIGN_64BYTES 0x00700000 //
+
+#define IMAGE_SCN_MEM_DISCARDABLE 0x02000000 // Section can be discarded.
+#define IMAGE_SCN_MEM_NOT_CACHED 0x04000000 // Section is not cachable.
+#define IMAGE_SCN_MEM_NOT_PAGED 0x08000000 // Section is not pageable.
+#define IMAGE_SCN_MEM_SHARED 0x10000000 // Section is shareable.
+#define IMAGE_SCN_MEM_EXECUTE 0x20000000 // Section is executable.
+#define IMAGE_SCN_MEM_READ 0x40000000 // Section is readable.
+#define IMAGE_SCN_MEM_WRITE 0x80000000 // Section is writeable.
+
+//
+// Symbol format.
+//
+
+typedef struct _IMAGE_SYMBOL {
+ union {
+ UCHAR ShortName[8];
+ struct {
+ ULONG Short; // if 0, use LongName
+ ULONG Long; // offset into string table
+ } Name;
+ PUCHAR LongName[2];
+ } N;
+ ULONG Value;
+ SHORT SectionNumber;
+ USHORT Type;
+ UCHAR StorageClass;
+ UCHAR NumberOfAuxSymbols;
+} IMAGE_SYMBOL;
+typedef IMAGE_SYMBOL UNALIGNED *PIMAGE_SYMBOL;
+
+#define IMAGE_SIZEOF_SYMBOL 18
+
+//
+// Section values.
+//
+// Symbols have a section number of the section in which they are
+// defined. Otherwise, section numbers have the following meanings:
+//
+
+#define IMAGE_SYM_UNDEFINED (SHORT)0 // Symbol is undefined or is common.
+#define IMAGE_SYM_ABSOLUTE (SHORT)-1 // Symbol is an absolute value.
+#define IMAGE_SYM_DEBUG (SHORT)-2 // Symbol is a special debug item.
+
+//
+// Type (fundamental) values.
+//
+
+#define IMAGE_SYM_TYPE_NULL 0 // no type.
+#define IMAGE_SYM_TYPE_VOID 1 //
+#define IMAGE_SYM_TYPE_CHAR 2 // type character.
+#define IMAGE_SYM_TYPE_SHORT 3 // type short integer.
+#define IMAGE_SYM_TYPE_INT 4 //
+#define IMAGE_SYM_TYPE_LONG 5 //
+#define IMAGE_SYM_TYPE_FLOAT 6 //
+#define IMAGE_SYM_TYPE_DOUBLE 7 //
+#define IMAGE_SYM_TYPE_STRUCT 8 //
+#define IMAGE_SYM_TYPE_UNION 9 //
+#define IMAGE_SYM_TYPE_ENUM 10 // enumeration.
+#define IMAGE_SYM_TYPE_MOE 11 // member of enumeration.
+#define IMAGE_SYM_TYPE_UCHAR 12 //
+#define IMAGE_SYM_TYPE_USHORT 13 //
+#define IMAGE_SYM_TYPE_UINT 14 //
+#define IMAGE_SYM_TYPE_ULONG 15 //
+
+//
+// Type (derived) values.
+//
+
+#define IMAGE_SYM_DTYPE_NULL 0 // no derived type.
+#define IMAGE_SYM_DTYPE_POINTER 1 // pointer.
+#define IMAGE_SYM_DTYPE_FUNCTION 2 // function.
+#define IMAGE_SYM_DTYPE_ARRAY 3 // array.
+
+//
+// Storage classes.
+//
+
+#define IMAGE_SYM_CLASS_END_OF_FUNCTION (UCHAR)-1
+#define IMAGE_SYM_CLASS_NULL 0
+#define IMAGE_SYM_CLASS_AUTOMATIC 1
+#define IMAGE_SYM_CLASS_EXTERNAL 2
+#define IMAGE_SYM_CLASS_STATIC 3
+#define IMAGE_SYM_CLASS_REGISTER 4
+#define IMAGE_SYM_CLASS_EXTERNAL_DEF 5
+#define IMAGE_SYM_CLASS_LABEL 6
+#define IMAGE_SYM_CLASS_UNDEFINED_LABEL 7
+#define IMAGE_SYM_CLASS_MEMBER_OF_STRUCT 8
+#define IMAGE_SYM_CLASS_ARGUMENT 9
+#define IMAGE_SYM_CLASS_STRUCT_TAG 10
+#define IMAGE_SYM_CLASS_MEMBER_OF_UNION 11
+#define IMAGE_SYM_CLASS_UNION_TAG 12
+#define IMAGE_SYM_CLASS_TYPE_DEFINITION 13
+#define IMAGE_SYM_CLASS_UNDEFINED_STATIC 14
+#define IMAGE_SYM_CLASS_ENUM_TAG 15
+#define IMAGE_SYM_CLASS_MEMBER_OF_ENUM 16
+#define IMAGE_SYM_CLASS_REGISTER_PARAM 17
+#define IMAGE_SYM_CLASS_BIT_FIELD 18
+#define IMAGE_SYM_CLASS_BLOCK 100
+#define IMAGE_SYM_CLASS_FUNCTION 101
+#define IMAGE_SYM_CLASS_END_OF_STRUCT 102
+#define IMAGE_SYM_CLASS_FILE 103
+// new
+#define IMAGE_SYM_CLASS_SECTION 104
+#define IMAGE_SYM_CLASS_WEAK_EXTERNAL 105
+
+// type packing constants
+
+#define N_BTMASK 017
+#define N_TMASK 060
+#define N_TMASK1 0300
+#define N_TMASK2 0360
+#define N_BTSHFT 4
+#define N_TSHIFT 2
+
+// MACROS
+
+// Basic Type of x
+#define BTYPE(x) ((x) & N_BTMASK)
+
+// Is x a pointer?
+#ifndef ISPTR
+#define ISPTR(x) (((x) & N_TMASK) == (IMAGE_SYM_DTYPE_POINTER << N_BTSHFT))
+#endif
+
+// Is x a function?
+#ifndef ISFCN
+#define ISFCN(x) (((x) & N_TMASK) == (IMAGE_SYM_DTYPE_FUNCTION << N_BTSHFT))
+#endif
+
+// Is x an array?
+
+#ifndef ISARY
+#define ISARY(x) (((x) & N_TMASK) == (IMAGE_SYM_DTYPE_ARRAY << N_BTSHFT))
+#endif
+
+// Is x a structure, union, or enumeration TAG?
+#ifndef ISTAG
+#define ISTAG(x) ((x)==IMAGE_SYM_CLASS_STRUCT_TAG || (x)==IMAGE_SYM_CLASS_UNION_TAG || (x)==IMAGE_SYM_CLASS_ENUM_TAG)
+#endif
+
+#ifndef INCREF
+#define INCREF(x) ((((x)&~N_BTMASK)<<N_TSHIFT)|(IMAGE_SYM_DTYPE_POINTER<<N_BTSHFT)|((x)&N_BTMASK))
+#endif
+#ifndef DECREF
+#define DECREF(x) ((((x)>>N_TSHIFT)&~N_BTMASK)|((x)&N_BTMASK))
+#endif
+
+//
+// Auxiliary entry format.
+//
+
+typedef union _IMAGE_AUX_SYMBOL {
+ struct {
+ ULONG TagIndex; // struct, union, or enum tag index
+ union {
+ struct {
+ USHORT Linenumber; // declaration line number
+ USHORT Size; // size of struct, union, or enum
+ } LnSz;
+ ULONG TotalSize;
+ } Misc;
+ union {
+ struct { // if ISFCN, tag, or .bb
+ ULONG PointerToLinenumber;
+ ULONG PointerToNextFunction;
+ } Function;
+ struct { // if ISARY, up to 4 dimen.
+ USHORT Dimension[4];
+ } Array;
+ } FcnAry;
+ USHORT TvIndex; // tv index
+ } Sym;
+ struct {
+ UCHAR Name[IMAGE_SIZEOF_SYMBOL];
+ } File;
+ struct {
+ ULONG Length; // section length
+ USHORT NumberOfRelocations; // number of relocation entries
+ USHORT NumberOfLinenumbers; // number of line numbers
+ ULONG CheckSum; // checksum for communal
+ SHORT Number; // section number to associate with
+ UCHAR Selection; // communal selection type
+ } Section;
+} IMAGE_AUX_SYMBOL;
+typedef IMAGE_AUX_SYMBOL UNALIGNED *PIMAGE_AUX_SYMBOL;
+
+#define IMAGE_SIZEOF_AUX_SYMBOL 18
+
+//
+// Communal selection types.
+//
+
+#define IMAGE_COMDAT_SELECT_UNKNOWN 0
+#define IMAGE_COMDAT_SELECT_NODUPLICATES 1
+#define IMAGE_COMDAT_SELECT_ANY 2
+#define IMAGE_COMDAT_SELECT_SAME_SIZE 3
+#define IMAGE_COMDAT_SELECT_EXACT_MATCH 4
+#define IMAGE_COMDAT_SELECT_ASSOCIATIVE 5
+
+#define IMAGE_WEAK_EXTERN_SEARCH_UNKNOWN 0
+#define IMAGE_WEAK_EXTERN_SEARCH_NOLIBRARY 1
+#define IMAGE_WEAK_EXTERN_SEARCH_LIBRARY 2
+
+
+//
+// Relocation format.
+//
+
+typedef struct _IMAGE_RELOCATION {
+ ULONG VirtualAddress;
+ ULONG SymbolTableIndex;
+ USHORT Type;
+} IMAGE_RELOCATION;
+typedef IMAGE_RELOCATION UNALIGNED *PIMAGE_RELOCATION;
+
+#define IMAGE_SIZEOF_RELOCATION 10
+
+//
+// I386 relocation types.
+//
+
+#define IMAGE_REL_I386_ABSOLUTE 0 // Reference is absolute, no relocation is necessary
+#define IMAGE_REL_I386_DIR16 01 // Direct 16-bit reference to the symbols virtual address
+#define IMAGE_REL_I386_REL16 02 // PC-relative 16-bit reference to the symbols virtual address
+#define IMAGE_REL_I386_DIR32 06 // Direct 32-bit reference to the symbols virtual address
+#define IMAGE_REL_I386_DIR32NB 07 // Direct 32-bit reference to the symbols virtual address, base not included
+#define IMAGE_REL_I386_SEG12 011 // Direct 16-bit reference to the segment-selector bits of a 32-bit virtual address
+#define IMAGE_REL_I386_SECTION 012
+#define IMAGE_REL_I386_SECREL 013
+#define IMAGE_REL_I386_REL32 024 // PC-relative 32-bit reference to the symbols virtual address
+
+//
+// MIPS relocation types.
+//
+
+#define IMAGE_REL_MIPS_ABSOLUTE 0 // Reference is absolute, no relocation is necessary
+#define IMAGE_REL_MIPS_REFHALF 01
+#define IMAGE_REL_MIPS_REFWORD 02
+#define IMAGE_REL_MIPS_JMPADDR 03
+#define IMAGE_REL_MIPS_REFHI 04
+#define IMAGE_REL_MIPS_REFLO 05
+#define IMAGE_REL_MIPS_GPREL 06
+#define IMAGE_REL_MIPS_LITERAL 07
+#define IMAGE_REL_MIPS_SECTION 012
+#define IMAGE_REL_MIPS_SECREL 013
+#define IMAGE_REL_MIPS_REFWORDNB 042
+#define IMAGE_REL_MIPS_PAIR 045
+
+//
+// Alpha Relocation types.
+//
+
+#define IMAGE_REL_ALPHA_ABSOLUTE 0x0
+#define IMAGE_REL_ALPHA_REFLONG 0x1
+#define IMAGE_REL_ALPHA_REFQUAD 0x2
+#define IMAGE_REL_ALPHA_GPREL32 0x3
+#define IMAGE_REL_ALPHA_LITERAL 0x4
+#define IMAGE_REL_ALPHA_LITUSE 0x5
+#define IMAGE_REL_ALPHA_GPDISP 0x6
+#define IMAGE_REL_ALPHA_BRADDR 0x7
+#define IMAGE_REL_ALPHA_HINT 0x8
+#define IMAGE_REL_ALPHA_INLINE_REFLONG 0x9
+#define IMAGE_REL_ALPHA_REFHI 0xA
+#define IMAGE_REL_ALPHA_REFLO 0xB
+#define IMAGE_REL_ALPHA_PAIR 0xC
+#define IMAGE_REL_ALPHA_MATCH 0xD
+#define IMAGE_REL_ALPHA_SECTION 0xE
+#define IMAGE_REL_ALPHA_SECREL 0xF
+#define IMAGE_REL_ALPHA_REFLONGNB 0x10
+
+//
+// Based relocation format.
+//
+
+typedef struct _IMAGE_BASE_RELOCATION {
+ ULONG VirtualAddress;
+ ULONG SizeOfBlock;
+// USHORT TypeOffset[1];
+} IMAGE_BASE_RELOCATION, *PIMAGE_BASE_RELOCATION;
+
+#define IMAGE_SIZEOF_BASE_RELOCATION 8
+
+//
+// Based relocation types.
+//
+
+#define IMAGE_REL_BASED_ABSOLUTE 0
+#define IMAGE_REL_BASED_HIGH 1
+#define IMAGE_REL_BASED_LOW 2
+#define IMAGE_REL_BASED_HIGHLOW 3
+#define IMAGE_REL_BASED_HIGHADJ 4
+#define IMAGE_REL_BASED_MIPS_JMPADDR 5
+
+//
+// Line number format.
+//
+
+typedef struct _IMAGE_LINENUMBER {
+ union {
+ ULONG SymbolTableIndex; // Symbol table index of function name if Linenumber is 0.
+ ULONG VirtualAddress; // Virtual address of line number.
+ } Type;
+ USHORT Linenumber; // Line number.
+} IMAGE_LINENUMBER;
+typedef IMAGE_LINENUMBER UNALIGNED *PIMAGE_LINENUMBER;
+
+#define IMAGE_SIZEOF_LINENUMBER 6
+
+//
+// Archive format.
+//
+
+#define IMAGE_ARCHIVE_START_SIZE 8
+#define IMAGE_ARCHIVE_START "!<arch>\n"
+#define IMAGE_ARCHIVE_END "`\n"
+#define IMAGE_ARCHIVE_PAD "\n"
+#define IMAGE_ARCHIVE_LINKER_MEMBER "/ "
+#define IMAGE_ARCHIVE_LONGNAMES_MEMBER "// "
+
+typedef struct _IMAGE_ARCHIVE_MEMBER_HEADER {
+ UCHAR Name[16]; // File member name - `/' terminated.
+ UCHAR Date[12]; // File member date - decimal.
+ UCHAR UserID[6]; // File member user id - decimal.
+ UCHAR GroupID[6]; // File member group id - decimal.
+ UCHAR Mode[8]; // File member mode - octal.
+ UCHAR Size[10]; // File member size - decimal.
+ UCHAR EndHeader[2]; // String to end header.
+} IMAGE_ARCHIVE_MEMBER_HEADER, *PIMAGE_ARCHIVE_MEMBER_HEADER;
+
+#define IMAGE_SIZEOF_ARCHIVE_MEMBER_HDR 60
+
+//
+// DLL support.
+//
+
+//
+// Export Format
+//
+
+typedef struct _IMAGE_EXPORT_DIRECTORY {
+ ULONG Characteristics;
+ ULONG TimeDateStamp;
+ USHORT MajorVersion;
+ USHORT MinorVersion;
+ ULONG Name;
+ ULONG Base;
+ ULONG NumberOfFunctions;
+ ULONG NumberOfNames;
+ PULONG *AddressOfFunctions;
+ PULONG *AddressOfNames;
+ PUSHORT *AddressOfNameOrdinals;
+} IMAGE_EXPORT_DIRECTORY, *PIMAGE_EXPORT_DIRECTORY;
+
+//
+// Import Format
+//
+
+typedef struct _IMAGE_IMPORT_BY_NAME {
+ USHORT Hint;
+ UCHAR Name[1];
+} IMAGE_IMPORT_BY_NAME, *PIMAGE_IMPORT_BY_NAME;
+
+typedef struct _IMAGE_THUNK_DATA {
+ union {
+ PULONG Function;
+ ULONG Ordinal;
+ PIMAGE_IMPORT_BY_NAME AddressOfData;
+ } u1;
+} IMAGE_THUNK_DATA, *PIMAGE_THUNK_DATA;
+
+#define IMAGE_ORDINAL_FLAG 0x80000000
+#define IMAGE_SNAP_BY_ORDINAL(Ordinal) ((Ordinal & IMAGE_ORDINAL_FLAG) != 0)
+#define IMAGE_ORDINAL(Ordinal) (Ordinal & 0xffff)
+
+typedef struct _IMAGE_IMPORT_DESCRIPTOR {
+ ULONG Characteristics;
+ ULONG TimeDateStamp;
+ ULONG ForwarderChain;
+ ULONG Name;
+ PIMAGE_THUNK_DATA FirstThunk;
+} IMAGE_IMPORT_DESCRIPTOR, *PIMAGE_IMPORT_DESCRIPTOR;
+
+#if 0
+//
+// Thread Local Storage
+//
+
+typedef VOID
+(NTAPI *PIMAGE_TLS_CALLBACK) (
+ PVOID DllHandle,
+ ULONG Reason,
+ PVOID Reserved
+ );
+
+typedef struct _IMAGE_TLS_DIRECTORY {
+ ULONG StartAddressOfRawData;
+ ULONG EndAddressOfRawData;
+ PULONG AddressOfIndex;
+ PIMAGE_TLS_CALLBACK *AddressOfCallBacks;
+ ULONG SizeOfZeroFill;
+ ULONG Characteristics;
+} IMAGE_TLS_DIRECTORY, *PIMAGE_TLS_DIRECTORY;
+#endif //0
+
+
+//
+// Resource Format.
+//
+
+//
+// Resource directory consists of two counts, following by a variable length
+// array of directory entries. The first count is the number of entries at
+// beginning of the array that have actual names associated with each entry.
+// The entries are in ascending order, case insensitive strings. The second
+// count is the number of entries that immediately follow the named entries.
+// This second count identifies the number of entries that have 31-bit integer
+// Ids as their name. These entries are also sorted in ascending order.
+//
+// This structure allows fast lookup by either name or number, but for any
+// given resource entry only one form of lookup is supported, not both.
+// This is consistant with the syntax of the .RC file and the .RES file.
+//
+
+typedef struct _IMAGE_RESOURCE_DIRECTORY {
+ ULONG Characteristics;
+ ULONG TimeDateStamp;
+ USHORT MajorVersion;
+ USHORT MinorVersion;
+ USHORT NumberOfNamedEntries;
+ USHORT NumberOfIdEntries;
+// IMAGE_RESOURCE_DIRECTORY_ENTRY DirectoryEntries[];
+} IMAGE_RESOURCE_DIRECTORY, *PIMAGE_RESOURCE_DIRECTORY;
+
+#define IMAGE_RESOURCE_NAME_IS_STRING 0x80000000
+#define IMAGE_RESOURCE_DATA_IS_DIRECTORY 0x80000000
+
+//
+// Each directory contains the 32-bit Name of the entry and an offset,
+// relative to the beginning of the resource directory of the data associated
+// with this directory entry. If the name of the entry is an actual text
+// string instead of an integer Id, then the high order bit of the name field
+// is set to one and the low order 31-bits are an offset, relative to the
+// beginning of the resource directory of the string, which is of type
+// IMAGE_RESOURCE_DIRECTORY_STRING. Otherwise the high bit is clear and the
+// low-order 31-bits are the integer Id that identify this resource directory
+// entry. If the directory entry is yet another resource directory (i.e. a
+// subdirectory), then the high order bit of the offset field will be
+// set to indicate this. Otherwise the high bit is clear and the offset
+// field points to a resource data entry.
+//
+
+typedef struct _IMAGE_RESOURCE_DIRECTORY_ENTRY {
+ ULONG Name;
+ ULONG OffsetToData;
+} IMAGE_RESOURCE_DIRECTORY_ENTRY, *PIMAGE_RESOURCE_DIRECTORY_ENTRY;
+
+//
+// For resource directory entries that have actual string names, the Name
+// field of the directory entry points to an object of the following type.
+// All of these string objects are stored together after the last resource
+// directory entry and before the first resource data object. This minimizes
+// the impact of these variable length objects on the alignment of the fixed
+// size directory entry objects.
+//
+
+typedef struct _IMAGE_RESOURCE_DIRECTORY_STRING {
+ USHORT Length;
+ CHAR NameString[ 1 ];
+} IMAGE_RESOURCE_DIRECTORY_STRING, *PIMAGE_RESOURCE_DIRECTORY_STRING;
+
+
+typedef struct _IMAGE_RESOURCE_DIR_STRING_U {
+ USHORT Length;
+ WCHAR NameString[ 1 ];
+} IMAGE_RESOURCE_DIR_STRING_U, *PIMAGE_RESOURCE_DIR_STRING_U;
+
+
+//
+// Each resource data entry describes a leaf node in the resource directory
+// tree. It contains an offset, relative to the beginning of the resource
+// directory of the data for the resource, a size field that gives the number
+// of bytes of data at that offset, a CodePage that should be used when
+// decoding code point values within the resource data. Typically for new
+// applications the code page would be the unicode code page.
+//
+
+typedef struct _IMAGE_RESOURCE_DATA_ENTRY {
+ ULONG OffsetToData;
+ ULONG Size;
+ ULONG CodePage;
+ ULONG Reserved;
+} IMAGE_RESOURCE_DATA_ENTRY, *PIMAGE_RESOURCE_DATA_ENTRY;
+
+//
+// Load Configuration Directory Entry
+//
+
+typedef struct _IMAGE_LOAD_CONFIG_DIRECTORY {
+ ULONG Characteristics;
+ ULONG TimeDateStamp;
+ USHORT MajorVersion;
+ USHORT MinorVersion;
+ ULONG GlobalFlagsClear;
+ ULONG GlobalFlagsSet;
+ ULONG CriticalSectionDefaultTimeout;
+ ULONG DeCommitFreeBlockThreshold;
+ ULONG DeCommitTotalFreeThreshold;
+ PVOID LockPrefixTable;
+ ULONG MaximumAllocationSize;
+ ULONG VirtualMemoryThreshold;
+ ULONG Reserved[ 5 ];
+} IMAGE_LOAD_CONFIG_DIRECTORY, *PIMAGE_LOAD_CONFIG_DIRECTORY;
+
+
+//
+// Function table entry format for MIPS/ALPHA images. Function table is
+// pointed to by the IMAGE_DIRECTORY_ENTRY_EXCEPTION directory entry.
+// This definition duplicates ones in ntmips.h and ntalpha.h for use
+// by portable image file mungers.
+//
+
+typedef struct _IMAGE_RUNTIME_FUNCTION_ENTRY {
+ ULONG BeginAddress;
+ ULONG EndAddress;
+ PVOID ExceptionHandler;
+ PVOID HandlerData;
+ ULONG PrologEndAddress;
+} IMAGE_RUNTIME_FUNCTION_ENTRY, *PIMAGE_RUNTIME_FUNCTION_ENTRY;
+
+//
+// Debug Format
+//
+
+typedef struct _IMAGE_DEBUG_DIRECTORY {
+ ULONG Characteristics;
+ ULONG TimeDateStamp;
+ USHORT MajorVersion;
+ USHORT MinorVersion;
+ ULONG Type;
+ ULONG SizeOfData;
+ ULONG AddressOfRawData;
+ ULONG PointerToRawData;
+} IMAGE_DEBUG_DIRECTORY, *PIMAGE_DEBUG_DIRECTORY;
+
+#define IMAGE_DEBUG_TYPE_UNKNOWN 0
+#define IMAGE_DEBUG_TYPE_COFF 1
+#define IMAGE_DEBUG_TYPE_CODEVIEW 2
+#define IMAGE_DEBUG_TYPE_FPO 3
+#define IMAGE_DEBUG_TYPE_MISC 4
+#define IMAGE_DEBUG_TYPE_EXCEPTION 5
+#define IMAGE_DEBUG_TYPE_FIXUP 6
+#define IMAGE_DEBUG_TYPE_OMAP_TO_SRC 7
+#define IMAGE_DEBUG_TYPE_OMAP_FROM_SRC 8
+
+typedef struct _IMAGE_COFF_SYMBOLS_HEADER {
+ ULONG NumberOfSymbols;
+ ULONG LvaToFirstSymbol;
+ ULONG NumberOfLinenumbers;
+ ULONG LvaToFirstLinenumber;
+ ULONG RvaToFirstByteOfCode;
+ ULONG RvaToLastByteOfCode;
+ ULONG RvaToFirstByteOfData;
+ ULONG RvaToLastByteOfData;
+} IMAGE_COFF_SYMBOLS_HEADER, *PIMAGE_COFF_SYMBOLS_HEADER;
+
+#define FRAME_FPO 0
+#define FRAME_TRAP 1
+#define FRAME_TSS 2
+
+typedef struct _FPO_DATA {
+ ULONG ulOffStart; // offset 1st byte of function code
+ ULONG cbProcSize; // # bytes in function
+ ULONG cdwLocals; // # bytes in locals/4
+ USHORT cdwParams; // # bytes in params/4
+ USHORT cbProlog : 8; // # bytes in prolog
+ USHORT cbRegs : 3; // # regs saved
+ USHORT fHasSEH : 1; // TRUE if SEH in func
+ USHORT fUseBP : 1; // TRUE if EBP has been allocated
+ USHORT reserved : 1; // reserved for future use
+ USHORT cbFrame : 2; // frame type
+} FPO_DATA, *PFPO_DATA;
+#define SIZEOF_RFPO_DATA 16
+
+
+#define IMAGE_DEBUG_MISC_EXENAME 1
+
+typedef struct _IMAGE_DEBUG_MISC {
+ ULONG DataType; // type of misc data, see defines
+ ULONG Length; // total length of record, rounded to four
+ // byte multiple.
+ BOOLEAN Unicode; // TRUE if data is unicode string
+ UCHAR Reserved[ 3 ];
+ UCHAR Data[ 1 ]; // Actual data
+} IMAGE_DEBUG_MISC, *PIMAGE_DEBUG_MISC;
+
+
+//
+// Debugging information can be stripped from an image file and placed
+// in a separate .DBG file, whose file name part is the same as the
+// image file name part (e.g. symbols for CMD.EXE could be stripped
+// and placed in CMD.DBG). This is indicated by the IMAGE_FILE_DEBUG_STRIPPED
+// flag in the Characteristics field of the file header. The beginning of
+// the .DBG file contains the following structure which captures certain
+// information from the image file. This allows a debug to proceed even if
+// the original image file is not accessable. This header is followed by
+// zero of more IMAGE_SECTION_HEADER structures, followed by zero or more
+// IMAGE_DEBUG_DIRECTORY structures. The latter structures and those in
+// the image file contain file offsets relative to the beginning of the
+// .DBG file.
+//
+// If symbols have been stripped from an image, the IMAGE_DEBUG_MISC structure
+// is left in the image file, but not mapped. This allows a debugger to
+// compute the name of the .DBG file, from the name of the image in the
+// IMAGE_DEBUG_MISC structure.
+//
+
+typedef struct _IMAGE_SEPARATE_DEBUG_HEADER {
+ USHORT Signature;
+ USHORT Flags;
+ USHORT Machine;
+ USHORT Characteristics;
+ ULONG TimeDateStamp;
+ ULONG CheckSum;
+ ULONG ImageBase;
+ ULONG SizeOfImage;
+ ULONG NumberOfSections;
+ ULONG ExportedNamesSize;
+ ULONG DebugDirectorySize;
+ ULONG Reserved[ 3 ];
+} IMAGE_SEPARATE_DEBUG_HEADER, *PIMAGE_SEPARATE_DEBUG_HEADER;
+
+#define IMAGE_SEPARATE_DEBUG_SIGNATURE 0x4944
+
+#ifndef RC_INVOKED
+#pragma pack ()
+#endif // !RC_INVOKED
+
+//
+// End Image Format
+//
+
+// end_winnt
+
+#endif // _NTIMAGE_
diff --git a/private/oleauto/src/typelib/ntstring.cxx b/private/oleauto/src/typelib/ntstring.cxx
new file mode 100644
index 000000000..e21a31f4e
--- /dev/null
+++ b/private/oleauto/src/typelib/ntstring.cxx
@@ -0,0 +1,397 @@
+/***
+* ntstring.cxx - Multibyte interface to Wide Character APIs
+*
+* Copyright (C) 1993-1994, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Purpose:
+* This module provides handy functions which can be used to manipulate
+* LPOLESTR strings on both Win32 (Unicode) and Win16/Mac (Ansi)
+*
+* Revision History:
+*
+* [00] 12-Aug-93 w-barryb: Module created.
+* [01] 22-Jun-94 barrybo: Revived for Chicago/Daytona unicode
+*
+* Implementation Notes:
+*
+*****************************************************************************/
+
+#include <errno.h>
+#include <sys/stat.h>
+#include "silver.hxx"
+
+#pragma hdrstop(RTPCHNAME)
+
+#if !OE_WIN32
+#error This file is NT-only
+#endif //!OE_WIN32
+
+#include "debug.h"
+#include "ntstring.h"
+#include "winerror.h"
+#include "mem.hxx" // for MemAlloc, MemFree
+#include "convert.hxx"
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+static char szNtString[] = __FILE__;
+#define SZ_FILE_NAME szNtString
+#endif
+
+#ifdef _X86_
+extern "C" BOOL g_fChicago;
+#endif //_X86_
+
+
+
+
+
+
+
+
+
+
+LONG APIENTRY oRegSetValue (HKEY hKey, LPCWSTR lpSubKey, DWORD dwType, LPCWSTR lpData, DWORD cbData)
+{
+ DebAssert(lpSubKey == NULL, "lpSubKey is not required by our callers");
+
+#ifdef _X86_
+ if (g_fChicago) {
+ LPSTR szAnsi;
+ int cbAnsi;
+ LONG ret;
+
+ cbAnsi = WideCharToMultiByte(CP_ACP, 0, lpData, cbData, NULL, 0, NULL, NULL);
+ if (cbAnsi == 0)
+ return NULL;
+
+ szAnsi = (LPSTR)MemAlloc(cbAnsi);
+ if (szAnsi == NULL)
+ return NULL;
+
+ if (WideCharToMultiByte(CP_ACP, 0, lpData, cbData, szAnsi, cbAnsi, NULL, NULL) == 0) {
+ MemFree(szAnsi);
+ return NULL;
+ }
+
+ ret = RegSetValueA(hKey, NULL /* lpSubKey */, dwType, szAnsi, cbAnsi);
+
+ MemFree(szAnsi);
+
+ return ret;
+
+ } else
+#endif //_X86_
+ return RegSetValueW(hKey, lpSubKey, dwType, lpData, cbData);
+}
+
+DWORD APIENTRY oWNetGetConnection (LPCWSTR lpLocalName, LPWSTR lpRemoteName, LPDWORD lpnLength)
+{
+ UINT drivetype;
+
+ DebAssert(*lpnLength == 40, "All callers pass a fixed-length string");
+ DebAssert(wcslen(lpLocalName) == 2, "All callers pass a fixed-length string");
+ DebAssert(lpLocalName[1] == ':', "All callers pass a drive letter only");
+
+
+#ifdef _X86_
+ if (g_fChicago) {
+ CHAR szRemoteName[40];
+ CHAR szLocalName[4];
+ DWORD ret;
+
+ if (WideCharToMultiByte(CP_ACP, 0, lpLocalName, 2, szLocalName, sizeof(szLocalName), NULL, NULL) == 0)
+ return ERROR_MORE_DATA;
+
+ // Performance: WNetGetConnection is slow, so call GetDriveType do
+ // determine if the drive letter is really a local drive or not.
+ szLocalName[2] = '\\'; // GetDriveType expects a root dir (ie.
+ szLocalName[3] = '\0';
+ drivetype = GetDriveType(szLocalName);
+ szLocalName[2] = '\0'; // WNetGetConnection wants a drive and a colon only.
+
+ if ( DRIVE_FIXED == drivetype ||
+ DRIVE_CDROM == drivetype ||
+ DRIVE_RAMDISK == drivetype ||
+ DRIVE_REMOVABLE == drivetype) {
+ return ERROR_NOT_CONNECTED;
+ }
+
+ ret = WNetGetConnectionA(szLocalName, szRemoteName, lpnLength);
+
+ if (ret != NO_ERROR)
+ return ret;
+
+ if (MultiByteToWideChar(CP_ACP, 0, szRemoteName, -1, lpRemoteName, *lpnLength) == 0)
+ return ERROR_MORE_DATA;
+
+ return NO_ERROR;
+
+ } else
+#endif //_X86_
+ {
+ OLECHAR szLocalRootDir[4];
+
+ // GetDriveType() must be passed the root directory (ie "C:\")
+ szLocalRootDir[0] = lpLocalName[0];
+ szLocalRootDir[1] = lpLocalName[1];
+ szLocalRootDir[2] = '\\';
+ szLocalRootDir[3] = '\0';
+
+ // Performance: WNetGetConnection is slow, so call GetDriveType do
+ // determine if the drive letter is really a local drive or not.
+ drivetype = GetDriveTypeW(szLocalRootDir);
+
+ if ( DRIVE_FIXED == drivetype ||
+ DRIVE_CDROM == drivetype ||
+ DRIVE_RAMDISK == drivetype ||
+ DRIVE_REMOVABLE == drivetype) {
+ return ERROR_NOT_CONNECTED;
+ }
+
+ return WNetGetConnectionW(lpLocalName, lpRemoteName, lpnLength);
+ }
+}
+
+LONG APIENTRY oRegOpenKey (HKEY hKey, LPCWSTR lpSubKey, PHKEY phkResult)
+{
+#ifdef _X86_
+ if (g_fChicago) {
+ char rgchSubKey[50];
+
+ DebAssert(wcslen(lpSubKey) < 50, "ANSI buffer too small");
+ if (WideCharToMultiByte(CP_ACP, 0, lpSubKey, -1, rgchSubKey, sizeof(rgchSubKey), NULL, NULL) == 0)
+ return ERROR_OUTOFMEMORY;
+
+ return RegOpenKeyA(hKey, rgchSubKey, phkResult);
+
+ } else
+#endif //_X86_
+ return RegOpenKeyW(hKey, lpSubKey, phkResult);
+}
+
+
+#if OE_OB
+STDAPI LoadTypeLibA(const char FAR* szFile, ITypeLib FAR* FAR* pptlib)
+{
+ LPOLESTR lpwstr;
+ HRESULT err;
+
+ err = ConvertStringToW(szFile, &lpwstr);
+ if (err)
+ return err;
+
+ err = LoadTypeLib(lpwstr, pptlib);
+
+ ConvertStringFree((LPSTR)lpwstr);
+
+ return err;
+}
+#endif //EI_OB
+
+#if 0
+STDAPI RegisterTypeLibA(ITypeLib FAR* ptlib, char FAR* szFullPath, char FAR* szHelpDir)
+{
+ LPOLESTR lpwstrPath, lpwstrHelp;
+ HRESULT err;
+
+ err = ConvertStringToW(szFullPath, &lpwstrPath);
+ if (err)
+ return err;
+
+ err = ConvertStringToW(szHelpDir, &lpwstrHelp);
+ if (err) {
+ ConvertStringFree((LPSTR)lpwstrPath);
+ return err;
+ }
+
+ err = RegisterTypeLib(ptlib, lpwstrPath, lpwstrHelp);
+
+ ConvertStringFree((LPSTR)lpwstrPath);
+ ConvertStringFree((LPSTR)lpwstrHelp);
+
+ return err;
+}
+#endif //0
+
+
+
+
+
+
+
+
+
+LONG APIENTRY oRegEnumKey(HKEY hKey, DWORD dwIndex, LPWSTR lpName, DWORD cbName)
+{
+#ifdef _X86_
+ if (g_fChicago) {
+ LONG ret;
+ LPSTR lpNameA = (LPSTR)MemAlloc(cbName*2);
+
+ if (lpNameA == NULL)
+ return E_OUTOFMEMORY;
+
+ ret = RegEnumKeyA(hKey, dwIndex, lpNameA, cbName*2);
+
+ if (ret == ERROR_SUCCESS)
+ if (MultiByteToWideChar(CP_ACP, 0, lpNameA, -1, lpName, cbName) == 0)
+ ret = E_OUTOFMEMORY;
+
+ MemFree(lpNameA);
+
+ return ret;
+
+ } else
+#endif //_X86_
+ return RegEnumKeyW(hKey, dwIndex, lpName, cbName);
+}
+
+
+
+int ostat(const OLECHAR *pathname, struct _stat *buffer)
+{
+ char oempath[_MAX_PATH+1];
+
+ // translate from Unicode to OEM characters (NOT ANSI!!)
+ if (WideCharToMultiByte(CP_OEMCP, 0, pathname, -1, oempath, _MAX_PATH+1, NULL, NULL) == 0) {
+ return -1;
+ }
+
+#if OE_WIN32 && _X86_
+ // win32s is wierd, and returns 0 for _stat("");
+ if (*oempath == '\0')
+ return -1;
+#endif //OE_WIN32
+ return _stat(oempath, buffer);
+}
+
+
+
+HFILE WINAPI oOpenFile(LPCWSTR lpFileName, LPOFSTRUCT lpReOpenBuff, UINT uStyle)
+{
+ char lpAnsiName[_MAX_PATH+1];
+
+ // convert from Unicode to OEM characters (NOT ANSI!!)
+ if (WideCharToMultiByte(CP_OEMCP, 0, lpFileName, -1, lpAnsiName, _MAX_PATH+1, NULL, NULL) == 0)
+ return HFILE_ERROR; // GetLastError() will report whatever the error was
+
+ return OpenFile(lpAnsiName, lpReOpenBuff, uStyle);
+}
+
+
+
+LONG APIENTRY oRegQueryValue (HKEY hKey, LPCWSTR lpSubKey, LPWSTR lpValue, PLONG lpcbValue)
+{
+ DebAssert(lpValue != NULL, "Querying key size is NYI");
+
+#ifdef _X86_
+ if (g_fChicago) {
+ LONG cbAnsiValue, ret;
+ LPSTR lpSubKeyA;
+ LPSTR lpValueA;
+
+ if (ConvertStringToA(lpSubKey, &lpSubKeyA))
+ return ERROR_OUTOFMEMORY;
+
+ // get the required size of the buffer to receive the Ansi value into
+ ret = RegQueryValueA(hKey, lpSubKeyA, NULL, &cbAnsiValue);
+ if (ret != ERROR_SUCCESS) {
+ ConvertStringFree(lpSubKeyA);
+ return ret;
+ }
+
+ lpValueA = (LPSTR)MemAlloc(cbAnsiValue);
+ if (lpValueA == NULL) {
+ ConvertStringFree(lpSubKeyA);
+ return ERROR_OUTOFMEMORY;
+ }
+
+ ret = RegQueryValueA(hKey, lpSubKeyA, lpValueA, &cbAnsiValue);
+
+ if (ret == ERROR_SUCCESS) {
+ if (MultiByteToWideChar(CP_ACP, 0, lpValueA, cbAnsiValue, lpValue, *lpcbValue) == 0)
+ ret = GetLastError();
+ }
+
+ MemFree(lpValueA);
+ ConvertStringFree(lpSubKeyA);
+
+ return ret;
+ } else
+#endif //_X86_
+ return RegQueryValueW(hKey, lpSubKey, lpValue, lpcbValue);
+}
+
+
+LONG APIENTRY oRegCreateKey (HKEY hKey, LPCWSTR lpSubKey, PHKEY phkResult)
+{
+#ifdef _X86_
+ if (g_fChicago) {
+ LPSTR lpSubKeyA;
+ LONG ret;
+
+ if (ConvertStringToA(lpSubKey, &lpSubKeyA))
+ return ERROR_OUTOFMEMORY;
+
+ ret = RegCreateKeyA(hKey, lpSubKeyA, phkResult);
+
+ ConvertStringFree(lpSubKeyA);
+
+ return ret;
+
+ } else
+#endif //_X86_
+ return RegCreateKeyW(hKey, lpSubKey, phkResult);
+}
+
+
+// defined in CRT.LIB, but not in CRTDLL.LIB
+wchar_t * _CRTAPI1 _ultow (unsigned long val, wchar_t *buf, int radix)
+{
+ char temp[34]; // C help for ultoa says the max. string length is 33 bytes
+
+ _ultoa(val, temp, radix);
+
+ MultiByteToWideChar(CP_ACP, 0, temp, -1, buf, 34);
+
+ return buf;
+}
+
+#if 0 //Dead Code
+// defined in CRT.LIB, but not in CRTDLL.LIB
+wchar_t * _CRTAPI1 _itow (int val, wchar_t *buf, int radix)
+{
+ char temp[18]; // C help for ultoa says the max. string length is 17 bytes
+
+ _itoa(val, temp, radix);
+
+ MultiByteToWideChar(CP_ACP, 0, temp, -1, buf, 18);
+
+ return buf;
+}
+#endif //0
+
+// defined in CRT.LIB, but not in CRTDLL.LIB
+int _CRTAPI1 _wtoi(const wchar_t *nptr)
+{
+ char temp[16]; // big enough for any kind of signed integer value
+
+ WideCharToMultiByte(CP_ACP, 0, nptr, -1, temp, sizeof(temp), NULL, NULL);
+
+ return atoi(temp);
+}
+
+
+#if 0 //Dead Code
+// defined in CRT.LIB, but not in CRTDLL.LIB
+long _CRTAPI1 _wtol(const wchar_t *nptr)
+{
+ char temp[16]; // big enough for any kind of signed long value
+
+ WideCharToMultiByte(CP_ACP, 0, nptr, -1, temp, sizeof(temp), NULL, NULL);
+
+ return atol(temp);
+}
+#endif //0
diff --git a/private/oleauto/src/typelib/ntstring.h b/private/oleauto/src/typelib/ntstring.h
new file mode 100644
index 000000000..510d3d91a
--- /dev/null
+++ b/private/oleauto/src/typelib/ntstring.h
@@ -0,0 +1,153 @@
+/***
+* ntstring.h - Wide Character interface to Multibyte APIs
+*
+* Copyright (C) 1994, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+* Purpose:
+* This module provides handy functions which can be used to manipulate
+* LPOLESTR strings on both Win32 (Unicode) and Win16/Mac (Ansi)
+*
+*
+* Revision History:
+*
+* [00] 12-Aug-93 w-barryb: Module created.
+* [01] 22-Jun-94 barrybo: Revived for Chicago/Daytona unicode
+*
+* Implementation Notes:
+*
+*****************************************************************************/
+
+#ifndef NTSTRING_H_INCLUDED
+#define NTSTRING_H_INCLUDED
+
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#if OE_WIN32
+
+#define ostrcat wcscat
+#define ostrchr wcschr
+#define ostrcpy wcscpy
+#define ostrlen wcslen
+#define ostricmp wcsicmp
+#define ostrcmp wcscmp
+#define ostrncmp wcsncmp
+#define ostrpbrk wcspbrk
+#define ostrblen(x) wcslen(x) //NOTE: returns count of characters - not BYTES
+#define ostrblen0(x) (wcslen(x)+1) //NOTE: returns count of characters - not BYTES
+#define ostrrchr wcsrchr
+#define ostrncpy wcsncpy
+#define ostrinc(p) ((p)+1)
+#define ostrdec(s,p) ((p)-1)
+#define ostrnicmp wcsnicmp
+#define ostrncat wcsncat
+#define ogetc(p) (*(p))
+
+#define oultoa _ultow
+#define ostrtoul wcstoul
+#define ostrtod wcstod
+#define oisxdigit iswxdigit
+#define oisspace iswspace
+#define oisdigit iswdigit
+#define oatoi _wtoi
+#if 0
+#define oitoa _itow
+#define oatol _wtol
+#endif
+
+
+HFILE WINAPI oOpenFile(LPCWSTR lpFileName, LPOFSTRUCT lpReOpenBuff, UINT uStyle);
+LONG APIENTRY oRegSetValue (HKEY hKey, LPCWSTR lpSubKey, DWORD dwType, LPCWSTR lpData, DWORD cbData);
+LONG APIENTRY oRegQueryValue (HKEY hKey, LPCWSTR lpSubKey, LPWSTR lpValue, PLONG lpcbValue);
+LONG APIENTRY oRegCreateKey (HKEY hKey, LPCWSTR lpSubKey, PHKEY phkResult);
+DWORD APIENTRY oWNetGetConnection (LPCWSTR lpLocalName, LPWSTR lpRemoteName, LPDWORD lpnLength);
+LONG APIENTRY oRegOpenKey (HKEY hKey, LPCWSTR lpSubKey, PHKEY phkResult);
+OLECHAR oIntlNormCharFromStr(LCID, OLECHAR *, int, OLECHAR **);
+OLECHAR oIntlNormChar(LCID, OLECHAR);
+#define oIntlNormStr IntlNormStrW
+#define LHashValOfNameA(lcid, szName) \
+ LHashValOfNameSysA(SYS_WIN32, lcid, szName)
+LONG APIENTRY oRegEnumKey(HKEY kKey, DWORD dwIndex, LPWSTR lpName, DWORD cbName);
+int ostat(const OLECHAR *pathname, struct _stat *buffer);
+
+#else
+
+#define ostrcat xstrcat
+#define ostrchr xstrchr
+#define ostrcpy xstrcpy
+#define omemset memset
+#define ostrlen xstrlen
+#define ostricmp xstricmp
+#define ostrcmp xstrcmp
+#define ostrncmp xstrncmp
+#define ostrpbrk xstrpbrk
+#define ostrblen(x) xstrblen(x)
+#define ostrblen0(x) xstrblen0(x)
+#define ostrrchr xstrrchr
+#define ostrinc(x) xstrinc(x)
+#define ostrdec(s,p) xstrdec(s,p)
+#define ostrncpy xstrncpy
+#define ostrnicmp xstrnicmp
+#define ostrncat xstrncat
+#define ogetc xgetc
+
+#define oultoa _ultoa
+#define ostrtoul strtoul
+#define ostrtod strtod
+#define oisxdigit isxdigit
+#define oisspace ISSPACE
+#define oisdigit ISDIGIT
+#define oitoa itoa
+#define oatoi atoi
+#define oatol atol
+
+#define oLCMapString LCMapStringA
+#define oGetLocaleInfo GetLocaleInfoA
+#define oCompareString CompareStringA
+#define oFindWindow FindWindow
+#define oVarDateFromStr VarDateFromStr
+#define oVarR8FromStr VarR8FromStr
+#define oVarCyFromStr VarCyFromStr
+#define oRegSetValue RegSetValue
+#define oRegOpenKey RegOpenKey
+#define oRegQueryValue RegQueryValue
+#define oRegCreateKey RegCreateKey
+#define oIntlNormStr IntlNormStr
+#define oIntlNormCharFromStr IntlNormCharFromStr
+#define oIntlNormChar IntlNormChar
+#define LHashValOfNameA LHashValOfName
+#define LHashValOfNameSysA LHashValOfNameSys
+#define RegisterTypeLibA RegisterTypeLib
+#define CreateTypeLibA CreateTypeLib
+#define CLSIDFromStringA CLSIDFromString
+#define StringFromCLSIDA StringFromCLSID
+#define StringFromGUID2A StringFromGUID2
+#define ofullpath _fullpath
+#define oRegEnumKey RegEnumKey
+#define ostat _stat
+#define oLoadLibrary LoadLibrary
+#define oOpenFile OpenFile
+
+// this is a helper even on Win16/Mac (defined in clutil.cxx)
+UINT WINAPI oWNetGetConnection(LPSTR, LPSTR, UINT FAR*);
+
+#if OE_WIN16
+#define oCharUpperBuff AnsiUpperBuff
+#define oCharLowerBuff AnsiLowerBuff
+#else
+#define oCharUpperBuff CharUpperBuff
+#define oCharLowerBuff CharLowerBuff
+#endif
+
+#endif
+
+#ifdef __cplusplus
+}
+#endif
+
+
+
+#endif
diff --git a/private/oleauto/src/typelib/oautil.cxx b/private/oleauto/src/typelib/oautil.cxx
new file mode 100644
index 000000000..79305c612
--- /dev/null
+++ b/private/oleauto/src/typelib/oautil.cxx
@@ -0,0 +1,522 @@
+/**
+*oautil.cxx - OLE Automation-wide utility routines
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Holds all of the per-process and per-thread information for OLE Autmation.
+*
+*Revision History:
+*
+* 23-Nov-94 andrewso: Created.
+*
+*****************************************************************************/
+
+#include "typelib.hxx"
+#include "silver.hxx"
+
+#if OE_WIN32
+#include "oautil.h"
+#endif // OE_WIN32
+
+#pragma hdrstop(RTPCHNAME)
+
+// Per-app APP_DATA instance
+ITLS g_itlsAppData = ITLS_EMPTY;
+
+#if !OE_WIN32
+// AppData cache speeds up Pappdata.
+extern "C" {
+ TID g_tidAppdataCache = NULL; // cache threadid to speed up Pappdata
+ APP_DATA* g_pAppdataCache = NULL; // pointer to equivalent thread
+}
+#endif // !OE_WIN32
+
+#if OE_WIN32
+// Per process AO table.
+AppObjectTable g_AppObjectTable;
+
+STDAPI CoSetState(IUnknown FAR *punk);
+STDAPI_(void) ReleaseBstrCache(APP_DATA *);
+#endif // OE_WIN32
+
+#if !OE_WIN32
+/***
+*APP_DATA *Pappdata()
+*
+*Purpose:
+* Returns per-app struct shared by typelib and obrun.
+*
+*Inputs:
+*
+*Outputs:
+* APP_DATA *
+*
+******************************************************************************/
+#pragma code_seg(CS_INIT)
+APP_DATA *Pappdata()
+{
+ // If the APP_DATA has not yet been allocated, return NULL.
+ if (g_itlsAppData == ITLS_EMPTY)
+ return NULL;
+ TlsCache(g_itlsAppData, (LPVOID *)&g_pAppdataCache, &g_tidAppdataCache);
+ return g_pAppdataCache;
+}
+#pragma code_seg()
+#endif // !OE_WIN32
+
+#if OE_MAC
+// flag for initialization of the lead byte table
+static BOOL fLeadByteTableInit = FALSE;
+#endif //OE_MAC
+
+
+#if OE_WIN32
+/***
+*HRESULT InitProcessData()
+*
+*Purpose:
+* Initialize the per-process data used by OLE Automation.
+*
+*Inputs:
+*
+*Outputs:
+* HRESULT
+*
+******************************************************************************/
+
+HRESULT InitProcessData()
+{
+ if (g_itlsAppData == ITLS_EMPTY) {
+ // Check if the APP_DATA has been initialized.
+ if ((g_itlsAppData = TlsAlloc()) == ITLS_EMPTY) {
+ return TIPERR_OutOfMemory;
+ }
+ }
+
+ return TIPERR_None;
+}
+#endif // OE_WIN32
+
+#if OE_WIN32
+/***
+*HRESULT ReleaseProcessData()
+*
+*Purpose:
+* Destroy the per-process data.
+*
+*Inputs:
+*
+*Outputs:
+*
+******************************************************************************/
+
+VOID ReleaseProcessData()
+{
+ TlsFree(g_itlsAppData);
+
+#if ID_DEBUG
+ g_AppObjectTable.DebIsTableEmpty();
+#endif // ID_DEBUG
+}
+
+/***
+*CReleaseAppData, etc
+*
+*Purpose:
+* Silly class that exists for the sole purpose of calling ReleaseAppData
+* at OleUninitialize time.
+*
+*Inputs:
+*
+*Outputs:
+*
+******************************************************************************/
+
+class CReleaseAppData
+{
+ STDMETHOD(QueryInterface)(REFIID riid, void ** ppvObj);
+ STDMETHOD_(unsigned long, AddRef)();
+ STDMETHOD_(unsigned long, Release)();
+};
+
+STDMETHODIMP
+CReleaseAppData::QueryInterface(REFIID riid, void ** ppvObj)
+{
+ return E_NOTIMPL; // shouldn't ever be called
+};
+
+STDMETHODIMP_(unsigned long)
+CReleaseAppData::AddRef()
+{
+ return 1; // shouldn't ever be called
+};
+
+STDMETHODIMP_(unsigned long)
+CReleaseAppData::Release()
+{
+ ReleaseAppData();
+ return 0; // should only be called once
+};
+
+static CReleaseAppData MyReleaseAppData;
+
+#endif // OE_WIN32
+
+/***
+*TIPERROR InitAppData()
+*
+*Purpose:
+* Initializes per-app data that is used by typelib.dll.
+* The point is that typelib.dll can't use
+* the per-app EBAPP struct since it is OB only.
+*
+*Inputs:
+*
+*Outputs:
+* TIPERROR
+*
+******************************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR InitAppData()
+{
+ APP_DATA *pappdata;
+ IMalloc FAR* pmalloc;
+ TIPERROR err;
+
+#if !OE_WIN32
+ // Check if the APP_DATA has been initialized.
+ if (g_itlsAppData == ITLS_EMPTY) {
+ if ((g_itlsAppData = TlsAlloc()) == ITLS_EMPTY)
+ return TIPERR_OutOfMemory;
+ }
+#endif // !OE_WIN32
+
+ if ((pappdata = (APP_DATA *)TlsGetValue(g_itlsAppData)) == NULL) {
+ // 1st call for this instance
+
+#if OE_MAC // for OE_WIN16 and OE_WIN32, this is done by LibMain/DllMain
+ // init mbstring lead byte table
+ if (!fLeadByteTableInit) {
+ InitMbString();
+ fLeadByteTableInit = TRUE;
+ }
+#endif //OE_MAC
+
+ if (CoGetMalloc(MEMCTX_TASK, &pmalloc)) {
+ return TIPERR_OutOfMemory;
+ }
+
+ // allocate struct for the Appdata
+ pappdata =(APP_DATA *) pmalloc->Alloc(sizeof(APP_DATA));
+ if (pappdata == NULL) {
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+
+ // Call the constructor for APP_DATA
+ pappdata = new(pappdata) APP_DATA;
+
+ // Cache the pointer to IMalloc in App_Data
+ pappdata->m_pimalloc = pmalloc;
+
+ // Cache the value of the g_itlsAppData
+ if (!TlsSetValue(g_itlsAppData, pappdata)) {
+ err = TIPERR_OutOfMemory;
+ goto Error2;
+ }
+
+ // Invalidate the cache, so the next attempt to get the appdata
+ // will succeed.
+#if !OE_WIN32
+ // Invalidate the cache also.
+ g_tidAppdataCache = TID_EMPTY;
+#endif
+
+ // Initialize the OLE_TYPEMGR.
+ IfErrGoTo(OLE_TYPEMGR::Create(&pappdata->m_poletmgr), Error3);
+
+#if OE_WIN32
+ // lastly, tell OLE to call us back at OleUninitialize time for this
+ // thread, so we can clean up after ourselves.
+ IfErrGoTo(CoSetState((IUnknown *)&MyReleaseAppData), Error4);
+#endif //OE_WIN32
+ }
+
+ return TIPERR_None;
+
+#if OE_WIN32
+Error4:
+ pappdata->m_poletmgr->Release();
+#endif // OE_WIN32
+
+Error3:
+ TlsSetValue(g_itlsAppData, NULL);
+
+Error2:
+ pmalloc->Free(pappdata);
+
+Error:
+ pmalloc->Release();
+ return err;
+}
+#pragma code_seg()
+
+/***
+*VOID ReleaseAppData()
+*
+*Purpose:
+* Release per-app data that is shared by both typelib.dll
+* and obrun.dll. The point is that typelib.dll can't use
+* the per-app EBAPP struct since it is OB only.
+*
+*Inputs:
+*
+*Outputs:
+*
+******************************************************************************/
+#pragma code_seg(CS_INIT)
+VOID ReleaseAppData()
+{
+ APP_DATA *pappdata;
+ IMalloc *pmalloc;
+
+ DebAssert(g_itlsAppData != ITLS_EMPTY, "bad itls.");
+
+ if (pappdata = Pappdata()) {
+
+ if (pappdata->m_ptlibStdole)
+ pappdata->m_ptlibStdole->Release();
+
+#if OE_WIN32
+ g_AppObjectTable.Release();
+#endif // OE_WIN32
+
+ pappdata->m_poletmgr->Release();
+
+ pmalloc = pappdata->m_pimalloc;
+
+#if OE_WIN32
+ if (pappdata->m_perrinfo != NULL) {
+ pappdata->m_perrinfo->Release();
+ }
+
+ ReleaseBstrCache(pappdata); // no BSTR ops must happen after this.
+#endif // OE_WIN32
+
+ pmalloc->Free(pappdata);
+
+ // Release the IMalloc
+ pmalloc->Release();
+
+ // releases this app's resources
+ TlsSetValue(g_itlsAppData, NULL);
+
+#if !OE_WIN32
+ // Invalidate the cache also.
+ g_tidAppdataCache = TID_EMPTY;
+#endif
+ }
+}
+#pragma code_seg()
+
+
+#if OE_WIN32
+/***
+*PUBLIC AppObjectTable::Release()
+*
+*Purpose:
+* Release the app object table.
+*
+*Inputs:
+*
+*Outputs:
+*
+******************************************************************************/
+
+VOID AppObjectTable::Release()
+{
+ UINT iNode;
+
+ if (m_rgaotbl == NULL) {
+ return;
+ }
+
+ // Loop over all of the nodes, seeing if ANY of them
+ // still have a reference.
+ //
+ for (iNode = 0; iNode < m_cNodes; iNode++) {
+ // If there is a reference left, don't do anything.
+ if (m_rgaotbl[iNode].m_cRefs != 0) {
+ return;
+ }
+ }
+
+ // Delete the pv members.
+ for (iNode = 0; iNode < m_cNodes; iNode++) {
+ MemFree((VOID *)m_rgaotbl[iNode].m_ppv);
+ }
+
+ // Delete the node table.
+ MemFree(m_rgaotbl);
+ m_rgaotbl = NULL;
+
+ // Get rid of the critical section.
+ DeleteCriticalSection(&m_criticalsection);
+
+ return;
+}
+
+#if ID_DEBUG
+/***
+*PUBLIC AppObjectTable::DebIsTableEmpty()
+*
+*Purpose:
+* Make sure the table has been completely released.
+*
+*Inputs:
+*
+*Outputs:
+*
+******************************************************************************/
+
+VOID AppObjectTable::DebIsTableEmpty()
+{
+ DebAssert(m_rgaotbl == NULL, "Table not empty.");
+}
+#endif // ID_DEBUG
+
+/***
+*PUBLIC AppObjectTable::AddTypeLib()
+*
+*Purpose:
+* Add a new typelib to the appobject table.
+*
+*Inputs:
+* clsid - the IID of the typeinfo
+*
+*Outputs:
+* phtinfo - the handle of the typelib in this table.
+*
+******************************************************************************/
+
+HRESULT AppObjectTable::AddTypeInfo(CLSID *pclsid,
+ HTINFO *phtinfo)
+{
+ AOTABLE_NODE *paotblNew;
+ UINT iNode;
+ HRESULT hresult = NOERROR;
+
+ EnterCriticalSection(&m_criticalsection);
+
+ // See if it already exists in the table.
+ for (iNode = 0; iNode < m_cNodes; iNode++) {
+ if (m_rgaotbl[iNode].m_clsid == *pclsid) {
+ // Increment the reference count and return.
+ m_rgaotbl[iNode].m_cRefs++;
+ DebAssert(m_rgaotbl[iNode].m_cRefs != 0, "Overflow");
+
+ *phtinfo = iNode;
+
+ goto Exit;
+ }
+ }
+
+ // Doesn't exist in the table, add a new entry for it.
+ paotblNew = (AOTABLE_NODE *)MemRealloc(m_rgaotbl,
+ (m_cNodes + 1) * sizeof(AOTABLE_NODE));
+
+ if (paotblNew == NULL) {
+ hresult = ResultFromScode(E_OUTOFMEMORY);
+ goto Exit;
+ }
+
+ m_rgaotbl = paotblNew;
+
+ // Allocate the member to return. If it fails, just return. We'll
+ // fix up the size of the allocate node array the next time we add
+ // a new member.
+ //
+ if (!(m_rgaotbl[iNode].m_ppv = (VOID **)MemZalloc(sizeof(VOID *)))) {
+ hresult = ResultFromScode(E_OUTOFMEMORY);
+ goto Exit;
+ }
+
+ // Initialize the new entry. iNode has the correct value from the
+ // above for loop.
+ //
+ m_rgaotbl[iNode].m_clsid = *pclsid;
+ m_rgaotbl[iNode].m_cRefs = 1;
+
+ // Increase the table size.
+ m_cNodes++;
+
+ // Return the handle.
+ *phtinfo = iNode;
+
+Exit:
+ LeaveCriticalSection(&m_criticalsection);
+
+ return hresult;
+}
+
+/***
+*PUBLIC AppObjectTable::RemoveTypeInfo()
+*
+*Purpose:
+* Remove a typeinfo from the appobject table.
+*
+*Inputs:
+* htnfo - the handle of the typelib in this table.
+*
+*Outputs:
+
+******************************************************************************/
+
+VOID AppObjectTable::RemoveTypeInfo(HTINFO htinfo)
+{
+ EnterCriticalSection(&m_criticalsection);
+
+ DebAssert(htinfo < m_cNodes, "Out of range.");
+ DebAssert(m_rgaotbl[htinfo].m_cRefs != 0, "Underflow");
+
+ m_rgaotbl[htinfo].m_cRefs--;
+
+ // Release the appobjects if there is nobody left.
+ if (m_rgaotbl[htinfo].m_cRefs == 0) {
+ if (*m_rgaotbl[htinfo].m_ppv) {
+ ((IUnknown *)*m_rgaotbl[htinfo].m_ppv)->Release();
+ *m_rgaotbl[htinfo].m_ppv = NULL;
+ }
+ }
+
+ LeaveCriticalSection(&m_criticalsection);
+}
+
+/***
+*PUBLIC AppObjectTable::AddressOfAppObject()
+*
+*Purpose:
+* Return the slot to hold the appobject.
+*
+*Inputs:
+* htinfo - the typelib of the object.
+* ityp - the typeinfo to get the appobject for
+*
+*Outputs:
+* ppv - the address of the object.
+*
+******************************************************************************/
+
+VOID AppObjectTable::AddressOfAppObject(HTINFO htinfo, VOID **ppv)
+{
+ EnterCriticalSection(&m_criticalsection);
+
+ DebAssert(htinfo < m_cNodes, "Out of range.");
+
+ *ppv = (VOID *)m_rgaotbl[htinfo].m_ppv;
+ LeaveCriticalSection(&m_criticalsection);
+}
+
+#endif // OE_WIN32
diff --git a/private/oleauto/src/typelib/obguid.c b/private/oleauto/src/typelib/obguid.c
new file mode 100644
index 000000000..07349682a
--- /dev/null
+++ b/private/oleauto/src/typelib/obguid.c
@@ -0,0 +1,65 @@
+/***
+*obguid.c - All OB-owned GUIDs are defined in this module.
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This module contains the definitions of the GUIDs for all classes
+* in ob.dll and obrun.dll that derive (or will eventually derive)
+* from OLE's IUnknown.
+*
+* Do not allocate GUIDs anywhere else, since we need to ensure that
+* they are unique throughout the project.
+*
+*Revision History:
+*
+* [00] 10-Nov-92 mikewo: created
+*
+*****************************************************************************/
+
+#include "switches.hxx"
+#include "version.hxx"
+#if BLD_MAC
+#include "silver.hxx"
+#endif //BLD_MAC
+#include "typelib.hxx"
+
+#if OE_MAC
+// HACK to make GUID's be defined in a FAR segment w/o changing the OLE
+// header files (works arounds a Wings bug). Define-away 'const' so that
+// they get put into .fardata like they're supposed to.
+#define const
+#endif
+
+//OLE uses _MAC to determine if this is a Mac build
+#if OE_MAC
+# define _MAC
+#endif
+
+// initguid.h requires this
+#if OE_WIN32
+#define INC_OLE2
+#include <ole2.h>
+#else
+#include <compobj.h>
+#endif
+
+// this redefines the DEFINE_GUID() macro to do allocation.
+#include <initguid.h>
+
+#if OE_MAC
+# undef _MAC
+#endif
+
+// due to the previous header, including this causes our DEFINE_GUID defs
+// in dispatch.h to actually allocate data.
+//
+#include "obguid.h"
+
+// UNDONE: PPC: [jimcool]: The PowerPC linker can't handle multiple defn's.
+// They cause errors. To remove the multiple defn's, we use the typelib's
+// compilation of obguid.c. If we included obguid.h here, we'd get multiple
+// defn's. So, we include these symbols whose names are mangled
+// (hence unusable) in the TypeLib compilation of obguid.c
+
diff --git a/private/oleauto/src/typelib/obguid.h b/private/oleauto/src/typelib/obguid.h
new file mode 100644
index 000000000..ce035b2a4
--- /dev/null
+++ b/private/oleauto/src/typelib/obguid.h
@@ -0,0 +1,46 @@
+/***
+*obguid.h
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Definitions of private OB owned GUIDs.
+*
+* [00] 26-Jan-93 gustavj: Created.
+*
+*Implementation Notes:
+* OLE has given OB a range of GUIDs to use for its classes. This range
+* consists of 256 possible GUIDs. The GUIDs for public classes
+* (such as ItypeInfo) take GUIDs starting at the low end of the range,
+* private classes(such as GEN_DTINFO), take GUIDs starting at the high
+* end. New GUIDs that are added should maintain this convention.
+*
+* GUIDs for OB public classes are defined in typelib.hxx.
+*
+*****************************************************************************/
+
+#ifndef obguid_HXX_INCLUDED
+#define obguid_HXX_INCLUDED
+
+#define DEFINE_OBOLEGUID(name, b) DEFINE_OLEGUID(name,(0x00020400+b), 0, 0);
+
+DEFINE_OBOLEGUID(CLSID_GenericTypeLibOLE, 0xff);
+
+DEFINE_OBOLEGUID(IID_TYPEINFO , 0xfc);
+DEFINE_OBOLEGUID(IID_DYNTYPEINFO , 0xfb);
+
+DEFINE_OBOLEGUID(IID_CDefnTypeComp , 0xf5);
+
+DEFINE_OBOLEGUID(IID_TYPELIB_GEN_DTINFO , 0xf2);
+
+// {DD23B040-296F-101B-99A1-08002B2BD119}
+DEFINE_GUID(CLSID_TypeLibCF,
+ 0xDD23B040L,0x296F,0x101B,0x99,0xA1,0x08,0x00,0x2B,0x2B,0xD1,0x19);
+//{F5AA2660-BA14-1069-8AEE-00DD010F7D13}
+DEFINE_GUID(IID_IGenericTypeLibOLE,
+ 0xF5AA2660L,0xBA14,0x1069,0x8A,0xEE,0x00,0xDD,0x01,0x0F,0x7D,0x13);
+
+
+#endif // !obguid_HXX_INCLUDED
+
diff --git a/private/oleauto/src/typelib/obole2.h b/private/oleauto/src/typelib/obole2.h
new file mode 100644
index 000000000..d8343a38c
--- /dev/null
+++ b/private/oleauto/src/typelib/obole2.h
@@ -0,0 +1,224 @@
+/***
+*obole2.hxx - Cover for including Win16, Win32, and Mac Ole include files
+*
+* Copyright (C) 1993, Microsoft Corporation
+*
+*Purpose:
+* This include file includes the Ole2 include files and covers any
+* differences between the versions. Ole2.h should never be directly
+* included.
+*
+*Revision History:
+*
+* 03-Feb-93 dennisc: Created.
+*
+*******************************************************************************/
+
+#ifndef OBOLE2_H_INCLUDED
+#define OBOLE2_H_INCLUDED
+
+#if OE_MAC
+ #define _MAC
+ #undef _fmemcmp
+ #define _fmemcmp memcmp
+ #undef _fstrncpy
+ #define _fstrncpy strncpy
+ #undef _fstrcmp
+ #define _fstrcmp strcmp
+ #define HINSTANCE long
+ #define USE_INCLUDE
+#endif
+
+#if OE_WIN32
+# define __export
+# undef EXPORT
+# define EXPORT
+#endif
+
+#if ID_DEBUG
+#define _DEBUG 1 // OLE wants _DEBUG defined
+#endif
+
+#if OE_MACPPC
+#include "olenames.h"
+#endif
+
+#if !OE_WIN32 && !OE_MACPPC
+#pragma code_seg("OLEConst")
+#endif // !OE_WIN32 && !OE_MACPPC
+
+// On Win32, all the standard OLE2 headers get included by windows.h
+#if !OE_WIN32
+#include "ole2.h"
+#include "olenls.h"
+#include "dispatch.h"
+#endif
+
+// taken from the now-defunct ole2anac.h
+#define IIDEQ(riid1, riid2) IsEqualIID(riid1, riid2)
+#define CLSIDEQ(rclsid1, rclsid2) IsEqualCLSID(rclsid1, rclsid2)
+
+#define ReportResult(a,b,c,d) ResultFromScode(b) // this is now obsolete
+#define HresultOfScode(X) ResultFromScode(X)
+
+#ifndef OLESTR
+# if OE_MAC
+ typedef char OLECHAR;
+ typedef LPSTR LPOLESTR;
+ typedef LPCSTR LPCOLESTR;
+# define OLESTR(str) str
+# else
+# if OE_WIN32
+ typedef WCHAR OLECHAR;
+ typedef LPWSTR LPOLESTR;
+ typedef LPCWSTR LPCOLESTR;
+# define OLESTR(str) L##str
+# else
+ typedef char OLECHAR;
+ typedef LPSTR LPOLESTR;
+ typedef LPCSTR LPCOLESTR;
+# define OLESTR(str) str
+# endif
+# endif
+#endif
+
+#ifndef OLEBOOL
+# if OE_MAC
+# define OLEBOOL ULONG
+# else
+# define OLEBOOL BOOL
+# endif
+#endif
+
+//end of the SYSKIND enumeration
+#define SYS_MAX (SYS_MAC+1)
+
+// char count of a guid in ansi/unicode form (including trailing null)
+#define CCH_SZGUID0 39
+
+// Method counts for the interfaces commonly used by VBA
+#define CMETH_IUNKNOWN 3
+#define CMETH_IDISPATCH 7
+#define CMETH_ITYPELIB 13
+#define CMETH_ITYPEINFO 22
+#define CMETH_ISTORAGE 18
+#define CMETH_IMONIKER 23
+#define CMETH_IBINDCTX 13
+
+
+#if FV_UNICODE_OLE
+#define CreateTypeLibW CreateTypeLib
+#define RegisterTypeLibW RegisterTypeLib
+#define LHashValOfNameSysW LHashValOfNameSys
+
+#else //FV_UNICODE_OLE
+
+#define LoadRegTypeLibA LoadRegTypeLib
+#define LHashValOfNameSysW LHashValOfNameSys
+
+#endif //FV_UNICODE_OLE
+
+// In general, the "A" versions just map onto the non-A names.
+#define IStreamA IStream
+#define IStorageA IStorage
+#define ILockBytesA ILockBytes
+#define IDispatchA IDispatch
+#define IDispatchAVtbl IDispatchVtbl
+#define ITypeInfoA ITypeInfo
+#define ITypeLibA ITypeLib
+#define ICreateTypeInfoA ICreateTypeInfo
+#define ICreateTypeLibA ICreateTypeLib
+#define ITypeCompA ITypeComp
+#define IEnumSTATSTGA IEnumSTATSTG
+#define IEnumVARIANTA IEnumVARIANT
+#define IPersistFileA IPersistFile
+
+//[bb] this is where BSTR is defined
+#define BSTRA LPSTR
+#define LPBSTRA LPSTR *
+
+#define STATSTGA STATSTG
+#define SNBA SNB
+#define VARIANTA VARIANT
+#define VARIANTARGA VARIANTARG
+#define SAFEARRAYA SAFEARRAY
+#define EXCEPINFOA EXCEPINFO
+#define VARDESCA VARDESC
+#define BINDPTRA BINDPTR
+#define DISPPARAMSA DISPPARAMS
+#define PARAMDATAA PARAMDATA
+
+#define LPDISPATCHA LPDISPATCH
+#define LPEXCEPINFOA LPEXCEPINFO
+#define LPVARIANTA LPVARIANT
+#define LPVARIANTARGA LPVARIANTARG
+
+#define ReadClassStgA ReadClassStg
+#define WriteClassStgA WriteClassStg
+#define WriteFmtUserTypeStgA WriteFmtUserTypeStg
+#define CLSIDFromProgIDA CLSIDFromProgID
+#define MkParseDisplayNameA MkParseDisplayName
+#define VariantInitA VariantInit
+#define VariantClearA VariantClear
+#define VariantChangeTypeA VariantChangeType
+#define VariantCopyA VariantCopy
+#define VariantCopyIndA VariantCopyInd
+#define VarBstrFromI2A VarBstrFromI2
+#define VarBstrFromI4A VarBstrFromI4
+#define VarBstrFromR4A VarBstrFromR4
+#define VarBstrFromR8A VarBstrFromR8
+#define VarBstrFromCyA VarBstrFromCy
+#define VarBstrFromDateA VarBstrFromDate
+#define VarI2FromStrA VarI2FromStr
+#define VarI4FromStrA VarI4FromStr
+#define VarR4FromStrA VarR4FromStr
+#define VarR8FromStrA VarR8FromStr
+#define VarCyFromStrA VarCyFromStr
+#define VarDateFromStrA VarDateFromStr
+
+#define IID_ICreateTypeLibA IID_ICreateTypeLib
+#define IID_ICreateTypeInfoA IID_ICreateTypeInfo
+#define IID_ITypeLibA IID_ITypeLib
+#define IID_ITypeInfoA IID_ITypeInfo
+#define IID_ITypeCompA IID_ITypeComp
+#define IID_IStorageA IID_IStorage
+#define IID_IStreamA IID_IStream
+#define IID_ILockBytesA IID_ILockBytes
+#define IID_IDispatchA IID_IDispatch
+#define IID_IEnumVARIANTA IID_IEnumVARIANT
+#define IID_IPersistFileA IID_IPersistFile
+
+#if FV_UNICODE_OLE
+
+STDAPI
+RegisterTypeLibA(
+ ITypeLibA * ptlib,
+ char * szFullPath,
+ char * szHelpDir);
+
+STDAPI
+CreateTypeLibA(SYSKIND syskind, const char * szFile, ICreateTypeLibA * * ppctlib);
+#endif //FV_UNICODE_OLE
+
+
+#ifndef FACILITY_CONTROL
+# define FACILITY_CONTROL 0x9
+#endif
+
+
+#pragma code_seg()
+
+#if OE_MAC
+# undef _fstrncmp
+# undef _fstrcmp
+# undef _fmemcmp
+# undef _MAC
+# ifndef CALLBACK
+# define CALLBACK FAR PASCAL
+# endif // !defined(CALLBACK)
+//
+// OLE Vectoring is only needed for 68k builds
+//
+#endif // OE_MAC
+
+#endif // OBOLE2_H_INCLUDED
diff --git a/private/oleauto/src/typelib/obwin.hxx b/private/oleauto/src/typelib/obwin.hxx
new file mode 100644
index 000000000..ea0944684
--- /dev/null
+++ b/private/oleauto/src/typelib/obwin.hxx
@@ -0,0 +1,93 @@
+/***
+*obwin.hxx - Fundamental Silver include file
+*
+* Copyright (C) 1990, Microsoft Corporation
+*
+*Purpose:
+* Includes the correct version of the windows header file (windows.h
+* or wlm.h) depending on the settings of the switches.
+*
+*Revision History:
+*
+* 12-May-92 martinc: created
+*
+*******************************************************************************/
+
+#ifndef OBWIN_HXX_INCLUDED
+#define OBWIN_HXX_INCLUDED
+
+#include "switches.hxx"
+#include "version.hxx"
+
+
+#if OE_WIN
+
+#if !OE_WLM
+
+ // This is either the Win16 or Win32 build.
+ #define STRICT
+
+#if OE_WIN32
+// force include of OLE2 rather than OLE1
+# define INC_OLE2
+#define _OLEAUT32_ // for the new oleauto.h when we pick it up
+
+// On Win32, windows.h pulls in so damn much stuff that even the
+// 32bit compiler croaks on some of our files. So trim it down a bit...
+# define WIN32_LEAN_AND_MEAN
+// Yea, right...
+#endif
+
+ #include "windows.h"
+
+#if OE_WIN16
+ #include "windowsx.h16"
+#else
+ #include "windowsx.h"
+#endif
+
+#ifdef __cplusplus
+ extern "C" {
+#endif //__cplusplus
+ #include "shellapi.h"
+#ifdef __cplusplus
+ }
+#endif //__cplusplus
+
+#else // OE_WLM
+
+ // This is the WLM build.
+ #define _MACNAMES
+ // wlm.h defines its own PASCAL
+ #undef PASCAL
+ #include "wlm.h"
+ #undef PASCAL
+ #define PASCAL
+
+#endif // !OE_WLM
+
+#endif // !OE_WIN
+
+
+// This is the native Mac build.
+#if OE_MAC && !OE_WLM
+ #define _MAC
+ #include <macos\types.h>
+ #include <macos\quickdra.h>
+ #include <macos\events.h>
+ #include <macos\controls.h>
+ #include <macos\windows.h>
+
+ typedef int BOOL;
+ #define CONST
+ //#define NEAR
+
+ #include "obwlm.h"
+
+ // min, max are defined in stdlib.h
+ #undef min
+ #undef max
+
+#endif // !OE_WIN
+
+#endif // OBWIN_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/obwlm.h b/private/oleauto/src/typelib/obwlm.h
new file mode 100644
index 000000000..af8732235
--- /dev/null
+++ b/private/oleauto/src/typelib/obwlm.h
@@ -0,0 +1,374 @@
+/***
+*obwlm.h - Hacked up wlm include file for OB
+*
+* Copyright (C) 1992, Microsoft Corporation
+*
+*Purpose:
+* This file extracts all currently used functions of wlm for the "native"
+* mac build.
+* Do NOT directly include thsi file, but include silver.hxx, or obwin.hxx
+* since these files will correctly set up all our mac-types.
+*
+*Revision History:
+*
+* 2-Feb-93 martinc: File created.
+*
+*******************************************************************************/
+//
+//
+//
+
+// NOTE - wlm.h defines _WINDOWS_ and not _INC_WINDOWS_
+// but for compatibility with windows.h we keep _INC_WINDOWS
+#ifndef _INC_WINDOWS
+#define _INC_WINDOWS
+
+#ifndef OE_MAC
+#error - obwlm should not be included in non-mac builds
+#endif
+
+#if OE_MACPPC
+#define _PPC_
+#else
+#define _68K_
+#endif
+
+#define HWND WLMHWND
+#define HCURSOR WLMHCURSOR
+
+#undef PASCAL
+
+//#define HWND UINT
+// we set HWND to WindowPtr in owr native Mac build. When we are going
+// to move to full WLM we will have to fix this
+
+#include "windef.h"
+
+#if OE_MAC68K
+#include "wlmdef.h"
+#endif
+#include "wingdi.h"
+
+#if HE_WIN32
+#include "windowsx.h"
+#else
+#include "wlmx.h"
+#endif
+
+#undef HWND
+#undef HCURSOR
+
+
+// our wlm-version does not define this value
+#define DEFAULT_CHARSET 1
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+typedef struct tagCOLOR48
+{
+ WORD red;
+ WORD green;
+ WORD blue;
+} COLOR48, FAR* LPCOLOR48;
+
+
+#define CA_NONE 0x0000
+#define CA_COLOR 0x0001
+#define CA_PEN 0x0002
+#define CA_BRUSH 0x0004
+#define CA_FONT 0x0008
+#define CA_CLIP 0x0010
+#define CA_TRANSFORM 0x0020
+#define CA_PORT 0x8000
+#define CA_ALL 0xffff
+
+int WINAPI AfxFillRect(HDC hDC,CONST RECT *lprc,HBRUSH hbr);
+BOOL WINAPI AfxLineTo(HDC, int, int);
+BOOL WINAPI SetRectEmpty(LPRECT lprc);
+
+
+#define AfxMoveTo MoveToEx
+BOOL WINAPI MoveToEx(HDC, int, int, LPPOINT);
+
+BOOL WINAPI AfxPtInRect(const RECT FAR*, POINT);
+BOOL WINAPI AfxEqualRect(CONST RECT *lprc1, CONST RECT *lprc2);
+
+void WINAPI CheckinPort(HDC hdc, UINT ca);
+struct GrafPort FAR* WINAPI CheckoutPort(HDC hdc, UINT ca);
+
+
+#ifndef UNICODE
+#define CreateFont CreateFontA
+#define CreateIC CreateICA
+#define ExtTextOut ExtTextOutA
+#define TextOut TextOutA
+
+HFONT WINAPI CreateFontA(int, int, int, int, int, DWORD,
+ DWORD, DWORD, DWORD, DWORD, DWORD,
+ DWORD, DWORD, LPCSTR);
+HDC WINAPI CreateICA(LPCSTR, LPCSTR , LPCSTR , CONST DEVMODEA *);
+BOOL WINAPI ExtTextOutA(HDC, int, int, UINT, CONST RECT *, LPCSTR, UINT, LPINT);
+BOOL WINAPI TextOutA(HDC, int, int, LPCSTR, int);
+#else
+#error UNICODE defined!
+#endif
+
+
+HDC WINAPI WrapPort(struct GrafPort*);
+
+HPEN WINAPI CreatePen(int, int, COLORREF);
+HBRUSH WINAPI CreateSolidBrush(COLORREF);
+
+BOOL WINAPI DeleteDC(HDC);
+BOOL WINAPI UnwrapPort(HDC);
+BOOL WINAPI LockDC(HDC);
+BOOL WINAPI UnlockDC(HDC);
+
+BOOL WINAPI DeleteObject(HGDIOBJ);
+int WINAPI ExcludeClipRect(HDC, int, int, int, int);
+
+BOOL WINAPI GDIInit(DWORD fdCreator);
+void WINAPI GDITerm(void);
+
+COLORREF WINAPI GetBkColor(HDC);
+int WINAPI GetClipBox(HDC, LPRECT);
+BOOL WINAPI GetCurrentPositionEx(HDC, LPPOINT);
+HGDIOBJ WINAPI GetStockObject(int);
+COLORREF WINAPI GetTextColor(HDC);
+BOOL WINAPI GetTextMetricsA(HDC, LPTEXTMETRICA);
+BOOL WINAPI InitDC(HDC);
+int WINAPI IntersectClipRect(HDC, int, int, int, int);
+BOOL WINAPI IsRectEmpty(CONST RECT *lprc);
+
+BOOL WINAPI PatBlt(HDC, int, int, int, int, DWORD);
+BOOL WINAPI Rectangle(HDC, int, int, int, int);
+
+BOOL WINAPI ResetMacDC(HDC);
+BOOL WINAPI RestoreDC(HDC, int);
+int WINAPI SaveDC(HDC);
+
+HGDIOBJ WINAPI SelectObject(HDC, HGDIOBJ);
+COLORREF WINAPI SetBkColor(HDC, COLORREF);
+int WINAPI SetBkMode(HDC, int);
+UINT WINAPI SetTextAlign(HDC, UINT);
+COLORREF WINAPI SetTextColor(HDC, COLORREF);
+
+int WINAPI lstrcmp(LPCSTR, LPCSTR);
+int WINAPI lstrcmpi(LPCSTR, LPCSTR);
+
+#if ID_DEBUG
+ void WINAPI DebugBreak(void);
+// This is provided by Mac OLE as of MM6.2.
+// void WINAPI OutputDebugString(LPCSTR);
+#endif
+
+// from winbase.h
+
+int
+WINAPI
+MulDiv(
+ int nNumber,
+ int nNumerator,
+ int nDenominator
+ );
+
+UINT
+WINAPI
+GetPrivateProfileIntA(
+ LPCSTR lpAppName,
+ LPCSTR lpKeyName,
+ DWORD nDefault,
+ LPCSTR lpFileName
+ );
+UINT
+WINAPI
+GetPrivateProfileIntW(
+ LPCWSTR lpAppName,
+ LPCWSTR lpKeyName,
+ DWORD nDefault,
+ LPCWSTR lpFileName
+ );
+#ifdef UNICODE
+#define GetPrivateProfileInt GetPrivateProfileIntW
+#else
+#define GetPrivateProfileInt GetPrivateProfileIntA
+#endif // !UNICODE
+
+DWORD
+WINAPI
+GetPrivateProfileStringA(
+ LPCSTR lpAppName,
+ LPCSTR lpKeyName,
+ LPCSTR lpDefault,
+ LPSTR lpReturnedString,
+ DWORD nSize,
+ LPCSTR lpFileName
+ );
+DWORD
+WINAPI
+GetPrivateProfileStringW(
+ LPCWSTR lpAppName,
+ LPCWSTR lpKeyName,
+ LPCWSTR lpDefault,
+ LPWSTR lpReturnedString,
+ DWORD nSize,
+ LPCWSTR lpFileName
+ );
+#ifdef UNICODE
+#define GetPrivateProfileString GetPrivateProfileStringW
+#else
+#define GetPrivateProfileString GetPrivateProfileStringA
+#endif // !UNICODE
+
+BOOL
+WINAPI
+WritePrivateProfileStringA(
+ LPCSTR lpAppName,
+ LPCSTR lpKeyName,
+ LPCSTR lpString,
+ LPCSTR lpFileName
+ );
+BOOL
+WINAPI
+WritePrivateProfileStringW(
+ LPCWSTR lpAppName,
+ LPCWSTR lpKeyName,
+ LPCWSTR lpString,
+ LPCWSTR lpFileName
+ );
+#ifdef UNICODE
+#define WritePrivateProfileString WritePrivateProfileStringW
+#else
+#define WritePrivateProfileString WritePrivateProfileStringA
+#endif // !UNICODE
+
+
+DWORD
+WINAPI
+CharUpperBuffA(
+ LPSTR lpsz,
+ DWORD cchLength);
+DWORD
+WINAPI
+CharUpperBuffW(
+ LPWSTR lpsz,
+ DWORD cchLength);
+#ifdef UNICODE
+#define CharUpperBuff CharUpperBuffW
+#else
+#define CharUpperBuff CharUpperBuffA
+#endif // !UNICODE
+
+
+DWORD
+WINAPI
+CharLowerBuffA(
+ LPSTR lpsz,
+ DWORD cchLength);
+DWORD
+WINAPI
+CharLowerBuffW(
+ LPWSTR lpsz,
+ DWORD cchLength);
+#ifdef UNICODE
+#define CharLowerBuff CharLowerBuffW
+#else
+#define CharLowerBuff CharLowerBuffA
+#endif // !UNICODE
+
+int
+WINAPI
+lstrcmpA(
+ LPCSTR lpString1,
+ LPCSTR lpString2
+ );
+int
+WINAPI
+lstrcmpW(
+ LPCWSTR lpString1,
+ LPCWSTR lpString2
+ );
+#ifdef UNICODE
+#define lstrcmp lstrcmpW
+#else
+#define lstrcmp lstrcmpA
+#endif // !UNICODE
+
+int
+WINAPI
+lstrcmpiA(
+ LPCSTR lpString1,
+ LPCSTR lpString2
+ );
+int
+WINAPI
+lstrcmpiW(
+ LPCWSTR lpString1,
+ LPCWSTR lpString2
+ );
+#ifdef UNICODE
+#define lstrcmpi lstrcmpiW
+#else
+#define lstrcmpi lstrcmpiA
+#endif // !UNICODE
+
+
+LPSTR
+WINAPI
+lstrcpyA(
+ LPSTR lpString1,
+ LPCSTR lpString2
+ );
+LPWSTR
+WINAPI
+lstrcpyW(
+ LPWSTR lpString1,
+ LPCWSTR lpString2
+ );
+#ifdef UNICODE
+#define lstrcpy lstrcpyW
+#else
+#define lstrcpy lstrcpyA
+#endif // !UNICODE
+
+LPSTR
+WINAPI
+lstrcatA(
+ LPSTR lpString1,
+ LPCSTR lpString2
+ );
+LPWSTR
+WINAPI
+lstrcatW(
+ LPWSTR lpString1,
+ LPCWSTR lpString2
+ );
+#ifdef UNICODE
+#define lstrcat lstrcatW
+#else
+#define lstrcat lstrcatA
+#endif // !UNICODE
+
+int
+WINAPI
+lstrlenA(
+ LPCSTR lpString
+ );
+int
+WINAPI
+lstrlenW(
+ LPCWSTR lpString
+ );
+#ifdef UNICODE
+#define lstrlen lstrlenW
+#else
+#define lstrlen lstrlenA
+#endif // !UNICODE
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif // _INC_WINDOWS_
diff --git a/private/oleauto/src/typelib/oleaut32.def b/private/oleauto/src/typelib/oleaut32.def
new file mode 100644
index 000000000..447802942
--- /dev/null
+++ b/private/oleauto/src/typelib/oleaut32.def
@@ -0,0 +1,241 @@
+#include "switches.hxx"
+
+//
+// Note: To currently debug shared libraries on PPC, the LIBRARY clause must be of the form xxx.dll.dll
+// The ouput from the linker must be xxx.dll, and the name in the 'cfrg' segment must be xxx.dll
+//
+#if OE_MACPPC
+LIBRARY MicrosoftOLE2AutomationLib
+#else // OE_MACPPC
+LIBRARY OLEAUT32
+#endif // OE_MACPPC
+
+#if OE_WIN
+DESCRIPTION 'OLE Automation Library'
+CODE EXECUTE READ SHARED
+;DATA READ WRITE
+#endif
+
+EXPORTS
+
+ ; (Not used in Win32)
+ ;WEP @0 RESIDENTNAME
+
+ ; DLL Support API
+ DllGetClassObject @1
+
+ ; BSTR API (ANSI)
+ ;
+ SysAllocString @2
+ SysReAllocString @3
+ SysAllocStringLen @4
+ SysReAllocStringLen @5
+ SysFreeString @6
+ SysStringLen @7
+
+ ; VARIANT API
+ ;
+ VariantInit @8
+ VariantClear @9
+ VariantCopy @10
+ VariantCopyInd @11
+ VariantChangeType @12
+
+ ; VARIANT TIME API
+ ;
+ VariantTimeToDosDateTime @13
+ DosDateTimeToVariantTime @14
+
+ ; SAFEARRAY API
+ ;
+ SafeArrayCreate @15
+ SafeArrayDestroy @16
+ SafeArrayGetDim @17
+ SafeArrayGetElemsize @18
+ SafeArrayGetUBound @19
+ SafeArrayGetLBound @20
+ SafeArrayLock @21
+ SafeArrayUnlock @22
+ SafeArrayAccessData @23
+ SafeArrayUnaccessData @24
+ SafeArrayGetElement @25
+ SafeArrayPutElement @26
+ SafeArrayCopy @27
+
+ ; IDispatch helpers/implementation
+ ;
+ DispGetParam @28
+ DispGetIDsOfNames @29
+ DispInvoke @30
+ CreateDispTypeInfo @31
+ CreateStdDispatch @32
+
+ ; Active Object API
+ ;
+ RegisterActiveObject @33
+ RevokeActiveObject @34
+ GetActiveObject @35
+
+ ; additional SafeArray APIs
+ ;
+ SafeArrayAllocDescriptor @36
+ SafeArrayAllocData @37
+ SafeArrayDestroyDescriptor @38
+ SafeArrayDestroyData @39
+ SafeArrayRedim @40
+
+ ; low-level VARTYPE coersion API
+ ;
+ VarI2FromUI1 @48
+ VarI2FromI4 @49
+ VarI2FromR4 @50
+ VarI2FromR8 @51
+ VarI2FromCy @52
+ VarI2FromDate @53
+ VarI2FromStr @54
+ VarI2FromDisp @55
+ VarI2FromBool @56
+
+ VarI4FromUI1 @58
+ VarI4FromI2 @59
+ VarI4FromR4 @60
+ VarI4FromR8 @61
+ VarI4FromCy @62
+ VarI4FromDate @63
+ VarI4FromStr @64
+ VarI4FromDisp @65
+ VarI4FromBool @66
+
+ VarR4FromUI1 @68
+ VarR4FromI2 @69
+ VarR4FromI4 @70
+ VarR4FromR8 @71
+ VarR4FromCy @72
+ VarR4FromDate @73
+ VarR4FromStr @74
+ VarR4FromDisp @75
+ VarR4FromBool @76
+
+ VarR8FromUI1 @78
+ VarR8FromI2 @79
+ VarR8FromI4 @80
+ VarR8FromR4 @81
+ VarR8FromCy @82
+ VarR8FromDate @83
+ VarR8FromStr @84
+ VarR8FromDisp @85
+ VarR8FromBool @86
+
+ VarDateFromUI1 @88
+ VarDateFromI2 @89
+ VarDateFromI4 @90
+ VarDateFromR4 @91
+ VarDateFromR8 @92
+ VarDateFromCy @93
+ VarDateFromStr @94
+ VarDateFromDisp @95
+ VarDateFromBool @96
+
+ VarCyFromUI1 @98
+ VarCyFromI2 @99
+ VarCyFromI4 @100
+ VarCyFromR4 @101
+ VarCyFromR8 @102
+ VarCyFromDate @103
+ VarCyFromStr @104
+ VarCyFromDisp @105
+ VarCyFromBool @106
+
+ VarBstrFromUI1 @108
+ VarBstrFromI2 @109
+ VarBstrFromI4 @110
+ VarBstrFromR4 @111
+ VarBstrFromR8 @112
+ VarBstrFromCy @113
+ VarBstrFromDate @114
+ VarBstrFromDisp @115
+ VarBstrFromBool @116
+
+ VarBoolFromUI1 @118
+ VarBoolFromI2 @119
+ VarBoolFromI4 @120
+ VarBoolFromR4 @121
+ VarBoolFromR8 @122
+ VarBoolFromDate @123
+ VarBoolFromCy @124
+ VarBoolFromStr @125
+ VarBoolFromDisp @126
+
+ VarUI1FromI2 @130
+ VarUI1FromI4 @131
+ VarUI1FromR4 @132
+ VarUI1FromR8 @133
+ VarUI1FromCy @134
+ VarUI1FromDate @135
+ VarUI1FromStr @136
+ VarUI1FromDisp @137
+ VarUI1FromBool @138
+
+ ; IIDs
+ ;
+#if OE_MACPPC
+ IID_IDispatch @144
+ IID_IEnumVARIANT @145
+#endif
+
+ ; Not needed in combined DLL's
+ ;DoInvokeMethod @146
+
+ ; Varaint Coersion API Extension
+ ;
+ VariantChangeTypeEx @147
+
+ ; SAFEARRAY APIs
+ ;
+ SafeArrayPtrOfIndex @148
+
+#if OE_WIN32
+ ; BSTR Byte APIs
+ ;
+ SysStringByteLen @149
+ SysAllocStringByteLen @150
+ ;SysReAllocStringByteLen @151
+#endif //OE_WIN32
+
+ ; Type librarary APIs
+ CreateTypeLib @160
+ LoadTypeLib @161
+ LoadRegTypeLib @162
+ RegisterTypeLib @163
+ QueryPathOfRegTypeLib @164
+ LHashValOfNameSys @165
+#if OE_WIN32
+ LHashValOfNameSysA @166
+#endif //OE_WIN32
+
+ ; New API's for OA94
+ OaBuildVersion @170
+
+ ; Rich error APIs
+ GetErrorInfo @200
+ SetErrorInfo @201
+ CreateErrorInfo @202
+
+ ; Mac Specific Entry Points
+#if OE_MACPPC
+
+ ; TypeLib
+ LoadTypeLibFSp @300
+ QueryTypeLibFolder @301
+ RegisterTypeLibFolder @302
+
+ ; NLS
+ CompareStringA @403
+ LCMapStringA @400
+ GetLocaleInfoA @404
+ GetStringTypeA @405
+ GetSystemDefaultLangID @406
+ GetUserDefaultLangID @407
+ GetSystemDefaultLCID @408
+ GetUserDefaultLCID @409
+#endif
diff --git a/private/oleauto/src/typelib/oleaut32.rc b/private/oleauto/src/typelib/oleaut32.rc
new file mode 100644
index 000000000..e5da7e63f
--- /dev/null
+++ b/private/oleauto/src/typelib/oleaut32.rc
@@ -0,0 +1,96 @@
+/***
+*oleaut32.rc - Resource file for oleaut32.DLL
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file in the resource file for oleaut32.DLL that is compiled and
+* added to the file. String resources are included in this file
+* via an include statement, since these are automatically generated.
+*
+*Revision History:
+*
+* [00] 07-Feb-94 dougf: Created from ole2disp.rc & typelib.rc
+* [00] 04-Jan-93 ilanc: Created --
+*
+*****************************************************************************/
+
+// This includes WINDOWS.H, and all the OB switches, like ID_DEBUG, etc.
+#include "obwin.hxx"
+
+#include "verstamp.h" // for 'rup'
+
+#ifndef OLEMINORVERS
+#define OLEMINORVERS 10 // assume OLE 2.10
+#endif //!OLEMINORVERS
+
+/* Version information -- hardcoded */
+VS_VERSION_INFO VERSIONINFO
+FILEVERSION 2,OLEMINORVERS,rup,01
+PRODUCTVERSION 2,OLEMINORVERS,rup,01
+FILEFLAGSMASK VS_FFI_FILEFLAGSMASK
+
+#if 0
+#define BETAFLAG VS_FF_PRERELEASE
+#else //1
+#define BETAFLAG 0L
+#endif //1
+
+#if ID_DEBUG
+FILEFLAGS VS_FF_DEBUG | BETAFLAG
+#else // !ID_DEBUG
+FILEFLAGS BETAFLAG
+#endif // !ID_DEBUG
+FILEOS VOS_NT_WINDOWS32
+
+FILETYPE VFT_DLL
+FILESUBTYPE 0
+
+BEGIN
+ BLOCK "StringFileInfo"
+ BEGIN
+ BLOCK "040904E4"
+ BEGIN
+ VALUE "CompanyName", "Microsoft Corporation\0"
+ VALUE "FileDescription", "Microsoft OLE 2.1 for Windows NT(TM) Operating System\0"
+ VALUE "FileVersion", "2.1\0"
+ VALUE "InternalName", "OLEAUT32.DLL\0"
+ VALUE "LegalCopyright", "Copyright \251 Microsoft Corp. 1993-1995.\0"
+ VALUE "LegalTrademarks", "Microsoft\256 is a registered trademark of Microsoft Corporation. Windows NT(TM) is a trademark of Microsoft Corporation.\0"
+ VALUE "ProductName", "Microsoft OLE 2.1 for Windows NT(TM) Operating System\0"
+ VALUE "ProductVersion", "2.1\0"
+ VALUE "Comments", "Microsoft OLE 2.1 for Windows NT(TM) Operating System\0"
+ END
+
+ END
+
+ BLOCK "VarFileInfo"
+ BEGIN
+ VALUE "Translation", 0x409, 1252
+ END
+
+END
+
+#if ID_DEBUG
+// Assertion stuff for ole2disp
+#define ASSERT_ID_BREAK 5103
+#define ASSERT_ID_EXIT 5104
+#define ASSERT_ID_IGNORE 5105
+#define ASSERT_ID_LOC 5106
+#define ASSERT_ID_EXPR 5107
+#define ASSERT_ID_MSG 5108
+
+
+ASSERTFAILDLG DIALOG 72, 32, 260, 67
+STYLE DS_MODALFRAME | WS_POPUP | WS_VISIBLE | WS_CAPTION
+CAPTION "Assertion failure!"
+FONT 8, "MS Sans Serif"
+BEGIN
+ CTEXT "", ASSERT_ID_LOC, 11, 15, 240, 8
+ CTEXT "", ASSERT_ID_MSG, 11, 28, 240, 8
+ PUSHBUTTON "&Break", ASSERT_ID_BREAK, 54, 47, 40, 14
+ PUSHBUTTON "E&xit", ASSERT_ID_EXIT, 110, 47, 40, 14
+ PUSHBUTTON "&Ignore", ASSERT_ID_IGNORE, 166, 47, 40, 14
+END
+#endif // ID_DEBUG
diff --git a/private/oleauto/src/typelib/olenames.h b/private/oleauto/src/typelib/olenames.h
new file mode 100644
index 000000000..806384d6c
--- /dev/null
+++ b/private/oleauto/src/typelib/olenames.h
@@ -0,0 +1,100 @@
+/*==========================================================================*
+ | olenames.h - redefinition of OLE function names for DLL entry points
+ |
+ | Purpose:
+ |
+ |
+ | Revision History:
+ |
+ |---------------------------------------------------------------------------
+ | Implementation Notes:
+ |
+ | The actual macros are generated via AWK from the OLE def files.
+ |
+ *==========================================================================*
+ | Copyright: (c) 1992, 1993 Microsoft Corporation, all rights reserved.
+ | Information Contained Herin is Proprietary and Confidential.
+ *==========================================================================*/
+
+
+
+#if !OE_MAC
+#error !This file is intended for Macintosh only
+#endif
+
+//==============================================================================
+//
+// MAC PPC Definitions
+//
+//==============================================================================
+#if OE_MACPPC
+#define ID_OLE_STAT_DOCFILE 0
+#define ID_OLE_STAT_USER 0
+#define ID_OLE_STAT_OLE2DISP 0
+#define ID_OLE_STAT_TYPELIB 0
+#define ID_OLE_STAT_DEF 0
+#define ID_OLE_STAT_COMPOBJ 0
+#define ID_OLE_STAT_PROXY 0
+#define ID_OLE_STAT_OLE2NLS 0
+
+#define ID_MUNGE_DLL_NAMES 0
+#define ID_MUNGE_STAT_NAMES 1
+
+#else // OE_MACPPC
+
+#if defined( OLENAMES_MUNGE_FOR_STATIC )
+
+#define ID_OLE_STAT_DOCFILE 1
+#define ID_OLE_STAT_USER 1
+#define ID_OLE_STAT_OLE2DISP 1
+#define ID_OLE_STAT_TYPELIB 1
+#define ID_OLE_STAT_DEF 1
+#define ID_OLE_STAT_COMPOBJ 1
+#define ID_OLE_STAT_PROXY 0
+#define ID_OLE_STAT_OLE2NLS 1
+
+#define ID_MUNGE_DLL_NAMES 0
+#define ID_MUNGE_STAT_NAMES 1
+
+#endif // OLENAMES_MUNGE_FOR_STATIC
+
+#if defined( OLENAMES_MUNGE_FOR_DLL ) // No DLL munging at this time,
+ // keep the functionality just in
+ // case we need it later!
+
+#define ID_OLE_STAT_DOCFILE 0
+#define ID_OLE_STAT_USER 0
+#define ID_OLE_STAT_OLE2DISP 0
+#define ID_OLE_STAT_TYPELIB 0
+#define ID_OLE_STAT_DEF 0
+#define ID_OLE_STAT_COMPOBJ 0
+#define ID_OLE_STAT_PROXY 0
+#define ID_OLE_STAT_OLE2NLS 0
+
+#define ID_MUNGE_DLL_NAMES 0
+#define ID_MUNGE_STAT_NAMES 0
+
+#endif // OLENAMES_MUNGE_FOR_DLL
+
+#endif// OE_MACPPC
+
+#include "namemacs.h"
+
+#if OE_MAC68K
+
+#undef ID_OLE_STAT_DOCFILE
+#undef ID_OLE_STAT_USER
+#undef ID_OLE_STAT_OLE2DISP
+#undef ID_OLE_STAT_TYPELIB
+#undef ID_OLE_STAT_DEF
+#undef ID_OLE_STAT_COMPOBJ
+#undef ID_OLE_STAT_PROXY
+#undef ID_OLE_STAT_OLE2NLS
+#undef ID_MUNGE_STAT_NAMES
+#undef ID_MUNGE_DLL_NAMES
+
+#undef OLENAMES_MUNGE_FOR_STATIC
+#undef OLENAMES_MUNGE_FOR_DLL
+
+#endif // OE_MAC68K
+
diff --git a/private/oleauto/src/typelib/oletmgr.cxx b/private/oleauto/src/typelib/oletmgr.cxx
new file mode 100644
index 000000000..a6bca2c9c
--- /dev/null
+++ b/private/oleauto/src/typelib/oletmgr.cxx
@@ -0,0 +1,468 @@
+/***
+*oletmgr.cxx - OLE_TYPEMGR definition
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* There is a single instance of the OLE_TYPEMGR per process.
+* The OLE_TYPEMGR maintains an in-memory collection of typelibs,
+* so that multiple copies of the same typelib need not be loaded
+* simultaneously.
+*
+*Implementation:
+* Each TYPEMGR instance is embedded within a SHEAP_MGR's "reserved block".
+* The memory map for this looks like:
+*
+* +--------------------------+
+* | SHEAP_MGR instance |
+* +--------------------------+ -- This is the SHEAP_MGR's reserved
+* | TYPEMGR instance | <--- block allocated by SHEAP_MGR::Create.
+* +--------------------------+
+* | LIBENTRY |
+* | instances alloc'd by | <--- Additional space allocated at the
+* | m_blkmgr in the TYPEMGR. | request of the embedded block manager.
+* +--------------------------+
+*
+*
+* The SHEAP_MGR is used instead of normal (malloc/new) heap management
+* because it is more efficient in win16 to grow a segment than to try
+* to call realloc(). On the other (flat) platforms, the SHEAP_MGR is
+* probably implemented with malloc/realloc anyway.
+*
+* This is similar to, but much more limited in functionality than,
+* OB's TYPEMGR class. There is no inheritance or code sharing between
+* them (except that OB's TYPEMGR will defer to OLE_TYPEMGR to register
+* all non-OB typelibs.
+*
+*Revision History:
+*
+* 26-Feb-93 mikewo: Created.
+*
+*****************************************************************************/
+
+#include "silver.hxx"
+#include "oletmgr.hxx"
+#include "sheapmgr.hxx"
+#include "mem.hxx"
+#include "clutil.hxx"
+#include "xstring.h"
+
+#pragma hdrstop(RTPCHNAME)
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+static char szOleTMgrCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleTMgrCxx
+#endif
+
+// This assumes OLE_TYPEMGR_cTypeLibBuckets is a power of two. Code using
+// this macro should assert that this is true (using the IsPowerOf2 macro
+// defined below.
+#define HashFileName(szFile) (HashSz(szFile) & (OLE_TYPEMGR_cTypeLibBuckets-1))
+
+// This macro determines whether or not an integer is an integral power of 2.
+// Trust me.
+#define IsPowerOf2(i) (!((i) & ((i)-1)))
+
+
+#if ID_DEBUG
+extern "C" void
+FnAssertCover(LPSTR lpstrExpr, LPSTR lpstrMsg, LPSTR lpstrFileName, UINT iLine);
+#endif // ID_DEBUG
+
+// This whole file is in the init segment of TYPELIB.DLL
+#pragma code_seg(CS_INIT)
+
+OLE_TYPEMGR::OLE_TYPEMGR()
+{
+ UINT i;
+
+ // Initialize all the locals to 0.
+ for (i = 0; i < sizeof(m_rghlibeBucket)/sizeof(m_rghlibeBucket[0]); i++)
+ m_rghlibeBucket[i] = HCHUNK_Nil;
+}
+
+OLE_TYPEMGR::~OLE_TYPEMGR()
+{
+ // Does nothing.
+}
+
+
+/***
+*static TIPERROR OLE_TYPEMGR::Create() - Create and init a new OLE_TYPEMGR instance.
+*Purpose:
+* Create and initialize a new OLE_TYPEMGR instance. Called by InitAppData.
+*
+*Entry:
+* psheapmgr - pointer to a SHEAP_MGR to be used for allocating
+* any space needed by the OLE_TYPEMGR.
+*
+*Exit:
+* Returns TIPERR_None and points *ppoletmgr to the new OLE_TYPEMGR
+* if successful.
+*
+* Returns something other than TIPERR_None if not successful. In this
+* case, *ppoletmgr remains unchanged.
+*
+***********************************************************************/
+TIPERROR OLE_TYPEMGR::Create(OLE_TYPEMGR **ppoletmgr)
+{
+ OLE_TYPEMGR *poletmgr;
+ TIPERROR tiperr;
+ SHEAP_MGR *psheapmgr;
+
+ // Create the SHEAP_MGR in which the OLE_TYPEMGR will reside.
+ if ((tiperr = SHEAP_MGR::Create(&psheapmgr, sizeof(OLE_TYPEMGR) + sizeof(SHEAP_MGR))))
+ return tiperr;
+
+ // Instantiate the OLE_TYPEMGR in the SHEAP_MGR created above.
+ poletmgr = new(psheapmgr+1) OLE_TYPEMGR;
+
+ // There should be no way for this to fail.
+ DebAssert(poletmgr != NULL, "OLE_TYPEMGR::Create");
+
+ // Initialize the OLE_TYPEMGR's block manager with the sheapmgr.
+ // Note that the only future clients of the SHEAP_MGR are this block
+ // manager and the OLE_TYPEMGR's destructor. The destructor obtains
+ // the SHEAP_MGR by subtracting its size from the OLE_TYPEMGR *.
+
+ if ((tiperr = poletmgr->m_bm.Init(psheapmgr)) != TIPERR_None) {
+ delete psheapmgr;
+ return(tiperr);
+ }
+
+ *ppoletmgr = poletmgr;
+ return(TIPERR_None);
+}
+
+/***
+* void Release() - Delete this OLE_TYPEMGR. There is no reference count,
+* so this will always delete the OLE_TYPEMGR.
+*
+***********************************************************************/
+void OLE_TYPEMGR::Release()
+{
+#if ID_DEBUG
+ // Make sure that all of the typelibs have been released.
+ CHAR szMsg[256];
+ ULONG iBucket, cLeak;
+ HLIBENTRY hlibe;
+ LIBENTRY *qlibe;
+ GenericTypeLibOLE *pgtlibole;
+ STL_TYPEINFO *pstlti;
+
+ UINT ityp, ctyps;
+
+ for (iBucket = 0; iBucket < OLE_TYPEMGR_cTypeLibBuckets; iBucket++) {
+ for (hlibe = m_rghlibeBucket[iBucket];
+ hlibe != HCHUNK_Nil;
+ hlibe = qlibe->m_hlibeNext) {
+
+ qlibe = QlibentryOfHlibentry(hlibe);
+
+ // Determine what's leaking and report it.
+ cLeak = 0;
+ pgtlibole = (GenericTypeLibOLE *)qlibe->m_ptlib;
+ ctyps = pgtlibole->GetTypeInfoCount();
+
+ for (ityp = 0; ityp < ctyps; ityp++) {
+ pstlti = pgtlibole->Qte(ityp)->m_pstltinfo;
+
+ if (pstlti) {
+ if (pstlti->CRefs() > 0) {
+ sprintf(szMsg,
+ "OLE Automation has determined that the application has leaked the following:\n\nTypeInfo \"%s\" (hte = 0x%X) of TypeLib \"%s\" (htlibe = 0x%X), cRefs = %ld\n",
+ pstlti->SzDebName(),
+ pstlti->GetIndex(),
+ pstlti->PgtlibOleContaining()->SzDebName(),
+ hlibe,
+ pstlti->CRefs());
+
+ FnAssertCover(NULL, szMsg, __FILE__, __LINE__);
+
+ cLeak += pstlti->CRefs();
+ }
+ }
+ }
+
+ // See if the typelib has leaked at all.
+ if (cLeak != pgtlibole->CRefs() || !cLeak) {
+ sprintf(szMsg,
+ "OLE Automation has determined that the application has leaked the following:\n\nTypeLib \"%s\" (htlibe = 0x%X), cRefs = %ld\n",
+ pgtlibole->SzDebName(),
+ hlibe,
+ pgtlibole->CRefs() - cLeak);
+
+ FnAssertCover(NULL, szMsg, __FILE__, __LINE__);
+ }
+ }
+ }
+#endif // ID_DEBUG
+
+ // Delete this OLE_TYPEMGR by deleting its containing SHEAP_MGR.
+ delete (((SHEAP_MGR *)this)-1);
+}
+
+
+/***
+* TIPERROR TypeLibLoaded() - Called by every typelib creator.
+*
+* Purpose:
+* This function is called by LoadTypeLib. It adds an element
+* to the szFile==>LoadedTypeLib map, mapping a copy of szFile to ptlib.
+*
+* Inputs:
+* szFile - The full path of the type library just loaded by LoadTypeLib.
+* A copy of this is made. The copy is released by
+* TipTypeLibUnloaded().
+* ptlib - The type library just created.
+*
+* Outputs:
+* Returns TIPERR_None if successful.
+* Asserts if the specified ITypeLib is already in the szFile==>ITypeLib map.
+*
+* This function does not perform any operations on ptlib itself.
+* Specifically, it does not grab another reference to the library.
+*
+*****************************************************************************/
+TIPERROR OLE_TYPEMGR::TypeLibLoaded(LPOLESTR szFile, ITypeLibA *ptlib)
+{
+ TIPERROR err = TIPERR_None;
+ HLIBENTRY hlibe = HLIBENTRY_Nil;
+ LIBENTRY *qlibe;
+
+ // Get the handle to the LIBENTRY for szFile.
+ IfErrRet(GetHlibentryOfFileName(szFile, &hlibe));
+
+ // The above call should always succeed
+ DebAssert(hlibe != HLIBENTRY_Nil, "GetHlibentryOfFileName failed");
+
+ qlibe = QlibentryOfHlibentry(hlibe);
+
+ // It should never happen that this method is called twice for
+ // the same library. Verify this.
+ DebAssert(qlibe->m_ptlib == NULL, "ITypeLib is already loaded");
+
+ qlibe->m_ptlib = ptlib;
+
+ return TIPERR_None;
+}
+
+
+/***
+* void TypeLibUnloaded() - Called by every typelib's destructor.
+*
+* Purpose:
+* This function must be called by the destructor of all implementations
+* of the ITypeLib protocol. It removes the element of the
+* szFile==>LoadedTypeLib map corresponding to ptlib.
+*
+* Inputs:
+* ptlib - The typelib being unloaded from memory.
+*
+* Outputs:
+* Asserts if ptlib was not in the map for this process.
+*
+* This function does not perform any operations on ptlib itself.
+* Specifically, it does not free ptlib. That is the responsibility
+* of the caller.
+*
+* NOTE!!!! DO NOT DEREFERENCE ptlib. It is almost certainly an invalid
+* (i.e. freed/deleted/dead/bad) pointer by this time.
+*
+*****************************************************************************/
+void OLE_TYPEMGR::TypeLibUnloaded(ITypeLibA *ptlib)
+{
+ HLIBENTRY hlibe, *qhlibe;
+ int i;
+
+ // Look up ptlib using a linear search through all the LIBENTRYs.
+ for (i = 0; i < sizeof(m_rghlibeBucket)/sizeof(m_rghlibeBucket[0]); i++) {
+ qhlibe = m_rghlibeBucket+i;
+ while (*qhlibe != HCHUNK_Nil &&
+ ptlib != QlibentryOfHlibentry(*qhlibe)->m_ptlib) {
+ qhlibe = &QlibentryOfHlibentry(*qhlibe)->m_hlibeNext;
+ }
+
+ // If the specified typelib is found, exit the loop.
+ if (*qhlibe != HCHUNK_Nil)
+ break;
+ }
+
+ // If the specified typelib is not in the hash table, don't remove it.
+ if (*qhlibe != HCHUNK_Nil) {
+
+ // Unlink the LIBENTRY from its hash collision list.
+ hlibe = *qhlibe;
+ *qhlibe = QlibentryOfHlibentry(hlibe)->m_hlibeNext;
+
+ // Free the filename string pointed at by the LIBENTRY.
+ m_bm.FreeChunk(QlibentryOfHlibentry(hlibe)->m_hszFile,
+ xstrblen0((XSZ)m_bm.QtrOfHandle(((LIBENTRY *)
+ m_bm.QtrOfHandle(hlibe))->m_hszFile)));
+
+
+ }
+
+#if !OE_WIN32
+ // Release the AppData. If there isn't any
+ // typelib loaded then the APP_DATA and the
+ // ole's typemgr will get released.
+ // Release the typemgr and IMalloc if the count of typelib
+ // goes to 0.
+ if ((--Pappdata()->m_cTypeLib) == 0) {
+ ReleaseAppData();
+ }
+#endif // !OE_WIN32
+}
+
+
+/***
+* ITypeLib *LookupTypeLib() - Maps a filename to a loaded typelib.
+*
+* Purpose:
+* This function returns a pointer to the specified ITypeLib, if it
+* is already in this OLE_TYPEMGR. If it isn't, then the caller must
+* load the typelib itself.
+*
+* Input:
+* szFile - The full path of the desired typelib.
+*
+* Output:
+* If there is a file of the specified name already in this OLE_TYPEMGR,
+* its associated typelib is returned. Otherwise, NULL is returned.
+*
+*****************************************************************************/
+ITypeLibA *OLE_TYPEMGR::LookupTypeLib(LPOLESTR szFile)
+{
+ HLIBENTRY *qhlibe;
+
+ qhlibe = LookupLibEntry(szFile);
+
+ if (qhlibe == NULL)
+ return NULL;
+
+ else
+ return (QlibentryOfHlibentry(*qhlibe))->m_ptlib;
+}
+
+/***
+* HCHUNK *LookupLibEntry() - Looks up a LIBENTRY, given its full path.
+*
+* Purpose:
+* This method looks for a LIBENTRY corresponding to the specified
+* filename. If successful, it returns a pointer to the hchunk
+* field referring to that LIBENTRY. This pointer can either be
+* dereferenced if only the value is desired, or overwritten if
+* the LIBENTRY is to be deleted. NULL is returned if the filename
+* is not found in the table.
+*
+*****************************************************************************/
+HLIBENTRY *OLE_TYPEMGR::LookupLibEntry(LPOLESTR szFile)
+{
+ UINT ihlibeHash;
+ HLIBENTRY *qhlibe;
+
+ // Get the index of the bucket in which szFile would be hashed
+ // if present.
+ ihlibeHash = HashFileName(szFile);
+
+ // Search down the hash list for a LIBENTRY whose filename string
+ // matches szFile exactly.
+ qhlibe = m_rghlibeBucket + ihlibeHash;
+ while (*qhlibe != HLIBENTRY_Nil &&
+ !IsFilenameEqual(szFile,
+ (LPOLESTR)(m_bm.QtrOfHandle(((LIBENTRY *)m_bm.QtrOfHandle(*qhlibe))->m_hszFile)))) {
+ qhlibe = &((LIBENTRY *)m_bm.QtrOfHandle(*qhlibe))->m_hlibeNext;
+ }
+
+ // If no match is found, return NULL.
+ if (*qhlibe == HLIBENTRY_Nil)
+ qhlibe = NULL;
+
+ return qhlibe;
+}
+
+
+/***
+*TIPERROR GetHlibentryOfFileName(LPSTR szFile, HLIBENTRY *qhlibe)
+*
+* Purpose: Returns the handle to the LIBENTRY corresponding to szFile.
+*
+* Defers to LookUpLibEntry() to look for a LIBENTRY corresponding
+* to the specified library id. If successful, it returns a pointer
+* to the handle of the LIBENTRY.
+* If LookUpLibEntry returns null ( LIBENTRY does not exist for this
+* filename) then a dummy LIBENTRY is created for this filename and handle
+* to this dummy LIBENTRY is returned.
+*
+* Note : for detailed description of the data structure and related
+* algorithm, pl refer to the edtcont.doc.
+*
+* Input:
+* szFile : full path of the library whose LIBENTRY needs to be returned.
+*
+* Output:
+* TIPERROR
+*
+*
+*****************************************************************************/
+TIPERROR OLE_TYPEMGR::GetHlibentryOfFileName(LPOLESTR szFile, HLIBENTRY *qhlibe)
+{
+ TIPERROR err = TIPERR_None;
+ UINT ihlibeHash;
+ HCHUNK hchunkFile;
+ HLIBENTRY hlibe, *qhlibeTmp;
+ LIBENTRY *qlibe;
+
+
+ // Check if LIBENTRY already exist
+ qhlibeTmp = LookupLibEntry(szFile);
+
+ // if there is no LIBENTRY for this filename then we need to create a
+ // dummy LIBENTRY and attach it to the hash table
+ //
+ if (qhlibeTmp == NULL) {
+ // Allocate a new LIBENTRY structure
+ if ((err = m_bm.AllocChunk(&hlibe, sizeof(LIBENTRY))))
+ return(err);
+
+ // Allocate space for a copy of szFile.
+ if ((err = m_bm.AllocChunk(&hchunkFile, ostrblen0(szFile)*sizeof(OLECHAR)))) {
+ m_bm.FreeChunk(hlibe, sizeof(LIBENTRY));
+ return(err);
+ }
+
+ // Copy szFile to the space allocated above.
+ ostrcpy((LPOLESTR)m_bm.QtrOfHandle(hchunkFile), szFile);
+
+ // Assert that OLE_TYPEMGR_cTypeLibBuckets is a power of 2.
+ DebAssert(IsPowerOf2(OLE_TYPEMGR_cTypeLibBuckets), "TypeLibLoaded");
+
+ // Get a hash value in the range 0 to <# of buckets>-1.
+ ihlibeHash = HashFileName(szFile);
+
+ qlibe = QlibentryOfHlibentry(hlibe);
+
+ // Fill the new LIBENTRY
+ qlibe->m_hszFile = hchunkFile;
+
+ // This is a dummy node so initialize m_ptlib to NULL.
+ qlibe->m_ptlib = NULL;
+
+ // Insert the new LIBENTRY into the appropriate hash list.
+ qlibe->m_hlibeNext = m_rghlibeBucket[ihlibeHash];
+ m_rghlibeBucket[ihlibeHash] = hlibe;
+
+ // Initialize the return value
+ *qhlibe = hlibe;
+
+ }
+ else
+ *qhlibe = *qhlibeTmp;
+
+ return err;
+}
+
+#pragma code_seg()
diff --git a/private/oleauto/src/typelib/oletmgr.hxx b/private/oleauto/src/typelib/oletmgr.hxx
new file mode 100644
index 000000000..8c43ba25c
--- /dev/null
+++ b/private/oleauto/src/typelib/oletmgr.hxx
@@ -0,0 +1,100 @@
+/***
+*oletmgr.hxx - TYPE_MGR header file
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* There is a single instance of the TYPE_MGR per process (per task in
+* in win16). The TYPE_MGR maintains an in-memory collection of TYPEINFOs
+* and ITypeLibs. It supports change information notification for types
+* and libraries under development. It also prevents a type library from
+* being loaded more than once.
+*
+*Revision History:
+*
+* 08-Apr-91 alanc: Created.
+* 18-Feb-92 mikewo: commented out old code and added ITypeLib handling.
+* 17-Sep-92 rajivk: Edit & Continue support ( CanTypeChange Register/UnRegister ).
+*
+*****************************************************************************/
+
+#ifndef OLE_TYPEMGR_HXX_INCLUDED
+#define OLE_TYPEMGR_HXX_INCLUDED
+
+#include "silver.hxx"
+#include "sheapmgr.hxx"
+#include "blkmgr.hxx"
+#include "cltypes.hxx"
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szOLE_TYPEMGR_HXX)
+#define SZ_FILE_NAME g_szOLE_TYPEMGR_HXX
+#endif
+
+
+typedef HCHUNK HLIBENTRY;
+typedef sHCHUNK sHLIBENTRY;
+#define HLIBENTRY_Nil HCHUNK_Nil
+
+/***
+* This structure appears in the hash table lists hanging off of
+* m_rghlibeBucket[].
+******************************************************************/
+struct LIBENTRY
+{
+ HCHUNK m_hszFile;
+ ITypeLibA *m_ptlib;
+ HLIBENTRY m_hlibeNext;
+};
+
+const UINT OLE_TYPEMGR_cTypeLibBuckets = 32;
+
+/***
+*class OLE_TYPEMGR - 'oletmgr'
+*Purpose:
+* There is a single instance of the OLE_TYPEMGR per process.
+* It maintains a mapping from LIBIDs to ITypeLibs loaded into
+* this process. This is also used for Change Notification between
+* typeinfos. This also has the knowledge of backward dependencies
+* within loaded projects.
+*
+*Implementation
+* The OLE_TYPEMGR uses a hash table to map from the LIBID string to a
+* ITypeLib pointer.
+***********************************************************************/
+
+class OLE_TYPEMGR
+{
+
+public:
+ static TIPERROR Create(OLE_TYPEMGR **ppoletmgr);
+ nonvirt void Release();
+ nonvirt TIPERROR TypeLibLoaded(LPOLESTR szFile, ITypeLibA *ptlib);
+ nonvirt void TypeLibUnloaded(ITypeLibA *ptlib);
+ nonvirt ITypeLibA *LookupTypeLib(LPOLESTR szFile);
+
+private:
+ OLE_TYPEMGR(); // Clients should use Create() and Release() methods
+ ~OLE_TYPEMGR(); // instead of new/delete.
+
+ // Helper methods.
+ nonvirt HLIBENTRY *LookupLibEntry(LPOLESTR szFile);
+ nonvirt TIPERROR GetHlibentryOfFileName(LPOLESTR szFile, HLIBENTRY *qhlibe);
+ nonvirt LIBENTRY *QlibentryOfHlibentry(HLIBENTRY hlibe);
+
+ // Data members.
+ HCHUNK m_rghlibeBucket[OLE_TYPEMGR_cTypeLibBuckets];
+ BLK_MGR m_bm;
+};
+
+/*****
+* Wrapper function
+********************************************************************/
+inline LIBENTRY *OLE_TYPEMGR::QlibentryOfHlibentry(HLIBENTRY hlibe)
+{
+ return (LIBENTRY *) (m_bm.QtrOfHandle((HCHUNK) hlibe));
+}
+
+#endif // ! OLE_TYPEMGR_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/rtarray.h b/private/oleauto/src/typelib/rtarray.h
new file mode 100644
index 000000000..ef86a9e15
--- /dev/null
+++ b/private/oleauto/src/typelib/rtarray.h
@@ -0,0 +1,39 @@
+/* rtarray.h - variable array support
+*
+* Revision History:
+* 11-Aug-92 w-peterh: added suppport for UserDefined Types
+* 30-Apr-93 w-jeffc: added layout strings for DD and AD
+*
+*************************************************************************/
+
+
+#ifndef RTARRAY_H_INCLUDED
+#define RTARRAY_H_INCLUDED
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+// HARRAY_DESC- harraydesc
+
+typedef HCHUNK HARRAY_DESC;
+typedef sHCHUNK sHARRAY_DESC;
+const HARRAY_DESC HARRAYDESC_Nil = (HARRAY_DESC)HCHUNK_Nil;
+
+
+// layout string for TYPE_DATA byte swapping
+#define DD_LAYOUT "ll"
+
+
+// layout string for TYPE_DATA byte swapping
+#define AD_LAYOUT "ssssll"
+
+
+extern UINT ENCALL CbSizeArrayDesc(UINT);
+
+#ifdef __cplusplus
+} /* extern C */
+#endif
+
+
+#endif /* RTARRAY_H_INCLUDED */
diff --git a/private/oleauto/src/typelib/rtsheap.cxx b/private/oleauto/src/typelib/rtsheap.cxx
new file mode 100644
index 000000000..f7c2bf0a3
--- /dev/null
+++ b/private/oleauto/src/typelib/rtsheap.cxx
@@ -0,0 +1,473 @@
+/**
+*rtsheap.cxx - Implementation of C wrapper for SHEAPMGR.
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This module implements the C API needed to wrap the
+* SHEAPMGR/BLKMGR/DYN_BLKMGR so that the run-time can call it.
+*
+*Revision History:
+*
+* 31-Aug-92 ilanc: Created.
+* 10-Feb-93 RajivK: Changed the error checking in HsysAlloc
+*
+*
+*****************************************************************************/
+
+#include "switches.hxx"
+#include "version.hxx"
+
+#if OE_MAC
+// include Mac stuff
+#include "macos\memory.h"
+#endif
+
+#include "silver.hxx"
+#include "typelib.hxx"
+#include "rtsheap.h"
+#include "sheapmgr.hxx"
+#include "blkmgr.hxx"
+#include "dblkmgr.hxx"
+#include <stdlib.h>
+
+#pragma hdrstop(RTPCHNAME)
+
+#if OE_MAC
+ #include "macos\errors.h"
+ THz g_pOBZone = NULL; // ptr to zone to alloc out of
+ // this is initialized in EbThreadDllInit.
+ // size declarations are also carried there.
+#endif
+
+#if OE_WIN16
+#pragma optimize("q",off)
+#endif //OE_WIN16
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+char szOleRtsheapCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleRtsheapCxx
+#else
+static char szRtsheapCxx[] = __FILE__;
+#define SZ_FILE_NAME szRtsheapCxx
+#endif
+#endif
+
+
+
+// **************************************************
+// Low-level system moveable memory allocation wrappers
+// **************************************************
+//
+
+/***
+* HsysAlloc
+*
+* Purpose:
+* Allocate a system memblock of given size and return its handle.
+* Note: on Win16 dereferences handle and produce 32-bit
+* address = selector:offset=0.
+*
+* Inputs:
+* bch Allocation request. Can be >64K.
+*
+* Outputs:
+* Returns an HSYS. HSYS_Nil if unsuccessful.
+*
+*****************************************************************************/
+
+#pragma code_seg( CS_CORE )
+HSYS PASCAL EXPORT HsysAlloc(BCH bch)
+{
+#if OE_WIN16
+
+ VOID *pv;
+ HANDLE hMem;
+
+ if (DebErrorNow(TIPERR_OutOfMemory) ||
+ ((hMem = GlobalAlloc(GMEM_MOVEABLE, bch)) == NULL)) {
+ return HSYS_Nil;
+ }
+ else if ((pv = GlobalLock(hMem)) == NULL) {
+ return HSYS_Nil;
+ }
+ else {
+#if ID_DEBUG
+ // debug-only: init alloced mem to a weird bitpattern
+ //
+ if (bch <= USHRT_MAX) {
+ memset(pv, 0x69, (size_t)bch);
+ }
+#endif // ID_DEBUG
+ return (HSYS)pv;
+ }
+
+#elif OE_MACNATIVE
+
+ Handle hMemBlock;
+ THz pCurrZone;
+ OSErr oserr;
+
+ //--------------------------------------------------------
+ // The following is a work-around to our bogus code that
+ // caches pointers to moveable memory. The basic idea
+ // is that we allocate all such memory out of a sub-heap
+ // inside the host application (or inside our own heap when
+ // a .DLL). The zone is switched in briefly to allocate,
+ // then switched back to avoid the OS or CODE seg loads
+ // from allocating there-in.
+ //
+ // The practice of caching pointers to moveable memory on
+ // the mac should be fixed to gain optimal use of available
+ // memory. The sub-heap scheme pools available memory
+ // and keeps it from being used for loading code when data
+ // is small. Visa-versa, we cannot flush more code out
+ // when the data expands to the heap limit. (jwc)
+ //--------------------------------------------------------
+
+ DebAssert(g_pOBZone != NULL, "OB Zone used before being allocated.");
+ pCurrZone = GetZone(); // save current heap zone.
+ SetZone(g_pOBZone); // set to OB's zone.
+
+ // Allocate moveable mac memblock.
+ hMemBlock = NewHandle(bch);
+ // get the error before calling SetZone. 'Cos SetZone can
+ // change the memory error.
+ oserr = MemError();
+
+ SetZone(pCurrZone); // always restore zone.
+
+ if (oserr) {
+ return HSYS_Nil;
+ }
+ else {
+ return (HSYS)hMemBlock;
+ }
+
+#elif OE_MAC
+
+ Handle hMemBlock;
+ OSErr oserr;
+
+ // Allocate moveable mac memblock.
+ hMemBlock = NewHandle(bch);
+ oserr = MemError();
+ if (oserr) {
+ return HSYS_Nil;
+ }
+ else {
+ return (HSYS)hMemBlock;
+ }
+
+#elif OE_WIN32
+
+ // Reserve and commit bch bytes.
+ return (HSYS)VirtualAlloc(NULL, bch, MEM_COMMIT, PAGE_READWRITE);
+
+#else
+#error Bad OE
+#endif
+}
+#pragma code_seg( )
+
+
+/***
+* HsysReallocHsys
+*
+* Purpose:
+* Reallocate a system memblock given handle to new size.
+* Shrinking won't move block.
+*
+* Inputs:
+* hsys Handle to sys memblock they want to realloc.
+* bchNew New size they want. Can be >64K.
+*
+* Outputs:
+* Returns an HSYS. HSYS_Nil if unsuccessful.
+*
+*****************************************************************************/
+
+HSYS PASCAL EXPORT HsysReallocHsys(HSYS hsys, BCH bchNew)
+{
+ DebAssert(hsys != HSYS_Nil, "null HSYS.");
+
+#if OE_WIN16
+
+ HANDLE hMem, hMemNew;
+ VOID *pv, *pvNew;
+ USHORT usSel;
+ DWORD dwMem;
+ DWORD dwNewSize = bchNew;
+#if ID_DEBUG
+ ULONG cbOld;
+#endif // ID_DEBUG
+
+ pv = (VOID *)hsys;
+
+ // Get selector
+ usSel = OOB_SELECTOROF(pv);
+
+ if ((dwMem = GlobalHandle((WORD)usSel)) == NULL) {
+ return HSYS_Nil;
+ }
+ else {
+ // Extract the handle.
+ hMem = (HANDLE) LOWORD(dwMem);
+
+#if ID_DEBUG
+ // get the size of the old block
+ cbOld = GlobalSize(hMem);
+#endif // ID_DEBUG
+
+ if (DebErrorNow(TIPERR_OutOfMemory) ||
+ ((hMemNew =
+ GlobalReAlloc(hMem, bchNew, GMEM_MOVEABLE)) == NULL)) {
+ return HSYS_Nil;
+ }
+ else if ((pvNew = GlobalLock(hMemNew)) == NULL) {
+ return HSYS_Nil;
+ }
+ else {
+#if ID_DEBUG
+ // if growing then init new memory with weird bitpattern
+ if (bchNew > cbOld) {
+ ULONG cbNew = bchNew - cbOld;
+ if (cbNew <= USHRT_MAX) {
+ memset((BYTE HUGE *)pvNew + cbOld, 0x69, (size_t)cbNew);
+ }
+ }
+#endif // ID_DEBUG
+ return (HSYS)pvNew;
+ }
+ }
+
+#elif OE_MACNATIVE
+
+ Handle hMemBlock;
+ THz pCurrZone;
+ OSErr oserr;
+#if ID_DEBUG
+ ULONG cbOld;
+#endif // ID_DEBUG
+
+ hMemBlock = (Handle)hsys;
+
+#if ID_DEBUG
+ // get the size of the old block
+ cbOld = GetHandleSize(hMemBlock);
+#endif // ID_DEBUG
+
+ pCurrZone = GetZone(); // save current zone
+ SetZone(HandleZone((Handle)hsys)); // must set proper zone or
+ SetHandleSize(hMemBlock, bchNew); // handle will likely
+ // jump to curr zone if it moves.
+ oserr = MemError();
+ SetZone(pCurrZone); // restore current zone.
+
+
+ if (oserr == memFullErr) {
+ // Out of memory
+ return HSYS_Nil;
+ }
+
+ DebAssert ((MemError() != nilHandleErr),
+ "HsysReallocHsys: NIL master pointer ");
+
+ DebAssert ((MemError() != memWZErr),
+ "HsysReallocHsys: Attempt to operate on free Block");
+
+ // anything else would be an undocumented error
+ DebAssert (MemError() == noErr,
+ "HsysReallocHsys: undocumented Mac error");
+
+#if ID_DEBUG
+ // if growing then init new memory with weird bitpattern
+ if (bchNew > cbOld) {
+ memset((BYTE *)*hMemBlock + cbOld, 0x69, (size_t)(bchNew - cbOld));
+ }
+#endif // ID_DEBUG
+ return (HSYS)hMemBlock;
+
+#elif OE_MAC
+
+ Handle hMemBlock;
+ OSErr oserr;
+#if ID_DEBUG
+ ULONG cbOld;
+#endif // ID_DEBUG
+
+ hMemBlock = (Handle)hsys;
+
+#if ID_DEBUG
+ // get the size of the old block
+ cbOld = GetHandleSize(hMemBlock);
+#endif // ID_DEBUG
+
+ SetHandleSize(hMemBlock, bchNew); // realloc
+ oserr = MemError();
+
+ if (oserr == memFullErr) {
+ // Out of memory
+ return HSYS_Nil;
+ }
+
+ DebAssert ((MemError() != nilHandleErr),
+ "HsysReallocHsys: NIL master pointer ");
+
+ DebAssert ((MemError() != memWZErr),
+ "HsysReallocHsys: Attempt to operate on free Block");
+
+ // anything else would be an undocumented error
+ DebAssert (MemError() == noErr,
+ "HsysReallocHsys: undocumented Mac error");
+
+#if ID_DEBUG
+ // if growing then init new memory with weird bitpattern
+ if (bchNew > cbOld) {
+ memset((BYTE *)*hMemBlock + cbOld, 0x69, (size_t)(bchNew - cbOld));
+ }
+#endif // ID_DEBUG
+ return (HSYS)hMemBlock;
+
+#elif OE_WIN32
+ HSYS hsysNew;
+ // Get current block size
+ BCH bchOld = BchSizeBlockHsys(hsys);
+
+ // Alloc memory for the new block
+ hsysNew = HsysAlloc(bchNew);
+ if (hsysNew != HSYS_Nil) {
+ // Copy old block to new
+ memcpy((BYTE *)hsysNew, (BYTE* )hsys, bchOld < bchNew ?
+ (size_t)bchOld :
+ (size_t)bchNew);
+#if ID_DEBUG
+ // if growing then init new memory with weird bitpattern
+ if (bchNew > bchOld) {
+ memset((BYTE *)hsysNew + bchOld, 0x69, (size_t)(bchNew - bchOld));
+ }
+#endif // ID_DEBUG
+
+ }
+ return hsysNew;
+
+#else
+#error Bad OE
+#endif
+}
+
+
+/***
+* FreeHsys
+*
+* Purpose:
+* Free the sys memblock given a handle.
+* Implementation:
+* On Win16, get selector part of hsys,
+* get its handle, unlock and finally free.
+* On Mac: Just use DisposHandle
+*
+* Inputs:
+* hsys Handle to memblock they want to free.
+*
+* Outputs:
+* Returns HSYS_Nil if successful, otherwise on failure
+* returns the input param.
+*
+*****************************************************************************/
+
+#pragma code_seg( CS_CORE )
+HSYS PASCAL EXPORT FreeHsys(HSYS hsys)
+{
+ DebAssert(hsys != HSYS_Nil, "null hsys.");
+
+#if OE_WIN16
+
+ HANDLE hMem;
+ DWORD dwMem;
+ USHORT usSel = OOB_SELECTOROF((VOID *)hsys);
+
+ dwMem = GlobalHandle((WORD)usSel);
+ if (dwMem == NULL) {
+ // error
+ return hsys;
+ }
+ else {
+ hMem = (HANDLE) LOWORD(dwMem);
+ GlobalUnlock(hMem); // Can't fail cos nondiscardable.
+ if (GlobalFree(hMem) != NULL) {
+ // error
+ return hsys;
+ }
+ else {
+ // ok
+ return HSYS_Nil;
+ }
+ }
+
+#elif OE_MACNATIVE
+ THz pCurrZone;
+#if ID_DEBUG
+ OSErr oserr;
+#endif
+
+ pCurrZone = GetZone(); // save current zone
+ SetZone(HandleZone((Handle)hsys)); // must set to proper zone to correctly update free list.
+
+ DisposHandle((Handle)hsys);
+
+#if ID_DEBUG
+ oserr = MemError(); // SetZone() will destroy MemError() result.
+#endif
+
+ SetZone(pCurrZone); // restore zone.
+
+ DebAssert (oserr != memWZErr,
+ "FreeHsys: attempt to operate on already free block.");
+
+ DebAssert(oserr == noErr,
+ "FreeHsys: unexpected error.");
+
+ return HSYS_Nil;
+
+#elif OE_MAC
+#if ID_DEBUG
+ OSErr oserr;
+#endif
+
+ DisposHandle((Handle)hsys);
+
+#if ID_DEBUG
+ oserr = MemError(); // SetZone() will destroy MemError() result.
+#endif
+
+ DebAssert (oserr != memWZErr,
+ "FreeHsys: attempt to operate on already free block.");
+
+ DebAssert(oserr == noErr,
+ "FreeHsys: unexpected error.");
+
+ return HSYS_Nil;
+
+#elif OE_WIN32
+
+ BOOL fFreeOk = VirtualFree((LPVOID) hsys, 0, MEM_RELEASE);
+#if ID_DEBUG
+ if (!fFreeOk) {
+ DWORD oserr = GetLastError();
+ DebHalt("FreHSys: VirtualFree failed.");
+ }
+#endif
+ return HSYS_Nil;
+#else
+#error Bad OE
+#endif
+
+}
+#pragma code_seg( )
+
+
diff --git a/private/oleauto/src/typelib/rtsheap.h b/private/oleauto/src/typelib/rtsheap.h
new file mode 100644
index 000000000..d7939264c
--- /dev/null
+++ b/private/oleauto/src/typelib/rtsheap.h
@@ -0,0 +1,128 @@
+/***
+*rtsheap.hxx - Run-time SHEAP wrapper for C API.
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Defines the Rtsheap* entry points exported from ob.dll. These entry
+* points are documented in the Object Basic Host Application
+* Implementor's Guide (obguide.doc).
+*
+*Revision History:
+*
+* 31-Aug-92 ilanc: Created.
+* 28-Jan-93 ilanc: Added IsSheapEmpty
+*
+*****************************************************************************/
+
+#ifndef RTSHEAP_H_INCLUDED
+#define RTSHEAP_H_INCLUDED
+
+#include "types.h"
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szRTSHEAP_H)
+#define SZ_FILE_NAME g_szRTSHEAP_H
+#endif
+
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+// Handle to system memory
+// On Win16: selector:offset==0 address
+// On Win32: 32-bit pointer
+// On Mac: 32-bit Handle (pointer to master pointer).
+//
+typedef VOID* HSYS;
+#define HSYS_Nil ((HSYS)NULL)
+
+// Byte count of system alloc -- dword for "huge" arrays.
+typedef DWORD BCH;
+
+// HH: Handle to a heap -- return by a call to e.g. SheapInit.
+typedef struct SHEAP_WRAPPER* HH;
+#define HH_Nil ((HH)NULL)
+
+// BC: byte count -- entrysize.
+typedef WORD BC;
+
+// HBP: handle to entry block: implemented as HCHUNK.
+typedef sHCHUNK HBP;
+#define HBP_Nil ((HBP)HCHUNK_Nil)
+
+// **************************************************
+// Low-level system memory allocation wrappers
+// **************************************************
+//
+
+// Allocate system memory
+HSYS PASCAL EXPORT HsysAlloc(BCH bch);
+
+// Reallocate system memory.
+HSYS PASCAL EXPORT HsysReallocHsys(HSYS hsys, BCH bch);
+
+// Free system memory.
+HSYS PASCAL EXPORT FreeHsys(HSYS hsys);
+
+// Get memblock size.
+BCH PASCAL EXPORT BchSizeBlockHsys(HSYS hsys);
+
+// Lock system memblock.
+VOID * PASCAL EXPORT PvLockHsys(HSYS hsys);
+
+// Unlock system memblock.
+VOID PASCAL EXPORT UnlockHsys(HSYS hsys);
+
+// Dereference system memblock.
+VOID * PASCAL EXPORT PvDerefHsys(HSYS hsys);
+
+
+// **************************************************
+// Sheapmgr wrappers
+// **************************************************
+//
+// Sheap initialization
+HH PASCAL EXPORT SheapInit(BC bc);
+
+// Sheap termination
+VOID PASCAL EXPORT SheapTerm(HH hh);
+
+// Heap entry allocation.
+HBP PASCAL EXPORT HbpAllocHh(HH hh, BC bc);
+
+// Heap entry reallocation.
+HBP PASCAL EXPORT HbpReallocHhHbp(HH hh, HBP hbp, BC bc);
+
+// Heap entry reallocation.
+HBP PASCAL EXPORT HbpReallocHhHbp(HH hh, HBP hbp, BC bc);
+
+// Heap entry deallocation.
+VOID PASCAL EXPORT FreeHhHbp(HH hh, HBP hbp);
+
+// Return heap entry size.
+BC PASCAL EXPORT BcSizeBlockHhHbp(HH hh, HBP hbp);
+
+// Heap compaction.
+BC PASCAL EXPORT BcHeapCompactHh(HH hh, BC bc);
+
+// Handle dereference.
+VOID * PASCAL EXPORT PvDerefHhHbp(HH hh, HBP hbp);
+
+// Handle locking.
+VOID * PASCAL EXPORT PvLockHhHbp(HH hh, HBP hbp);
+
+// Handle unlocking.
+VOID PASCAL EXPORT UnlockHhHbp(HH hh, HBP hbp);
+
+// Is sheap empty?
+BOOL PASCAL EXPORT IsSheapEmpty(HH hh);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif // ! RTSHEAP_H_INCLUDED
diff --git a/private/oleauto/src/typelib/segnames.h b/private/oleauto/src/typelib/segnames.h
new file mode 100644
index 000000000..f076c99e2
--- /dev/null
+++ b/private/oleauto/src/typelib/segnames.h
@@ -0,0 +1,246 @@
+/***
+*segnames.h - Segment name declarations
+*
+* Copyright (C) 1991-1994, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file is to provide names for segmentation purposes and to forward declare
+* those segment names on platforms that require it.
+*
+*
+*Revision History:
+*
+* [00] 19-Feb-94 jimcool: Created
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+
+ // ------------ Include Files --------------------
+#if !defined (SWITCHES_HXX_INCLUDED)
+#include "switches.hxx"
+#endif
+
+
+ // ------------ Defines --------------------------
+// REVIEW: the following could be HC_ specific depending on what WIN32
+// wants to do with these.
+//
+// USAGE:
+//
+// ALLOC_NEAR - use to allocate data near or in the current data seg.
+// ALLOC_FAR - use to allocate data far. Use #pragma data_seg() to
+// change segment name & attributes. (Win16)
+// ALLOC_STACK - use to allocate data in stack segment
+// ALLOC_CODE - use to allocate data in the current code seg. Use
+// #pragma code_seg() to change seg name. (Win16,Mac,Win32)
+//
+#if OE_MAC68K
+#define ALLOC_CODE(type) __declspec(allocate("_CODE")) type
+#define ALLOC_NEAR(type) __declspec(allocate("_DATA")) type
+#define ALLOC_FAR(type) __declspec(allocate("_FAR_DATA")) type
+#define ALLOC_STACK(type) type
+#endif
+
+#if OE_WIN32 || OE_MACPPC
+#define ALLOC_NEAR(type) type
+#define ALLOC_FAR(type) type
+#define ALLOC_STACK(type) type
+#define ALLOC_CODE(type) type
+#endif
+
+#if OE_WIN16
+#define ALLOC_NEAR(type) type __based(__segname("_DATA"))
+#define ALLOC_FAR(type) type __based(__segname("_DATA"))
+#define ALLOC_STACK(type) type __based(__segname("_STACK"))
+#define ALLOC_CODE(type) type __based(__segname("_CODE"))
+#endif
+
+
+
+//
+// Segment Names:
+//
+//
+// Definitions:
+// ------------
+//
+// CS_CORE - Frequently called code (working set)
+// CS_CORE2 - split into two segs under debug for size reasons
+// CS_DEBUG - ID_DEBUG only code (cuts working set)
+// CS_INIT - Code used at startup and after
+// CS_CREATE - Code used only at typelib creation (by mktyplib)
+// CS_LAYOUT - GEN_DTINFO::LayOut() and things it calls. This
+// is used when loading a Dual Interface typelib
+// (CS_INIT) and from mktyplib (CS_CREATE), so split
+// into its own segment
+// CS_QUERY - Code used by QueryPathOfRegTypeLib (only routine
+// called at startup by some apps)
+// CS_RARE - Rarely called code (cuts working set size)
+// CS_DBCSHASH - LHashValOfDBCSName and its tables and helpers
+// CS_CP - Common code page data for LHashValOfNameSys
+// CS_CPW... - Windows code page data for LHashValOfNameSys
+// CS_CPM... - Mac code page data for LHashValOfNameSys
+//
+
+#if !OE_WIN32 && !OE_MACPPC
+
+#if OE_MAC
+
+#define CS_CORE "TLibCore", "swappable"
+#define CS_CORE2 "TLibCore", "swappable"
+#define CS_DEBUG "TLibDebug", "swappable"
+#define CS_INIT "TLibLoad", "swappable"
+#define CS_CREATE "TLibCreate", "swappable"
+#define CS_LAYOUT "TLibLayOut", "swappable"
+#define CS_QUERY "TLibQuery", "swappable"
+#define CS_RARE "TLibRare", "swappable"
+#define CS_DBCSHASH "TLibHash", "swappable"
+#define CS_CP1250 "TLibCP1250", "swappable"
+#define CS_CP1251 "TLibCP1251", "swappable"
+#define CS_CP1252 "TLibCP1252", "swappable"
+#define CS_CP1255 "TLibCP1255", "swappable"
+#define CS_CP1256 "TLibCP1256", "swappable"
+#define CS_CP10000 "TLibCP10000", "swappable"
+#define CS_CP10004 "TLibCP10004", "swappable"
+#define CS_CP10005 "TLibCP10005", "swappable"
+#define CS_CP10029 "TLibCP10029", "swappable"
+#define CS_CP10007 "TLibCP10007", "swappable"
+#define CS_CPWGREEK "TLibCPWGre", "swappable"
+#define CS_CPWICELAND "TLibCPWIce", "swappable"
+#define CS_CPWTURKISH "TLibCPWTur", "swappable"
+#define CS_CPWNORWEGIAN "TLibCPWNor", "swappable"
+#define CS_CPWENGIRELAND "TLibCPWIre", "swappable"
+#define CS_CPMGREEK "TLibCPMGre", "swappable"
+#define CS_CPMNORWEGIAN "TLibCPMNor", "swappable"
+#define CS_CPMENGIRELAND "TLibCPMIre", "swappable"
+
+#elif OE_WIN16
+
+#define CS_CORE "TLibCore"
+#define CS_CORE2 "TLibCore"
+#define CS_DEBUG "TLibDebug"
+#define CS_INIT "TLibLoad"
+#define CS_CREATE "TLibCreate"
+#define CS_LAYOUT "TLibLayOut"
+#define CS_QUERY "TLibQuery"
+#define CS_RARE "TLibRare"
+#define CS_DBCSHASH "TLibHash"
+#define CS_CP1250 "TLibCP1250"
+#define CS_CP1251 "TLibCP1251"
+#define CS_CP1252 "TLibCP1252"
+#define CS_CP1255 "TLibCP1255"
+#define CS_CP1256 "TLibCP1256"
+#define CS_CP10000 "TLibCP10000"
+#define CS_CP10004 "TLibCP10004"
+#define CS_CP10005 "TLibCP10005"
+#define CS_CP10029 "TLibCP10029"
+#define CS_CP10007 "TLibCP10007"
+#define CS_CPWGREEK "TLibCPWGre"
+#define CS_CPWICELAND "TLibCPWIce"
+#define CS_CPWTURKISH "TLibCPWTur"
+#define CS_CPWNORWEGIAN "TLibCPWNor"
+#define CS_CPWENGIRELAND "TLibCPWIre"
+#define CS_CPMGREEK "TLibCPMGre"
+#define CS_CPMNORWEGIAN "TLibCPMNor"
+#define CS_CPMENGIRELAND "TLibCPMIre"
+
+#else // OE_WIN16
+#error !Unsupported Platform
+#endif // OE_WIN16
+
+//
+// Win-32 & PowerPC prefers no explicit segmentation.
+//
+#else // !OE_WIN32 && !OE_MACPPC
+
+#define CS_CORE
+#define CS_CORE2
+#define CS_DEBUG
+#define CS_INIT
+#define CS_CREATE
+#define CS_LAYOUT
+#define CS_QUERY
+#define CS_RARE
+#define CS_DBCSHASH
+#define CS_CP1250
+#define CS_CP1251
+#define CS_CP1252
+#define CS_CP1255
+#define CS_CP1256
+#define CS_CP10000
+#define CS_CP10004
+#define CS_CP10005
+#define CS_CP10029
+#define CS_CP10007
+#define CS_CPWGREEK
+#define CS_CPWICELAND
+#define CS_CPWTURKISH
+#define CS_CPWNORWEGIAN
+#define CS_CPWENGIRELAND
+#define CS_CPMGREEK
+#define CS_CPMNORWEGIAN
+#define CS_CPMENGIRELAND
+
+#endif // !OE_WIN32 && !OE_MACPPC
+
+
+// On Wings & PowerPC compilers, must forward declare section names.
+#if OE_MAC
+
+#pragma code_seg(CS_CORE)
+#pragma code_seg(CS_CORE2)
+#pragma code_seg(CS_DEBUG)
+#pragma code_seg(CS_INIT)
+#pragma code_seg(CS_CREATE)
+#pragma code_seg(CS_LAYOUT)
+#pragma code_seg(CS_QUERY)
+#pragma code_seg(CS_RARE)
+#pragma code_seg(CS_DBCSHASH)
+#pragma code_seg(CS_CP1250)
+#pragma code_seg(CS_CP1251)
+#pragma code_seg(CS_CP1252)
+#pragma code_seg(CS_CP1255)
+#pragma code_seg(CS_CP1256)
+#pragma code_seg(CS_CP10000)
+#pragma code_seg(CS_CP10004)
+#pragma code_seg(CS_CP10005)
+#pragma code_seg(CS_CP10029)
+#pragma code_seg(CS_CP10007)
+#pragma code_seg(CS_CPWGREEK)
+#pragma code_seg(CS_CPWICELAND)
+#pragma code_seg(CS_CPWTURKISH)
+#pragma code_seg(CS_CPWNORWEGIAN)
+#pragma code_seg(CS_CPWENGIRELAND)
+#pragma code_seg(CS_CPMGREEK)
+#pragma code_seg(CS_CPMNORWEGIAN)
+#pragma code_seg(CS_CPMENGIRELAND)
+#pragma code_seg()
+
+#endif // OE_MAC
+
+
+// Some more #pragma macros //
+
+#if OE_MAC
+
+#if defined (_PCODE)
+
+#define PCODE_OFF optimize( "q", off )
+#define PCODE_ON optimize( "q", on )
+
+#else // _PCODE
+
+#define PCODE_OFF
+#define PCODE_ON
+
+#endif // _PCODE
+
+#else // OE_MAC
+
+#define PCODE_OFF
+#define PCODE_ON
+
+#endif //OE_MAC
diff --git a/private/oleauto/src/typelib/segorder.asm b/private/oleauto/src/typelib/segorder.asm
new file mode 100644
index 000000000..553c2c1eb
--- /dev/null
+++ b/private/oleauto/src/typelib/segorder.asm
@@ -0,0 +1,99 @@
+;***
+;segorder.asm - Control segment ordering in the Win16 build
+;
+; Copyright (C) 1994, Microsoft Corporation. All Rights Reserved.
+; Information Contained Herein Is Proprietary and Confidential.
+;
+;Purpose:
+; This file defines the segment order for Win16 Typelib.dll. Segments
+; not listed here will be at the mercy of the linker.
+;
+; WARNING: THIS FILE MUST BE THE FIRST OBJECT FILE IN THE LIST PASSED TO
+; THE LINKER. IF IT IS NOT, THIS FILE WILL NOT WORK.
+;
+;Revision History:
+;
+; [00] 27-Sep-94 barrybo: Created
+;
+;Implementation Notes:
+;
+;******************************************************************************
+
+ .286
+ .MODEL LARGE, C
+
+ ; Pack these logical segments into one physical segment
+ .CODE _TEXT
+ .CODE TLibQuery
+ .CODE WEP_TEXT
+
+ INITGROUP GROUP _TEXT, TLibQuery, WEP_TEXT
+
+
+ ; Pack segments not used during typelib load or registration
+ .CODE MEM_TEXT
+ .CODE DFSTREAM_TEXT
+ .CODE ENTRYMGR_TEXT
+ .CODE DFNTBIND_TEXT
+ .CODE GBINDTBL_TEXT
+ .CODE DSTRMGR_TEXT
+ .CODE GPTBIND_TEXT
+ .CODE DFNTCOMP_TEXT
+
+ RAREGROUP GROUP MEM_TEXT, DFSTREAM_TEXT, ENTRYMGR_TEXT, DFNTBIND_TEXT
+ RAREGROUP GROUP GBINDTBL_TEXT, DSTRMGR_TEXT, GPTBIND_TEXT, DFNTCOMP_TEXT
+
+ ; Pack other segments together as tightly as possible
+
+ .CODE BLKMGR_TEXT
+ .CODE FSTREAM_TEXT
+ .CODE SHEAPMGR_TEXT
+ .CODE RTSHEAP_TEXT
+ .CODE TLIBUTIL_TEXT
+ .CODE TLIBGUID_TEXT
+ .CODE OBGUID_TEXT
+ .CODE STLTINFO_TEXT
+ .CODE NAMMGR_TEXT
+ .CODE GTLIBOLE_TEXT
+ .CODE IMPMGR_TEXT
+
+ MISC1GROUP GROUP BLKMGR_TEXT, FSTREAM_TEXT, SHEAPMGR_TEXT, RTSHEAP_TEXT
+ MISC1GROUP GROUP TLIBUTIL_TEXT, TLIBGUID_TEXT, OBGUID_TEXT, STLTINFO_TEXT
+ MISC1GROUP GROUP NAMMGR_TEXT, GTLIBOLE_TEXT, IMPMGR_TEXT
+
+ .CODE ERRMAP_TEXT
+ .CODE CLUTIL_TEXT
+ .CODE TDATA1_TEXT
+ .CODE TDATA2_TEXT
+ .CODE DTMBRS_TEXT
+ .CODE DTBIND_TEXT
+ .CODE OLEConst
+ .CODE DBINDTBL_TEXT
+ .CODE GTLIBSTG_TEXT
+ .CODE COMDAT_SEG1
+
+ MISC2GROUP GROUP ERRMAP_TEXT, CLUTIL_TEXT, TDATA1_TEXT, TDATA2_TEXT
+ MISC2GROUP GROUP DTMBRS_TEXT, DTBIND_TEXT, DTBIND_TEXT, OLEConst
+IFDEF _DEBUG
+ ; MISC2 is too big for the debug build, so add an extra physical segment
+ MISC3GROUP GROUP DBINDTBL_TEXT, GTLIBSTG_TEXT, COMDAT_SEG1
+ELSE
+ MISC2GROUP GROUP DBINDTBL_TEXT, GTLIBSTG_TEXT, COMDAT_SEG1
+ENDIF
+
+ ; CORE is really the MBString stuff and TLibCore
+
+ .CODE TLibCore
+ .CODE MBSTRING_TEXT
+ COREGROUP GROUP TLibCore, MBSTRING_TEXT
+
+ ; put debugging stuff together here
+IFDEF _DEBUG
+ .CODE DEBUG2_TEXT
+ .CODE TLibDebug
+ DEBUGGROUP GROUP DEBUG2_TEXT, TLibDebug
+ENDIF
+
+ ; all other segments are not packed
+
+ END
diff --git a/private/oleauto/src/typelib/sheapmgr.cxx b/private/oleauto/src/typelib/sheapmgr.cxx
new file mode 100644
index 000000000..5aae0d6b1
--- /dev/null
+++ b/private/oleauto/src/typelib/sheapmgr.cxx
@@ -0,0 +1,1996 @@
+/***
+*sheapmgr.cxx - Silver Heap Manager
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* The silver Heap Manager describes a heap manager that
+* manages contiguous blocks of memory in a heap. Blocks are
+* accessed via block descriptor object (BLK_DESC)
+* upon allocation and maybe grown/shrunk.
+* See \silver\doc\ic\sheapmgr.doc for more information.
+*
+* This file implements the following classes:
+* SHEAP_MGR
+* BLK_DESC
+*
+*Revision History:
+* 14-Feb-91 ilanc: Created.
+* 27-Feb-91 ilanc: Removed 2nd param on SHEAP_MGR::Init()
+* 07-Mar-91 petergo: added NO_INCLUDE_AFX
+* 15-Mar-91 ilanc: Modified to use OS-independent mem mgmt.
+* 28-Mar-91 ilanc: Constructor asserts if not seg aligned.
+* 31-Mar-91 ilanc: Fixed Realloc. (Allow |dbSize| > 2^15).
+* 04-Apr-91 ilanc: Subsumes blkdesc.cxx -- all BLK_DESC
+* outline methods are here as well.
+* 15-Apr-91 ilanc: Removed NO_INCLUDE_AFX since need exceptions.
+* 29-Aug-91 ilanc: Zapped #if (_MSC_VER) test (C7 does static
+* const members ok now).
+* 26-Sep-91 ilanc: Return TIPERR_OutOfMemory instead of
+* asserting that blocksize <= USHRT_MAX for
+* segmented archs.
+* 20-Mar-92 martinc: added support for Mac (OE_MAC)
+* changed REALMODEMemRealloc to call MemRealloc
+* 07-Apr-92 ilanc: Added DebSheapShake().
+* 15-Apr-92 martinc: Commented the Mac specific memory mgmt out
+* (now does the same as in Realmode)
+* 20-Apr-92 martinc: restored file i/o for OE_MAC
+* 20-Sept-92 Rajivk: Sheapshaking
+* 19-Mar-93 ilanc: OE_MAC renamed OE_MACNATIVE (since it uses
+* macos moveable memory). Introduced new OE_MAC
+* to mean fixed memory for blocks.
+*
+*
+*Implementation Notes:
+* Uses AllocSeg to allocate heap segment.
+* Uses ReallocSeg to reallocate.
+* Uses FreeSeg to free.
+* [All of above implemented in mem.cxx -- which has Win and Os/2 versions]
+*
+* CONSIDER: using BASED POINTERS - unclear whether
+* supported on 32-bit flat and Mac. If SHEAP_MGR
+* goes away in 32-bit world, then can use
+* based pointers in 16:16 plus use block allocation lib.
+*
+*****************************************************************************/
+
+#define SHEAPMGR_VTABLE // export sheap mgr vtable.
+#define BLKDESC_VTABLE // export blk desc vtable
+
+#include "switches.hxx"
+#include "version.hxx"
+#include "obwin.hxx"
+
+#include <stdlib.h> // for min.
+#include <string.h> // for memmove.
+
+// Nonuse of precompiled headers only works for WIN16
+// and WIN32.
+
+#if OE_REALMODE || OE_MAC
+
+// do nothing...
+
+#elif OE_MACNATIVE
+# include "macos\Memory.h"
+#endif
+
+#include "silver.hxx"
+#include "typelib.hxx"
+#include "tls.h"
+#include "mem.hxx"
+#include "sheapmgr.hxx"
+#include "debug.hxx"
+#include "stream.hxx"
+#include "rtsheap.h"
+
+#pragma hdrstop(RTPCHNAME)
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+char szOleSheapmgrCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleSheapmgrCxx
+#else
+static char szSheapmgrCxx[] = __FILE__;
+#define SZ_FILE_NAME szSheapmgrCxx
+#endif
+#endif
+
+
+
+
+#if ID_DEBUG
+extern BOOL g_fSheapShakingOn; // defaults to FALSE (in tshell.cxx)
+
+static LONG g_cSheapmgr = 0;
+BOOL g_fValidSheapmgrList = TRUE;
+ITLS g_itlsSheapmgr = ITLS_EMPTY;
+#endif
+
+
+// allocs bigger than this cause trouble on Win16 when running in Standard
+// Mode on a 80286/NT Wow: GlobalReAlloc of sizes > CBALLOCMAX may cause
+// the selector to change. To avoid this, the max size of all sheaps has
+// been shrunk by 32 bytes. (vba2 #3982)
+#define CBALLOCMAX (WORD)0xFFDF
+
+
+#if !(OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+
+#if OE_SEGMENTED
+
+#if ID_DEBUG
+// These are tracked only in the os/2 debug build.
+ULONG g_cbSegsAllocd, g_cbSegsAllocdMax;
+#endif
+
+// Segment alloc stuff.
+/***
+*USHORT AllocSeg - Allocates a segment under Win or Os/2.
+*
+*Purpose:
+* Allocates a segment under Win or Os/2.
+*
+*Entry:
+* usSize - Count of bytes to allocate. Must be < 64K.
+* If usSize == 0, 64K will be allocated.
+*
+*Exit:
+* Returns a 16-bit segment selector. Return (invalid selector) 0
+* if fails.
+*
+*Implementation Notes:
+* Os/2: Simply calls DosAllocSeg.
+* Win: Calls GlobalAlloc to get a handle, then dereferences
+* the handle with GlobalLock and returns selector part
+* of pointer to memblock.
+*
+*Errors:
+* Returns 0 if:
+* Os/2: ERR_DosAllocSegFailed
+* Win: ERR_GlobalAllocFailed
+* ERR_GlobalLockFailed
+*
+****************************************************************/
+
+USHORT AllocSeg(ULONG ulSize)
+{
+#if OE_WIN16
+
+ VOID *pv;
+ HSYS hsys;
+ DWORD dwSize = ulSize;
+
+ if (ulSize > CBALLOCMAX) //GlobalReAlloc causes selector movement for allocs > 0xffdf bytes
+ return 0;
+
+ // If ulSize == 0, then actually want to allocate 64K.
+ if (!ulSize)
+ dwSize = CBALLOCMAX;
+
+ if ((hsys = HsysAlloc(dwSize)) == HSYS_Nil) {
+ return 0;
+ }
+ else {
+ pv = (VOID *)hsys;
+ DebAssert(OOB_OFFSETOF(pv) == 0, "HsysAlloc: whoops! non-seg aligned.");
+ return OOB_SELECTOROF(pv);
+ }
+
+#else
+#error
+#endif // OE_WIN16
+}
+
+
+/***
+*TIPERROR ReallocSeg - Reallocates a segment under Win or Os/2.
+*
+*Purpose:
+* Reallocates a segment under Win or Os/2.
+*
+*Entry:
+* usNewSize - Count of bytes to allocate. Must be < 64K.
+* If usNewSize == 0, 64K will be allocated.
+* usSel - Selector of segment to reallocate.
+*Exit:
+* TIPERROR
+*
+*Implementation Notes:
+* Os/2: Simply calls DosReallocSeg.
+* Win: Calls GlobalHandle to get handle of selector and then
+* GlobalReAlloc. Since we are managing segments of <=64K
+* the handle returned is the same as the handle passed in.
+*
+*Errors:
+* Returns TIPERR_OutOfMemory if:
+* Os/2: ERR_DosReallocSegFailed
+* Win: ERR_GlobalHandleFailed
+* ERR_GlobalReAllocFailed
+****************************************************************/
+
+TIPERROR ReallocSeg(ULONG ulNewSize, USHORT usSel)
+{
+#if OE_WIN16
+
+ HSYS hsys, hsysNew;
+ DWORD dwNewSize = ulNewSize;
+
+ if (ulNewSize > CBALLOCMAX) //GlobalReAlloc causes selector movement for allocs > 0xffdf bytes
+ return TIPERR_OutOfMemory;
+
+ // If ulNewSize == 0, then actually want to allocate 64K.
+ if (!ulNewSize)
+ dwNewSize = CBALLOCMAX;
+
+ hsys = (HSYS)OOB_MAKEP(usSel, 0);
+
+ // Finally, do the reallocation.
+ hsysNew = HsysReallocHsys(hsys, dwNewSize);
+ if (hsysNew == HSYS_Nil) {
+ return TIPERR_OutOfMemory;
+ }
+ else {
+ DebAssert(hsysNew == hsys, "whoops! block moved.");
+ return TIPERR_None;
+ }
+
+#else
+#error
+#endif
+}
+
+
+/***
+*TIPERROR FreeSeg - Frees an allocated segment under Win or Os/2.
+*
+*Purpose:
+* Frees an allocated segment under Win or Os/2.
+*
+*Entry:
+* usSel - Selector of segment to free.
+*
+*Exit:
+* TIPERROR
+*
+*Implementation Notes:
+* Os/2: Simply calls DosFreeSeg.
+* Win: Calls GlobalHandle to get handle of selector and then
+* GlobalUnlock to release it. Finally GlobalFree.
+*
+*Errors:
+* Return TIPERR_OutOfMemory if:
+* Os/2: ERR_DosFreeSegFailed
+* Win: ERR_GlobalHandleFailed
+* ERR_GlobalUnlockFailed
+* ERR_GlobalFreeFailed
+****************************************************************/
+
+TIPERROR FreeSeg(USHORT usSel)
+{
+
+#if OE_WIN16
+
+ HSYS hsys;
+
+ hsys = (HSYS)OOB_MAKEP(usSel, 0);
+
+ if (FreeHsys(hsys) != HSYS_Nil) {
+ return TIPERR_OutOfMemory;
+ }
+ else {
+ return TIPERR_None;
+ }
+
+#else
+#error
+#endif
+}
+
+#endif // OE_SEGMENTED
+
+#endif // !(OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+
+// The static class constant "initial heap size" is initialized here.
+
+#if OE_SEGMENTED || OE_REALMODE || OE_MACNATIVE || OE_MAC || OE_RISC || OE_WIN32
+
+// const UINT SHEAP_MGR::m_cbSizeInitial = 0x100; // Initial heap size
+CONSTDATA UINT SHEAP_MGR::m_cbSizeInitial = 0x20; // Initial heap size
+
+#endif // OE
+
+
+/***
+*STATIC PUBLIC SHEAP_MGR::Create - Create a heap manager.
+*Purpose:
+* Allocs and inits a heap manager.
+* Operator new is protected so that clients can't call it
+* and have to call Create. The actual implementation
+* of new is inlined here.
+*
+*Implementation Notes:
+* If Init() fails, deletes heap and resets *ppsheapmgr.
+*
+*Entry:
+* cbSizeReserved - Byte count to reserve at start of seg.
+*
+*Exit:
+* Inits m_pblkdescFirst.
+* Returns TRUE if successful.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR SHEAP_MGR::Create(SHEAP_MGR **ppsheapmgr, UINT cbSizeReserved)
+{
+ TIPERROR err;
+ SHEAP_MGR *psheapmgr;
+
+ DebAssert(ppsheapmgr, "bad param.");
+
+ err = TIPERR_None;
+
+
+#if OE_SEGMENTED
+
+ USHORT usSel;
+
+ usSel = AllocSeg(cbSizeReserved);
+ psheapmgr = (usSel == 0) ? NULL : (SHEAP_MGR *)OOB_MAKEP(usSel, 0);
+
+#elif OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32
+ // On Mac, MemAlloc is defined in terms of host-supplied implementation
+ // of IMalloc.
+ //
+ psheapmgr = (SHEAP_MGR *)MemAlloc(cbSizeReserved);
+
+#elif OE_MACNATIVE
+
+ psheapmgr = (SHEAP_MGR *)MemAlloc(cbSizeReserved);
+
+#endif
+
+ if (psheapmgr == NULL) {
+ return TIPERR_OutOfMemory;
+ }
+
+#if ID_DEBUG
+ if (g_itlsSheapmgr == ITLS_EMPTY) {
+ if ((g_itlsSheapmgr = TlsAlloc()) == ITLS_EMPTY)
+ return TIPERR_OutOfMemory;
+ }
+
+ ++g_cSheapmgr;
+
+ // Add the sheap manager to the per-thread list of sheapmgrs.
+ //
+ DebAddSheapmgrToList(psheapmgr);
+#endif
+
+ // Construct in place
+ ::new (psheapmgr) SHEAP_MGR;
+
+
+#if !(OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+ psheapmgr->m_cbSizeHeap = cbSizeReserved;
+#endif // !(OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+
+ // And initialize
+ if (err = psheapmgr->Init(cbSizeReserved)) {
+ delete psheapmgr;
+ return err;
+ }
+
+ *ppsheapmgr = psheapmgr;
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC SHEAP_MGR::operator new - allocates memory for heap seg.
+*Purpose:
+*
+*Implementation Notes:
+* We assert in debug -- clients aren't supposed to be able
+* to call.
+*
+*Entry:
+*
+*Exit:
+*
+*Errors:
+*
+*
+***********************************************************************/
+
+void *SHEAP_MGR::operator new(size_t size)
+{
+ DebHalt("SHEAP_MGR::operator new: can't call.");
+ return NULL;
+}
+
+
+/***
+*PUBLIC SHEAP_MGR::operator delete - destroys heap seg mem.
+*Purpose:
+* Destroys heap seg mem.
+*
+*Implementation Notes:
+* Uses FreeSeg.
+*
+*Entry:
+* pv - Pointer to SHEAP_MGR to delete.
+*
+*Exit:
+* None.
+*
+*Errors:
+* IGNORED
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+void SHEAP_MGR::operator delete(void *pv)
+{
+#if OE_SEGMENTED
+
+ FreeSeg(OOB_SELECTOROF(pv));
+
+#elif OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32
+ // On Mac, MemFree is defined in terms of host-supplied
+ // implementation of IMalloc.
+ //
+ MemFree(pv);
+
+#elif OE_MACNATIVE
+ // Free the sheapmgr instance itself.
+ MemFree(pv);
+
+#endif
+}
+#pragma code_seg()
+
+// SHEAP_MGR: Class methods
+//
+
+/***
+*PUBLIC SHEAP_MGR::SHEAP_MGR - constructor
+*Purpose:
+*
+* Asserts that is allocated on seg boundary, hence no other
+* need assert that.
+* Calls Invalidate().
+* Note that Init() must still be called before
+* this heap manager can be used.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+SHEAP_MGR::SHEAP_MGR()
+{
+#if OE_SEGMENTED
+
+ DebAssert(OOB_OFFSETOF(this) == 0,
+ "SHEAP_MGR:SHEAP_MGR: Heap mgr not allocated on seg boundary.");
+#endif // OE_SEGMENTED
+
+ // Invalidate semaphore
+ m_cLocks = (UINT)~0;
+
+#if ID_DEBUG
+ m_canSheapShake = FALSE; // assume can't be shaken
+ m_cbSizeReserved = (UINT)~0;
+ m_cDebLocks = (UINT)~0;
+#endif
+
+ m_pblkdescFirst = BD_pblkdescNil;
+#if !(OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+ m_cbSizeHeap = 0;
+ m_qbFree = (BYTE *)~0;
+#if OE_MACNATIVE
+ m_hMemHeap = (Handle)HSYS_Nil;
+#endif
+#endif
+}
+#pragma code_seg()
+
+/***
+*PUBLIC SHEAP_MGR::~SHEAP_MGR - destructor
+*Purpose:
+* Destroys a heap manager.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+SHEAP_MGR::~SHEAP_MGR()
+{
+#if ID_DEBUG
+ // remove this sheapmgr from the threads current list of sheapmgrs
+ DebRemoveSheapmgrFromList(this);
+
+ --g_cSheapmgr;
+ DebAssert(g_cSheapmgr >= 0, "");
+
+ if (g_cSheapmgr == 0){
+ TlsFree(g_itlsSheapmgr);
+ g_itlsSheapmgr = ITLS_EMPTY;
+ }
+#endif
+
+#if OE_MACNATIVE
+ // Free the relocatable memblock referenced by m_hMemHeap.
+ if (m_hMemHeap != HSYS_Nil) {
+ FreeHsys((Handle)m_hMemHeap);
+ }
+#elif OE_MAC || OE_RISC || OE_WIN32
+ // Walk the blkdescs and destruct each of them.
+ BLK_DESC *pblkdescNext, *pblkdescCur = m_pblkdescFirst;
+ while (pblkdescCur != BD_pblkdescNil) {
+ pblkdescNext = pblkdescCur->m_pblkdescNext;
+ pblkdescCur->BLK_DESC::~BLK_DESC();
+ pblkdescCur = pblkdescNext;
+ }
+#else
+ // A heap is destroyed by deleting it (delete is overloaded).
+#endif
+
+}
+#pragma code_seg()
+
+/***
+*PROTECTED SHEAP_MGR::Init - initialize the heap manager.
+*Purpose:
+* Initializes a heap manager.
+* On Win16/32: Assumes that a heap segment of
+* some initial size has been allocated by client.
+* Reserves some number of bytes (for heap management
+* overhead). In particular, the heap manager itself is
+* allocated at the start of the heap segment itself.
+* On Mac: allocates a relocatable block of cbSizeReserved.
+*
+*Implementation Notes:
+* 16-bit:
+* Asserts if cbSizeHeapSeg < cbSizeReserved.
+* Asserts if cbSizeHeapSeg > 64K.
+* 32-bit:
+*
+*Entry:
+* cbSizeReserved - Byte count to reserve at start of seg.
+*
+*Exit:
+* Inits m_cbSizeheap with m_cbSizeInitial.
+ Inits m_pblkdescFirst.
+* Returns TRUE if successful.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR SHEAP_MGR::Init(UINT cbSizeReserved)
+{
+
+#if ID_DEBUG
+ m_cbSizeReserved = 0;
+ m_cDebLocks = 0;
+#endif // ID_DEBUG
+
+ // Init semaphore.
+ m_cLocks = 0;
+
+#if !(OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+
+#if OE_MACNATIVE
+
+ HSYS hsys;
+
+ DebAssert(m_hMemHeap == (Handle)HSYS_Nil,
+ "Init: attempt to reinit a sheap.");
+
+ hsys = HsysAlloc(cbSizeReserved);
+ if (hsys == (Handle)HSYS_Nil) {
+ return TIPERR_OutOfMemory;
+ }
+ m_hMemHeap = (Handle)hsys;
+ m_qbFree = (BYTE *)cbSizeReserved;
+
+#else
+
+ m_qbFree = OOB_MAKEP3(this, cbSizeReserved);
+
+#endif
+
+#endif // !(OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+
+ m_pblkdescFirst = BD_pblkdescNil; // init blkdesc list
+
+#if ID_DEBUG
+ m_cbSizeReserved = cbSizeReserved; // mainly for debugging.
+ // Make sure that by default the sheap will shake
+#if !(OE_MAC || OE_RISC || OE_WIN32)
+ m_canSheapShake=TRUE;
+ m_cDebLocks = 0;
+#endif
+#endif
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+/***
+*PROTECTED SHEAP_MGR::PtrOfBlkDescPrev - Returns previous blk desc in list.
+*Purpose:
+* Returns pointer to previous blk desc in linked list, given
+* an offset to blk desc. Returns NULL if at list head.
+*
+*Implementation Notes:
+* Assumes that pblkdesc is offset in heap seg.
+* Asserts if pblkdesc not in reserved range at start of heap.
+*
+* Since no back pointers are maintained, the list is traversed from
+* the start until the current blk desc is reached -- the previous
+* blk desc is remembered and thus can be returned.
+*
+*Entry:
+* pblkdesc - offset of block desc in heap.
+*
+*Exit:
+* Returns NULL if the parameter refers to the list head,
+* otherwise returns pointer to previous blk desc.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+BLK_DESC *SHEAP_MGR::PtrOfBlkDescPrev(BLK_DESC *pblkdesc) const
+{
+ BLK_DESC *pblkdescPrev;
+ BLK_DESC *pblkdescCur;
+
+#if ID_DEBUG
+ ULONG oBlkDesc;
+
+#if OE_MACNATIVE || OE_MAC || OE_RISC || OE_WIN32
+ DebAssert((BYTE *)pblkdesc > (BYTE *)this, "bad pblkdesc.");
+ oBlkDesc = (ULONG)((BYTE *)pblkdesc - (BYTE *)this);
+#else
+ oBlkDesc = OOB_MAKEOFFSET(this, pblkdesc);
+#endif
+
+ DebAssert(oBlkDesc < (ULONG)m_cbSizeReserved,
+ "SHEAP_MGR::PtrOfBlkDescPrev: blk desc not in reserved heap part.");
+
+#endif // ID_DEBUG
+
+ pblkdescPrev = NULL;
+ pblkdescCur = m_pblkdescFirst;
+ pblkdescCur = PtrOfBlkDesc(pblkdescCur);
+ while (pblkdescCur != pblkdesc) {
+ pblkdescPrev = PtrOfBlkDesc(pblkdescCur); // Save prev.
+ pblkdescCur = PtrOfBlkDesc(pblkdescCur->m_pblkdescNext); // Get next.
+ }
+ return pblkdescPrev;
+}
+#pragma code_seg()
+
+/***
+*PROTECTED SHEAP_MGR::PtrOfBlkDescLast - Returns previous blk desc in list.
+*Purpose:
+* Returns pointer to last blk desc in linked list.
+* (Returns NULL if empty list).
+*
+*Implementation Notes:
+* Since no back pointers are maintained, the list is traversed from
+* the start until the last entry is reached.
+*
+*Entry:
+*
+*Exit:
+* Returns NULL if the parameter refers to the list head,
+* otherwise returns pointer to last blk desc.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+BLK_DESC *SHEAP_MGR::PtrOfBlkDescLast() const
+{
+ BLK_DESC *pblkdesc;
+ BLK_DESC *pblkdescCur = m_pblkdescFirst;
+
+ while (pblkdescCur != BD_pblkdescNil) {
+ pblkdesc = PtrOfBlkDesc(pblkdescCur);
+ pblkdescCur = pblkdesc->m_pblkdescNext;
+ if (pblkdescCur == BD_pblkdescNil)
+ return pblkdesc;
+ }
+ DebAssert(pblkdescCur == BD_pblkdescNil,
+ "SHEAP_MGR::PtrOfBlkDescFirst: bad list.");
+ return NULL;
+}
+#pragma code_seg()
+
+/***
+*PROTECTED SHEAP_MGR::RemoveBlkdesc -- removes blkdesc
+*Purpose:
+* Removes a blkdesc by delinking from linked list of blkdescs
+* in sheap and initing some fields.
+*
+*Entry:
+* pblkdesc IN
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+VOID SHEAP_MGR::RemoveBlkdesc(BLK_DESC *pblkdesc)
+{
+ // Remove block desc from list and
+ // update listhead if needed.
+ //
+ BLK_DESC *pblkdescPrev = PtrOfBlkDescPrev(pblkdesc);
+ if (pblkdescPrev != NULL) {
+ pblkdescPrev->m_pblkdescNext = pblkdesc->m_pblkdescNext; // link
+ }
+ else {
+ // blk desc is now first in list, so update list head.
+ m_pblkdescFirst = pblkdesc->m_pblkdescNext;
+ }
+ return;
+}
+#pragma code_seg()
+
+/***
+*PROTECTED SHEAP_MGR::AddBlkdesc -- updates new blkdesc
+*Purpose:
+* Inits a new blkdesc by linking to linked list of blkdescs
+* in sheap and initing some fields.
+*
+*Entry:
+* pblkdesc IN
+* cbSize IN
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+VOID SHEAP_MGR::AddBlkdesc(BLK_DESC *pblkdesc, ULONG cbSize)
+{
+ DebAssert(cbSize <= USHRT_MAX, "Should have caught this earlier.");
+
+ // Update size field.
+ pblkdesc->m_cbSize = (USHORT)cbSize;
+
+ // Now link in blkdesc to linked list.
+ // Get end of blk desc list.
+ //
+ BLK_DESC *pblkdescLast = PtrOfBlkDescLast();
+ if (pblkdescLast != NULL) {
+ DebAssert(pblkdescLast->m_pblkdescNext == BD_pblkdescNil,
+ "AddBlkdesc: bad Nil of blk desc list.");
+
+ pblkdescLast->m_pblkdescNext = pblkdesc;
+ }
+ else {
+ // No last blk desc, must be no first blk desc... if not,
+ // had better Assert...
+ DebAssert(m_pblkdescFirst == BD_pblkdescNil,
+ "BLK_DESC::Init: bad BOL of blk desc list -- should be null.");
+
+ m_pblkdescFirst = pblkdesc;
+ }
+ // Since blk desc is always added at end of list,
+ // simply set the next field to null.
+ //
+ pblkdesc->m_pblkdescNext = BD_pblkdescNil;
+ return;
+}
+#pragma code_seg()
+
+#if !(OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+
+/***
+*PUBLIC SHEAP_MGR::Alloc - Allocates block on heap.
+*Purpose:
+* Allocates moveable block on heap.
+* Appends blkdesc to end of list of blk descs describing
+* blocks in heap.
+*
+*Implementation Notes:
+* 16-bit:
+* Asserts if block descriptor not in same seg as heap.
+* Returns OOM if sheap locked and need to grow heap to
+* satisfy this alloc request. Actually ReallocHeap will
+* do this for us.
+* Only called by BLK_DESC::Init which does some post-processing
+* to insert blkdesc into linked list sheapmgr maintains. The
+* reason we do this in BLK_DESC rather than here is that not
+* all implementations have Alloc.
+*
+*Entry:
+* pblkdesc - Pointer to a block descriptor.
+* cbSize - Requested block size.
+*
+*Exit:
+* Updates block descriptor.
+* TIPERROR
+*
+*Errors:
+* OutOfMemory
+***********************************************************************/
+
+// NOTE: the following is to work around a C7 bug, see below
+// CONSIDER: turn back on optimizations when are using C8 on all
+// platforms.
+//
+#if OE_WIN16
+#pragma optimize("cegl", off)
+#endif //OE_WIN16
+TIPERROR SHEAP_MGR::Alloc(BLK_DESC *pblkdesc, ULONG cbSize)
+{
+ ULONG cbSizeNewHeap;
+ ULONG cbGrowHeap; // How much to grow heap if needed.
+ ULONG oFree; // Distance from heap start to first free
+ // byte.
+ TIPERROR err;
+
+ // Assert if the sheapmgr has a debug lock
+ DebAssert(!DebIsLocked(), "SHEAPMGR::Alloc: Sheapmgr is locked");
+
+#if OE_SEGMENTED
+ DebAssert(OOB_SELECTOROF(this) == OOB_SELECTOROF(pblkdesc),
+ "SHEAP_MGR::Alloc: Block desc not in same seg as heap.");
+ cbGrowHeap = m_cbSizeInitial;
+#elif OE_MACNATIVE
+ cbGrowHeap = m_cbSizeInitial;
+#else
+#error bad OE
+#endif
+
+ // Ensure enough memory, if not then try to grow heap.
+ // This is a bit weird: we want the actual offset of the next
+ // free byte in the managed memblock. On Mac we have to convert
+ // the "pseudo-pointer" m_qbFree to an offset, i.e. we just take
+ // the loword (OOB_OFFSETOF just takes the low 16-bits of a long).
+ // On win16/32, the managed memblock is physically contiguous with
+ // the sheapmgr itself so we can use the OOB_MAKEOFFSET macro
+ // which knows how to deal with all this stuff. Note that we use
+ // an actual pointer for Win32, which is why the variable is
+ // called m_qbFree.
+ //
+#if OE_MACNATIVE
+ oFree = OOB_OFFSETOF(m_qbFree);
+#else
+ oFree = OOB_MAKEOFFSET(this, m_qbFree);
+#endif
+
+ if (m_cbSizeHeap - oFree < cbSize) {
+ // Grow heap since not enough room for this new block alloc request.
+ // We grow heap in multiple blocks of cbGrowHeap bytes.
+ //
+
+ // NOTE: C7 generates incorrect code (under -Oxswz) for the
+ // following line - the division by cbGrowHeap is omitted. This
+ // is worked around above by using #pragma optimize.
+ // CONSIDER: when we go to C8 on all platforms we won't
+ // have this problem.
+ //
+ cbSizeNewHeap = (ULONG)m_cbSizeHeap +
+ (((cbSize / cbGrowHeap)+1) * cbGrowHeap);
+
+ IfErrRet(ReallocHeap(cbSizeNewHeap));
+ }
+
+ // Update blkdesc
+ pblkdesc->m_qbMemBlock = m_qbFree;
+ AddBlkdesc(pblkdesc, cbSize);
+
+ // Update next available byte pointer.
+ m_qbFree += cbSize;
+
+ return TIPERR_None;
+}
+#if OE_WIN16
+// NOTE: restore optimization, see above
+#pragma optimize("",on)
+#endif //OE_WIN16
+
+
+/***
+*PRIVATE SHEAP_MGR::ShiftHeap - Shifts heap.
+*Purpose:
+* Shifts heap.
+*
+*Implementation Notes:
+* We assert that sheap is locked cos we invalidate ptrs.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+VOID SHEAP_MGR::ShiftHeap(BLK_DESC *pblkdesc, LONG dbSize)
+{
+ BLK_DESC *pblkdescCur, *pblkdescNext;
+ ULONG oFree;
+ ULONG oMemBlockCur;
+ BYTE *qbBlockSrc;
+
+ DebAssert(IsLocked() == FALSE, "SHEAP_MGR::ShiftHeap: locked!");
+
+ // Now shift blocks at higher addresses up by dbSize
+ // which could be negative of course (corresponding to
+ // to a shrinking heap).
+ //
+ pblkdescNext = pblkdesc->m_pblkdescNext;
+ if (pblkdescNext != BD_pblkdescNil) {
+ pblkdescCur = PtrOfBlkDesc(pblkdescNext);
+
+ // Shift heap by dbSize: newSize-curSize.
+ // Note that dbSize could be negative of course.
+ // The bytecount to shift is oFree-oMemBlockCur: this
+ // is the cumulative size of the blocks at higher addresses.
+ //
+#if OE_MACNATIVE
+ oMemBlockCur = OOB_OFFSETOF(pblkdescCur->m_qbMemBlock);
+#else
+ oMemBlockCur = OOB_MAKEOFFSET(this, pblkdescCur->m_qbMemBlock);
+#endif
+ qbBlockSrc = pblkdescCur->QtrOfBlockActual();
+
+ DebAssert(qbBlockSrc != NULL, "SHEAP_MGR::ShiftHeap: NULL qbBlockSrc.");
+
+#if OE_MACNATIVE
+ oFree = OOB_OFFSETOF(m_qbFree);
+#else
+ oFree = OOB_MAKEOFFSET(this, m_qbFree);
+#endif
+ memmove(qbBlockSrc + dbSize, qbBlockSrc, (UINT)(oFree - oMemBlockCur));
+
+ // Now iterate over the block desc list, updating
+ // block locations, starting at pblkdescCur.
+ //
+ do {
+ // Update blk desc
+ pblkdescCur->m_qbMemBlock += dbSize;
+ // Get next in list.
+ pblkdescNext = pblkdescCur->m_pblkdescNext;
+ if (pblkdescNext != BD_pblkdescNil)
+ pblkdescCur = PtrOfBlkDesc(pblkdescNext);
+ } while (pblkdescNext != BD_pblkdescNil);
+ }
+ // Update free offset.
+ m_qbFree += dbSize;
+}
+
+
+/***
+*PUBLIC SHEAP_MGR::Free - Frees block on heap.
+*Purpose:
+* Frees block on heap. Relocates all blocks with higher
+* addresses so that heap is contiguous.
+* Removes block desc from linked list of blk descs.
+*
+*Implementation Notes:
+* Asserts if block descriptor not in same seg as heap.
+* Since invariant is that nth blk desc corresponds
+* to nth alloced block from start of heap seg, can simply
+* shift all blocks from the n+1'th up by size of block to be
+* freed.
+* This is done simply by moving en masse all the blocks
+* at once. The invariant is that the blocks are
+* contiguous. Once the blocks have been moved, we only
+* have to update the block descriptors with the blocks'
+* new locations -- that's easy, just iterate
+* and subtract size of freed block.
+* memmove is used since there might be overlap.
+*
+* We assert that sheap isn't locked since we shift heap
+* and thus invalidate pointers.
+*
+* CONSIDER: private non-virtual methods to manipulate blkdesc list.
+*
+*Entry:
+* pblkdesc - Pointer to a block descriptor of block to free.
+*
+*Exit:
+*
+***********************************************************************/
+
+VOID SHEAP_MGR::Free(BLK_DESC *pblkdesc)
+{
+ UINT cbSize; // size of block to be freed.
+
+ DebAssert(IsLocked() == FALSE, "SHEAP_MGR::Free: locked!");
+ DebAssert(pblkdesc != NULL, "SHEAP_MGR::Free: pblkdesc NULL.");
+ // Assert if the sheapmgr has a debug lock
+ DebAssert(!DebIsLocked(), "SHEAP_MGR::Free: Sheapmgr is locked ");
+
+#if OE_SEGMENTED
+ DebAssert(OOB_SELECTOROF(this) == OOB_SELECTOROF(pblkdesc),
+ "SHEAP_MGR::Free: Block desc not in same seg as heap.");
+#endif
+
+ // Must use actual memblock size cos of extra debug shift bytes.
+ cbSize = pblkdesc->CbSizeActual();
+
+ // Remove block desc from list and update listhead if needed.
+ RemoveBlkdesc(pblkdesc);
+
+ // Now shift heap.
+ // cbSize always positive so make it negative so
+ // that heap will shrink.
+ //
+ ShiftHeap(pblkdesc, -(LONG)cbSize);
+
+ // Shake the sheap.
+ DebSheapShake();
+}
+
+
+/***
+*PUBLIC SHEAP_MGR::Realloc - Grow/shrink block on heap.
+*Purpose:
+* Grow/shrink block on heap, preserving current contents.
+* Rest of heap is shifted to accomodate realloc. Relative
+* position of blocks is unchanged.
+*
+*Implementation Notes:
+* Asserts if block descriptor not in same seg as heap.
+* Since invariant is that nth blk desc corresponds
+* to nth alloced block from start of heap seg, all blocks
+* from the n+1'th are shifted up/down by the change in size
+* of the realloced block.
+* This is done simply by moving en masse all the blocks
+* at once. The invariant is that the blocks are
+* contiguous. Once the blocks have been moved, we only
+* have to update the block descriptors with the blocks'
+* new locations -- that's easy, just iterate
+* and add difference between size of new block and old block.
+* memmove is used since might be overlap.
+* dbSize is signed integer in range (-2^16, 2^16) indicating
+* difference in current size and new size (negative if shrinking,
+* positive if growing). Note: must use LONG.
+*
+* Return OOM if sheap is locked (since after resizing heap
+* we shift contents, thus invalidating contents).
+* CONSIDER: should this be an assert?
+* CONSIDER: since this code is almost identical to
+* similar section in Free, factor into private method.
+*
+*Entry:
+* pblkdesc - Pointer to a block descriptor of block to realloc.
+* cbSizeNew - New size of block.
+*
+*Exit:
+* TIPERROR
+***********************************************************************/
+TIPERROR SHEAP_MGR::Realloc(BLK_DESC *pblkdesc, ULONG cbSizeNew)
+{
+ LONG dbSize; // difference between new and cur size.
+ ULONG oFree, cbSizeNewHeap, cbFree;
+ TIPERROR err;
+
+ // Assert if the sheapmgr has a debug lock
+ DebAssert(!DebIsLocked(), "SHEAP_MGR::Realloc: Sheapmgr is locked ");
+
+#if OE_SEGMENTED
+ DebAssert(OOB_SELECTOROF(this) == OOB_SELECTOROF(pblkdesc),
+ "SHEAP_MGR::Realloc: Block desc not in same seg as heap.");
+#endif
+
+ // Request too big?
+ if ((ULONG)cbSizeNew > (ULONG)CBALLOCMAX) {
+ return TIPERR_OutOfMemory;
+ }
+
+ // Return OOM if we're locked.
+ if (IsLocked()) {
+ return TIPERR_OutOfMemory;
+ }
+
+ // How much to grow/shrink?
+ // Note must use actual blkdesc memblock size cos
+ // of extra debug shift bytes.
+ //
+ dbSize = (LONG)cbSizeNew - (LONG)pblkdesc->CbSizeActual();
+ if (dbSize == 0)
+ return TIPERR_None; // NOP if no size change.
+
+#if OE_MACNATIVE
+ oFree = OOB_OFFSETOF(m_qbFree);
+#else
+ oFree = OOB_MAKEOFFSET(this, m_qbFree);
+#endif
+
+ if (dbSize > 0) {
+ // Grow block.
+ // Ensure enough memory, if not then try to grow heap.
+ // cbFree is number of free allocated bytes currently in sheap,
+ // which we can use to accommodate this blkdesc realloc request.
+ //
+ cbFree = (ULONG)m_cbSizeHeap - (ULONG)oFree;
+ while (cbFree < (ULONG)dbSize) {
+ // Grow heap since not enough room for this new block alloc request.
+ cbSizeNewHeap = (ULONG)m_cbSizeHeap +
+ max((ULONG)dbSize - cbFree, (ULONG)m_cbSizeInitial);
+
+ // ReallocHeap side-effects m_cbSizeHeap
+ IfErrRet(ReallocHeap(cbSizeNewHeap));
+ cbFree = (ULONG)m_cbSizeHeap - (ULONG)oFree;
+ } // while
+ } // if
+
+ // Now shift heap.
+ // dbSize could be negative: corresponds to shrinking heap.
+ //
+ ShiftHeap(pblkdesc, dbSize);
+
+ // Update blk size attr
+ DebAssert(cbSizeNew <= USHRT_MAX, "Should have caught this by now.");
+ pblkdesc->m_cbSize = (USHORT)cbSizeNew;
+
+ // shake the heap.
+ DebSheapShake();
+
+ return TIPERR_None;
+}
+
+
+/***
+*PRIVATE SHEAP_MGR::ReallocHeap - Grows/shrinks heap.
+*Purpose:
+* Grows/shrinks heap as a result of block reallocation. Contents
+* preserved.
+*
+*Implementation Notes:
+* Asserts if live blocks would get zapped if heap shrunk by too much.
+* 16-bit: Uses ReallocSeg.
+* Returns OOM if sheap is locked and we are *growing* the heap.
+* NOTE: we assume that shrinking a heap does not move it.
+* CONSIDER: should this be an assert? i.e. clients shouldn't
+* be calling this method anyway if sheap is locked.
+*
+*Entry:
+* cbSizeNewHeap - Size of new heap.
+*
+*Exit:
+* Updates private member m_cbSizeHeap
+* Returns TIPERROR
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR SHEAP_MGR::ReallocHeap(ULONG cbSizeNewHeap)
+{
+ LONG dbSize;
+ TIPERROR err = TIPERR_None;
+
+ if (cbSizeNewHeap > (ULONG)CBALLOCMAX)
+ return TIPERR_OutOfMemory;
+
+ dbSize = cbSizeNewHeap - m_cbSizeHeap;
+
+
+ // Return OOM if we are growing and sheap is locked.
+ if ((dbSize > 0) && IsLocked()) {
+ return TIPERR_OutOfMemory;
+ }
+
+#if OE_MACNATIVE
+ DebAssert((dbSize > 0) ||
+ (-dbSize <
+ (INT)(m_cbSizeHeap - OOB_OFFSETOF(m_qbFree))),
+ "SHEAP_MGR::ReallocHeap: can't shrink heap -- will zap blocks.");
+#else
+ DebAssert((dbSize > 0) ||
+ (-dbSize < (INT)(m_cbSizeHeap - OOB_MAKEOFFSET(this, m_qbFree))),
+ "SHEAP_MGR::ReallocHeap: can't shrink heap -- will zap blocks.");
+#endif
+
+#if OE_SEGMENTED
+
+ err = ReallocSeg((USHORT)cbSizeNewHeap, OOB_SELECTOROF(this));
+ // fall through...
+
+#elif OE_MACNATIVE
+
+ HSYS hsys, hsysNew;
+
+ hsys = (HSYS)m_hMemHeap;
+
+ // Finally, do the reallocation.
+ hsysNew = HsysReallocHsys(hsys, cbSizeNewHeap);
+ if (hsysNew == HSYS_Nil) {
+ err = TIPERR_OutOfMemory;
+ }
+ else {
+ DebAssert(hsys == hsysNew,
+ "whoops! handle shouldn't have changed.");
+ err = TIPERR_None;
+ }
+ // fall through...
+
+#else
+#error bad OE.
+#endif
+
+ if (err == TIPERR_None) {
+ // update heap size.
+ m_cbSizeHeap = (UINT)cbSizeNewHeap;
+ }
+ return err;
+}
+
+#endif // ! (OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+
+#if ID_DEBUG
+
+/***
+*PUBLIC SHEAP_MGR::DebSheapShakeOn
+*Purpose:
+* Sets the flag indicating this sheapmgr can shake.
+*
+*Entry:
+* None
+*
+*Exit:
+* None
+*
+***********************************************************************/
+VOID SHEAP_MGR::DebSheapShakeOn()
+{
+ m_canSheapShake=TRUE;
+}
+
+
+/***
+*PUBLIC SHEAP_MGR::DebSheapShakeOff
+*Purpose:
+* Resets the flag that indicating this sheapmgr cannot shake.
+*
+*Entry:
+* None
+*
+*Exit:
+* None
+*
+***********************************************************************/
+VOID SHEAP_MGR::DebSheapShakeOff()
+{
+ m_canSheapShake=FALSE;
+}
+
+
+/***
+*PUBLIC SHEAP_MGR::DebCanSheapShake
+*Purpose:
+* returns true if this sheap can shake;
+*
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+BOOL SHEAP_MGR::DebCanSheapShake()
+{
+ return m_canSheapShake;
+}
+
+
+/***
+*PUBLIC SHEAP_MGR::DebAddSheapmgrToList
+*Purpose:
+* adds the sheapmgr to the per-thread list of sheapmgrs
+*
+*Entry:
+* psheapmgr : sheap mgr to be added.
+*
+*Exit:
+* None
+*
+***********************************************************************/
+VOID SHEAP_MGR::DebAddSheapmgrToList(SHEAP_MGR *psheapmgr)
+{
+ SHEAPMGR_LIST *psheapmgrlist;
+
+ // Stop error generation for now
+ DebSuspendError();
+
+ DebAssert(psheapmgr != NULL, "bad pointer");
+ DebAssert(g_itlsSheapmgr != ITLS_EMPTY, "");
+
+ // allocate space for the new node
+ psheapmgrlist = MemNew(SHEAPMGR_LIST);
+
+ // if we weren't able to allocate this entry, set the list
+ // to invalid. NOTE: this merely displays a warning when the
+ // list is displayed telling the user that the list is
+ // incomplete.
+ //
+ if (psheapmgrlist == NULL) {
+ g_fValidSheapmgrList = FALSE;
+ }
+ else {
+ ::new (psheapmgrlist) SHEAPMGR_LIST;
+
+ // add the current sheapmgr and add the node to the beginning of the list
+ psheapmgrlist->m_psheapmgr = psheapmgr;
+ psheapmgrlist->m_psheapmgrlistNext =
+ (SHEAPMGR_LIST*)TlsGetValue(g_itlsSheapmgr);
+
+ BOOL fSet = TlsSetValue(g_itlsSheapmgr, psheapmgrlist);
+ DebAssert(fSet == TRUE, "");
+ }
+
+ DebResumeError();
+}
+
+
+/***
+*PUBLIC SHEAP_MGR::DebRemoveSheapmgrFromList
+*Purpose:
+* removes the sheapmgr from the per-thread list of sheap managers.
+*
+*Entry:
+* psheapmgr : sheap mgr to be removed.
+*
+*Exit:
+* None
+*
+***********************************************************************/
+VOID SHEAP_MGR::DebRemoveSheapmgrFromList(SHEAP_MGR *psheapmgr)
+{
+ SHEAPMGR_LIST *psheapmgrlist, **ppsheapmgrlist, *psheapmgrlistDead;
+
+ DebAssert(psheapmgr != NULL, "bad pointer");
+ DebAssert(g_itlsSheapmgr != ITLS_EMPTY, "");
+
+ psheapmgrlist = (SHEAPMGR_LIST*)TlsGetValue(g_itlsSheapmgr);
+
+ for (ppsheapmgrlist = &psheapmgrlist;
+ *ppsheapmgrlist != NULL;
+ ppsheapmgrlist = &(*ppsheapmgrlist)->m_psheapmgrlistNext) {
+ // DebAssert(IsValidWritePtr(*ppsheapmgrlist, sizeof(**ppsheapmgrlist));
+
+ if ((*ppsheapmgrlist)->m_psheapmgr == psheapmgr) {
+ psheapmgrlistDead = *ppsheapmgrlist;
+ *ppsheapmgrlist = (*ppsheapmgrlist)->m_psheapmgrlistNext;
+ MemFree(psheapmgrlistDead);
+ BOOL fSet = TlsSetValue(g_itlsSheapmgr, psheapmgrlist);
+ DebAssert(fSet == TRUE, "");
+ return;
+ }
+ }
+
+ // The assertion below should only be reached if a sheapmgr could
+ // not be added to the debug list (caused by a lack of memory).
+ //
+ DebAssert(!g_fValidSheapmgrList, "");
+}
+
+
+
+/***
+*PUBLIC SHEAP_MGR::DebCheckState - Checks heap.
+*Purpose:
+* (1) Checks if heap is in a consistent state after initialization.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+VOID SHEAP_MGR::DebCheckState(UINT uLevel) const
+{
+#if !(OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+ // Check if heap is consistent after init.
+ if (uLevel == 0) {
+#if OE_MACNATIVE
+ DebAssert(OOB_OFFSETOF(m_qbFree) == m_cbSizeReserved &&
+ m_pblkdescFirst == BD_pblkdescNil,
+ "bad heap after init.");
+#else
+ DebAssert(OOB_MAKEOFFSET(this, m_qbFree) == m_cbSizeReserved &&
+ m_pblkdescFirst == BD_pblkdescNil,
+ "bad heap after init.");
+#endif
+ }
+#endif
+}
+
+/***
+*PUBLIC SHEAP_MGR::DebShowState - SHEAP_MGR state
+*Purpose:
+* Show SHEAP_MGR state
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+*Exceptions:
+* None.
+*
+***********************************************************************/
+
+VOID SHEAP_MGR::DebShowState(UINT uLevel) const
+{
+#if !(OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+ if (uLevel == 0) {
+ DebPrintf("*** SHEAP_MGR private members ***\n");
+ DebPrintf("m_pblkdescFirst = %u\n", m_pblkdescFirst);
+ DebPrintf("m_cbSizeHeap = %u\n", m_cbSizeHeap);
+ DebPrintf("m_qbFree = %u\n", m_qbFree);
+ DebPrintf("m_cbSizeReserved = %u\n", m_cbSizeReserved);
+ }
+#endif //!(OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+}
+
+
+/***
+*PUBLIC SHEAP_MGR::DebSheapShakeOne - Shakes Sheap.
+*Purpose:
+* Moves managed memblocks around in Sheap -- this is to ensure
+* that clients don't hold onto dereferenced handles too long.
+*
+*Implementation Notes:
+* Locked sheaps aren't shaken.
+*
+* Since a sheap is a contiguous memory block itself, we shake
+* its managed blocks (BLK_DESCs) by shifting each one
+* up or down into the extra SHM_cbShift at the top or bottom
+* of the memblock. This extra two bytes is always allocated
+* at the end of a memblock in the debug version and in addition
+* there is a debug-only flag indicating which way to shift.
+* this ensures that any cached ptrs into the memblocks would be
+* effectively invalidated).
+*
+* Note: we do not shift locked BLK_DESCs.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+VOID SHEAP_MGR::DebSheapShakeOne()
+{
+#if !(OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+ INT dbShift;
+ BLK_DESC *pblkdescCur, *pblkdescNext;
+
+#if 0
+ // NOP if they don't want to shake.
+ if (g_fSheapShakingOn == FALSE)
+ return;
+#endif // 0
+
+ // check to see if we can shake this sheap mgr.
+ if (DebCanSheapShake() == FALSE)
+ return;
+
+ // NOP if sheap locked.
+ if (IsLocked())
+ return;
+
+ // Else for each non-locked block, shift it up or down
+ // depending on its shift state.
+ //
+ pblkdescNext = m_pblkdescFirst;
+ while (pblkdescNext != BD_pblkdescNil) {
+ pblkdescCur = PtrOfBlkDesc(pblkdescNext);
+ // If block isn't locked, shift it.
+ // NOTE: this actually could be an assertion since
+ // with sheap-level-only locking, the sheap is locked
+ // if any of its blocks are locked.
+ //
+ if (pblkdescCur->IsLocked() == FALSE) {
+ // Calculate the displacement -- negative or positive?
+ dbShift = (pblkdescCur->m_fShiftUp) ?
+ SHM_cbShift :
+ -SHM_cbShift;
+
+ // Shift it based on the m_fShiftUp flag.
+ memmove(pblkdescCur->QtrOfBlock() + dbShift,
+ pblkdescCur->QtrOfBlock(),
+ pblkdescCur->CbSize());
+
+ // toggle shift flag
+ pblkdescCur->m_fShiftUp = !pblkdescCur->m_fShiftUp;
+ }
+ pblkdescNext = pblkdescCur->m_pblkdescNext;
+ }
+#endif
+}
+
+
+/***
+*PUBLIC SHEAP_MGR::DebSheapShake - Shakes Sheap.
+*Purpose:
+* Walks the list of sheapmgr and shakes the all the sheap in Unison.
+*
+* NOTE: If a sheap could not be added to the list due to a lack of
+* memory, it will not get shaken.
+*
+*Entry:
+* None
+*
+*Exit:
+* None
+*
+***********************************************************************/
+VOID SHEAP_MGR::DebSheapShake()
+{
+ SHEAPMGR_LIST *psheapmgrlist;
+
+ DebAssert(g_itlsSheapmgr != ITLS_EMPTY, "");
+
+ for(psheapmgrlist = (SHEAPMGR_LIST*)TlsGetValue(g_itlsSheapmgr);
+ psheapmgrlist != NULL;
+ psheapmgrlist = psheapmgrlist->m_psheapmgrlistNext)
+ {
+ psheapmgrlist->m_psheapmgr->DebSheapShakeOne();
+ }
+}
+
+#endif // ID_DEBUG
+
+
+
+// BLK_DESC: class methods
+//
+
+/***
+*PUBLIC BLK_DESC::BLK_DESC - constructor
+*Purpose:
+* Initializes private members.
+* Note that Init() must still be called before
+* this block descriptor can be used.
+* CONSIDER: making inline
+*
+* Invalidates block desc. Note that a 0-size block is valid,
+* however its oMemBlock must be non-zero to be valid (i.e. a
+* 0-size block does have an entry in the heap -- it just happens
+* to be of length 0). Since the SHEAP_MGR itself is always
+* allocated at offset 0 in the heap, this really does mean
+* that an oMemBlock of 0 is in fact invalid.
+* NOTE: definition must precede BLK_DESC constructor.
+*
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+BLK_DESC::BLK_DESC()
+{
+ m_qbMemBlock=NULL; // This is what invalidates a block.
+ m_pblkdescNext=BD_pblkdescNil;
+#if ID_DEBUG
+ m_fShiftUp = TRUE; // Initially shift up.
+#endif
+
+#if OE_WIN32 || OE_MACNATIVE || OE_MAC
+ // OE_RISC needs this, too
+ m_psheapmgr = NULL;
+#endif // OE_WIN32
+
+#if OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32
+ m_cLocks = (UINT)~0; // invalidate lock count
+#endif // OE_REALMODE || OE_MAC
+}
+#pragma code_seg()
+
+/***
+*PUBLIC BLK_DESC::~BLK_DESC - destructor
+*Purpose:
+* Destroys a block descriptor.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+BLK_DESC::~BLK_DESC()
+{
+ if (IsValid())
+ Free();
+}
+#pragma code_seg()
+
+/***
+*PUBLIC BLK_DESC::Init - initialize the block manager
+*Purpose:
+* Initializes a block descriptor. Allocates block of default
+* minimum size.
+*
+*Implementation Notes:
+* Defers to heap manager for allocation. Asserts if THIS and
+* its psheapmgr arg are not in the same segment. Note that
+* a heap is always allocated on a segment boundary.
+* Asserts if heap manager not allocated on seg boundary.
+* CONSIDER: making inline
+*
+*Entry:
+* psheapmgr - pointer to a heap manager object.
+* cbSize - initial block size.
+*
+*Exit:
+* TIPERROR
+*
+*Errors:
+* OutOfMemory (from SHEAP_MGR::Alloc)
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR BLK_DESC::Init(SHEAP_MGR *psheapmgr, UINT cbSize)
+{
+ TIPERROR err = TIPERR_None;
+
+#if OE_SEGMENTED
+ DebAssert(OOB_OFFSETOF(psheapmgr)==0,
+ "BLK_DESC::Init: Heap manager not allocated on seg boundary.");
+ DebAssert(OOB_SELECTOROF(this) == OOB_SELECTOROF(psheapmgr),
+ "BLK_DESC::Init: Block desc not in same seg as heap.");
+#endif // OE_SEGMENTED
+
+ DebAssert(IsValid() == FALSE,
+ "BLK_DESC::Init: Whoops! Block should be invalid.");
+
+ // "this" is passed to the heap manager's Alloc, which
+ // updates its members appropriately.
+ // (i.e. cbSize, oMemBlock and oBlkDescNext).
+ //
+
+ // Note that in the debug version we allocate an extra
+ // SHM_cbShift bytes.
+ // In the release version, cbShift is zero so this is nop.
+ //
+ cbSize += SHM_cbShift;
+
+#if OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32
+
+ m_cLocks = 0; // Init lockcount
+ m_qbMemBlock = (BYTE *)MemAlloc(cbSize);
+ if (m_qbMemBlock == NULL)
+ return TIPERR_OutOfMemory;
+#if OE_RISC
+ DebAssert (((ULONG)(this->m_qbMemBlock) & (SHM_cbAlign-1)) == 0, "RISC: Unaligned allocation");
+#endif
+
+#else
+
+ err = psheapmgr->Alloc(this, cbSize);
+
+#endif // OE
+
+ if (err == TIPERR_None) {
+ // Update this instance
+ psheapmgr->AddBlkdesc(this, cbSize);
+
+#if !(OE_SEGMENTED)
+ m_psheapmgr = psheapmgr;
+#endif
+ DebAssert(IsValid(), "BLK_DESC::Init: Block invalid.");
+ }
+
+ return err;
+}
+#pragma code_seg()
+
+/***
+*PUBLIC BLK_DESC::Realloc - Grows/shrinks block.
+*Purpose:
+* Grows/shrinks block, preserving contents. Defers to heap manager.
+*
+*Implementation Notes:
+* 16-bit: Assumes that heap manager is allocated at offset 0 in this
+* segment.
+* Returns OOM if block locked since reallocation will shift
+* other blocks around thus invalidating any pointers to them.
+* [Actually only those at higher addresses so there's a possible
+* optimization here].
+*
+*Entry:
+* cbSizeNew - new size of block.
+*
+*Exit:
+* TIPERROR
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+#pragma code_seg(CS_INIT)
+TIPERROR BLK_DESC::Realloc(ULONG cbSizeNew)
+{
+ DebAssert(IsValid(), "BLK_DESC::Realloc: Block invalid.");
+
+ // Request too big?
+ if ((ULONG)cbSizeNew > (ULONG)CBALLOCMAX) {
+ return TIPERR_OutOfMemory;
+ }
+
+ // Are we locked?
+ if (IsLocked()) {
+ return TIPERR_OutOfMemory;
+ }
+
+#if ID_DEBUG
+ // Note that in the debug version we allocate an extra
+ // SHM_cbShift bytes.
+ // In the release version, cbShift is zero so this is nop.
+ //
+ // Request too big?
+ //
+ if ((ULONG)(cbSizeNew+SHM_cbShift) > (ULONG)CBALLOCMAX) {
+ return TIPERR_OutOfMemory;
+ }
+ cbSizeNew += SHM_cbShift;
+#endif
+
+#if OE_SEGMENTED
+
+ return ((SHEAP_MGR *)OOB_MAKEP2(this, 0))->Realloc(this, cbSizeNew);
+
+#elif OE_MACNATIVE
+
+ return m_psheapmgr->Realloc(this, cbSizeNew);
+
+#elif OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32
+
+ BYTE *qbMemBlockNew;
+
+#if ID_DEBUG
+ // Alloc a new block to guarentee that any outstanding pointers
+ // are invalidated.
+ //
+ qbMemBlockNew = (BYTE *)MemAlloc(cbSizeNew);
+
+ if (qbMemBlockNew) {
+ memcpy(qbMemBlockNew, m_qbMemBlock, min(m_cbSize, cbSizeNew));
+ MemFree(m_qbMemBlock);
+ }
+#else // !ID_DEBUG
+ qbMemBlockNew = (BYTE *)MemRealloc(m_qbMemBlock, cbSizeNew);
+#endif // !ID_DEBUG
+
+ // return OutOfMemory if the returned pointer is NULL and the requested
+ // size of memory was > 0. Relloc returns NULL if the requested mem size
+ // is 0.
+ //
+ // NOTE: the semantics of BLK_DESC::Realloc are such that
+ // a valid non-null ptr is produced even if the request was
+ // for zero bytes.
+ // *** THIS IS DIFFERENT FROM ANSI REALLOC SEMANTICS. ***
+ //
+ if (qbMemBlockNew == NULL) {
+ if (cbSizeNew != 0) {
+ return TIPERR_OutOfMemory;
+ }
+ else {
+ // We've already freed the old block and we know that cbSizeNew is 0,
+ // so just get a new block of 0.
+ if ((m_qbMemBlock = (qbMemBlockNew = (BYTE *)MemAlloc(0))) == NULL) {
+ // Note that in this error case, m_qbMemBlock is set "correctly"
+ // but m_cbSize retains its old value which is ok because
+ // we use m_qbMemBlock to indicate a block's validity.
+ //
+ return TIPERR_OutOfMemory;
+ }
+ }
+ }
+
+#if OE_RISC
+ DebAssert (((ULONG)(this->m_qbMemBlock) & (SHM_cbAlign-1)) == 0,
+ "RISC: Unaligned allocation");
+#endif
+
+ m_qbMemBlock = qbMemBlockNew;
+
+ DebAssert(cbSizeNew <= USHRT_MAX, "Should have caught this by now.");
+ m_cbSize = (USHORT)cbSizeNew;
+ return TIPERR_None;
+
+#else
+#error bad OE.
+#endif
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC BLK_DESC::Read - Read in instance from stream
+*Purpose:
+* Load previously serialized BLK_DESC into this BLK_DESC.
+* The BlkDesc must be initialized.
+* The serialized representation is simply the size of the
+* block (a long) followed the data contained in the block.
+*
+*Entry:
+* cfile: stream to read data from
+*
+*Exit:
+* number of bytes read from the stream
+*
+***********************************************************************/
+
+TIPERROR BLK_DESC::Read(STREAM *pstrm)
+{
+ ULONG cbBlockSize;
+ TIPERROR err;
+
+ DebAssert(IsValid(), "BLK_DESC::Read: Block invalid.");
+
+ // read in block size from serialized rep.
+ if (!(err = pstrm->ReadULong(&cbBlockSize))) {
+ DebAssert(cbBlockSize <= CBALLOCMAX,
+ "BLK_DESC::Read: invalid block size");
+
+ // reallocate block to the size that was read in
+ if (!(err = Realloc((UINT)cbBlockSize)))
+ // There is a bug in the STREAM implementation of read : Returns an
+ // error if we try to read 0 bytes.
+ if (cbBlockSize > 0)
+ err = pstrm->Read(QtrOfBlock(), (UINT)cbBlockSize);
+ }
+ return err;
+}
+
+
+/***
+*PUBLIC BLK_DESC::Write - Write out instance to stream
+*Purpose:
+* Serialize the BLK_DESC to a stream.
+* The serialized representation is simply the size of the
+* block (a long) followed the data contained in the block.
+*
+*Entry:
+* cfile: stream to write data to
+*
+*Exit:
+* number of bytes written to stream
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR BLK_DESC::Write(STREAM *pstrm)
+{
+ ULONG cbBlockSize;
+ TIPERROR err;
+
+ DebAssert(IsValid(), "BLK_DESC::Write: Block invalid.");
+
+ cbBlockSize = CbSize();
+
+ // write out block size to serialized rep.
+ if (!(err = pstrm->WriteULong(cbBlockSize))) {
+ // write out contents of block.
+ err = pstrm->Write(QtrOfBlock(), (UINT)cbBlockSize);
+ }
+ return err;
+}
+
+#pragma code_seg()
+
+
+
+
+
+#if ID_DEBUG
+/***
+*PUBLIC BLK_DESC::DebShowState - BLK_DESC state
+*Purpose:
+* Show BLK_DESC state
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+*Exceptions:
+* None.
+*
+***********************************************************************/
+
+VOID BLK_DESC::DebShowState(UINT uLevel) const
+{
+ BYTE *pb;
+ UINT i;
+
+ DebPrintf("block size: %u \n", m_cbSize);
+ for (pb = QtrOfBlock(), i=0 ; i < m_cbSize; i++, pb++) {
+ DebPrintf("%u\n", (CHAR)*pb);
+ }
+}
+
+
+/***
+*PUBLIC SHEAP_MGR::DebLock
+*Purpose:
+* Lock the sheap to ensure that this sheap is not used until the
+* lock is removed.
+*
+*Implementation Notes:
+* Increment counting semaphore.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+VOID SHEAP_MGR::DebLock()
+{
+ m_cDebLocks++;
+}
+
+
+/***
+*PUBLIC SHEAP_MGR::DebUnlock
+*
+*Implementation Notes:
+* Decrements counting semaphore.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+VOID SHEAP_MGR::DebUnlock()
+{
+ DebAssert(m_cDebLocks > 0, "SHEAP_MGR::DebUnlock: underflow.");
+ m_cDebLocks--;
+
+}
+
+
+/***
+*PUBLIC SHEAP_MGR::DebIsLocked
+*Purpose:
+* Tests if sheap has a debug lock.
+*
+*Implementation Notes:
+* Tests counting semaphore.
+*
+*Entry:
+*
+*Exit:
+* TRUE if sheap is locked -- i.e. at least one lock.
+***********************************************************************/
+BOOL SHEAP_MGR::DebIsLocked()
+{
+ return (BOOL)(m_cDebLocks > 0);
+}
+
+
+#endif // ID_DEBUG
+
+// catches operator new
+#if OE_MAC
+#pragma code_seg(CS_INIT)
+#endif
diff --git a/private/oleauto/src/typelib/sheapmgr.hxx b/private/oleauto/src/typelib/sheapmgr.hxx
new file mode 100644
index 000000000..c83f73ab1
--- /dev/null
+++ b/private/oleauto/src/typelib/sheapmgr.hxx
@@ -0,0 +1,1057 @@
+/***
+*sheapmgr.hxx - Silver Heap Manager
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* The silver Heap Manager describes a heap manager that
+* manages contiguous blocks of memory in a heap. Blocks are
+* accessed via block descriptor object (see blkdesc.hxx)
+* upon allocation and maybe grown/shrunk.
+* See \silver\doc\ic\sheapmgr.doc for more information.
+*
+* This file defines the following classes:
+* SHEAP_MGR
+* BLK_DESC
+*
+* Implementation Notes:
+* Inline methods are *declared* inline in the class definition
+* even though our guidelines state that they should be
+* simply defined inline (i.e. at point of definition). The
+* reason is that there are interdependenices between inline
+* methods of BLK_DESC and SHEAP_MGR.
+*
+* In the 16-bit version, pointers into the heap that
+* are needed by the SHEAP_MGR and BLK_DESC are stored in a
+* far pointer but only the loword is used as an offset into
+* the heap segment. I.e. they are effectively based pointers.
+*
+* In the 32-bit version, pointers into the heap are stored as
+* 32-bit pointers ("far pointers").
+
+* In both cases, the NIL pointer is expressed as UINT_MAX (rather
+* than NULL) since 0 is a valid offset in the 16-bit version.
+*
+*Revision History:
+*
+* 13-Feb-91 ilanc: Created.
+* 04-Apr-91 ilanc: Incorporated blkdesc. All inline BLK_DESC
+* methods are here as well. Note that
+* there is a partial order imposed by
+* SHEAP_MGR/BLK_DESC interdependencies.
+* 15-Apr-91 ilanc: Made BLK_DESC destructor outline.
+* 05-Jun-91 ilanc: Rip exceptions... use C7
+* 29-Aug-91 ilanc: #define min and max. C7 uses __min/__max.
+* 06-Sep-91 ilanc: Start 32-bit version.
+* Make private/protected methods that
+* no one outside the SHEAP_MGR/BLK_DESC/BLK_MGR
+* need know about. Make those three incestuous.
+* Remove BLK_DESC::OMemBlock and OBlkDescNext.
+* 20-Mar-92 martinc: added support for Mac (OE_MACNATIVE)
+* 07-Apr-92 ilanc: Added DebSheapShakeOne().
+* 15-Apr-92 martinc: Commented the Mac specific memory mgmt out
+* (now does the same as in Realmode)
+* 03-Sep-92 ilanc: The (real?) mac version.
+* 07-Oct-92 Rajivk: Added DebSheapShake().
+* 19-Mar-93 ilanc: OE_MAC renamed OE_MACNATIVE (since it uses
+* macos moveable memory). Introduced new OE_MAC
+* to mean fixed memory for blocks.
+*
+*****************************************************************************/
+
+#ifndef SHEAPMGR_HXX_INCLUDED
+#define SHEAPMGR_HXX_INCLUDED
+
+#include <stddef.h> // for size_t
+#include <limits.h> // for USHRT_MAX
+
+
+#if OE_MACNATIVE
+#include "MacOs\types.h"
+#endif // OE_MACNATIVE
+
+#include "rtsheap.h"
+
+class STREAM;
+class BLK_DESC;
+class SHEAP_MGR;
+class SHEAPMGR_LIST;
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szSHEAPMGR_HXX)
+#define SZ_FILE_NAME g_szSHEAPMGR_HXX
+#endif
+
+#if OE_RISC
+// Sheap Alignment
+// [NOTE: The Sheap alignment factor must match the alignment of
+// our host's IMalloc() implimentation.]
+#if HP_R4000 || HP_ALPHA
+ #define SHM_cbAlign 8
+#elif HP_I386 || HP_POWERPC
+ #define SHM_cbAlign 4
+#else
+ #error Unknown Platform
+#endif
+#endif // OE_RISC
+
+#undef max
+#define max(a,b) (((a) > (b)) ? (a) : (b))
+#undef min
+#define min(a,b) (((a) < (b)) ? (a) : (b))
+
+// Setup OE_SEGMENTED
+//
+#undef OE_SEGMENTED
+#if OE_WIN16
+#define OE_SEGMENTED 1
+#else
+#define OE_SEGMENTED 0
+#endif
+
+#if OE_SEGMENTED
+
+USHORT AllocSeg(ULONG ulSize);
+TIPERROR ReallocSeg(ULONG ulNewSize, USHORT usSel);
+TIPERROR FreeSeg(USHORT usSel);
+
+#endif
+
+// Note: in the following macros we "abstract" low-level OS differences.
+// The fixed mac implementation (as opposed to native mac which uses
+// macos movable mem) can be thought of as yet another 32-bit
+// architecture.
+//
+// OOB_MAKEOFFSET - Makes offset from pointer.
+// On Win16: Simulate based pointers. Ignore seg selector. I.e.
+// assume offset is near ptr into seg addressed by selector.
+// On native Mac:
+// Do ptr arithmetic, assuming first arg is handle.
+// On mac:
+// On realmode:
+// On Win32: Do ptr arithmetic: i.e. subtract.
+//
+#undef OOB_MAKEOFFSET
+
+#if OE_SEGMENTED
+#define OOB_MAKEOFFSET(p, p2) OOB_OFFSETOF(p2)
+#elif OE_MACNATIVE
+#define OOB_MAKEOFFSET(p, p2) (ULONG)((BYTE *)(p2) - (BYTE *)(*p))
+#else
+// NOTE: want to assert here that p2 >= p but can't
+// have DebAssert inside of DebAssert.
+//
+#define OOB_MAKEOFFSET(p, p2) (ULONG)((BYTE *)(p2) - (BYTE *)(p))
+#endif
+
+
+// OOB_MAKEP2 - makes a 32-bit pointer
+// On 16-bit: makes ptr out of seg selector and seg ofs.
+// On native Mac:
+// makes ptr out of handle and offset in referenced block.
+// On 32-bit: ignore seg selector and uses 32-bit ofs as 32-bit ptr.
+//
+#undef OOB_MAKEP2
+#if OE_SEGMENTED
+#define OOB_MAKEP2(p, p2) (BYTE *)OOB_MAKEP(OOB_SELECTOROF(p), OOB_OFFSETOF(p2))
+#elif OE_MACNATIVE
+#define OOB_MAKEP2(p, p2) (BYTE *)((BYTE *)(*p) + OOB_OFFSETOF(p2))
+#else
+#define OOB_MAKEP2(p, p2) (BYTE *)(p2)
+#endif
+
+
+// OOB_MAKEP3 - makes a 32-bit pointer
+// On 16-bit: makes ptr out of seg selector and seg ofs: == OOB_MAKEP2
+// On native Mac:
+// makes ptr out of handle and offset in referenced block == OOB_MAKEP2
+// On 32-bit: pointer arithmetic: assume p is base and add in p2 offset.
+//
+#undef OOB_MAKEP3
+#if (OE_SEGMENTED || OE_MACNATIVE)
+#define OOB_MAKEP3(p, p2) OOB_MAKEP2(p, p2)
+#else
+#define OOB_MAKEP3(p, p2) (BYTE *)((BYTE *)(p) + (ULONG)(p2))
+#endif
+
+
+// The constant sheapshake size is inited here.
+// Note: we don't use a static class member since it's
+// referenced in an inline method and hxxtoinc would
+// end up requiring its definition.
+//
+#if ID_DEBUG
+#if OE_RISC
+// CONSIDER: This value must be correspond to the hardware alignment
+// CONSIDER: for each platform. [jeffrob]
+#define SHM_cbShift 0
+#else
+#define SHM_cbShift 2
+#endif
+#else
+// no shifting unless debug
+#define SHM_cbShift 0
+#endif
+
+#if ID_DEBUG
+// struct defined for keeping the list of sheap mgr in the system.
+class SHEAPMGR_LIST {
+public:
+ SHEAPMGR_LIST();
+
+ SHEAP_MGR *m_psheapmgr;
+ SHEAPMGR_LIST *m_psheapmgrlistNext;
+};
+#endif
+
+//
+// **********************************
+// *** class SHEAP_MGR starts here **
+// **********************************
+//
+
+/***
+*class SHEAP_MGR - 'sheapmgr': Silver heap manager
+*Purpose:
+* The class implements the Silver heap manager.
+*
+***********************************************************************/
+
+class SHEAP_MGR
+{
+ friend class BLK_DESC;
+ friend class BLK_MGR;
+ friend void CreateEbInc(void); //tool that generates EB.INC file
+#if ID_TEST
+ friend TIPERROR GetSheapSize(UINT argc, BSTRA *rglstr);
+ friend TIPERROR GetAllSizes(UINT argc, BSTRA *rglstr);
+#endif
+public:
+ static TIPERROR Create(SHEAP_MGR **ppsheapmgr, UINT cbSizeReserved);
+ nonvirt UINT CbSizeHeap() const;
+
+ SHEAP_MGR();
+ ~SHEAP_MGR();
+ void operator delete(void *pv);
+
+ // Locking methods
+ nonvirt VOID Lock();
+ nonvirt VOID Unlock();
+ nonvirt BOOL IsLocked() const;
+
+ // CONSIDER: make private???
+ static CONSTDATA UINT m_cbSizeInitial;
+
+#if ID_DEBUG
+ static VOID DebSheapShake();
+ nonvirt VOID DebShowState(UINT uLevel) const;
+ nonvirt VOID DebCheckState(UINT uLevel) const;
+ nonvirt BOOL DebCanSheapShake();
+ nonvirt VOID DebSheapShakeOn();
+ nonvirt VOID DebSheapShakeOff();
+ nonvirt VOID DebSheapShakeOne();
+ nonvirt VOID DebLock();
+ nonvirt VOID DebUnlock();
+ nonvirt BOOL DebIsLocked();
+ nonvirt static VOID DebAddSheapmgrToList(SHEAP_MGR *psheapmgr);
+ nonvirt static VOID DebRemoveSheapmgrFromList(SHEAP_MGR *psheapmgr);
+
+#else
+ static VOID DebSheapShake() {}
+ nonvirt VOID DebShowState(UINT uLevel) const {}
+ nonvirt VOID DebCheckState(UINT uLevel) const {}
+ nonvirt VOID DebCanSheapShake() {}
+ nonvirt VOID DebSheapShakeOn() {}
+ nonvirt VOID DebSheapShakeOff() {}
+ nonvirt VOID DebSheapShakeOne() {}
+ nonvirt VOID DebLock() {}
+ nonvirt VOID DebUnlock() {}
+ nonvirt VOID DebIsLocked() {}
+ nonvirt static VOID DebAddSheapmgrToList(SHEAP_MGR *psheapmgr) {}
+ nonvirt static VOID DebRemoveSheapmgrFromList(SHEAP_MGR *psheapmgr) {}
+
+#endif // ID_DEBUG
+
+protected:
+ // Clients should use Create().
+ void *operator new(size_t cbSize);
+
+ nonvirt TIPERROR Init(UINT cbSizeReserved);
+
+ // 24-Mar-93 ilanc: needed by OE_MAC as well
+ /* inline */ nonvirt BLK_DESC *PtrOfBlkDesc(BLK_DESC *pblkdesc) const;
+ nonvirt BLK_DESC *PtrOfBlkDescPrev(BLK_DESC *pblkdesc) const;
+ nonvirt BLK_DESC *PtrOfBlkDescLast() const;
+
+ nonvirt VOID AddBlkdesc(BLK_DESC *pblkdesc, ULONG cbSize);
+ nonvirt VOID RemoveBlkdesc(BLK_DESC *pblkdesc);
+
+#if !(OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+ nonvirt BOOL IsValid() const;
+
+ // Following methods are in principle public, but really
+ // only accessed by the BLK_MGR/BLK_DESC, thus instead
+ // of making them globally accessible we "restrict"
+ // their access to BLK_MGR/BLK_DESC by making BLK_MGR/BLK_DESC
+ // friends.
+ // (So, friendship can be useful...).
+ //
+ nonvirt TIPERROR Alloc(BLK_DESC *pblkdesc, ULONG cbSize);
+ nonvirt VOID Free(BLK_DESC *pblkdesc);
+ nonvirt TIPERROR Realloc(BLK_DESC *pblkdesc, ULONG cbSizeNew);
+
+private:
+ // These are *really* private
+ nonvirt TIPERROR ReallocHeap(ULONG cbSizeNewHeap);
+ nonvirt VOID ShiftHeap(BLK_DESC *pblkdesc, LONG dbSize);
+
+ // 32-bits are reserved even if 16-bit version for
+ // following two pointer members.
+ // In Win16, used as "near" pointer in heap seg.
+ // Hiword ignored (should be 0).
+ //
+ // On native Mac: m_pblkdescFirst is a 32-bit ptr to the first blkdesc
+ // managed by this heap and m_pbFree is a 16-bit "near" ptr
+ // into the relocatable memory block managed by the sheap,
+ // i.e. to get a ptr to the first free byte:
+ // (BYTE *)(*m_hMemHeap + LOWORD(m_pbFree))
+ //
+ // On 32-bits: each is a true 32-bit ptr.
+ //
+ BYTE *m_qbFree;
+
+#endif // ! (OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+
+ // All implementation link together their blkdescs -- for
+ // purposes of destruction.
+ //
+ BLK_DESC *m_pblkdescFirst;
+
+ // All implementations have a counting semaphore for locking.
+ // Note however that for REALMODE and MAC we lock memory directly at
+ // the block level as well.
+ // We use a 16-bit counter on 16-bit machines since
+ // sheaps are limited to 64K and thus there can't be
+ // more than 64K entries -- likewise we use a 32-bit counter
+ // on 32-bit archs, since in principle their sheaps can be
+ // larger and thus more than 64K entries can be managed.
+ //
+ // Locking implementation: a sheap is locked (i.e. the counter
+ // is incremented) by locking a chunk, a block or the heap
+ // itself. It is considered unlocked iff the counting semaphore
+ // is zero -- unlocking a chunk, block or heap decrements
+ // this counter. A locked sheap cannot be grown or shrunk
+ // in such a way that will move any contained blocks or chunks.
+ //
+ // Allocating a new chunk however will succeed if there's a
+ // large enough chunk on the freelist. Freeing a chunk always
+ // succeeds.
+ //
+ // In addition the sheap is physically locked. On Win16 this
+ // is a NOP since sheaps are addressed with selectors. On
+ // native Mac, sheaps are implemented as relocatable memblocks and
+ // are actually locked and unlocked.
+ //
+ UINT m_cLocks;
+
+#if ID_DEBUG
+ BOOL m_canSheapShake;
+ UINT m_cbSizeReserved;
+ UINT m_cDebLocks;
+#endif
+
+#if OE_SEGMENTED
+
+ USHORT m_cbSizeHeap;
+
+#elif OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32
+
+ // Each block is separately managed, i.e. there is no
+ // contiguous sheap memblock
+
+#elif OE_MACNATIVE
+
+ USHORT m_cbSizeHeap;
+ Handle m_hMemHeap; // On mac: the sheap is a single
+ // relocatable block within which
+ // we manage blkdescs.
+#else
+#error Incorrect OE
+#endif // OE
+
+#ifdef SHEAPMGR_VTABLE
+#pragma VTABLE_EXPORT
+#endif
+};
+
+
+// **********************************
+// *** class BLK_DESC starts here ***
+// **********************************
+//
+
+// This constant defines the end of list sentinel
+// (used by the linked list of block descriptors).
+//
+BLK_DESC* const BD_pblkdescNil = (BLK_DESC *)UINT_MAX;
+
+/***
+*class BLK_DESC - 'blkdesc': block descriptor
+*Purpose:
+* The class implements block descriptors.
+* Describes a block allocated the heap manager.
+* See \silver\doc\ic\sheapmgr.doc for more information.
+*
+*Implementation Notes:
+* Since block descriptors and the heap manager, that it interfaces
+* to, are both allocated in the same segment, there's no need to
+* explicitly contain a reference to the allocating heap (of the
+* block described by this descriptor).
+*
+* The debug version allocates an extra two bytes at the end
+* of the managed memblock for sheapshaking purposes
+* and has a debug-only flag indicating the state of shift:
+* up or down.
+*
+*Friends: SHEAP_MGR
+*
+***********************************************************************/
+
+class BLK_DESC
+{
+ friend class SHEAP_MGR;
+ friend class BLK_MGR;
+ friend class DYN_BLK_MGR;
+ friend void CreateEbInc(void); //tool that generates EB.INC file
+
+public:
+ BLK_DESC();
+ ~BLK_DESC();
+
+ nonvirt TIPERROR Init(SHEAP_MGR *psheapmgr, UINT cbSize);
+
+ inline nonvirt BYTE *QtrOfBlock() const;
+ inline nonvirt UINT CbSize() const;
+ inline nonvirt VOID Free();
+ nonvirt TIPERROR Realloc(ULONG cbSizeNew);
+ inline nonvirt BOOL IsValid() const;
+ nonvirt TIPERROR Read(STREAM *pstrm);
+ nonvirt TIPERROR Write(STREAM *pstrm);
+ nonvirt UINT GetSize() const;
+ nonvirt UINT GetRemainingSize() const;
+ nonvirt SHEAP_MGR *Psheapmgr() const;
+
+ // Locking methods
+ nonvirt VOID Lock();
+ nonvirt VOID Unlock();
+ nonvirt BOOL IsLocked() const;
+
+ // Debug/test methods
+#if ID_DEBUG
+ nonvirt VOID DebShowState(UINT uLevel) const;
+#else
+ nonvirt VOID DebShowState(UINT uLevel) const {}
+#endif
+
+private:
+ inline nonvirt BYTE *QtrOfBlockActual() const;
+ inline nonvirt UINT CbSizeActual() const;
+
+
+ // 32-bits are reserved even if 16-bit version for
+ // following two pointer members.
+ //
+ // In Win16/Os2 1.x: used as "near" pointer in heap seg.
+ // Hiword ignored (should be 0).
+ //
+ // In realmode used as "far" pointer to memblock/blkdesc.
+ //
+ // In 32-bit: 32-bit pointer to memblock/blkdesc.
+ //
+ // On Mac: m_pbMemBlock is "near ptr" relative to *m_hMemHeap:
+ // i.e. to get pointer to memblock:
+ // (BYTE *)(*m_hMemHeap + LOWORD(m_pbMemBlock));
+ // m_pblkdescNext is 32-bit pointer to next blkdesc.
+ //
+ BYTE *m_qbMemBlock;
+ BLK_DESC *m_pblkdescNext;
+
+#if OE_SEGMENTED
+
+ USHORT m_cbSize;
+
+#elif OE_REALMODE || OE_MACNATIVE || OE_MAC || OE_RISC || OE_WIN32
+
+ USHORT m_cbSize;
+ SHEAP_MGR *m_psheapmgr;
+
+#else
+#error Incorrect OE
+#endif // OE
+
+#if (OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+ // Since blocks are managed separately in realmode and fixed mem
+ // Mac, we lock them at the block level rather than deferring
+ // to the containing sheap as is the case for other implementations.
+ //
+ UINT m_cLocks;
+#endif // (OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+
+#if ID_DEBUG
+ // Debug-only flag indicating state of shift for sheapshaking
+ // purposes.
+ // TRUE if extra two bytes is at end of memblock and thus
+ // should shift up (to a higher address) to shake,
+ // otherwise should shift down.
+ // Initially set to TRUE.
+ //
+ BOOL m_fShiftUp;
+#endif
+
+#ifdef BLKDESC_VTABLE
+#pragma VTABLE_EXPORT
+#endif
+};
+
+
+
+
+// **************************************
+// *** SHEAP_MGR inline class methods ***
+// **************************************
+
+// Most inline methods have been made *temporarily* outline.
+// The reason is that cfront complains (spuriously) about
+// about "const cast away" then the this pointer for const
+// methods (which these all are) is cast to an integer.
+// C7 doesn't complain though... so....
+//
+
+/***
+*PUBLIC SHEAP_MGR::Lock
+*Purpose:
+* Lock the sheap.
+*
+*Implementation Notes:
+* Increment counting semaphore.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID SHEAP_MGR::Lock()
+{
+#if OE_MACNATIVE
+ // We could do this for OE_WIN as well, but since
+ // it's a NOP why waste the funccall.
+ //
+ // Only need to physically lock if never locked.
+ if (m_cLocks == 0) {
+ (VOID)PvLockHsys((HSYS)m_hMemHeap);
+ }
+#endif
+ m_cLocks++;
+}
+
+
+/***
+*PUBLIC SHEAP_MGR::Unlock
+*Purpose:
+* Unlock the sheap.
+*
+*Implementation Notes:
+* Decrements counting semaphore.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID SHEAP_MGR::Unlock()
+{
+ DebAssert(m_cLocks > 0, "SHEAP_MGR::Unlock: underflow.");
+ m_cLocks--;
+
+#if OE_MACNATIVE
+ // We could do this for OE_WIN as well, but since
+ // it's a NOP why waste the funccall.
+ //
+ if (m_cLocks == 0) {
+ // No more outstanding locks, we can physically unlock.
+ UnlockHsys((HSYS)m_hMemHeap);
+ }
+#endif
+}
+
+
+/***
+*PUBLIC SHEAP_MGR::IsLocked
+*Purpose:
+* Tests if sheap is locked.
+*
+*Implementation Notes:
+* Tests counting semaphore.
+*
+*Entry:
+*
+*Exit:
+* TRUE if sheap is locked -- i.e. at least one lock.
+***********************************************************************/
+
+inline BOOL SHEAP_MGR::IsLocked() const
+{
+ return (BOOL)(m_cLocks > 0);
+}
+
+
+#if !(OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+
+
+/***
+*PROTECTED SHEAP_MGR::IsValid
+*Purpose:
+* Is sheap valid -- i.e has it been initialized?
+*
+*Implementation Notes:
+* We test the m_cbSizeHeap member. After initialization
+* it must always be >= sizeof(SHEAP_MGR).
+*
+*Entry:
+*
+*Exit:
+* TRUE if already initialized, else FALSE
+*
+***********************************************************************/
+
+inline BOOL SHEAP_MGR::IsValid() const
+{
+ return (BOOL)(m_cbSizeHeap > 0);
+}
+
+
+
+#endif // !(OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+
+/***
+*PUBLIC SHEAP_MGR::CbSizeHeap
+*Purpose:
+* Returns the current size of the heap.
+*
+* Note: NA for MAC or REALMODE (since no sheap really).
+*
+*Entry:
+*
+*Exit:
+* ULONG size of the sheap.
+*
+***********************************************************************/
+
+inline UINT SHEAP_MGR::CbSizeHeap() const
+{
+#if !(OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+ return (UINT)m_cbSizeHeap;
+#else
+ return UINT_MAX;
+#endif //(OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32)
+}
+
+// *******************************
+// *** BLK_DESC inline methods ***
+// *******************************
+//
+
+
+/***
+*PUBLIC BLK_DESC::Psheapmgr
+*Purpose:
+* Get containing sheapmgr
+*
+*Implementation Notes:
+* Defers to sheap.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+inline SHEAP_MGR *BLK_DESC::Psheapmgr() const
+{
+#if OE_SEGMENTED
+ return ((SHEAP_MGR *)OOB_MAKEP2(this, 0));
+#else
+ return m_psheapmgr;
+#endif
+}
+
+/***
+*PROTECTED SHEAP_MGR::PtrOfBlkDesc - Convert blk desc offset to address.
+*Purpose:
+* Convert blk desc offset to address.
+*
+*Implementation Notes:
+* On Win16: Assumes that pblkdesc is offset in heap seg.
+* Asserts if oBlkDesc not in reserved range at start of heap.
+* On Mac: Assumes the pblkdesc 32-bit ptr.
+* NOTE: wants to be inline. Will be when C7 is used cos
+* then spurious "const castaway" warning won't be
+* generated.
+*
+*Entry:
+* 16-bit:
+* pblkdesc - offset of block desc in heap.
+*
+*Exit:
+*
+***********************************************************************/
+
+inline BLK_DESC *SHEAP_MGR::PtrOfBlkDesc(BLK_DESC *pblkdesc) const
+{
+ DebAssert(pblkdesc != BD_pblkdescNil,
+ "SHEAP_MGR::PtrOfBlkDesc: NIL BlkDesc handle.");
+
+#if OE_SEGMENTED
+ DebAssert(OOB_MAKEOFFSET(this, pblkdesc) < m_cbSizeReserved,
+ "SHEAP_MGR::PtrOfBlkDesc: blk desc not in reserved heap part.");
+#endif
+
+#if OE_MACNATIVE || OE_MAC || OE_RISC || OE_WIN32
+ return pblkdesc;
+#else
+ return (BLK_DESC *)OOB_MAKEP2(this, pblkdesc);
+#endif // OE_MACNATIVE || OE_MAC || OE_RISC || OE_WIN32
+}
+
+
+/***
+*PUBLIC BLK_DESC::Lock
+*Purpose:
+* Lock the block.
+*
+*Implementation Notes:
+* Defers to sheap.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID BLK_DESC::Lock()
+{
+ DebAssert(IsValid(), "BLK_DESC::Lock: Block invalid.");
+
+#if OE_SEGMENTED || OE_MACNATIVE
+ Psheapmgr()->Lock();
+#elif OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32
+ m_cLocks++;
+#else
+#error bad OE.
+#endif
+}
+
+
+/***
+*PUBLIC BLK_DESC::Unlock
+*Purpose:
+* Unlock the block.
+*
+*Implementation Notes:
+* Defers to sheap.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID BLK_DESC::Unlock()
+{
+ DebAssert(IsValid(), "BLK_DESC::Unlock: Block invalid.");
+
+#if OE_SEGMENTED || OE_MACNATIVE
+
+ Psheapmgr()->Unlock();
+
+#elif OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32
+
+ DebAssert(m_cLocks > 0, "BLK_DESC::Unlock: underflow.");
+ m_cLocks--;
+
+#else
+#error bad OE.
+#endif
+}
+
+
+/***
+*PUBLIC BLK_DESC::IsLocked
+*Purpose:
+* Tests if block is locked.
+*
+*Implementation Notes:
+* Defers to sheap.
+*
+*Entry:
+*
+*Exit:
+* TRUE if block is locked -- i.e. at least one lock.
+***********************************************************************/
+
+inline BOOL BLK_DESC::IsLocked() const
+{
+ DebAssert(IsValid(), "BLK_DESC::IsLocked: Block invalid.");
+
+#if OE_SEGMENTED || OE_MACNATIVE
+
+ return Psheapmgr()->IsLocked();
+
+#elif OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32
+
+ // we're locked also if our containing sheap is locked.
+ return (BOOL)(m_cLocks > 0) || Psheapmgr()->IsLocked();
+
+#else
+#error bad OE.
+#endif
+
+}
+
+
+/***
+*PUBLIC BLK_DESC::IsValid - Tests if block is valid.
+*Purpose:
+* Tests if block is valid. Note that a 0-size block is valid,
+* however its oMemBlock must be non-zero to be valid (i.e. a
+* 0-size block does have an entry in the heap -- it just happens
+* to be of length 0). Since the SHEAP_MGR itself is always
+* allocated at offset 0 in the heap, this really does mean
+* that an oMemBlock of 0 is in fact invalid.
+* CONSIDER: making inline
+*
+*Entry:
+* None.
+*
+*Exit:
+* Returns TRUE if block valid (i.e. oMemBlock != 0), else FALSE.
+*
+***********************************************************************/
+
+inline BOOL BLK_DESC::IsValid() const
+{
+ return (m_qbMemBlock != NULL);
+}
+
+
+/***
+*PUBLIC BLK_DESC::CbSizeActual - actual size of block accessor (get).
+*Purpose:
+* Returns size of block + extra debug shift bytes.
+*
+*Implementation Notes:
+* In the debug version the extra cbShift bytes are included
+* in the actual size already.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+inline UINT BLK_DESC::CbSizeActual() const
+{
+ DebAssert(IsValid(), "BLK_DESC::cbSize: Block invalid.");
+ return m_cbSize;
+}
+
+
+/***
+*PUBLIC BLK_DESC::CbSize - size of block accessor (get).
+*Purpose:
+* Returns size of block.
+*
+*Implementation Notes:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+inline UINT BLK_DESC::CbSize() const
+{
+ DebAssert(IsValid(), "BLK_DESC::cbSize: Block invalid.");
+ // We could actually just use the debug version for release
+ // as well since m_cbShift will be zero in that case --
+ // however we make it explicit that there's no shakeshift
+ // in the rel version here.
+ //
+#if ID_DEBUG
+ return CbSizeActual() - SHM_cbShift;
+#else
+ return CbSizeActual();
+#endif
+}
+
+
+/***
+*PUBLIC BLK_DESC::Free - Frees an allocated block.
+*Purpose:
+* Frees a block from the heap. Defers to heap manager.
+*
+*Implementation Notes:
+* 16-bit: Assumes that heap manager is allocated at offset 0 in this
+* segment.
+* CONSIDER: making inline
+*
+*Entry:
+* None.
+*
+*Exit:
+* Sets private members to invalid state.
+*
+***********************************************************************/
+
+inline VOID BLK_DESC::Free()
+{
+ DebAssert(IsValid(), "BLK_DESC::Free: Block invalid.");
+
+#if OE_SEGMENTED || OE_MACNATIVE
+
+ Psheapmgr()->Free(this);
+
+#elif OE_REALMODE || OE_MAC || OE_RISC || OE_WIN32
+
+ MemFree(m_qbMemBlock);
+ Psheapmgr()->RemoveBlkdesc(this);
+
+#else
+#error bad OE.
+#endif
+
+ // Reinitialize by reconstructing in place.
+ ::new (this) BLK_DESC;
+
+ DebAssert(IsValid() == FALSE,
+ "BLK_DESC::Free: Whoops! Block should be invalid.");
+}
+
+
+/***
+*PUBLIC BLK_DESC::QtrOfBlockActual - returns block address.
+*Purpose:
+* Returns ptr to actual memblock -- ignoring the extra cbShift.
+*
+*Implementation Notes:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+// CONSIDER: andrewso 30-Jun-93
+// QtrOfBlockActual is merged with QtrOfBlock, which in turn has
+// been merged with BLK_MGR::QtrOfHandle to avoid a problem
+// with inlining QtrOfBlockActual when QtrOfHandle is called.
+//
+// When we upgrade to a better compiler, we should think of putting
+// all of this back.
+//
+inline BYTE *BLK_DESC::QtrOfBlockActual() const
+{
+ DebAssert(IsValid(), "BLK_DESC::QtrOfBlockActual: Block invalid.");
+
+#if OE_MACNATIVE
+ return OOB_MAKEP2(m_psheapmgr->m_hMemHeap, m_qbMemBlock);
+#else
+ return OOB_MAKEP2(this, m_qbMemBlock);
+#endif
+}
+
+/***
+*PUBLIC BLK_DESC::QtrOfBlock - returns block address.
+*Purpose:
+* Returns pointer to logical memblock -- i.e. in debug
+* version takes into account cbShift, in release version
+* there is no cbShift.
+*
+*Implementation Notes:
+* In debug version we test the fShiftUp flag -- if set,
+* that means that if we need to shake the block, we
+* should shift it up, thus QtrOfBlockActual() is actually
+* correct, otherwise we should shift it down, thus
+* we should offset QtrOfBlockActual() by SHM_cbShift
+* bytes in order to reference the logical memblock.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+// CONSIDER: andrewso 30-Jun-93
+// QtrOfBlockActual is merged with QtrOfBlock, which in turn has
+// been merged with BLK_MGR::QtrOfHandle to avoid a problem
+// with inlining QtrOfBlockActual when QtrOfHandle is called.
+//
+// When we upgrade to a better compiler, we should consider putting
+// this back.
+//
+inline BYTE *BLK_DESC::QtrOfBlock() const
+{
+ DebAssert(IsValid(), "BLK_DESC::QtrOfBlock: Block invalid.");
+
+ return
+
+#if OE_MACNATIVE
+ OOB_MAKEP2(m_psheapmgr->m_hMemHeap, m_qbMemBlock)
+#else
+ OOB_MAKEP2(this, m_qbMemBlock)
+#endif
+
+#if ID_DEBUG
+ + ((m_fShiftUp == TRUE) ? 0 : SHM_cbShift)
+#endif
+ ;
+}
+
+#if ID_DEBUG
+
+//////////////////////////////////////////////////////////////////
+// SHEAPMGR_LIST methods
+//////////////////////////////////////////////////////////////////
+/***
+*PUBLIC SHEAPMGR_LIST::SHEAPMGR_LIST - returns block address.
+*Purpose:
+* constructor : initializes the data member
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+inline SHEAPMGR_LIST::SHEAPMGR_LIST() {
+
+ m_psheapmgr = NULL;
+ m_psheapmgrlistNext = NULL;
+
+
+}
+#endif
+
+
+#endif // ! SHEAPMGR_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/silver.hxx b/private/oleauto/src/typelib/silver.hxx
new file mode 100644
index 000000000..5272a2860
--- /dev/null
+++ b/private/oleauto/src/typelib/silver.hxx
@@ -0,0 +1,143 @@
+/***
+*silver.hxx - Fundamental Silver include file
+*
+* Copyright (C) 1990, Microsoft Corporation
+*
+*Purpose:
+* This include file defines the basic types used by Silver, and
+* sets up the compile switches and the debug macros.
+*
+* This file should be included before all others.
+*
+*
+*Revision History:
+*
+* 15-AUG-90 petergo: File created.
+* 14-Feb-91 ilanc: added macros.hxx
+* 02-Dec-91 ilanc: debug.hxx must be included before tiperrs.hxx
+* (which includes cltypes.hxx) cos of
+* operator new and explicit ctors (cfront prob).
+* 22-Apr-92 martinc: moved #include "version.hxx" to top of file
+*
+*******************************************************************************/
+
+#ifndef SILVER_HXX_INCLUDED
+#define SILVER_HXX_INCLUDED
+
+#include "switches.hxx"
+#include "version.hxx"
+
+
+#if OE_WIN32
+#define __export
+#define EXPORT
+//This line specifies widechar ctype table instead of ascii (ctype.h).
+#define _NEWCTYPETABLE
+#endif
+
+#if 0
+// ingore certain high-frequency, almost always benign warnings when compiling
+// at high warning levels, in order to cut down on the noise
+#pragma warning(disable:4100) // unreferenced formal parameter
+#pragma warning(disable:4209) // benign typedef redefinition
+#pragma warning(disable:4214) // non-standard extension used
+#pragma warning(disable:4505) // unreferenced local function has been removed
+#if !OE_WIN16
+#pragma warning(disable:4706) // assignment in conditional expression
+#endif
+#endif //0
+
+#if OE_MAC
+// Wings doesn't put all data far even though we told it to. This is a
+// problem for ASLM 1.1 dll's (which includes the mac typelib.dll). We don't
+// have much constant data, so it's easiest to just to put all data far.
+#if OE_MAC68K
+#pragma data_seg("_FAR_DATA")
+#endif
+
+// Even with the above pragma, constant data doesn't go into the proper segment
+// so we define OLECONST which un-const's the problem data items
+#define CONSTDATA
+#else
+#define CONSTDATA const
+#endif
+
+#if !FV_UNICODE_OLE && 0
+// NOTE: 21-Jan-93 ilanc: we #define some long typenames to
+// something shorter to appease the buggy C compiler/linker
+// we're using. Apparently when mangled names get too long
+// (more than 64 chars) it does evil things.
+//
+// UNDONE: these hacks should be removed when we switch over to use C8.
+//
+
+#define tagARRAYDESC tAD
+#define tagBINDPTR tBPTR
+#define tagCALLCONV tCC
+#define tagDESCKIND tDK
+#define tagDISPPARAMS tDPS
+#define tagELEMDESC tED
+#define tagEXCEPINFO tEXI
+#define tagFUNCDESC tFD
+#define tagFUNCFLAGS tFF
+#define tagFUNCKIND tFK
+#define tagIDLDESC tIDLD
+#define tagINTERFACEDATA tID
+#define tagINVOKEKIND tIK
+#define tagMETHODDATA tMD
+#define tagPARAMDATA tPD
+#define tagSYSKIND tSK
+#define tagTLIBATTR tTLA
+#define tagTYPEATTR tTA
+#define tagTYPEDESC tTD
+#define tagTYPEFLAGS tTF
+#define tagTYPEKIND tTK
+#define tagVARDESC tVD
+#define tagVARIANT tVAR
+#define tagVARKIND tVK
+
+#endif //!FV_UNICODE_OLE
+
+
+// These name result in "multiply defined" errors for Mtypelib.lib(on MAC).
+// So we have to rename these names in mtypelib.lib
+
+// <NOTE: I think these were moved to typelib.hxx - jimcool>
+
+
+#include "obwin.hxx"
+
+#include "obole2.h"
+#include "types.h"
+#include "xutil.h" // core functions/macros to manupilate xstring
+
+
+
+// REVIEW: temporarily ifdef out C++ specific stuff (so this header can
+// be included in C files as well). Eventually this needs to be fixed by
+// a better factorization of the header files.
+//
+#ifdef __cplusplus
+
+// A bit of new C++ syntax
+#define nonvirt
+
+#define START_PAS_INCLUDE
+#define END_PAS_INCLUDE
+
+// Setup OE_REALMODE if not already set.
+// (It's only explicitly defined and set in dos (bound) builds).
+//
+#ifndef OE_REALMODE
+#define OE_REALMODE 0
+#endif
+
+#include "mem.hxx" // FYI: defines operator new and delete
+#include "debug.hxx"
+#include "macros.hxx"
+#include "tiperr.h"
+
+#endif // }
+
+
+#endif // !SILVER_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/stltinfo.cxx b/private/oleauto/src/typelib/stltinfo.cxx
new file mode 100644
index 000000000..e4e9bae58
--- /dev/null
+++ b/private/oleauto/src/typelib/stltinfo.cxx
@@ -0,0 +1,500 @@
+/***
+*stltinfo.cxx - STL_TYPEINFO definition
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* STL_TYPEINFO must be inherited by those TYPEINFOs which are stored
+* in a GenericTypeLibOLE.
+*
+*Revision History:
+*
+* 14-May-91 alanc: Created.
+* 12-Feb-93 w-peterh: GetContainingTypeLib returns HRESULT
+* 02-Mar-93 w-peterh: GetContainingTypeLib takes UINT* not USHORT*
+*
+*****************************************************************************/
+
+#include "silver.hxx"
+
+#define STL_TYPEINFO_VTABLE // export STL_TYPEINFO vtable
+#include "typelib.hxx"
+#include "stltinfo.hxx"
+#include "gdtinfo.hxx"
+#include "string.h"
+
+
+#pragma hdrstop(RTPCHNAME)
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+static char szOleDTInfoCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleDTInfoCxx
+#else
+static char szDTInfoCxx[] = __FILE__;
+#define SZ_FILE_NAME szDTInfoCxx
+#endif
+#endif
+
+
+
+/***
+*PUBLIC STL_TYPEINFO::GetLcid
+*Purpose:
+* Get the lcid from the containing typelibs nammgr
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+TIPERROR STL_TYPEINFO::GetLcid(LCID *plcid)
+{
+ *plcid = PgtlibOleContaining()->GetLcid();
+
+ return TIPERR_None;
+}
+
+
+/***
+*PUBLIC STL_TYPEINFO::RelInternalRef
+*Purpose:
+* Release an internal (from a TypeInfo in the same TypeLib) reference
+* to the TypeInfo.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg( CS_CORE2 )
+VOID STL_TYPEINFO::RelInternalRef()
+{
+ DebAssert(m_pgtliboleContainer != NULL,
+ "STL_TYPEINFO::RelInternalRef m_pgtliboleContainer NULL");
+
+
+ // If the count is equal to zero, we are only being called to destroy
+ // this object...so don't decrement either our or our partner's
+ // internal refcount.
+ //
+ if (m_cInternalRefs != 0) {
+ m_cInternalRefs--;
+
+ if (PstltiPartner() != NULL) {
+ // Now release a reference on our partner.
+ ReleasePartner();
+ }
+ }
+
+ if (m_cRefs + m_cInternalRefs == 0) {
+
+ // Make sure our partner's pointer to use is invalidated.
+ if (PstltiPartner() != NULL) {
+ PstltiPartner()->SetPstltiPartner(NULL);
+ }
+
+ if (m_hte != HTENTRY_Nil) {
+ // unlink from TypeLib's list
+ m_pgtliboleContainer->Deleting(m_hte);
+ }
+ ((GEN_DTINFO *)this)->GEN_DTINFO::~GEN_DTINFO();
+ MemFree(this);
+ }
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC DYNTYPEINFO::QueryInterface
+*Purpose:
+* Implementation of QueryInterface method. Supports casting to
+* DYNTYPEINFO.
+*Entry:
+* riid - Interface GUID
+* ppvObj - LPVOID * that receives the requested protocol.
+*
+*Exit:
+* Return NOERROR or ReportResult(0, E_NOINTERFACE, 0, 0)
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+HRESULT DYNTYPEINFO::QueryInterface(REFIID riid, LPVOID FAR* ppvObj)
+{
+ if (IIDEQ(riid, IID_IUnknown)) {
+ *ppvObj = (LPVOID) (IUnknown *) this;
+ AddRef();
+ return NOERROR;
+ }
+
+ if (IIDEQ(riid, IID_ITypeInfoA)) {
+ *ppvObj = (LPVOID) (ITypeInfoA *) this;
+ AddRef();
+ return NOERROR;
+ }
+
+ if (IIDEQ(riid, IID_TYPEINFO)) {
+ *ppvObj = (LPVOID) (TYPEINFO *) this;
+ AddRef();
+ return NOERROR;
+ }
+
+ if (IIDEQ(riid, IID_DYNTYPEINFO)) {
+ *ppvObj = (LPVOID) (DYNTYPEINFO *) this;
+ AddRef();
+ return NOERROR;
+ }
+
+ *ppvObj = NULL; // required by OLE
+ return ReportResult(0, E_NOINTERFACE, 0, 0);
+}
+#pragma code_seg( )
+
+
+
+/***
+*PUBLIC STL_TYPEINFO::QueryInterface
+*Purpose:
+* Implementation of QueryInterface method. Supports casting to
+* STL_TYPEINFO.
+*Entry:
+* riid - Interface GUID
+* ppvObj - LPVOID * that receives the requested protocol.
+*
+*Exit:
+* Return NOERROR or ReportResult(0, E_NOINTERFACE, 0, 0)
+***********************************************************************/
+HRESULT STL_TYPEINFO::QueryInterface(REFIID riid, LPVOID FAR* ppvObj)
+{
+ if (IIDEQ(riid, IID_ITypeInfoA)) {
+ *ppvObj = (LPVOID) (ITypeInfoA *) this;
+ AddRef();
+ return NOERROR;
+ }
+
+ if (IIDEQ(riid, IID_ICreateTypeInfoA)) {
+ *ppvObj = (LPVOID) (ICreateTypeInfoA *) this;
+ AddRef();
+ return NOERROR;
+ }
+
+ if (IIDEQ(riid, IID_IUnknown)) {
+ *ppvObj = (LPVOID) (IUnknown *)(ITypeInfoA *) this;
+ AddRef();
+ return NOERROR;
+ }
+
+ *ppvObj = NULL; // required by OLE
+ return ReportResult(0, E_NOINTERFACE, 0, 0);
+}
+
+/***
+*PUBLIC STL_TYPEINFO::AddRef
+*Purpose:
+* Add an external reference to the TypeInfo.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+ULONG STL_TYPEINFO::AddRef()
+{
+ m_cRefs++;
+
+ // Since there are at least test cases which invoke this function
+ // on a TYPEINFO that has no container we must check for NULL.
+ if (m_pgtliboleContainer != NULL)
+ m_pgtliboleContainer->AddRef();
+
+ // Check to see if we're a dual interface, if so, increment
+ // the count on our partner.
+ //
+ if (PstltiPartner() != NULL) {
+ AddPartnerRef();
+ }
+
+ return m_cRefs;
+}
+#pragma code_seg( )
+
+
+
+/***
+*PUBLIC STL_TYPEINFO::Release
+*Purpose:
+* Release an external reference to the STL_TYPEINFO.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg( CS_CORE2 )
+ULONG STL_TYPEINFO::Release()
+{
+ ULONG cRefs;
+ GenericTypeLibOLE *pgtliboleContainer = m_pgtliboleContainer;
+
+ DebAssert(m_cRefs > 0, "underflow.");
+ m_cRefs--;
+ cRefs = m_cRefs;
+
+ // Check to see if we're a dual interface, if so, decrement
+ // the count on our partner.
+ //
+ if (PstltiPartner() != NULL) {
+ ReleasePartner();
+ }
+
+ // If our external references go to zero, release the appobject
+ // in case it holds a reference to the typelib.
+ //
+ if (cRefs == 0) {
+ ReleasePublicResources();
+ }
+
+ if (m_cRefs + m_cInternalRefs == 0) {
+ if (pgtliboleContainer != NULL) {
+ if (m_hte != HTENTRY_Nil) {
+ // unlink from typelib's list
+ pgtliboleContainer->Deleting(m_hte);
+ }
+ }
+
+ ((GEN_DTINFO *)this)->GEN_DTINFO::~GEN_DTINFO();
+ MemFree(this);
+ }
+
+ if (pgtliboleContainer != NULL)
+ pgtliboleContainer->Release(); // if this reduces the typelib's
+ // ref count to zero, then the typelib
+ // plus all ref'ed TYPEINFOs are deleted
+ return cRefs;
+
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC STL_TYPEINFO::SetModified
+*Purpose:
+* Sets the TYPEINFO's modified status.
+*
+*Entry:
+* isModified
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR STL_TYPEINFO::SetModified(BOOL isModified)
+{
+ TIPERROR err = TIPERR_None;
+
+ // Only do something if we're actually changing the isModified
+ // state. This comparison is done with ! in order to normalize
+ // against different non-zero "true" values.
+ if (!m_isModified != !isModified) {
+
+ // In any case, update the isModified flag.
+ // It is important to do this before the RelInternalRef, since
+ // the RelInternalRef potentially causes THIS to be deleted.
+ m_isModified = isModified;
+
+ // If we're marking the type as modified, then add an internal
+ // reference so that the typeinfo won't go away (and lose the
+ // changes). The reference is released when the type is saved.
+ if (isModified) {
+ AddInternalRef();
+ err = m_pgtliboleContainer->SetModified(TRUE);
+ DebAssert(err == TIPERR_None, "SetModified");
+ }
+ // If we're marking the type as not modified, then we need to
+ // release the internal reference that was added when the type
+ // was marked modified.
+ else {
+
+ RelInternalRef();
+ }
+ }
+
+ return err;
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC STL_TYPEINFO::SetContainingTypeLib - Set container of Type
+*Purpose:
+* Called when TYPEINFO is added or removed from a ITypeLib.
+*
+*Entry:
+* pgtlibole - pointer to ITypeLib or NULL if being removed from ITypeLib
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+VOID STL_TYPEINFO::SetContainingTypeLib(GenericTypeLibOLE *pgtlibole)
+{
+ UINT i;
+
+ if (pgtlibole != NULL) {
+ DebAssert(m_pgtliboleContainer == NULL, "");
+ // increment the containing TypeLib's reference count by the
+ // number of reference counts to this TypeInfo
+ for (i = 0; i < m_cRefs; i++)
+ pgtlibole->AddRef();
+
+ // Fix for bug#: 6153.
+ // set the containing typelib/project.
+ m_pgtliboleContainer = pgtlibole;
+
+ }
+ else {
+ // decrement the containing TypeLib's reference count by the
+ // number of reference counts to this TypeInfo
+ for (i = 0; i < m_cRefs; i++)
+ m_pgtliboleContainer->Release();
+
+ // Now blow this TYPEINFO away. Nobody should have any references
+ // of any kind this this anymore.
+ ((GEN_DTINFO *)this)->GEN_DTINFO::~GEN_DTINFO();
+ MemFree(this);
+ }
+
+}
+#pragma code_seg( )
+
+
+/***
+*PUBLIC STL_TYPEINFO::~STL_TYPEINFO
+*Purpose:
+* Destruct a STL_TYPEINFO.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+#pragma code_seg( CS_CORE )
+STL_TYPEINFO::~STL_TYPEINFO()
+{
+}
+#pragma code_seg( )
+
+
+
+/***
+*PUBLIC STL_TYPEINFO::name - return the name of the Type
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+//TIPERROR STL_TYPEINFO::SetName(SZ namebuf, USHORT cbMax)
+//{
+// return SzCopy(sz_Name, namebuf, cbMax);
+//}
+
+
+/***
+*PUBLIC STL_TYPEINFO::GetContainingTypeLib
+*Purpose:
+* Return the TypeLib which contains the given TypeInfo
+*Entry:
+* lplpTypeLib returns pointer to the TypeLib.
+* *lplpTypeLib is set only if lplpTypeLib is not NULL.
+* pindex returns the index of this typeinfo in the containing typelib.
+* *pindex is set only if pindex is not NULL.
+*
+*Exit:
+* TIPERROR --- if no containing TypeLib returns TIPERR_NoContainingLib
+*
+*NOTE:
+* This method can be used in several ways:
+* To get the containing typelib only, pass NULL for pindex.
+* To get the index only, pass NULL for lplpTypeLib.
+* To get both, pass valid pointers.
+* To get neither, but find out if there is a containing typelib,
+* pass NULL for both parameters and look at the return value.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+HRESULT STL_TYPEINFO::GetContainingTypeLib(ITypeLibA **lplpTypeLib, UINT *pindex)
+{
+ if (m_pgtliboleContainer == NULL)
+ return HresultOfScode(E_NOINTERFACE);
+
+ if (lplpTypeLib != NULL) {
+ m_pgtliboleContainer->AddRef();
+ *lplpTypeLib = m_pgtliboleContainer;
+ }
+
+ if (pindex != NULL)
+ *pindex = m_hte;
+
+ return NOERROR;
+}
+#pragma code_seg()
+
+
+/***
+*STL_TYPEINFO::PrepareForDestructio
+*Purpose:
+* NO OP
+*Entry:
+* None
+*Exit:
+* None
+***********************************************************************/
+VOID STL_TYPEINFO::PrepareForDestruction()
+{
+ // No op
+}
+
+/***
+*STL_TYPEINFO::Invoke
+*Purpose:
+* NO OP
+*Entry:
+* None
+*Exit:
+* None
+***********************************************************************/
+HRESULT STL_TYPEINFO::Invoke(VOID FAR* pvInstance,
+ MEMBERID memid,
+ WORD wFlags,
+ DISPPARAMSA FAR *pdispparams,
+ VARIANTA FAR *pvarResult,
+ EXCEPINFOA FAR *pexcepinfo,
+ UINT FAR *puArgErr)
+{
+ return NOERROR; // NOP
+}
diff --git a/private/oleauto/src/typelib/stltinfo.hxx b/private/oleauto/src/typelib/stltinfo.hxx
new file mode 100644
index 000000000..5ea4f512d
--- /dev/null
+++ b/private/oleauto/src/typelib/stltinfo.hxx
@@ -0,0 +1,558 @@
+/***
+*stltinfo.hxx - STL_TYPEINFO header file
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* STL_TYPEINFO is inherited by those TYPEINFO derivatives that
+* are stored in STAT_TYPELIBs.
+*
+*
+*Revision History:
+*
+* 14-May-91 alanc: Created.
+* 25-Aug-92 rajivk: support for bringing all needed class to runnable state
+*
+*****************************************************************************/
+
+#ifndef stltinfo_HXX_INCLUDED
+#define stltinfo_HXX_INCLUDED
+
+#include "errmap.hxx"
+#include "dyntinfo.hxx"
+#include "gtlibole.hxx"
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szSTLTINFO_HXX)
+#define SZ_FILE_NAME g_szSTLTINFO_HXX
+#endif
+
+struct TINODE;
+class GEN_DTINFO; //needed for friendship declaration
+class GenericTypeLibOLE;
+class GEN_PROJECT;
+class GEN_DTINFO;
+
+#define STAT_TYPELIB GEN_PROJECT
+
+
+/***
+*class STL_TYPEINFO
+*Purpose:
+* STL_TYPEINFO is inherited by those TYPEINFO derivatives that
+* are stored in STAT_TYPELIBs.
+*
+***********************************************************************/
+
+class STL_TYPEINFO : public DYNTYPEINFO, public ICreateTypeInfoA
+{
+friend GenericTypeLibOLE;
+friend STAT_TYPELIB;
+friend GEN_PROJECT;
+
+friend GEN_DTINFO;
+
+#if ID_TEST
+friend TIPERROR WriteTypeInfoToFile(LPSTR szFileName, GEN_DTINFO *pgdtinfo);
+friend TIPERROR ReadTypeInfoFromFile(LPSTR szFileName, GEN_DTINFO **ppgdtinfo);
+#endif
+
+public:
+
+ STDMETHOD(QueryInterface) (THIS_ REFIID riid, LPVOID FAR* ppvObj);
+ STDMETHOD_(ULONG,AddRef) (THIS);
+ STDMETHOD_(ULONG,Release) (THIS);
+
+ // Stubbed inherited virtual functions from ITypeInfo and
+ // ICreateTypeInfo.
+ // NOTE: They are simply stubbed here with a null body.
+ //
+
+ // Methods from ITypeInfo
+ STDMETHOD(GetTypeAttr)(THIS_ TYPEATTR FAR* FAR* lplptypeattr) { return 0; }
+ STDMETHOD(GetTypeComp)(THIS_ ITypeCompA FAR* FAR* lplptcomp) { return 0; }
+ STDMETHOD(GetFuncDesc)(THIS_ UINT index,
+ FUNCDESC FAR* FAR* lplpfuncdesc) { return 0; }
+ STDMETHOD(GetVarDesc)(THIS_ UINT index,
+ VARDESCA FAR* FAR* lplpvardesc) { return 0; }
+ STDMETHOD(GetNames)(THIS_ MEMBERID memid,
+ BSTR FAR* rgbstrNames,
+ UINT cMaxNames,
+ UINT FAR* lpcNames) { return 0; }
+ STDMETHOD(GetRefTypeOfImplType)(THIS_ UINT index,
+ HREFTYPE FAR* phreftype) { return 0; }
+ STDMETHOD(GetImplTypeFlags)(THIS_ UINT index,
+ INT FAR* pimpltypeflags) { return 0; }
+ STDMETHOD(GetIDsOfNames)(THIS_ OLECHAR FAR* FAR* rgszNames,
+ UINT cNames,
+ MEMBERID FAR* rgmemid) { return 0; }
+ STDMETHOD(Invoke)(THIS_ VOID FAR* lpvInstance,
+ MEMBERID memid,
+ WORD wFlags,
+ DISPPARAMSA FAR *lpdispparams,
+ VARIANTA FAR *lpvarResult,
+ EXCEPINFOA FAR *lpexcepinfo,
+ UINT FAR *lpuArgErr); // stub in stltinfo.cxx
+ STDMETHOD(GetDocumentation)(THIS_ MEMBERID memid,
+ BSTR FAR* lpbstrName,
+ BSTR FAR* lpbstrDocString,
+ DWORD FAR* lpdwHelpContext,
+ BSTR FAR* lpbstrHelpFile) { return 0; }
+ STDMETHOD(GetDllEntry)(THIS_
+ MEMBERID memid,
+ INVOKEKIND invkind,
+ BSTR FAR* lpbstrDllName,
+ BSTR FAR* lpbstrName,
+ WORD FAR* lpwOrdinal)
+ { return 0; }
+ STDMETHOD(GetRefTypeInfo)(THIS_ HREFTYPE hreftype,
+ ITypeInfoA FAR* FAR* lplptinfo) { return 0; }
+ STDMETHOD(AddressOfMember)(THIS_ MEMBERID memid,
+ INVOKEKIND invkind,
+ VOID FAR* FAR* lplpv) { return 0; }
+ STDMETHOD(CreateInstance)(THIS_
+ IUnknown FAR* punkOuter,
+ REFIID iid,
+ VOID FAR* FAR* lplpvObject) { return 0; }
+ STDMETHOD(GetMops)(THIS_ MEMBERID memid,
+ BSTR FAR* lpbstrMops) { return 0; }
+ STDMETHOD(GetContainingTypeLib)(THIS_ ITypeLibA FAR* FAR* lplptlib,
+ UINT FAR* lpindex);
+ STDMETHOD_(void, ReleaseTypeAttr)(THIS_ TYPEATTR FAR* lptypeattr) {}
+ STDMETHOD_(void, ReleaseFuncDesc)(THIS_ FUNCDESC FAR* lpfuncdesc) {}
+ STDMETHOD_(void, ReleaseVarDesc)(THIS_ VARDESCA FAR* lpvardesc) {}
+
+ // Methods from ICreateTypeInfo
+ STDMETHOD(SetGuid)(THIS_ REFGUID guid) { return 0; }
+ STDMETHOD(SetTypeFlags)(THIS_ UINT uTypeFlags) { return 0; }
+ STDMETHOD(SetDocString)(THIS_ LPOLESTR lpstrDoc) { return 0; }
+ STDMETHOD(SetHelpContext)(THIS_ DWORD dwHelpContext) { return 0; }
+ STDMETHOD(SetVersion)(THIS_ WORD wMajorVerNum,
+ WORD wMinorVerNum) { return 0; }
+ STDMETHOD(AddRefTypeInfo)(THIS_ ITypeInfoA FAR* ptinfo,
+ HREFTYPE FAR* lphreftype) { return 0; }
+ STDMETHOD(AddFuncDesc)(THIS_ UINT index,
+ FUNCDESC FAR* lpfuncdesc) { return 0; }
+ STDMETHOD(AddImplType)(THIS_ UINT index,
+ HREFTYPE hreftype) { return 0; }
+ STDMETHOD(SetImplTypeFlags)(THIS_ UINT index,
+ INT impltypeflags) { return 0; }
+ STDMETHOD(SetAlignment)(THIS_ WORD cbAlignment) { return 0; }
+ STDMETHOD(SetSchema)(THIS_ LPOLESTR lpstrSchema) { return 0; }
+ STDMETHOD(AddVarDesc)(THIS_ UINT index,
+ VARDESCA FAR* lpvardesc) { return 0; }
+ STDMETHOD(SetFuncAndParamNames)(THIS_ UINT index,
+ LPSTR FAR* rgszNames,
+ UINT cNames) { return 0; }
+ STDMETHOD(SetVarName)(THIS_ UINT index,
+ LPSTR szName) { return 0; }
+ STDMETHOD(SetTypeDescAlias)(THIS_ TYPEDESC FAR* lptdescAlias) { return 0; }
+ STDMETHOD(DefineFuncAsDllEntry)(THIS_ UINT index,
+ LPOLESTR szDllName,
+ LPOLESTR szProcName) { return 0; }
+ STDMETHOD(SetFuncDocString)(THIS_ UINT index,
+ LPOLESTR szDocString) { return 0; }
+ STDMETHOD(SetVarDocString)(THIS_ UINT index,
+ LPOLESTR szDocString) { return 0; }
+ STDMETHOD(SetFuncHelpContext)(THIS_ UINT index,
+ DWORD dwHelpContext) { return 0; }
+ STDMETHOD(SetVarHelpContext)(THIS_ UINT index,
+ DWORD dwHelpContext) { return 0; }
+ STDMETHOD(SetMops)(THIS_
+ UINT index, BSTR bstrMops)
+ { return 0; }
+ STDMETHOD(SetTypeIdldesc)(THIS_
+ IDLDESC FAR* lpidldesc)
+ { return 0; }
+ STDMETHOD(LayOut)(THIS) { return 0; }
+
+// Inherited Pure methods
+ virtual TIPERROR GetMemberName(HMEMBER hmember, BSTRA *plstrName) = 0;
+ virtual TIPERROR GetDynTypeMembers(LPLPDYNTYPEMEMBERS lplpDynTypeMembers) = 0;
+ virtual TIPERROR GetDefnTypeBind(DEFN_TYPEBIND **pdfntbind) = 0;
+ virtual TIPERROR GetTypeFixups(LPLPTYPEFIXUPS lplpTypeFixups) = 0;
+ //virtual TYPEKIND GetTypeKind() = 0;
+#if 0
+ virtual TIPERROR CreateInst(LPLPVOID lplpObj) = 0;
+#endif
+ virtual TIPERROR Reset() = 0;
+ // Method to remove cycle problem within a project.
+ virtual VOID RemoveInternalRefs()=0;
+
+ // inherited methods for bringing needed modules to runnable state.
+ virtual TIPERROR BeginDepIteration(TINODE **pptinode,
+ TINODE ***ppptinodeCycleMax) = 0;
+ virtual VOID EndDepIteration() = 0;
+ virtual TIPERROR GetNextDepTypeInfo(DYNTYPEINFO
+ **ppdtiNext) = 0;
+ virtual BOOL IsReady() = 0;
+ virtual TIPERROR AllDepReady() = 0;
+ virtual TIPERROR NotReady() = 0;
+
+ // Introduced Methods
+ virtual TIPERROR Read() = 0;
+ virtual TIPERROR Write() = 0;
+ virtual TIPERROR WriteToStream(STREAM *pstrm) = 0;
+ virtual LPOLESTR SzTypeIdofTypeInfo() = 0;
+ virtual TIPERROR EnsurePartsRead() = 0;
+ virtual TIPERROR GetEmbeddedTypeInfo(LPOLESTR szTypeId,
+ LPLPTYPEINFO pptinfo) = 0;
+
+ virtual VOID ReleasePublicResources() = 0;
+
+ nonvirt VOID AddPartnerRef();
+ nonvirt VOID ReleasePartner();
+
+ nonvirt STL_TYPEINFO *PstltiPartner();
+ nonvirt VOID SetPstltiPartner(STL_TYPEINFO *pstlti);
+
+// Overridden Inherited methods
+ // virtual TIPERROR GetIcon(DWORD *pdw);
+ // virtual TIPERROR GetDocumentation(BSTR *plstr);
+
+ // virtual DWORD GetHelpContext();
+ // virtual TIPERROR GetHelpFileName(BSTR *plstrFile);
+/*****
+ These are disabled because our implementation make them confusing
+ since they change information stored in the TypeLib directory and
+ so require that the directory be saved
+ virtual TIPERROR SetDocumentation(LPSTR szDoc);
+ virtual TIPERROR SetHelpContext(ULONG ulHelpIndex);
+*****/
+
+
+
+// Introduced methods
+ nonvirt VOID AddInternalRef();
+ nonvirt VOID RelInternalRef();
+ nonvirt BOOL IsModified();
+ nonvirt TIPERROR SetModified(BOOL isModified);
+ nonvirt UINT GetIndex();
+
+ virtual VOID PrepareForDestruction();
+ nonvirt GenericTypeLibOLE *PgtlibOleContaining();
+ nonvirt TIPERROR OpenStream(STREAM **ppstrm, STREAM_OPEN_MODE som);
+
+#if ID_DEBUG
+ nonvirt CHAR *SzDebName();
+ nonvirt ULONG CRefs();
+ nonvirt ULONG CInternalRefs();
+#endif // ID_DEBUg
+
+protected:
+ STL_TYPEINFO();
+ virtual ~STL_TYPEINFO(); // Invoked by STAT_TYPELIB to delete TYPEINFO
+ nonvirt VOID SetHTEntry(HTENTRY hte);
+ nonvirt VOID SetContainingTypeLib(GenericTypeLibOLE *pgtlibole);
+ nonvirt TIPERROR GetLcid(LCID *plcid);
+ virtual TIPERROR CommitChanges() = 0;
+
+#if ID_DEBUG
+ CHAR m_szDebName[DEBNAMESIZE];
+#endif // ID_DEBUG
+
+private:
+ BOOL m_isModified;
+ GenericTypeLibOLE *m_pgtliboleContainer;
+ ULONG m_cRefs;
+ ULONG m_cInternalRefs;
+ HTENTRY m_hte;
+
+ STL_TYPEINFO *m_pstltiPartner;
+
+#ifdef STL_TYPEINFO_VTABLE
+#pragma VTABLE_EXPORT
+#endif
+};
+
+
+/***
+*PUBLIC STL_TYPEINFO::STL_TYPEINFO
+*Purpose:
+* STL_TYPEINFO constructor
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+inline STL_TYPEINFO::STL_TYPEINFO()
+{
+ m_cRefs = 1;
+ m_isModified = FALSE;
+ m_cInternalRefs = 0;
+ m_pgtliboleContainer = NULL;
+ m_hte = HTENTRY_Nil;
+
+#if ID_DEBUG
+ m_szDebName[0] = 0;
+#endif // ID_DEBUG
+
+ m_pstltiPartner = NULL;
+}
+
+
+/***
+*PUBLIC STL_TYPEINFO::GetIndex
+*Purpose:
+* Returns the index of this type in its containing lib.
+* NOTE: Assumes that the hte members it the correct index!
+*
+*Entry:
+*
+*Exit:
+* Index of type in lib.
+*
+***********************************************************************/
+
+inline UINT STL_TYPEINFO::GetIndex()
+{
+ return (UINT)m_hte;
+}
+
+
+
+/***
+*PUBLIC STL_TYPEINFO::PgtlibOleContaining
+*Purpose:
+* Return the GenericTypeLibOLE which contains the given TypeInfo --
+* however do not increment the reference count cos otherwise
+* this would create a circular reference.
+* Asserts if typelib null.
+*
+*Entry:
+* None
+*
+*Exit:
+* GenericTypeLibOLE *
+*
+***********************************************************************/
+
+inline GenericTypeLibOLE *STL_TYPEINFO::PgtlibOleContaining()
+{
+ DebAssert(m_pgtliboleContainer != NULL, "No containing lib.");
+
+ return m_pgtliboleContainer;
+}
+
+
+
+/***
+*PUBLIC STL_TYPEINFO::OpenStream - Open the STREAM for this TYPEINFO.
+*Purpose:
+* Return a STREAM opened in the specified mode on this TYPEINFO.
+*
+*Entry:
+* som - The access mode in which the stream is to be opened. See
+* DOCFILE_STREAM::Open for details.
+*
+*Exit:
+* TIPERROR
+*
+***********************************************************************/
+
+inline TIPERROR STL_TYPEINFO::OpenStream(STREAM **ppstrm, STREAM_OPEN_MODE som)
+{
+ return m_pgtliboleContainer->OpenTypeStream(m_hte, som, ppstrm);
+}
+
+
+/***
+*PUBLIC STL_TYPEINFO::PstltiPartner
+*Purpose:
+* Returns the typeinfo of the partner for this dual interface.
+*
+*Entry:
+* None.
+*
+*Exit:
+* returns the pointer to the partner.
+*
+*Errors:
+* None.
+***********************************************************************/
+
+inline STL_TYPEINFO *STL_TYPEINFO::PstltiPartner()
+{
+ return m_pstltiPartner;
+}
+
+
+/***
+*PUBLIC STL_TYPEINFO::SetPstltiPartner
+*Purpose:
+* Sets the typeinfo of the partner for this dual interface.
+*
+*Entry:
+* pstlti - the partner to set
+*
+*Exit:
+* None.
+*
+*Errors:
+* None.
+***********************************************************************/
+
+inline VOID STL_TYPEINFO::SetPstltiPartner(STL_TYPEINFO *pstlti)
+{
+ m_pstltiPartner = pstlti;
+}
+
+
+/***
+*PUBLIC STL_TYPEINFO::AddPartnerRef
+*Purpose:
+* Used to keep the number of references of the partners of a dual
+* interface in sync.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+*Errors:
+* None.
+***********************************************************************/
+
+inline VOID STL_TYPEINFO::AddPartnerRef()
+{
+ DebAssert(m_pstltiPartner != NULL, "Not a dual interface");
+
+ m_pstltiPartner->m_cInternalRefs++;
+}
+
+
+/***
+*PUBLIC STL_TYPEINFO::ReleasePartner
+*Purpose:
+* Used to keep the number of references of the partners of a dual
+* interface in sync.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+*Errors:
+* None.
+***********************************************************************/
+
+inline VOID STL_TYPEINFO::ReleasePartner()
+{
+ STL_TYPEINFO *pstlti = PstltiPartner();
+
+ DebAssert(pstlti != NULL, "Not a dual interface");
+
+ // We're a friend of STL_TYPEINFO.
+ DebAssert(pstlti->m_cInternalRefs > 0, "Bad refcount.");
+
+ pstlti->m_cInternalRefs--;
+
+ // If we have no more references, call the REAL ReleaseInternalRef
+ // and it will destroy this instance for us. Since the refcount
+ // is zero, it won't call ReleasePartner on our partner.
+ //
+ if ((pstlti->m_cInternalRefs + pstlti->m_cRefs) == 0) {
+ pstlti->RelInternalRef();
+ }
+}
+
+
+/***
+*PUBLIC STL_TYPEINFO::AddInternalRef
+*Purpose:
+*
+*Entry:
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+inline VOID STL_TYPEINFO::AddInternalRef()
+{
+ DebAssert(m_pgtliboleContainer != NULL, "AddInternalRef");
+ m_cInternalRefs++;
+
+ // Check to see if we're a dual interface, if so, increment
+ // the count on our partner.
+ //
+ if (PstltiPartner() != NULL) {
+ AddPartnerRef();
+ }
+}
+
+
+/***
+*PUBLIC STL_TYPEINFO::SetHTEntry
+*Purpose:
+* Inform a TYPEINFO instance of its HTEntry in its containing TypeLib
+*Entry:
+* HTENTRY
+*Exit:
+* None.
+*
+***********************************************************************/
+
+inline VOID STL_TYPEINFO::SetHTEntry(HTENTRY hte)
+{
+ m_hte = hte;
+}
+
+
+/***
+*PUBLIC STL_TYPEINFO::IsModified
+*Purpose:
+* Returns boolean indicating whether or not the TYPEINFO has been modified
+*
+*Entry:
+* None.
+*
+*Exit:
+* returns bool
+*
+***********************************************************************/
+
+inline BOOL STL_TYPEINFO::IsModified()
+{
+ return m_isModified;
+}
+
+
+#if ID_DEBUG
+/***
+*PUBLIC STL_TYPEINFO::SzDebName, CRefs, CInternalRefs
+*Purpose:
+* Memory leak reporting accessors.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+inline CHAR *STL_TYPEINFO::SzDebName()
+{
+ return m_szDebName;
+}
+
+inline ULONG STL_TYPEINFO::CRefs()
+{
+ return m_cRefs;
+}
+
+inline ULONG STL_TYPEINFO::CInternalRefs()
+{
+ return m_cInternalRefs;
+}
+#endif // ID_DEBUG
+
+#endif // ! stltinfo_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/strdcl.c b/private/oleauto/src/typelib/strdcl.c
new file mode 100644
index 000000000..451894bb4
--- /dev/null
+++ b/private/oleauto/src/typelib/strdcl.c
@@ -0,0 +1,2 @@
+void *rgMacStrdcl[]={
+(void *)0 };
diff --git a/private/oleauto/src/typelib/stream.hxx b/private/oleauto/src/typelib/stream.hxx
new file mode 100644
index 000000000..49fadbbee
--- /dev/null
+++ b/private/oleauto/src/typelib/stream.hxx
@@ -0,0 +1,188 @@
+/***
+*stream.hxx - stub stream class for Silver.
+*
+* Copyright (C) 1990, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* To provide a simple definition of streams
+*
+*****************************************************************************/
+
+#ifndef STREAM_HXX_INCLUDED
+#define STREAM_HXX_INCLUDED
+
+#include "stdio.h"
+#include "cltypes.hxx"
+#include "mem.hxx"
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szSTREAM_HXX)
+#define SZ_FILE_NAME g_szSTREAM_HXX
+#endif
+
+
+#define SwapShort(us) (((us & 0xFF) << 8) | (us >> 8))
+
+enum STREAM_OPEN_MODE {
+ SOM_Read,
+ SOM_Write,
+ SOM_Append
+};
+
+/***
+*class STREAM : Stream Abstract Class
+*Purpose:
+* Simple stream class with read, write, getpos and setpos methods.
+*
+*CONSIDER:
+* To reduce the overhead of individual Read/Write operations,
+* the virtual Read/Write functions could be modified to do
+* reading/writing to a buffer. When the buffer was empty/full
+* then they could invoke virtual functions that do the actual
+* device I/O.
+***********************************************************************/
+
+class STREAM
+{
+public:
+ virtual TIPERROR Read(VOID *buffer, ULONG cbsize) = 0;
+ nonvirt TIPERROR ReadByte(BYTE *pb);
+ nonvirt TIPERROR ReadChar(CHAR *pb);
+ nonvirt TIPERROR ReadShort(SHORT *ps);
+ nonvirt TIPERROR ReadUShort(USHORT *pus);
+ nonvirt TIPERROR ReadLong(LONG *pl);
+ nonvirt TIPERROR ReadULong(ULONG *pul);
+ nonvirt TIPERROR ReadSz(LPOLESTR *sz);
+
+ virtual TIPERROR ReadTextLine(XSZ szLine, UINT cchMax) = 0;
+
+ virtual TIPERROR Write(const VOID *buffer, ULONG cbsize) = 0;
+ nonvirt TIPERROR WriteByte(BYTE b);
+ nonvirt TIPERROR WriteChar(CHAR b);
+ nonvirt TIPERROR WriteShort(SHORT s);
+ nonvirt TIPERROR WriteUShort(USHORT us);
+ nonvirt TIPERROR WriteLong(LONG l);
+ nonvirt TIPERROR WriteULong(ULONG ul);
+ nonvirt TIPERROR WriteSz(LPCOLESTR sz);
+
+ virtual TIPERROR GetPos(LONG *plPos) = 0;
+ virtual TIPERROR SetPos(LONG lPos) = 0;
+
+ // Note: Release must be overridden by derived classes since
+ // there is no virtual destructor
+ virtual TIPERROR Release() = 0;
+
+protected:
+ ~STREAM(); // Included so clients can't use delete on a stream
+ STREAM(); // Included to avoid warning
+
+#ifdef STREAM_VTABLE
+#pragma VTABLE_EXPORT
+#endif
+};
+
+inline STREAM::~STREAM() {} // Included so clients can't use delete on a stream
+inline STREAM::STREAM() {} // Included to avoid warning
+
+
+/***
+*class SEEKSTREAM : Abstract class adding seek methods to STREAM
+*Purpose:
+* Derivative of STREAM class that adds seek methods.
+***********************************************************************/
+
+class SEEKSTREAM : public STREAM
+{
+public:
+// Inherited pure functions
+ virtual TIPERROR Read(VOID *buffer, ULONG cbsize) = 0;
+ virtual TIPERROR Write(const VOID *buffer, ULONG cbsize) = 0;
+ virtual TIPERROR SetPos(LONG lPos) = 0;
+ virtual TIPERROR GetPos(LONG *plPos) = 0;
+ virtual TIPERROR Release() = 0;
+
+// Introduced pure functions
+ virtual TIPERROR Seek(LONG lPosition) = 0; // lPosition always > 0.
+ virtual TIPERROR SeekFromEnd(LONG lPosition) = 0;// lPosition always > 0.
+ virtual TIPERROR SeekFromCur(LONG lPosition) = 0;// lPosition any value.
+
+#ifdef SEEKSTREAM_VTABLE
+#pragma VTABLE_EXPORT
+#endif
+};
+
+
+
+/***
+*Prototypes for byte swapping helpers
+*
+***********************************************************************/
+
+void SwapShortArray(void * pvArray, UINT cShorts);
+void SwapLongArray(void * pvArray, UINT cLongs);
+UINT SwapStruct(void * pvArray, SZ szFormat);
+void SwapStructArray(void * pvArray, UINT cStructs, SZ szFormat);
+
+
+
+/***
+*Read - read data from the stream.
+*Purpose:
+* These functions read data from the stream. Either a byte, word,
+* long, or user-specified amount of data.
+*
+*Exit:
+* Returns number of bytes written, which is always the
+* same as the numberof bytes requested.
+*
+***********************************************************************/
+
+
+
+inline TIPERROR STREAM::ReadChar(CHAR *pb)
+{
+ return ReadByte((BYTE *)pb);
+}
+
+inline TIPERROR STREAM::ReadShort(SHORT *ps)
+{
+ return ReadUShort((USHORT *)ps);
+}
+
+inline TIPERROR STREAM::ReadLong(LONG * pl)
+{
+ return ReadULong((ULONG *)pl);
+}
+
+
+/***
+*PUBLIC STREAM::Write - write data to the stream
+*Purpose:
+* These function write data to the stream. Bytes, words, longs,
+* or any length of data can be written.
+*
+*Exit:
+* Returns number of bytes written, which is always the number of
+* bytes requested.
+*
+***********************************************************************/
+
+inline TIPERROR STREAM::WriteChar(CHAR b)
+{
+ return WriteByte((BYTE)b);
+}
+
+inline TIPERROR STREAM::WriteShort(SHORT s)
+{
+ return WriteUShort((USHORT)s);
+}
+
+inline TIPERROR STREAM::WriteLong(LONG l)
+{
+ return WriteULong((ULONG)l);
+}
+
+
+#endif // !STREAM_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/switches.hxx b/private/oleauto/src/typelib/switches.hxx
new file mode 100644
index 000000000..144321685
--- /dev/null
+++ b/private/oleauto/src/typelib/switches.hxx
@@ -0,0 +1,457 @@
+/***
+*switches.hxx - Compile switches for Silver
+*
+* Copyright (C) 1990, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file contains all the conditional compilation switches used
+* by Silver. For making version-specific changes, see version.hxx.
+*
+*Revision History:
+*
+* 24-Aug-90 petergo: Created
+* 10-May-91 ilanc: add ID_TEST
+* 14-Jun-91 petergo: Added Kanji/Unicode switches
+* 06-Mar-92 tomc: Added several switches, generate switches.inc
+* 10-Dec-92 ilanc: Added EI_OB and EI_OLE2.
+* 25-Jan-93 jeffrob: Corrected WIN32 HP_I386 and added OE_WIN32MT
+* 12-Mar-93 kazusy: Added BLD_FEVER switch
+* 05-May-93 jeffrob: Added ID_PROFILE
+* 04-Oct-93 w-marioc Added support for MIPS
+* 02-Jan-94 gburns: Added EI_VBARUN.
+*
+*****************************************************************************/
+
+#ifndef SWITCHES_HXX_INCLUDED
+#define SWITCHES_HXX_INCLUDED
+
+#include "ebvers.h"
+#include "version.hxx"
+
+// Need to define some constants to 0 that weren't defined or
+// mrc will choke on them:
+#ifndef BLD_WIN16
+#define BLD_WIN16 0
+#endif
+
+#ifndef BLD_WIN32
+#define BLD_WIN32 0
+#endif
+
+#ifndef BLD_WLM
+#define BLD_WLM 0
+#endif
+
+#ifndef BLD_MAC
+#define BLD_MAC 0
+#endif
+
+#ifndef BLD_FEVER
+#define BLD_FEVER 0
+#endif
+
+#ifndef HE_WIN32
+#define HE_WIN32 0 // [jwc] undone: Right now, mac os/2 toolset & NT toolset have
+#endif // differences that require source changes. This allows
+ // coexistance of both builds
+
+// Unlike ID_PROFILE, BLD_PROFILE indicates that the build was built with
+// profiling stubs (-Gh cl68 & c8/32) to collecting timing information.
+// Currently, this must be set by hand either in a special version.hxx or on the
+// compile line.
+#ifndef BLD_PROFILE
+#define BLD_PROFILE 0
+#endif
+
+
+// ID_TEST - This is used to surround test code that will not be
+// part of the released build. This is assumed to be equal ID_DEBUG.
+// However, in the test build (twinc7), ID_TEST is turned on, but ID_DEBUG
+// is off.
+//
+#ifndef ID_TEST
+ #define ID_TEST ID_DEBUG
+#endif
+
+
+// ID_PROFILE - This is used to surround test code that collects profiling
+// data. Currently, it is defined to equal ID_DEBUG but could be turned
+// on in the release build, if desired.
+//
+#ifndef ID_PROFILE
+ #define ID_PROFILE ID_DEBUG
+#endif
+
+
+// ID_SWAPTUNE - This is used to surround code that collects segment swapping info.
+// Currently, it is always set off, and must be set on by hand. This need
+// not be tied to either debug or release builds, so assume that code under
+// this switch could be turned on for either.
+#ifndef ID_SWAPTUNE
+ #define ID_SWAPTUNE 0
+#endif
+
+
+// HC switches: relate to the Host Compiler or Compiler version
+// Use this to accomodate syntactic differences between compilers
+//
+#if defined (_MSC_VER)
+#if (_MSC_VER >= 800)
+#define HC_MSC8
+
+// Both these are versions of C8 or C9
+#ifdef _M_M68K
+#define HC_MSC68K
+#elif defined (_M_MPPC)
+#define HC_MSCPPC
+#else
+// REVIEW: Probably need to check for C8/32 vs. C8/16
+#define HC_MSC832
+#endif
+
+#else
+#if (_MSC_VER == 700)
+#define HC_MSC7
+#else
+#define HC_MSC6
+#endif
+#endif
+
+#else
+// UNDONE OA95: rc uses a c-preprocessor that doesn't define _MSC_VER...
+// need to figure out what to do here.
+//#error Unsupported Compiler!
+#endif
+
+
+
+//OE switches: relate to the Operating Environment, or
+//API set used by the program
+
+// If TRUE, OE_WIN indicates we are using one of the variant of the
+// Windows API sets. This is set for all of our released versions,
+// except the native Mac build.
+// It not set only for the OS/2 internal build, or for the DOS tools build.
+// It is set for the Mac WLM build (provided for WLM clients).
+//
+
+#if BLD_WIN16 || BLD_WIN32 || BLD_WLM
+#define OE_WIN 1
+#else
+#define OE_WIN 0
+#define OE_WIN16 0
+#define OE_WIN32 0
+#define OE_WLM 0
+#define OE_WIN32S 0
+#define OE_WIN32F 0
+#define OE_NT 0
+#endif
+
+
+//If OE_WIN is set, exactly one of the following 3 switches is set,
+//indicate which variant of the Windows API is being used.
+
+#if OE_WIN
+
+#if BLD_WLM
+ #define OE_WLM 1
+ //Indicates we are running the Windows Library for the Mac.
+ //This should only be used for those few cases that depend on
+ //differences in function signatures between WLM.H and WINDOWS.H.
+#else
+ #define OE_WLM 0
+#endif
+
+#if BLD_WIN16
+ #define OE_WIN16 1
+ //Indicates we are using the Windows 3.0/3.1 API set. Should
+ //be used when using features specific to Windows 3.0/3.1. You
+ //can assume protected mode only with this switch; we never have
+ //and never will support Real mode Windows.
+#else
+ #define OE_WIN16 0
+#endif
+
+#if BLD_WIN32
+ #define OE_WIN32 1
+ //Indicates we are using the Win32 API set, on either NT or
+ //DOS. On for both Win32/NT, Win32/DOS, and Win32S.
+#else
+ #define OE_WIN32 0
+#endif
+
+#endif
+
+// If OE_WIN32 is set, the following switches indicate which subvariant
+// of the Win32 API is being used. These should be rarely needed,
+// if at all. NOTE: currently there are no builds which turns these
+// on.
+
+#if OE_WIN32
+ #define OE_WIN32S 0
+ //Indicates we are using the Win32S API subset.
+
+ #define OE_WIN32F 0
+ //Indicates we are using the full Win32 API, under either
+ //DOS or NT. Should be used to control use of APIs
+ //not in the Win32S subset.
+
+ #define OE_NT 0
+ //Indicates we are running under NT, as opposed to Win32/DOS.
+ //Should be used only to control NT specific features, like
+ //calling an NT API directly.
+
+ #define OE_WIN32MT 0
+ //Indicates we support multiple WIN32 threads within a single
+ //process. (Version 1.0 of OB only supports one thread so
+ //we've optimized some code paths with this in mind.)
+
+#endif
+
+// OE_RISC is used to specify if the portable engine code is to be used
+// instead of the intel specific assembly
+#ifndef OE_RISC
+ #define OE_RISC 0
+#endif
+
+//OS/2 is no longer a target in any of the builds.
+#define OE_OS2 0
+
+
+// OE_MAC indicates that we are targetting the Macintosh. This
+// is set for both the WLM build and the native Mac build.
+#if BLD_WLM || BLD_MAC
+#define OE_MAC 1
+#else
+#define OE_MAC 0
+#endif
+
+#if OE_MAC
+
+ // OE_MACAPI indicates that we are using the MacIntosh API. This is
+ // set whenever we are targetting the Mac and we aren't using WLM.
+ //
+#if BLD_MAC
+ #define OE_MACAPI 1
+#else
+ #define OE_MACAPI 0
+#endif
+
+ // Macintosh PowerPC environment is slightly different than the 68k
+ // environment. You should use this switch to control differences rather
+ // than HP_POWERPC because they are operating environment differences, not
+ // true hardware differences (unless, you're talking about asm or something)
+ // Besides, there may even be an NT on PowerPC, and then use of HP_POWERPC
+ // would be a big mistake.
+ //
+ // This indicates MAC API and PowerPC runtime environment
+#if defined (HC_MSCPPC)
+ #define OE_MACPPC 1
+ #define OE_MAC68K 0
+#else
+ #define OE_MACPPC 0
+ #define OE_MAC68K 1
+#endif
+
+#else
+ #define OE_MACAPI 0
+ #define OE_MAC68K 0
+ #define OE_MACPPC 0
+ #define ID_SWAPPABLE 0
+#endif
+
+
+// OE_DLL: True for versions in which Object Basic code is linked into a DLL.
+// When TRUE, host routines are in a separate DLL or EXE. For now,
+// this is only TRUE for Windows versions, but future Macintosh
+// versions will likely have this set TRUE.
+//
+#if (BLD_WIN16 || BLD_WIN32 || defined (OE_DLL)) && !defined (VBARUNBLD)
+ #define OE_DLL 1
+#else
+ #define OE_DLL 0
+#endif
+
+#if OE_MAC && !OE_MACPPC
+// all mac versions are swappable now
+ #define ID_SWAPPABLE 1
+#endif //OE_MAC
+
+// DOS build. (Probably should be called OE_DOS, but isn't.)
+// There is no dos build. This is always off.
+#define OE_REALMODE 0
+
+//HP switches: relate to the Hardware Processor.
+// The hardware switches indicate what kind of processor we are running
+// on. These switches should be used when you need to do specific thing
+// depending on the hardware you are running on.
+//
+// Switches that indicate general characteristic of the processor
+//(16bit/32bit, etc).
+// HP switches are for Hardware Processor. If possible, do not use
+// the specific processor type switches, but instead use the following
+// switches pertaining to various characteristic of the processors.
+// This makes porting to a new processor easier.
+//
+// HP_16BIT = Using a 16-bit register processor
+// HP_32BIT = Using a 32-bit register processor
+// HP_BIGENDIAN = Using a big-endian machine
+// least significant byte of a word is
+// at the highest byte address.
+// HP_MUSTALIGN = Must load/store objects from natural alignments.
+// indicates that 2byte words must be read/written
+// from a two byte boundary, 4byte words must be
+// read/written from a 4 byte boundary, 8 byte word
+// must be read/written from an 8 byte boundary.
+
+#if BLD_WIN16
+ #define HP_16BIT 1
+#else
+ #define HP_16BIT 0
+#endif
+
+#if BLD_WIN32 || BLD_MAC || BLD_WLM
+ #define HP_32BIT 1
+#else
+ #define HP_32BIT 0
+#endif
+
+#if BLD_MAC || BLD_WLM
+ #define HP_BIGENDIAN 1
+#else
+ #define HP_BIGENDIAN 0
+#endif
+
+#if BLD_MAC || BLD_WLM
+ #define HP_MUSTALIGN 0
+#endif
+
+// Switches that indicate the exact chip family:
+// (It is preferable to use the above switches since they are more
+// general than the following switches.)
+//
+// HP_I286 = Intel 286 AND ABOVE, running in 16 bit mode
+// --- -----
+// HP_I386 = Intel 386 and above, running in 32 bit mode
+// HP_M68000 = Motorola 680x0
+// HP_R4000 MIPS = R4000
+// HP_ALPHA = DEC/AXP
+// HP_SPARC = SPARC
+//
+
+#if BLD_WIN16
+#define HP_I286 1
+#else
+#define HP_I286 0
+#endif
+
+#if BLD_WIN32
+
+#ifdef _M_MRX000
+#define HP_ALPHA 0
+#define HP_R4000 1
+#define HP_I386 0
+#else
+#ifdef _M_ALPHA
+#define HP_ALPHA 1
+#define HP_R4000 0
+#define HP_I386 0
+#else
+#define HP_ALPHA 0
+#define HP_R4000 0
+#define HP_I386 1
+#endif // _M_ALPHA_
+#endif // _M_MRX000
+
+#else
+#define HP_ALPHA 0
+#define HP_R4000 0
+#define HP_I386 0
+#endif // BLD_WIN32
+
+#if BLD_MAC || BLD_WLM
+#ifdef _M_MPPC
+#define HP_POWERPC 1
+#define HP_M68000 0
+#else
+#define HP_POWERPC 0
+#define HP_M68000 1
+#endif
+
+#else
+#define HP_POWERPC 0
+#define HP_M68000 0
+#endif
+
+#define HP_SPARC 0
+
+// The following switches distinguish between an OB specific build,
+// a build of a run-time only version of OB, and an OLE2 "generic" build.
+//
+#undef EI_OB
+#undef EI_OLE
+#undef EI_VBARUN
+
+#define EI_VBA 1 // This differentiates between VBA and hosts which
+ // may use VBA header files.
+
+// Runtime switches:
+#ifdef OLEBLD
+ #define EI_OB 0
+ #define EI_OLE 1
+ #define EI_VBARUN 0
+ #define EI_VBARUN_VB 0
+#else
+ #define EI_OLE 0
+ #define EI_OB 1
+#if defined (VBARUNBLD)
+ // Build VB version of runtime.
+ #define EI_VBARUN 1
+ #define EI_VBARUN_VB 1
+#else
+ // Build IDE.
+ #define EI_VBARUN 0
+ #define EI_VBARUN_VB 0
+#endif
+#endif
+
+
+// Base processor alignment values.
+// HP_ALIGNMENT is used is the sheapmgr to align data. Currently non-risc
+// set to 1.
+// HP_ALIGNMENT_MAX is used by OB in conjunction with the g_rgcbAlignment table
+// (in clutil.cxx) as a 'capping' value - used by typelib when laying out
+// a typeinfo.
+//
+#if OE_RISC
+#if HP_R4000 || HP_POWERPC || HP_ALPHA
+#define HP_ALIGNMENT 8
+#define HP_ALIGNMENT_MAX 8
+#elif HP_I386
+#define HP_ALIGNMENT 4
+#define HP_ALIGNMENT_MAX 4
+#else
+#error !Unsupported Platform -- [Add Processor Alignment Value here.]
+#endif
+
+#else // !OE_RISC
+#define HP_ALIGNMENT 1
+
+#if HP_I286
+#define HP_ALIGNMENT_MAX 1
+#elif HP_M68000
+#define HP_ALIGNMENT_MAX 2
+#elif HP_I386
+#define HP_ALIGNMENT_MAX 4
+#else
+#error !Unsupported Platform
+#endif
+
+#endif // !OE_RISC
+
+
+// Switches for code system.
+#define FV_UNICODE 0 // No unicode char set
+
+#endif // !SWITCHES_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/sysutils.h b/private/oleauto/src/typelib/sysutils.h
new file mode 100644
index 000000000..16e3e83fa
--- /dev/null
+++ b/private/oleauto/src/typelib/sysutils.h
@@ -0,0 +1,13 @@
+/*==========================================================================*
+ | Copyright: (c) 1992, 1993 Microsoft Corporation, all rights reserved.
+ | Information Contained Herin is Proprietary and Confidential.
+ *==========================================================================*/
+
+#ifndef _SYSUTILS
+#define _SYSUTILS
+
+#if OE_MAC
+ #define MacEnvHasAliasMgr() 1
+#endif //OE_MAC
+
+#endif // _SYSUTILS
diff --git a/private/oleauto/src/typelib/tdata.hxx b/private/oleauto/src/typelib/tdata.hxx
new file mode 100644
index 000000000..e0e3c7df8
--- /dev/null
+++ b/private/oleauto/src/typelib/tdata.hxx
@@ -0,0 +1,1372 @@
+/***
+*tdata.hxx - TYPE_DATA header file
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This class maintains listheads to threaded DEFNs for member
+* definitions. Has private instance of BLK_MGR to manage
+* block of DEFNs.
+* List tails are also maintained since when members are always
+* added to the *end* of each list (aka appended).
+*
+*Revision History:
+*
+* 24-Feb-91 ilanc: Created.
+* [01] 04-Mar-91 ilanc: Added HTYPE_DEFN
+* [02] 10-Mar-91 ilanc: Added bit to VAR_DEFN::varkind (for locals/formals).
+* [03] 15-Mar-91 ilanc: FUNC_TYPE_DEFN tag --> ftdefn
+* [04] 23-Jan-92 davebra: added EXMGR_FUNCDEFN member to FUNC_DEFN
+* [05] 31-Jan-92 stevenl: reorganized DEFN hierarchy, modified DEFN structs
+* [06] 28-Feb-92 ilanc: added public Pdtroot() method:
+* Clients can get at containing TYPEINFO
+* by going: TYPE_DATA::Pdtroot()->Pgdtinfo()
+* [07] 03-Mar-92 ilanc: added list count members and accessor meths.
+* [08] 10-Mar-92 davebra: added friend EXMGR::AllocVarDefn to TYPE_DATA
+* [09] 18-Mar-92 ilanc: fixed release def of DebShowFuncDefn.
+* [10] 19-Mar-92 ilanc: Modified BIND_DESC (1-1 mapping to members now).
+* [11] 03-Apr-92 ilanc: GetAdded VardesckindOfHvdefn, VAR_DEFN::Ptdefn()
+* [12] 05-Apr-92 martinc: Moved the definition of TYPE_DEFN::IsArray();
+* named the formerly anonymos struct in BIND_DESC to m_varaccess
+* [13] 12-Apr-92 ilanc: TYPE_DATA::DebCheckState decl and def.
+* [14] 24-Apr-92 ilanc: Added masses of struct inline accessor meths.
+* [15] 29-Apr-92 ilanc: Added HfdefnOfHmember().
+* [16] 30-Apr-92 stevenl: Changed DEFN initializers.
+* [17] 05-May-92 stevenl: Changed DEFN initializers again.
+* [18] 14-May-92 w-peterh: moved defns to defn.hxx
+* [19] 28-May-92 stevenl: Changed friend declarations in TDATA defn.
+* [20] 18-Jun-92 w-peterh: added RecTypeDefn list
+* [21] 02-Jul-92 w-peterh: merged data member/type lists
+* [22] 18-Jan-93 w-peterh: use TIPERROR instead of SCODE
+* 02-Feb-93 w-peterh: added IndexOfFuncName
+* 12-Feb-93 w-peterh: added m_htdefnAlias, ImpleType, RefType funcs
+* 23-Feb-93 rajivk : Support for Predeclared Identifier
+* 17-Mar-93 w-jeffc: added TYPE_DATA Lock & Unlock
+* 30-Apr-93 w-jeffc: made DEFN data members private; added Swap*defn functions
+*
+*Implementation Notes:
+* A DEFN is the struct used for the internal storage of an INFO
+* The DEFN hierarchy more or less mirrors the MEMBERINFO hierarchy:
+*
+* DEFN
+* |
+* ---------------------------
+* | |
+* VAR_DEFN MEMBER_DEFN |
+* | | | |
+* ----------| | -------------
+* | ----------- |
+* | | FUNC_DEFN
+* PARAM_DEFN MBR_VAR_DEFN |
+* VIRTUAL_FUNC_DEFN
+*
+* A DEFN really only has a single link field (to simplify
+* list manipulation) and an hlnam field.
+*
+* All of the DEFN structs (except MEMBER_DEFN) inherit from the
+* DEFN struct. In addition, those structs that represent object
+* members (i.e. MBR_VAR_DEFN, FUNC_DEFN, and VIRTUAL_FUNC_DEFN)
+* also inherit from MEMBER_DEFN. VAR_DEFN and PARAM_DEFN only
+* inherit from DEFN.
+*
+* This design allows us to share the commonalities between locals,
+* params and data members (member variables) and in addition, treat
+* params like locals (where appropriate).
+*
+*****************************************************************************/
+
+#ifndef TDATA_HXX_INCLUDED
+#define TDATA_HXX_INCLUDED
+
+#include "clutil.hxx"
+#include "defn.hxx" // also includes rtarray.h, exstruct.hxx, cltypes.hxx
+
+#include "blkmgr.hxx"
+
+#include "dstrmgr.hxx"
+
+
+class IMPMGR;
+class NAMMGR;
+class DYN_TYPEROOT; // #include "dtinfo.hxx"
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szTDATA_HXX)
+#define SZ_FILE_NAME g_szTDATA_HXX
+#endif
+
+// Definitions for structs used by DYN_TYPEBIND implementation.
+//
+enum BIND_KIND {
+ BKIND_Error, // look at returned TIPERROR for more info.
+ BKIND_NoMatch,
+ BKIND_OneVarMatch, // matched variable
+ BKIND_FuncMatch, // matche function
+ BKIND_DynTypeBindMatch, // matched module/class
+ BKIND_ProjTypeBindMatch, // matched project
+ BKIND_NestedTypeBindMatch, // matched nested type
+ BKIND_WrongArity, // UNUSED: Matched but wrong arity.
+ BKIND_TypeInfoMatch, // matched type: only typeinfo valid,
+ // no typebind.
+ BKIND_ImplicitAppobjMatch, // Matched an implicit appobj -- i.e.
+ // one that wasn't actually mentioned
+ // in the program text. Client
+ // should treat it like a OneVarMatch
+ // and extract the typebind from
+ // the VAR_DEFN and rebind.
+};
+
+TIPERROR EquivTypeDefnsIgnoreByRef(TYPE_DATA *ptdata1,
+ BOOL fSimple1,
+ sHTYPE_DEFN htdefn1,
+ TYPE_DATA *ptdata2,
+ BOOL fSimple2,
+ sHTYPE_DEFN htdefn2,
+ WORD wFlags,
+ BOOL *pfEqual,
+ BOOL fIgnoreByRef);
+
+BOOL IsTypeBasicIntrinsic(TYPEDESCKIND tdesckind);
+
+#define ARITY_Unknown ~(USHORT)0
+
+
+/***
+*class TYPE_DATA - 'tdata': Type descriptor class.
+*Purpose:
+* The class implements TYPE_DATA
+*
+***********************************************************************/
+
+class TYPE_DATA
+{
+ friend class DYN_TYPEMEMBERS;
+
+
+public:
+ nonvirt TIPERROR Init(SHEAP_MGR *psheapmgr, DYN_TYPEROOT *pdtroot);
+
+#if ID_TEST
+ // Only used in test code.
+ nonvirt VOID Release();
+#endif // ID_TEST
+
+ ~TYPE_DATA();
+ TYPE_DATA();
+
+ nonvirt SHEAP_MGR *Psheapmgr() const;
+
+ nonvirt VOID Compact();
+ nonvirt UINT CMeth() const;
+ nonvirt UINT CDataMember() const;
+ nonvirt UINT CBase() const;
+ nonvirt UINT CNestedType() const;
+
+ nonvirt UINT CAvailMeth() const;
+ nonvirt HFUNC_DEFN HfdefnFirstMeth() const;
+ nonvirt HFUNC_DEFN HfdefnFirstAvailMeth();
+ nonvirt HFUNC_DEFN HfdefnNextAvailMeth(HFUNC_DEFN hfdefn) const;
+
+ nonvirt HDEFN HdefnFirstDataMbrNestedType() const;
+ nonvirt HVAR_DEFN HvdefnFirstBase() const;
+ nonvirt HTYPE_DEFN HtdefnAlias() const;
+ nonvirt BOOL IsSimpleTypeAlias() const;
+ nonvirt VOID SetIsSimpleTypeAlias(BOOL isSimpleType);
+ nonvirt UINT SizeOfTypeDefn(HTYPE_DEFN htdefn) const;
+
+ // Locking functions
+ nonvirt inline VOID Lock() { m_blkmgr.Lock(); }
+ nonvirt inline VOID Unlock() { m_blkmgr.Unlock(); }
+
+ // DESC Functions
+ nonvirt TIPERROR GetFuncDesc(UINT index, FUNCDESC **ppfuncdesc);
+ nonvirt TIPERROR AddFuncDesc(UINT index,
+ FUNCDESC *pfuncdesc,
+ HFUNC_DEFN *phfdefn = NULL);
+
+ nonvirt TIPERROR GetVarDesc(UINT index, VARDESCA **ppvardesc);
+ nonvirt TIPERROR AllocTypeDefnOfTypeDesc(TYPEDESC *ptdesc,
+ UINT cb,
+ sHTYPE_DEFN *phtdefn,
+ BOOL fAllowCoClass,
+ BOOL * pfIsSimpleType);
+ nonvirt TIPERROR AllocTypeDescOfTypeDefn(HTYPE_DEFN htdefn,
+ BOOL isSimpleType,
+ TYPEDESC *ptdesc);
+ nonvirt TIPERROR AddVarDesc(UINT index,
+ VARDESCA *pvardesc,
+ HVAR_DEFN *phvdefn = NULL);
+ nonvirt TIPERROR GetVarDescOfHvdefn(HVAR_DEFN hvdefn,
+ VARDESCA **ppvardesc);
+ nonvirt TIPERROR GetFuncDescOfHfdefn(HFUNC_DEFN hfdefn,
+ FUNCDESC **ppfuncdesc);
+
+ nonvirt TIPERROR SetTypeDefnAlias(TYPEDESC *ptdesc);
+ nonvirt TIPERROR AddImplType(UINT index, HREFTYPE hreftype);
+ nonvirt TIPERROR GetRefTypeOfImplType(UINT index, HREFTYPE *phreftype);
+ nonvirt TIPERROR SetImplTypeFlags(UINT index, INT impltypeflags);
+ nonvirt TIPERROR GetImplTypeFlags(UINT index, INT *pimpltypeflags);
+
+ nonvirt TIPERROR GetNames(MEMBERID memid,
+ BSTR *rgbstrNames,
+ UINT cNameMax,
+ UINT *pcName);
+ nonvirt TIPERROR SetDllEntryDefn(UINT index, HDLLENTRY_DEFN hdllentrydefn);
+ nonvirt TIPERROR GetDllEntryDefn(UINT index, HDLLENTRY_DEFN *phdllentrydefn);
+ nonvirt TIPERROR SetFuncAndParamNames(UINT index,
+ LPOLESTR *rgszNames,
+ UINT cNames);
+ nonvirt TIPERROR SetFuncAndParamNamesOfHfdefn(HFUNC_DEFN hfdefn,
+ LPOLESTR *rgszNames,
+ UINT cNames);
+ nonvirt TIPERROR SetVarName(UINT index, LPSTR szName);
+ nonvirt HFUNC_DEFN GetFuncDefnForDoc(UINT index);
+ nonvirt TIPERROR SetFuncDocString(UINT index, LPSTR szDocString);
+ nonvirt TIPERROR SetVarDocString(UINT index, LPSTR szDocString);
+ nonvirt TIPERROR SetFuncHelpContext(UINT index, DWORD dwHelpContext);
+ nonvirt TIPERROR SetVarHelpContext(UINT index, DWORD dwHelpContext);
+ nonvirt TIPERROR GetDocumentation(MEMBERID memid,
+ BSTR FAR*lpbstrName,
+ BSTR FAR*lpbstrDocString,
+ DWORD FAR*lpdwHelpContext);
+ nonvirt TIPERROR GetDocumentationOfFuncName(LPOLESTR szFuncName,
+ BSTR FAR *lpbstrDocString,
+ DWORD FAR *lpdwHelpContext,
+ UINT *puIndex);
+
+ nonvirt TIPERROR UpdateDocStrings();
+ nonvirt PARAM_DEFN *QparamdefnOfIndex(HPARAM_DEFN hparamdefn, UINT i) const;
+ nonvirt VOID RemMbrVarDefn(HMBR_VAR_DEFN hmvdefn);
+ nonvirt VOID RemFuncDefn(HFUNC_DEFN hfdefn);
+ nonvirt VOID RemParamDefn(HPARAM_DEFN hparamdefn,
+ sHDEFN *phdefnFirst,
+ sHDEFN *phdefnLast);
+ nonvirt VOID RemRecTypeDefn(HRECTYPE_DEFN hrtdefn);
+ nonvirt DEFN *QdefnOfHdefn(HDEFN hdefn, UINT oChunk=0) const;
+ nonvirt VAR_DEFN *QvdefnOfHvdefn(HVAR_DEFN hvdefn, UINT oChunk=0) const;
+ nonvirt PARAM_DEFN *QparamdefnOfHparamdefn(HPARAM_DEFN hparamdefn, UINT oChunk=0) const;
+ nonvirt FUNC_DEFN *QfdefnOfHfdefn(HFUNC_DEFN hfdefn, UINT oChunk=0) const;
+ nonvirt VIRTUAL_FUNC_DEFN *QvfdefnOfHvfdefn(HVIRTUAL_FUNC_DEFN hfdefn, UINT oChunk=0) const;
+ nonvirt MBR_VAR_DEFN *QmvdefnOfHmvdefn(HMBR_VAR_DEFN hmvdefn, UINT oChunk=0) const;
+ nonvirt MEMBER_DEFN *QmdefnOfHmdefn(HMEMBER_DEFN hmdefn, UINT oChunk=0) const;
+ nonvirt TYPE_DEFN *QtdefnOfHtdefn(HTYPE_DEFN htdefn, UINT oChunk=0) const;
+ nonvirt RECTYPE_DEFN *QrtdefnOfHrtdefn(HRECTYPE_DEFN hrtdefn, UINT oChunk=0) const;
+ nonvirt FUNC_TYPE_DEFN *QftdefnOfHftdefn(HFUNC_TYPE_DEFN hftdefn,
+ UINT oChunk=0) const;
+
+ nonvirt BOOL HasOrdinalOfHdllentrydefn(HDLLENTRY_DEFN hdllentrydefn) const;
+ nonvirt HLNAM DllNameOfHdllentrydefn(HDLLENTRY_DEFN hdllentrydefn) const;
+ nonvirt USHORT DllOrdinalOfHdllentrydefn(HDLLENTRY_DEFN hdllentrydefn) const;
+ nonvirt HLNAM DllEntryOfHdllentrydefn(HDLLENTRY_DEFN hdllentrydefn) const;
+ nonvirt TIPERROR AllocDllentrydefnByName(HLNAM hlnamDllModule,
+ LPSTR szEntryName,
+ HDLLENTRY_DEFN *phdllentrydefn);
+ nonvirt TIPERROR AllocDllentrydefnByOrdinal(HLNAM hlnamDllModule,
+ USHORT ordinal,
+ HDLLENTRY_DEFN *phdllentrydefn);
+ nonvirt VOID ReleaseDllentrydefn(HDLLENTRY_DEFN hdllentrydefn);
+ nonvirt DLLENTRY_DEFN *QdllentrydefnOfHdllentrydefn(HDLLENTRY_DEFN hdllentrydefn) const;
+
+ nonvirt SAFEARRAYA *QarraydescOfHarraydesc(HARRAY_DESC, UINT oChunk=0) const;
+ nonvirt TYPE_DEFN *QtdefnOfHvdefn(HVAR_DEFN hvdefn, UINT oChunk=0) const;
+ nonvirt TYPE_DEFN *QtdefnResultOfHfdefn(HFUNC_DEFN hfdefn, UINT oChunk=0) const;
+ nonvirt TYPE_DEFN *QtdefnResultOfHfdefnUnmunged(HFUNC_DEFN hfdefn, UINT oChunk=0) const;
+ nonvirt TIPERROR StringOfHchunk(HCHUNK hchunkStr, BSTRA *plstr);
+ nonvirt ULONG LengthOfHchunk(HCHUNK hchunk);
+ nonvirt BYTE *QtrOfHandle(HCHUNK hchunk);
+ nonvirt IMPMGR *Pimpmgr() const;
+ nonvirt NAMMGR *Pnammgr() const;
+ nonvirt DYN_TYPEROOT *Pdtroot() const;
+ nonvirt TIPERROR Read(STREAM *pstrm);
+ nonvirt TIPERROR Write(STREAM *pstrm);
+ nonvirt VOID Free();
+ nonvirt TIPERROR GetVardesckindOfHvdefn(VARDESCKIND *pvdesckind,
+ HVAR_DEFN hvdefn);
+ nonvirt TIPERROR GetBvkindOfHimptype(HIMPTYPE himptype,
+ BASICVARKIND *pbasicvkind);
+ nonvirt HDEFN HdefnOfHmember(HMEMBER hmember,
+ UINT *pdefnkind);
+ nonvirt HFUNC_DEFN HfdefnOfHmember(HMEMBER hmember,
+ UINT fInvokekind = (UINT)(INVOKE_FUNC |
+ INVOKE_PROPERTYGET |
+ INVOKE_PROPERTYPUT |
+ INVOKE_PROPERTYPUTREF)) const;
+
+
+ nonvirt HVAR_DEFN HvdefnPredeclared() const;
+ nonvirt VOID SetHvdefnPredeclared(HVAR_DEFN hvdefnPredeclared);
+ nonvirt LONG GetSize();
+ nonvirt VOID FreeAllDefns();
+ nonvirt UINT MapTypeDefn(HTYPE_DEFN htdefn); // used by BTSRC::Compact
+
+ HVAR_DEFN HvdefnOfHlnam(HLNAM hlnam);
+ HFUNC_DEFN HfdefnFirstOfHlnam(HLNAM hlnam,INVOKEKIND *pinvokekind);
+ HFUNC_DEFN HfdefnNextOfHlnam(HLNAM hlnam, HFUNC_DEFN hfdefn,INVOKEKIND *pinvokekind);
+
+ nonvirt HMBR_VAR_DEFN HmvdefnOfHmember(HMEMBER hmember) const;
+ TIPERROR HfdefnOfIndex(UINT index, HFUNC_DEFN *phfdefn);
+
+ TIPERROR GetDynTypeBindOfHvdefn(HVAR_DEFN hvardefn,
+ DYN_TYPEBIND ** ppdtbind,
+ HIMPTYPE * phimptype);
+ TIPERROR GetTypeInfoOfHvdefn(HVAR_DEFN hvdefn,
+ ITypeInfoA **pptinfo,
+ HIMPTYPE *phimptype);
+ TIPERROR AllocVardefnPredeclared();
+
+ ULONG UHelpContextOfEncoding(WORD wHelpContext);
+ TIPERROR GetEncodedHelpContext(ULONG uHelpContext, WORD *pwHelpContext);
+
+ UINT SizeofConstVal(VAR_DEFN *qvdefn, HCHUNK hchunkConstVal);
+
+ VOID FreeArrayDescriptor(HARRAY_DESC harraydesc);
+ VOID FreeTypeDefn(HTYPE_DEFN htdefn);
+ VOID FreeTypeDefnResources(HTYPE_DEFN htdefn);
+ VOID FreeVarDefn(HVAR_DEFN hvdefn);
+ VOID FreeMbrVarDefn(HMBR_VAR_DEFN hmvdefn);
+ VOID FreeFuncDefn(HFUNC_DEFN hfdefn);
+ VOID FreeRecTypeDefn(HRECTYPE_DEFN hrtdefn);
+ VOID FreeParamDefn(HPARAM_DEFN hparamdefn);
+ nonvirt VOID FreeChunk(HCHUNK hchunk, UINT cbSizeChunk);
+
+#if HP_BIGENDIAN
+ HVAR_DEFN SwapVarDefnOfHvdefn(HVAR_DEFN hvdefn, BOOL fSwapFirst);
+ HFUNC_DEFN SwapFuncDefnOfHfdefn(HFUNC_DEFN hfdefn, BOOL fSwapFirst);
+ VOID SwapTypeDefnOfHtdefn(HTYPE_DEFN htdefn, BOOL fSwapFirst);
+ HRECTYPE_DEFN SwapRectypeDefnOfHrtdefn(HRECTYPE_DEFN hrtdefn,
+ BOOL fSwapFirst,
+ BOOL fSwapVarDefns);
+ VOID SwapbmData(BOOL fSwapFirst);
+ VOID SwapAllFuncDefns(BOOL fSwapFirst);
+ VOID SwapTypeDefnOfQtdefn(TYPE_DEFN *qtdefn, BOOL fSwapFirst);
+#endif
+
+
+#if ID_DEBUG
+ nonvirt VOID DebShowDefn(HDEFN hdefn, BOOL fShowList);
+ nonvirt VOID DebShowVarDefn(sHVAR_DEFN hvdefn, BOOL fShowList);
+ nonvirt VOID DebShowParamDefn(sHPARAM_DEFN hparamdefn, BOOL fShowList);
+ nonvirt VOID DebShowFuncDefn(sHFUNC_DEFN hfdefn, BOOL fShowList);
+ nonvirt VOID DebShowRecTypeDefn(sHRECTYPE_DEFN hrtdefn, BOOL fShowList);
+ nonvirt VOID DebShowSimpleTypeDefn(TYPE_DEFN *ptdefn);
+ nonvirt VOID DebShowTypeDefn(TYPE_DEFN *ptdefn);
+ nonvirt VOID DebShowDefnList(HDEFN hdefnFirst, HDEFN hdefnLast, UINT uLevel);
+ nonvirt VOID DebShowMemberLists(UINT uLevel);
+ nonvirt VOID DebCheckState(UINT uLevel) const;
+ nonvirt VOID DebCheckDefn(HDEFN hdefn) const;
+ nonvirt VOID DebCheckVarDefn(HVAR_DEFN hvdefn) const;
+ nonvirt VOID DebCheckParamDefn(HPARAM_DEFN hparamdefn) const;
+ nonvirt VOID DebCheckMbrVarDefn(HMBR_VAR_DEFN hmvdefn) const;
+ nonvirt VOID DebCheckFuncDefn(HFUNC_DEFN hfdefn) const;
+ nonvirt VOID DebCheckVirtualFuncDefn(HVIRTUAL_FUNC_DEFN hvfdefn) const;
+ nonvirt VOID DebCheckDllentryDefn(HDLLENTRY_DEFN hdllentrydefn) const;
+ nonvirt VOID DebCheckRecTypeDefn(HRECTYPE_DEFN hrtdefn) const;
+ nonvirt VOID DebCheckFuncTypeDefn(FUNC_TYPE_DEFN ftdefn) const;
+#else
+ nonvirt inline VOID DebShowDefn(HDEFN hdefn, BOOL fShowList) {};
+ nonvirt inline VOID DebShowVarDefn(sHVAR_DEFN hvdefn, BOOL fShowList) {};
+ nonvirt inline VOID DebShowParamDefn(sHPARAM_DEFN hparamdefn, BOOL fShowList) {};
+ nonvirt inline VOID DebShowFuncDefn(sHFUNC_DEFN hfdefn, BOOL fShowList) {};
+ nonvirt inline VOID DebShowRecTypeDefn(sHRECTYPE_DEFN hrtdefn, BOOL fShowList) {};
+ nonvirt inline VOID DebShowSimpleTypeDefn(TYPE_DEFN *ptdefn) {};
+ nonvirt inline VOID DebShowTypeDefn(TYPE_DEFN *ptdefn) {};
+ nonvirt inline VOID DebShowDefnList(HDEFN hdefnFirst, HDEFN hdefnLast, UINT uLevel) {};
+ nonvirt inline VOID DebShowMemberLists(UINT uLevel) {};
+ nonvirt VOID DebCheckState(UINT) const {}
+ nonvirt VOID DebCheckDefn(HDEFN hdefn) const {}
+ nonvirt VOID DebCheckVarDefn(HVAR_DEFN hvdefn) const {}
+ nonvirt VOID DebCheckParamDefn(HPARAM_DEFN hparamdefn) const {}
+ nonvirt VOID DebCheckMbrVarDefn(HMBR_VAR_DEFN hmvdefn) const {}
+ nonvirt VOID DebCheckFuncDefn(HFUNC_DEFN hfdefn) const {}
+ nonvirt VOID DebCheckVirtualFuncDefn(HVIRTUAL_FUNC_DEFN hvfdefn) const {}
+ nonvirt VOID DebCheckDllentryDefn(HDLLENTRY_DEFN hdllentrydefn) const {}
+ nonvirt VOID DebCheckRecTypeDefn(HRECTYPE_DEFN hrtdefn) const {}
+ nonvirt VOID DebCheckFuncTypeDefn(FUNC_TYPE_DEFN ftdefn) const {}
+#endif
+
+private:
+
+ BLK_MGR m_blkmgr;
+ DYN_TYPEROOT *m_pdtroot;
+ USHORT m_cMeth; // elem count in respective lists
+ USHORT m_cAvailMeth;
+ USHORT m_cDataMember;
+ USHORT m_cBase;
+ USHORT m_cNestedType;
+ ULONG m_uHelpContextBase;
+
+ sHDEFN m_hdefnFirstMeth;
+ sHDEFN m_hdefnFirstDataMbrNestedType;
+ sHDEFN m_hdefnFirstBase;
+
+ sHDEFN m_hdefnLastMeth;
+ sHDEFN m_hdefnLastDataMbrNestedType;
+ sHDEFN m_hdefnLastBase;
+
+ USHORT m_isSimpleTypeAlias:1; // serialized
+ USHORT m_UNUSED:15;
+
+ // unserialized
+ UINT m_uOrdinalHfdefnLast; // ordinal of last fdefn they wanted
+ HFUNC_DEFN m_hfdefnLast;
+
+ UINT m_uOrdinalHvdefnLast; // ordinal of last vdefn they wanted
+ HVAR_DEFN m_hvdefnLast;
+
+ // this union is switched on the TKIND of the conatining typeinfo
+ // m_htdefnAlias is for TKIND_ALIAS
+ // m_hfdefnValue is for TKIND_INTERFACE
+ union {
+ sHTYPE_DEFN m_htdefnAlias; // for ITypeInfo::SetTypeDescAlias
+ sHFUNC_DEFN m_hfdefnValue; // for DISPID_VALUE
+ };
+
+ IMPMGR *m_pimpmgr; // cached import manager
+ NAMMGR *m_pnammgr; // cached name manager
+ // for the predeclared instance of the class
+ sHMBR_VAR_DEFN m_hmvdefnPredeclared;
+
+ // private methods
+ HFUNC_DEFN HfdefnValue();
+ UINT SizeTypeDefnOfTDescKind(UINT cTypes, TYPEDESCKIND *rgtdesckind) const;
+ TIPERROR HchunkOfString(LPSTR szStr, HCHUNK *phchunk);
+ TIPERROR HlnamOfName(LPSTR szStr, HLNAM *phlnam);
+ VOID AppendDefn(HDEFN hdefn, sHDEFN *phdefnFirst, sHDEFN *phdefnLast);
+ VOID AppendMbrVarDefn(HMBR_VAR_DEFN hmvdefn);
+ VOID AppendFuncDefn(HFUNC_DEFN hfdefn);
+ VOID AppendRecTypeDefn(HRECTYPE_DEFN hrtdefn);
+ HDEFN HdefnPrev(HDEFN hdefn, HDEFN hdefnFirst);
+ nonvirt HMBR_VAR_DEFN HmvdefnOfIndex(UINT index);
+
+ TIPERROR HdefnOfIndex(UINT index, HDEFN *phdefn);
+ VOID RemDefn(HDEFN hdefn,
+ sHDEFN *phdefnFirst,
+ sHDEFN *phdefnLast,
+ VOID (TYPE_DATA::*FreeDefn)(HDEFN));
+
+ // These are used by "friend" clients
+ nonvirt TIPERROR AllocVarDefn(sHVAR_DEFN *phvdefn);
+ nonvirt TIPERROR AllocFuncDefn(sHFUNC_DEFN *phfdefn, BOOL fV2Flags);
+ nonvirt TIPERROR AllocVirtualFuncDefn(sHVIRTUAL_FUNC_DEFN *phvfdefn,
+ BOOL fV2Flags);
+ nonvirt TIPERROR AllocMbrVarDefn(sHMBR_VAR_DEFN *phmvdefn
+ , BOOL fV2Flags);
+ nonvirt TIPERROR AllocTypeDefn(UINT cTypes,
+ TYPEDESCKIND rgtdesckind[],
+ sHTYPE_DEFN *phtdefn);
+ nonvirt TIPERROR AllocArrayDescriptor(UINT uNumDim, sHARRAY_DESC *pharraydesc);
+ nonvirt TIPERROR AllocRecTypeDefn(sHRECTYPE_DEFN *phrtdefn);
+ nonvirt TIPERROR AllocChunk(HCHUNK *phchunk, UINT cbSizeChunk);
+
+ nonvirt TIPERROR AllocConstValOfVariant(VARIANTA *pvariant,
+ HVAR_DEFN hvdefn);
+ nonvirt TIPERROR SetTypeDefnOfVarDefn(HVAR_DEFN hvdefn, TYPE_DEFN *ptdefn, UINT cbSizeDefn);
+ nonvirt TIPERROR CopyTypeDefn(HTYPE_DEFN htdefnDest, HTYPE_DEFN htdefnSrc, TYPE_DATA *ptdataSrc);
+ nonvirt TIPERROR CopyArrayDescriptor(HARRAY_DESC harraydescDest, HARRAY_DESC harraydescSrc, TYPE_DATA *ptdataSrc);
+ nonvirt TIPERROR CopyTypeDefnIntoVarDefn(HVAR_DEFN hvdefn, HTYPE_DEFN htdefn, BOOL isSimpleType, TYPE_DATA *ptdataSrc);
+ nonvirt VOID ChangeTypeDefnOfVarDefn(HVAR_DEFN hvdefn, TYPE_DEFN *ptdefn, UINT cbSizeDefn);
+ nonvirt TIPERROR SetTypeDefnResultOfFuncDefn(HFUNC_DEFN hfdefn,
+ TYPE_DEFN *ptdefn,
+ UINT cbSizeDefn);
+ nonvirt UINT UOrdinalHfdefnLast() const {
+ return m_uOrdinalHfdefnLast;
+ }
+ nonvirt UINT UOrdinalHvdefnLast() const {
+ return m_uOrdinalHvdefnLast;
+ }
+ nonvirt VOID SetUOrdinalHfdefnLast(UINT uOrdinalHfdefnLast) {
+ m_uOrdinalHfdefnLast = uOrdinalHfdefnLast;
+ }
+ nonvirt VOID SetUOrdinalHvdefnLast(UINT uOrdinalHvdefnLast) {
+ m_uOrdinalHvdefnLast = uOrdinalHvdefnLast;
+ }
+ nonvirt HFUNC_DEFN HfdefnLast() const {
+ return m_hfdefnLast;
+ }
+ nonvirt HVAR_DEFN HvdefnLast() const {
+ return m_hvdefnLast;
+ }
+ nonvirt VOID SetHfdefnLast(HFUNC_DEFN hfdefnLast) {
+ m_hfdefnLast = hfdefnLast;
+ }
+ nonvirt VOID SetHvdefnLast(HVAR_DEFN hvdefnLast) {
+ m_hvdefnLast = hvdefnLast;
+ }
+};
+
+// Equivalence functions
+
+#define FEQUIVIGNORE_NULL 0
+#define FEQUIVIGNORE_FuncKind 0x0001
+#define FEQUIVIGNORE_Cc 0x0002
+#define FEQUIVIGNORE_EquivTypes 0x0004
+#define FEQUIVIGNORE_VarKind 0x0008
+#define FEQUIVIGNORE_HasLcid 0x0010
+
+TIPERROR EquivFuncDefns(TYPE_DATA * ptdata1, HFUNC_DEFN hfdefn1,
+ TYPE_DATA * ptdata2, HFUNC_DEFN hfdefn2,
+ WORD wFlags, BOOL * fEqual, HDEFN *phdefnFail);
+TIPERROR EquivFuncDescFuncDefn(FUNCDESC *pfuncdesc, ITypeInfo *ptinfo,
+ TYPE_DATA *ptdata, HFUNC_DEFN hfdefn,
+ WORD wFlags, BOOL *fEqual, HDEFN *phdefnFail);
+
+TIPERROR EquivVarDefns(TYPE_DATA * ptdata1, HVAR_DEFN hvdefn1,
+ TYPE_DATA * ptdata2, HVAR_DEFN hvdefn2,
+ WORD wFlags, BOOL * fEqual);
+
+TIPERROR EquivVarDescVarDefn(VARDESC *pvardesc, ITypeInfo *ptinfo,
+ TYPE_DATA *ptdata, HVAR_DEFN hvdefn,
+ WORD wFlags, BOOL *fEqual);
+
+TIPERROR EquivFuncDescVarDefn(FUNCDESC *pfuncdesc, ITypeInfo *ptinfo,
+ TYPE_DATA *ptdata, HVAR_DEFN hvdefn,
+ WORD wFlags, BOOL *fEqual);
+
+TIPERROR EquivFuncTypeDefns(TYPE_DATA * ptdata1, FUNC_TYPE_DEFN * pftdefn1,
+ TYPE_DATA * ptdata2, FUNC_TYPE_DEFN * pftdefn2,
+ WORD wFlags, BOOL * fEqual, HDEFN *phdefnFail);
+
+TIPERROR EquivTypeDefns(TYPE_DATA * ptdata1, BOOL fSimple1, sHTYPE_DEFN htdefn1,
+ TYPE_DATA * ptdata2, BOOL fSimple2, sHTYPE_DEFN htdefn2,
+ WORD wFlags, BOOL * fEqual);
+
+
+// inline methods
+//
+
+inline TYPE_DATA::TYPE_DATA()
+{
+ m_pdtroot = NULL;
+ m_hdefnFirstMeth =
+ m_hdefnFirstDataMbrNestedType =
+ m_hdefnFirstBase =
+ m_hdefnLastMeth =
+ m_hdefnLastDataMbrNestedType =
+ m_hdefnLastBase = (sHDEFN)HDEFN_Nil;
+ m_htdefnAlias = (sHTYPE_DEFN) HTYPEDEFN_Nil;
+ m_pimpmgr = NULL;
+ m_pnammgr = NULL;
+ m_cMeth = m_cDataMember = m_cBase = m_cNestedType = (USHORT)~0;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::Psheapmgr
+*Purpose:
+* Get containing sheapmgr
+*
+*Implementation Notes:
+* Defers to blkmgr.
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+inline SHEAP_MGR *TYPE_DATA::Psheapmgr() const
+{
+ return m_blkmgr.Psheapmgr();
+}
+
+
+/***
+*PUBLIC TYPE_DATA::CDataMember - Get length of data member list.
+*Purpose:
+* Get length of data member list.
+*
+*Implementation Notes:
+*
+*Entry:
+* None.
+*
+*Exit:
+* UINT
+*
+***********************************************************************/
+
+inline UINT TYPE_DATA::CDataMember() const
+{
+ return m_cDataMember;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::CBase - Get length of base list.
+*Purpose:
+* Get length of base list.
+*
+*Implementation Notes:
+*
+*Entry:
+* None.
+*
+*Exit:
+* UINT
+*
+***********************************************************************/
+
+inline UINT TYPE_DATA::CBase() const
+{
+ return m_cBase;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::CMeth - Get length of meth list.
+*Purpose:
+* Get length of meth list.
+*
+*Implementation Notes:
+*
+*Entry:
+* None.
+*
+*Exit:
+* UINT
+*
+***********************************************************************/
+
+inline UINT TYPE_DATA::CMeth() const
+{
+ return m_cMeth;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::CNestedType - Get length of nested type list.
+*Purpose:
+* Get length of nested type list.
+*
+*Implementation Notes:
+*
+*Entry:
+* None.
+*
+*Exit:
+* UINT
+*
+***********************************************************************/
+
+inline UINT TYPE_DATA::CNestedType() const
+{
+ return m_cNestedType;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::CAvailMeth - Get length of availible meth list.
+*Purpose:
+* Get length of availible meth list.
+*
+*Implementation Notes:
+*
+*Entry:
+* None.
+*
+*Exit:
+* UINT
+*
+***********************************************************************/
+
+inline UINT TYPE_DATA::CAvailMeth() const
+{
+ // All OLE methods are availible.
+ return CMeth();
+}
+
+
+
+
+/***
+*PUBLIC TYPE_DATA::Pnammgr - Get class's name manager.
+*Purpose:
+* Get class's name manager.
+*
+*Implementation Notes:
+b*
+*Entry:
+* None.
+*
+*Exit:
+* Returns pointer to NAMMGR object owned by containing GEN_DTINFO.
+*
+***********************************************************************/
+
+inline NAMMGR* TYPE_DATA::Pnammgr() const
+{
+ DebAssert(m_pnammgr != NULL,
+ "TYPE_DATA::Pnammgr: m_pnammgr NULL.");
+
+ return m_pnammgr;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::Pimpmgr - Get class's import manager.
+*Purpose:
+* Get class's import manager.
+*
+*Implementation Notes:
+b*
+*Entry:
+* None.
+*
+*Exit:
+* Returns pointer to IMPMGR object owned by containing GEN_DTINFO.
+*
+***********************************************************************/
+
+inline IMPMGR* TYPE_DATA::Pimpmgr() const
+{
+ DebAssert(m_pimpmgr != NULL,
+ "TYPE_DATA::Pimpmgr: m_pimpmgr NULL.");
+
+ return m_pimpmgr;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::Pdtroot - Get class's DYN_TYPEROOT.
+*Purpose:
+* Get class's DYN_TYPEROOT.
+*
+*Implementation Notes:
+b*
+*Entry:
+* None.
+*
+*Exit:
+* Returns pointer to DYN_TYPEROOT.
+*
+***********************************************************************/
+
+inline DYN_TYPEROOT* TYPE_DATA::Pdtroot() const
+{
+ DebAssert(m_pdtroot != NULL,
+ "TYPE_DATA::Pdtroot: m_pdtroot NULL.");
+
+ return m_pdtroot;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::QdefnOfHdefn - Address of a DEFN
+*Purpose:
+* Converts a handle to a DEFN to a pointer.
+*
+*Implementation Notes:
+*
+*Entry:
+* hdefn - Handle to a DEFN.
+* oChunk - Optional offset within chunk.
+*
+*Exit:
+* Returns a pointer to the DEFN.
+*
+***********************************************************************/
+
+inline DEFN* TYPE_DATA::QdefnOfHdefn(HDEFN hdefn, UINT oChunk) const
+{
+ return (DEFN *)m_blkmgr.QtrOfHandle(hdefn, oChunk);
+}
+
+
+/***
+*PUBLIC TYPE_DATA::QvdefnOfHvdefn - Address of a VAR_DEFN
+*Purpose:
+* Converts a handle to a VAR_DEFN to a pointer.
+*
+*Implementation Notes:
+*
+*Entry:
+* hvdefn - Handle to a VAR_DEFN.
+* oChunk - Optional offset within chunk.
+*
+*Exit:
+* Returns a pointer to the VAR_DEFN.
+*
+***********************************************************************/
+
+inline VAR_DEFN* TYPE_DATA::QvdefnOfHvdefn(HVAR_DEFN hvdefn, UINT oChunk) const
+{
+ return (VAR_DEFN *)QdefnOfHdefn((HDEFN)hvdefn, oChunk);
+}
+
+
+/***
+*PUBLIC TYPE_DATA::QparamdefnOfHparamdefn - Address of a PARAM_DEFN
+*Purpose:
+* Converts a handle to a PARAM_DEFN to a pointer.
+*
+*Implementation Notes:
+*
+*Entry:
+* hparamdefn - Handle to a PARAM_DEFN.
+* oChunk - Optional offset within chunk.
+*
+*Exit:
+* Returns a pointer to the PARAM_DEFN.
+*
+***********************************************************************/
+
+inline PARAM_DEFN* TYPE_DATA::QparamdefnOfHparamdefn(HPARAM_DEFN hparamdefn, UINT oChunk) const
+{
+ return (PARAM_DEFN *)QdefnOfHdefn((HDEFN)hparamdefn, oChunk);
+}
+
+
+/***
+*PUBLIC TYPE_DATA::QmdefnOfHmdefn - Address of a MEMBER_DEFN
+*Purpose:
+* Converts a handle to a MEMBER_DEFN to a pointer.
+*
+*Implementation Notes:
+*
+*Entry:
+* hmdefn - Handle to a MEMBER_DEFN.
+* oChunk - Optional offset within chunk.
+*
+*Exit:
+* Returns a pointer to the MEMBER_DEFN.
+*
+***********************************************************************/
+
+inline MEMBER_DEFN* TYPE_DATA::QmdefnOfHmdefn(HMEMBER_DEFN hmdefn, UINT oChunk) const
+{
+ return (MEMBER_DEFN *)QdefnOfHdefn((HDEFN)hmdefn, oChunk);
+}
+
+
+/***
+*PUBLIC TYPE_DATA::QmvdefnOfHmvdefn - Address of a MBR_VAR_DEFN
+*Purpose:
+* Converts a handle to a MBR_VAR_DEFN to a pointer.
+*
+*Implementation Notes:
+*
+*Entry:
+* hmvdefn - Handle to a MBR_VAR_DEFN.
+* oChunk - Optional offset within chunk.
+*
+*Exit:
+* Returns a pointer to the MBR_VAR_DEFN.
+*
+***********************************************************************/
+
+inline MBR_VAR_DEFN* TYPE_DATA::QmvdefnOfHmvdefn(HMBR_VAR_DEFN hmvdefn, UINT oChunk) const
+{
+ return (MBR_VAR_DEFN *)QdefnOfHdefn((HDEFN)hmvdefn, oChunk);
+}
+
+
+/***
+*PUBLIC TYPE_DATA::QfdefnOfHfdefn - Address of a FUNC_DEFN
+*Purpose:
+* Converts a handle to a FUNC_DEFN to a pointer.
+*
+*Implementation Notes:
+*
+*Entry:
+* hfdefn - Handle to a FUNC_DEFN.
+* oChunk - Optional offset within chunk.
+*
+*Exit:
+* Returns a pointer to the FUNC_DEFN.
+*
+***********************************************************************/
+
+inline FUNC_DEFN* TYPE_DATA::QfdefnOfHfdefn(HFUNC_DEFN hfdefn, UINT oChunk) const
+{
+ return (FUNC_DEFN *)m_blkmgr.QtrOfHandle((HDEFN)hfdefn, oChunk);
+}
+
+
+/***
+*PUBLIC TYPE_DATA::QvfdefnOfHvfdefn - Address of a VIRTUAL_FUNC_DEFN
+*Purpose:
+* Converts a handle to a VIRTUAL_FUNC_DEFN to a pointer.
+*
+*Implementation Notes:
+*
+*Entry:
+* hvfdefn - Handle to a FUNC_DEFN.
+* oChunk - Optional offset within chunk.
+*
+*Exit:
+* Returns a pointer to the VIRTUAL_FUNC_DEFN.
+*
+***********************************************************************/
+
+inline VIRTUAL_FUNC_DEFN* TYPE_DATA::QvfdefnOfHvfdefn(HVIRTUAL_FUNC_DEFN hvfdefn, UINT oChunk) const
+{
+ return (VIRTUAL_FUNC_DEFN *)QdefnOfHdefn((HDEFN)hvfdefn, oChunk);
+}
+
+
+/***
+*PUBLIC TYPE_DATA::QtdefnOfHtdefn - Address of a TYPE_DEFN
+*Purpose:
+* Converts a handle to a TYPE_DEFN to a pointer.
+*
+*Implementation Notes:
+*
+*Entry:
+* hvdefn - Handle to a TYPE_DEFN.
+* oChunk - Optional offset within chunk.
+*
+*Exit:
+* Returns a pointer to the TYPE_DEFN.
+*
+***********************************************************************/
+
+inline TYPE_DEFN* TYPE_DATA::QtdefnOfHtdefn(HTYPE_DEFN htdefn, UINT oChunk) const
+{
+ return (TYPE_DEFN *)m_blkmgr.QtrOfHandle(htdefn, oChunk);
+}
+
+
+/***
+*PUBLIC TYPE_DATA::QrtdefnOfHrtdefn - Address of a RECTYPE_DEFN
+*Purpose:
+* Converts a handle to a RECTYPE_DEFN to a pointer.
+*
+*Implementation Notes:
+*
+*Entry:
+* hrtdefn - Handle to a RECTYPE_DEFN.
+* oChunk - Optional offset within chunk.
+*
+*Exit:
+* Returns a pointer to the RECTYPE_DEFN.
+*
+***********************************************************************/
+
+inline RECTYPE_DEFN *TYPE_DATA::QrtdefnOfHrtdefn(HRECTYPE_DEFN hrtdefn, UINT oChunk) const
+{
+ return (RECTYPE_DEFN *)m_blkmgr.QtrOfHandle(hrtdefn, oChunk);
+}
+
+
+/***
+*PUBLIC TYPE_DATA::QftdefnOfHftdefn - Address of a FUNC_TYPE_DEFN
+*Purpose:
+* Converts a handle to a FUNC_TYPE_DEFN to a pointer.
+*
+*Implementation Notes:
+*
+*Entry:
+* hvdefn - Handle to a FUNC_TYPE_DEFN.
+* oChunk - Optional offset within chunk.
+*
+*Exit:
+* Returns a pointer to the FUNC_TYPE_DEFN.
+*
+***********************************************************************/
+
+inline FUNC_TYPE_DEFN* TYPE_DATA::QftdefnOfHftdefn(HFUNC_TYPE_DEFN hftdefn,
+ UINT oChunk) const
+{
+ return (FUNC_TYPE_DEFN *)m_blkmgr.QtrOfHandle(hftdefn, oChunk);
+}
+
+
+/***
+*PUBLIC TYPE_DATA::QarraydescOfHarraydesc - Get ptr to ARRAY_DESC.
+*Purpose:
+* Get ptr to ARRAY_DESC given handle.
+*
+*Implementation Notes:
+*
+*Entry:
+* harraydesc - Handle of arraydesc on local heap.
+* oChunk - Optional offset within chunk.
+*
+*Exit:
+* Returns pointer to ARRAY_DESC.
+*
+***********************************************************************/
+
+inline SAFEARRAYA* TYPE_DATA::QarraydescOfHarraydesc(
+ HARRAY_DESC harraydesc,
+ UINT oChunk) const
+{
+ return (SAFEARRAYA *)m_blkmgr.QtrOfHandle(harraydesc, oChunk);
+}
+
+
+
+/***
+*PUBLIC TYPE_DATA::QtdefnOfHvdefn - Get ptr to TYPE_DEFN.
+*Purpose:
+* Given a handle to a VAR_DEFN, get a pointer to its
+* TYPE_DEFN.
+*
+*Implementation Notes:
+*
+*Entry:
+* HVAR_DEFN hvdefn - Handle of VAR_DEFN.
+* oChunk - Optional offset within chunk.
+*
+*Exit:
+* Returns pointer to TYPE_DEFN.
+* Note: returns NULL if type handle is Nil.
+*
+***********************************************************************/
+
+inline TYPE_DEFN* TYPE_DATA::QtdefnOfHvdefn(
+ HVAR_DEFN hvdefn,
+ UINT oChunk) const
+{
+ VAR_DEFN *qvdefn;
+ HTYPE_DEFN htdefn;
+
+ DebAssert(hvdefn != HVARDEFN_Nil, "QtdefnOfHvdefn: bad hvdefn");
+
+ qvdefn = QvdefnOfHvdefn(hvdefn, oChunk);
+ htdefn = qvdefn->Htdefn();
+
+ // NOTE: for simple types must actually return address
+ // of embedded member and not address of stack-alloced
+ // local. I.e. can't use Htdefn() accessor.
+ //
+ return htdefn == HTYPEDEFN_Nil ?
+ NULL :
+ (qvdefn->IsSimpleType() ?
+ qvdefn->QtdefnOfSimpleType() :
+ QtdefnOfHtdefn(htdefn));
+}
+
+
+inline TYPE_DEFN* TYPE_DATA::QtdefnResultOfHfdefn(HFUNC_DEFN hfdefn,
+ UINT oChunk) const
+{
+ FUNC_DEFN *qfdefn;
+ HTYPE_DEFN htdefnResult;
+ DebAssert(hfdefn != HFUNCDEFN_Nil, "bad hfdefn");
+
+ qfdefn = QfdefnOfHfdefn(hfdefn, oChunk);
+ htdefnResult = qfdefn->m_ftdefn.HtdefnResult();
+
+ // NOTE: for simple types must actually return address
+ // of embedded member and not address of stack-alloced
+ // local. I.e. can't use HtdefnResult() accessor.
+ //
+ return htdefnResult == HTYPEDEFN_Nil ?
+ NULL :
+ (qfdefn->m_ftdefn.IsSimpleTypeResult() ?
+ qfdefn->m_ftdefn.QtdefnOfSimpleTypeResult() :
+ QtdefnOfHtdefn(htdefnResult));
+}
+
+
+inline TYPE_DEFN* TYPE_DATA::QtdefnResultOfHfdefnUnmunged(HFUNC_DEFN hfdefn,
+ UINT oChunk) const
+{
+ FUNC_DEFN *qfdefn;
+ HTYPE_DEFN htdefnResult;
+ DebAssert(hfdefn != HFUNCDEFN_Nil, "bad hfdefn");
+
+ qfdefn = QfdefnOfHfdefn(hfdefn, oChunk);
+ htdefnResult = qfdefn->m_ftdefn.HtdefnResultUnmunged();
+
+ // NOTE: for simple types must actually return address
+ // of embedded member and not address of stack-alloced
+ // local. I.e. can't use HtdefnResult() accessor.
+ //
+ return htdefnResult == HTYPEDEFN_Nil
+ ? NULL
+ : (qfdefn->m_ftdefn.IsSimpleTypeResultUnmunged()
+ ? qfdefn->m_ftdefn.QtdefnOfSimpleTypeResultUnmunged()
+ : QtdefnOfHtdefn(htdefnResult));
+}
+
+/***
+*PUBLIC TYPE_DATA::LengthOfHchunk - Gets length of chunk.
+*Purpose:
+* Gets length of chunk (assumes is ULONG prefixed ST).
+*
+*Implementation Notes:
+*
+*Entry:
+* hchunkStr - handle to chunk containing an ST.
+*
+*Exit:
+* ST length
+*
+***********************************************************************/
+
+inline ULONG TYPE_DATA::LengthOfHchunk(HCHUNK hchunk)
+{
+ return *(ULONG *)m_blkmgr.QtrOfHandle(hchunk);
+}
+
+
+/***
+*PUBLIC TYPE_DATA::QtrOfHandle - Gets pointer from handle.
+*Purpose:
+* Allows client to get pointer for TYPE_DATA owned handle.
+*
+*Implementation Notes:
+*
+*Entry:
+* hchunk - handle to get pointer of.
+*
+*Exit:
+* VOID pointer
+*
+***********************************************************************/
+
+inline BYTE *TYPE_DATA::QtrOfHandle(HCHUNK hchunk)
+{
+ return m_blkmgr.QtrOfHandle(hchunk);
+}
+
+
+/***
+*PUBLIC TYPE_DATA::Free - Frees instance.
+*Purpose:
+* Frees instance.
+*
+*Implementation Notes:
+*
+*Entry:
+*
+*Exit:
+*
+***********************************************************************/
+
+inline VOID TYPE_DATA::Free()
+{
+ m_blkmgr.Free();
+}
+
+
+/***
+*PUBLIC TYPE_DATA::HfdefnFirstMeth - First meth in list.
+*Purpose:
+* Returns first method in list of class's methods.
+*
+*Implementation Notes:
+*
+*Entry:
+* None
+*
+*Exit:
+* Returns handle to first method in list of methods.
+*
+***********************************************************************/
+
+inline HFUNC_DEFN TYPE_DATA::HfdefnFirstMeth() const
+{
+ return (HFUNC_DEFN) m_hdefnFirstMeth;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::HdefnFirstDataMbrNestedType - First data member in list.
+*Purpose:
+* Returns first data member in list of class's data members.
+*
+*Implementation Notes:
+* CONSIDER: making inline.
+*
+*Entry:
+* None
+*
+*Exit:
+* Returns handle to first data member in list of data members.
+*
+***********************************************************************/
+
+inline HDEFN TYPE_DATA::HdefnFirstDataMbrNestedType() const
+{
+ return (HDEFN) m_hdefnFirstDataMbrNestedType;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::HvdefnFirstBase - First base in list.
+*Purpose:
+* Returns first base in list of class's bases.
+*
+*Implementation Notes:
+* CONSIDER: making inline.
+*
+*Entry:
+* None
+*
+*Exit:
+* Returns handle to first base in list of bases.
+*
+***********************************************************************/
+
+inline HVAR_DEFN TYPE_DATA::HvdefnFirstBase() const
+{
+ return (HVAR_DEFN) m_hdefnFirstBase;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::HfdefnNextAvailMeth - Next availible method in list.
+*Purpose:
+* Returns next availible method in list of class's methods.
+*
+*Implementation Notes:
+*
+*Entry:
+* None
+*
+*Exit:
+* returns handle to next availible function.
+*
+***********************************************************************/
+
+inline HFUNC_DEFN TYPE_DATA::HfdefnNextAvailMeth(HFUNC_DEFN hfdefn) const
+{
+ // All OLE functions are availible.
+ return QfdefnOfHfdefn(hfdefn)->HdefnNext();
+}
+
+
+/***
+*PUBLIC TYPE_DATA::RemNestedTypeDefn - Remove a RECTYPE_DEFN from a list.
+*Purpose:
+* Remove a RECTYPE_DEFN from a list.
+*
+*Implementation Notes:
+* Defers to RemDefn
+*
+*Entry:
+* hrtdefn - Handle to a RECTYPE_DEFN to remove from list (IN).
+*
+*Exit:
+* Updates the appropriate listtail/listhead if needed.
+*
+*Errors:
+* NONE.
+*
+***********************************************************************/
+
+inline VOID TYPE_DATA::RemRecTypeDefn(HRECTYPE_DEFN hrtdefn)
+{
+ RemDefn(hrtdefn, &m_hdefnFirstDataMbrNestedType, &m_hdefnLastDataMbrNestedType,
+ &TYPE_DATA::FreeRecTypeDefn);
+ m_cNestedType--;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::RemParamDefn - Remove a PARAM_DEFN from a list.
+*Purpose:
+* Remove a PARAM_DEFN from a list.
+*
+*Implementation Notes:
+* Traverses list, searching for PARAM_DEFN reference by handle param
+* and remembers the previous element in list.
+* When it finds the element it removes it by linking the previous
+* to skip over the found element, and frees the memory associated
+* with the element to be removed.
+* It's a bug if the element can't be found, so assert.
+* Updates list head and tail if needed.
+*
+*Entry:
+* hparamdefn - Handle to a PARAM_DEFN to remove from list (IN).
+*
+*Exit:
+* Updates the appropriate listtail/listhead if needed.
+*
+*Errors:
+* NONE.
+*
+***********************************************************************/
+
+inline VOID TYPE_DATA::RemParamDefn(HPARAM_DEFN hparamdefn,
+ sHDEFN *phdefnFirst,
+ sHDEFN *phdefnLast)
+{
+ RemDefn(hparamdefn, phdefnFirst, phdefnLast, &TYPE_DATA::FreeParamDefn);
+}
+
+
+
+
+/***
+*TYPE_DATA::GetSize
+*Purpose:
+* returns the size of the TYPE_DEFN
+*Entry:
+*
+*Exit:
+* returns size
+***********************************************************************/
+inline LONG TYPE_DATA::GetSize()
+{
+ return m_blkmgr.GetSize();
+}
+
+
+/***
+*PRIVATE TYPE_DEFN::ChangeTypeDefnOfVarDefn()
+*Purpose:
+* Takes a pointer to a VAR_DEFN and puts the right
+* thing in the htdefn field.
+* For now, VAR_DEFN must already be isSimpleType and the
+* new TYPE_DEFN must also be isSimpleType.
+*
+*Implementation Notes:
+*
+*Entry:
+* pvdefn - pointer to the VAR_DEFN
+* ptdefn - pointer to the TYPE_DEFN
+* cbSizeDefn - size of the TYPE_DEFN
+*
+*Exit:
+*
+*
+***********************************************************************/
+
+inline VOID TYPE_DATA::ChangeTypeDefnOfVarDefn(HVAR_DEFN hvdefn,
+ TYPE_DEFN *ptdefn, UINT cbSizeDefn)
+{
+ VAR_DEFN *pvdefn;
+
+ DebAssert(hvdefn != HVARDEFN_Nil, "hvdefn is Nil");
+ DebAssert(ptdefn != NULL, "ptdefn is NULL");
+ DebAssert(IsSimpleType(ptdefn->Tdesckind()),
+ "not a simple TYPE_DEFN");
+
+ pvdefn = QvdefnOfHvdefn(hvdefn);
+ DebAssert(pvdefn->IsSimpleType(), "must currently be simple type");
+
+ // This copies the type defn directly in to the htdefn field
+ *((TYPE_DEFN *)(pvdefn->QtdefnOfSimpleType())) = *ptdefn;
+}
+
+
+/***
+*PUBLIC TYPE_DEFN::QparamdefnOfIndex()
+*Purpose:
+* Takes a handle to the first paramdefn in a paramdefn array and index(i)
+* returns a pointer to ith paramdefn.
+*
+*Implementation Notes:
+*
+*Entry:
+* hparamdefn
+* UINT : pointer to the PARAM DEFN to return.
+*Exit:
+* PARAM_DEFN *
+*
+***********************************************************************/
+
+inline PARAM_DEFN *TYPE_DATA::QparamdefnOfIndex(HPARAM_DEFN hparamdefn, UINT i) const
+{
+ return (PARAM_DEFN *) ((BYTE*)QparamdefnOfHparamdefn(hparamdefn) +
+ i*sizeof(PARAM_DEFN));
+}
+
+
+#endif // ! TDATA_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/tdata1.cxx b/private/oleauto/src/typelib/tdata1.cxx
new file mode 100644
index 000000000..8771544a3
--- /dev/null
+++ b/private/oleauto/src/typelib/tdata1.cxx
@@ -0,0 +1,2465 @@
+/***
+*tdata1.cxx - Type Data part 1
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* TYPEDATA manages the internal representation of a class's members.
+* In particular, it maintains three linked lists of data members,
+* base members and methods respectively.
+* See \silver\doc\ic\dtmbrs.doc for more information.
+*
+*Revision History:
+*
+* 27-Feb-91 ilanc: Created.
+* 28-Mar-91 alanc: Added include statement for impmgr
+* 06-Nov-91 ilanc: Mods cos of code review plus
+* implementaiotn of FreeDefn methods.
+* 31-Jan-91 stevenl: Modified for new hierarchy--see tdata.hxx.
+* 03-Apr-92 ilanc: Added GetVardesckindOfHvdefn
+* 03-Apr-92 martinc: Changed m_hdefn to m_varaccess.m_hdefn
+* (this change was required for cfront)
+* 12-Apr-92 ilanc: Implemented DebCheckState().
+* 29-Apr-92 ilanc: Added HfdefnOfHmember().
+* 30-Apr-92 stevenl: Minor changes to AllocTypeDefn.
+* 01-Jun-92 stevenl: DebShowVarDefn now dumps arraydescs.
+* 15-Jun-92 stevenl: Updated debug methods.
+* 16-Jun-92 w-peterh: Added RECTYPE_DEFN list
+* 18-Jun-92 stevenl: The debug .obj size of this file on the Mac
+* is greater than 32K, so any files after
+* the 32K boundary are not accessible outside
+* this module. Moved internal functions to the
+* end of the module so that all client calls
+* are in the first 32K.
+* 28-Jun-92 stevenl: Changed AllocArrayDescriptor so that it
+* allows zero-dimension arrays.
+* 02-Jul-92 w-peterh: merged data member/type lists
+* 13-Jul-92 stevenl: Added FreeVarDefn; fixed up FreeRectypeDefn
+* and FreeFuncDefn. Added DebShowDefn.
+* 11-Aug-92 stevenl: Put infrequently used functions into tdata2.cxx.
+* 18-Jan-93 w-peterh: removed TypeDefnResult
+* 12-Feb-93 w-peterh: VDK_BaseObject, htdefnAlias, HmvdefnOfHmember
+* 23-Feb-93 rajivk : Support for Predeclared Identifier
+* 23-Feb-93 davebra: Added FreeChunk
+* 30-Apr-93 w-jeffc: made DEFN data members private; added
+* Swap*defn functions
+*
+*Implementation Notes:
+* ST's are implemented as ULONG prefixed.
+*
+*****************************************************************************/
+
+#define TDATA_VTABLE // export blk mgr vtable
+
+#include "silver.hxx"
+#include "xstring.h" // for memcpy
+#include "typelib.hxx"
+#include "tdata.hxx" // no longer includes dtinfo.hxx
+#include "clutil.hxx"
+#include "nammgr.hxx"
+#include "impmgr.hxx"
+#include "entrymgr.hxx"
+#include "exbind.hxx"
+
+
+#pragma hdrstop(RTPCHNAME)
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+char szOleTdataCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleTdataCxx
+#else
+static char szTdataCxx[] = __FILE__;
+#define SZ_FILE_NAME szTdataCxx
+#endif
+#endif
+
+#if HP_BIGENDIAN
+// forward declarations
+static VOID Swap8Bytes(void * pv);
+#endif
+
+// defined in tdata2.cxx
+extern BYTE *PbConstVal(TYPE_DATA *ptdata, VAR_DEFN *qvdefn);
+extern VOID SetHchunkConstVal(VAR_DEFN *qvdefn, HCHUNK hchunk);
+
+// for help context encoding (defined in tdata2.cxx)
+#define IsHchunk(us) (!(us & 0x0001))
+#define GetHchunk(us) (us & ~0x0001)
+
+
+
+UINT ENCALL CbSizeArrayDesc(UINT);
+void ENCALL rtArrayInit(SAFEARRAY *, UINT);
+
+/***
+* CbSizeArrayDesc - return array descriptor size
+*
+* Purpose:
+* This function returns the size (in bytes) of an array
+* descriptor with uNDim dimensions.
+*
+* This static function is called by the AllocArrayDescriptor,
+* which needs a non-method function call to return the size of
+* an ARRAY_DESC.
+*
+* Entry:
+* uNDim - dimension count value
+*
+* Exit:
+* returns size in bytes of array descriptor
+*
+* Exceptions:
+***********************************************************************/
+
+UINT ENCALL CbSizeArrayDesc (UINT uNDim)
+{
+ if (uNDim > 0)
+ return sizeof(SAFEARRAY) + (uNDim - 1) * sizeof(SAFEARRAYBOUND);
+ else
+ return sizeof(SAFEARRAY);
+}
+
+void ENCALL rtArrayInit (SAFEARRAY * pad, UINT uNDim)
+{
+ UINT i;
+
+ pad->cDims = 0;
+ pad->fFeatures = 0;
+ pad->cbElements = 0;
+ pad->cLocks = 0;
+#if !OE_WIN32
+ pad->handle = 0;
+#endif
+ pad->pvData = NULL;
+
+ for (i = 0; i < uNDim; i++) {
+
+ pad->rgsabound[i].cElements = 0;
+ pad->rgsabound[i].lLbound = 0;
+ }
+}
+
+
+
+#if ID_DEBUG
+// EXBIND debug methods
+//
+VOID EXBIND::DebCheckState(UINT uLevel) const
+{
+}
+
+
+#endif // ID_DEBUG
+
+
+
+
+// Class methods
+//
+
+/***
+*PUBLIC TYPE_DATA::Initializer - initialize an instance
+*Purpose:
+* initializes a TYPE_DATA instance.
+*
+*Implementation Notes:
+*
+*Entry:
+* psheapmgr - Pointer to a heap mgr.
+* pdtroot - Pointer to owning DYN_TYPEROOT
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+TIPERROR TYPE_DATA::Init(SHEAP_MGR *psheapmgr, DYN_TYPEROOT *pdtroot)
+{
+ TIPERROR err = TIPERR_None;
+
+ DebAssert(pdtroot != NULL, "TYPE_DATA: pdtroot uninitialized.");
+ DebAssert(psheapmgr != NULL, "TYPE_DATA: psheapmgr uninitialized.");
+
+ m_pdtroot = pdtroot;
+
+ // Init block manager member.
+ IfErrRet(m_blkmgr.Init(psheapmgr));
+
+ // Cache name manager member
+ IfErrRet(pdtroot->GetNamMgr(&m_pnammgr));
+
+ // Cache import manager member
+ IfErrRet(pdtroot->GetImpMgr(&m_pimpmgr));
+
+ m_hdefnFirstMeth =
+ m_hdefnFirstDataMbrNestedType =
+ m_hdefnFirstBase =
+ m_hdefnLastMeth =
+ m_hdefnLastDataMbrNestedType =
+ m_hdefnLastBase = (sHDEFN)HDEFN_Nil;
+
+ // init elem count of lists.
+ m_cMeth = m_cDataMember = m_cBase = m_cNestedType = 0;
+ m_uHelpContextBase = 0;
+
+ // set alias to null
+ m_htdefnAlias = (sHTYPE_DEFN) HTYPEDEFN_Nil;
+
+ // Init iteration cache
+ m_uOrdinalHfdefnLast = m_uOrdinalHvdefnLast = 0xFFFF;
+ m_hfdefnLast = HFUNCDEFN_Nil;
+ m_hvdefnLast = HVARDEFN_Nil;
+
+ // Assume not a class.
+ SetHvdefnPredeclared(HMBRVARDEFN_Nil);
+ return err;
+}
+#pragma code_seg( )
+
+
+
+
+/***
+*PUBLIC TYPE_DATA::~TYPE_DATA - destructor
+*Purpose:
+* Destroys a TYPE_DATA instance.
+*
+*Implementation Notes:
+* If embedded BLKMGR is valid then free it.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE )
+TYPE_DATA::~TYPE_DATA()
+{
+ if (m_blkmgr.IsValid())
+ m_blkmgr.Free();
+}
+#pragma code_seg( )
+
+
+
+
+
+
+
+
+
+
+/***
+*PRIVATE TYPE_DATA::AppendDefn - Append a DEFN to end of list.
+*Purpose:
+* Append a DEFN to end of list: either base or data member.
+*
+*Implementation Notes:
+* Works out what list to append to by looking at the varkind attr.
+* NOTE: Since this function sets the hdefnNext field of the
+* DEFN to HCHUNK_Nil, you can't use it for appending a
+* list of DEFNs onto another list.
+*
+*Entry:
+* hdefn - Handle of a DEFN
+*
+*Exit:
+* Updates the appropriate listtail (and listhead if needed).
+*
+*Errors:
+* NONE.
+*
+***********************************************************************/
+
+#pragma code_seg(CS_LAYOUT)
+VOID TYPE_DATA::AppendDefn(HDEFN hdefn,
+ sHDEFN *phdefnFirst,
+ sHDEFN *phdefnLast)
+{
+ DEFN *pdefn, *pdefnLast;
+
+ pdefn = QdefnOfHdefn(hdefn);
+ pdefn->SetHdefnNext(HDEFN_Nil);
+
+ if (*phdefnLast != (sHDEFN)HDEFN_Nil) {
+ pdefnLast = QdefnOfHdefn((HDEFN)*phdefnLast);
+ *phdefnLast = (sHDEFN)hdefn;
+ pdefnLast->SetHdefnNext(hdefn);
+ }
+ else {
+ DebAssert((*phdefnFirst == (sHDEFN)HDEFN_Nil) &&
+ (*phdefnLast == (sHDEFN)HDEFN_Nil),
+ "TYPE_DATA::AppendDefn: whoops! bad listhead/listtail.");
+
+ *phdefnFirst = *phdefnLast = (sHDEFN)hdefn;
+ }
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_LAYOUT)
+/***
+*PRIVATE TYPE_DATA::AppendMbrVarDefn - Append MBR_VAR_DEFN to end of list.
+*Purpose:
+* Append a MBR_VAR_DEFN to end of list: either base or data member.
+*
+*Implementation Notes:
+* Works out what list to append to by looking at the varkind attr.
+*
+*Entry:
+* hmvdefn - Handle of a MBR_VAR_DEFN
+*
+*Exit:
+* Updates the appropriate listtail (and listhead if needed).
+*
+*Errors:
+* NONE.
+*
+***********************************************************************/
+
+VOID TYPE_DATA::AppendMbrVarDefn(HMBR_VAR_DEFN hmvdefn)
+{
+ sHDEFN *phdefnLast, *phdefnFirst;
+ MBR_VAR_DEFN *pmvdefn = QmvdefnOfHmvdefn(hmvdefn);
+
+ // Switch on kind of member (data member or base)
+ switch (pmvdefn->Vkind()) {
+ case VKIND_Base: {
+ phdefnFirst = &m_hdefnFirstBase;
+ phdefnLast = &m_hdefnLastBase;
+ m_cBase++;
+ break;
+ }
+ case VKIND_Enumerator:
+ case VKIND_DataMember: {
+ phdefnFirst = &m_hdefnFirstDataMbrNestedType;
+ phdefnLast = &m_hdefnLastDataMbrNestedType;
+ m_cDataMember++;
+ break;
+ }
+ default: {
+ DebHalt("TYPE_DATA::AppendMbrVarDefn: bad MBR_VAR_DEFN param.");
+ }
+ }
+ AppendDefn(hmvdefn, phdefnFirst, phdefnLast);
+}
+#pragma code_seg()
+
+
+
+
+
+
+/***
+*PRIVATE TYPE_DATA::ReleaseDllentrydefn
+*Purpose:
+* Releases a dll entry defn from the entrymgr
+*
+*Implementation Notes:
+*
+*Entry:
+* hdllentrydefn - the handle to release
+*Exit:
+* VOID
+*
+***********************************************************************/
+
+VOID TYPE_DATA::ReleaseDllentrydefn(HDLLENTRY_DEFN hdllentrydefn)
+{
+ ENTRYMGR *pentrymgr;
+ TIPERROR err;
+ err = m_pdtroot->GetEntMgr(&pentrymgr);
+
+ DebAssert(!err, "TYPE_DATA::AllocDllEntrydefn");
+ pentrymgr->ReleaseDllentrydefn(hdllentrydefn);
+
+ return;
+}
+
+
+/***
+*PRIVATE TYPE_DATA::FreeArrayDescriptor - Release AD memory.
+*Purpose:
+* Release memory for an AD and its parts.
+*
+*Implementation Notes:
+* Calculates the size of the array descriptor and then frees it.
+*
+*Entry:
+* harraydesc - handle to an AD.
+*
+*Exit:
+*
+*Errors:
+*
+***********************************************************************/
+
+VOID TYPE_DATA::FreeArrayDescriptor(HARRAY_DESC harraydesc)
+{
+ SAFEARRAY *pad;
+
+ if (harraydesc != HARRAYDESC_Nil) {
+ pad = QarraydescOfHarraydesc(harraydesc);
+ m_blkmgr.FreeChunk(harraydesc,
+ CbSizeArrayDesc(pad->cDims));
+ }
+}
+
+
+/***
+*PRIVATE TYPE_DATA::FreeTypeDefnResources - Release TYPE_DEFN memory.
+*Purpose:
+* Release and unref TYPE_DEFN-owned resources.
+*
+*Implementation Notes:
+* Works a lot like SizeOfTypeDefn: just frees/unrefs stuff
+* when necessary.
+*
+*Entry:
+* htdefn - handle to a TYPE_DEFN.
+*
+*Exit:
+*
+*Errors:
+*
+***********************************************************************/
+
+VOID TYPE_DATA::FreeTypeDefnResources(HTYPE_DEFN htdefn)
+{
+ TYPE_DEFN *ptdefn;
+ TYPEDESCKIND tdesckind;
+
+ ptdefn = (TYPE_DEFN *)m_blkmgr.QtrOfHandle(htdefn);
+ DebAssert(ptdefn != NULL, "bad TYPE_DEFN");
+
+ tdesckind = (TYPEDESCKIND)ptdefn->Tdesckind();
+ if (!IsSimpleType(tdesckind)) {
+ switch (tdesckind) {
+ case TDESCKIND_Ptr:
+ // adjust handle to next contiguous TYPE_DEFN.
+ FreeTypeDefnResources(htdefn + sizeof(TYPE_DEFN));
+ break;
+ case TDESCKIND_Carray:
+ case TDESCKIND_BasicArray:
+ FreeArrayDescriptor(ptdefn->Harraydesc());
+ FreeTypeDefnResources(htdefn + sizeof(TYPE_DEFN) + sizeof(sHARRAY_DESC));
+ break;
+ case TDESCKIND_UserDefined:
+ DebAssert(ptdefn->Qhimptype(), "whoops! null Phimptype.");
+ m_pimpmgr->Unref(ptdefn->Himptype());
+ break;
+ } // end switch
+ } // end if
+}
+
+
+/***
+*PRIVATE TYPE_DATA::FreeTypeDefn - Release TYPE_DEFN memory.
+*Purpose:
+* Release memory for a TYPE_DEFN and its parts.
+*
+*Implementation Notes:
+* Calls FreeTypeDefnResources to free anything owned by
+* the TYPE_DEFN, then frees the TYPE_DEFN itself.
+*
+*Entry:
+* htdefn - handle to a TYPE_DEFN.
+*
+*Exit:
+*
+*Errors:
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+VOID TYPE_DATA::FreeTypeDefn(HTYPE_DEFN htdefn)
+{
+ if (htdefn != HTYPEDEFN_Nil) {
+ FreeTypeDefnResources(htdefn);
+ m_blkmgr.FreeChunk(htdefn, SizeOfTypeDefn(htdefn));
+ }
+}
+#pragma code_seg( )
+
+
+
+
+/***
+*PRIVATE TYPE_DATA::FreeMbrVarDefn - Release MBR_VAR_DEFN memory.
+*Purpose:
+* Release memory for a MBR_VAR_DEFN and its parts.
+*
+*Implementation Notes:
+* Free referenced sub-chunks first (that this DEFN has
+* handles to, then free top-level chunk itself.
+* Namely: DLLENTRY_DEFN, doc string and TYPE_DEFN.
+*
+*Entry:
+* hmvdefn - handle to a MBR_VAR_DEFN.
+*
+*Exit:
+*
+*Errors:
+* NONE.
+*
+***********************************************************************/
+
+VOID TYPE_DATA::FreeMbrVarDefn(HMBR_VAR_DEFN hmvdefn)
+{
+ MBR_VAR_DEFN *pmvdefn;
+ HDLLENTRY_DEFN hdllentrydefn;
+ HST hstDocumentation;
+ ULONG uCbSizeStr;
+ HCHUNK hchunkConstVal;
+
+ DebAssert(hmvdefn != HMBRVARDEFN_Nil,
+ "TYPE_DATA::FreeMbrVarDefn: bad param.");
+
+ pmvdefn = (MBR_VAR_DEFN *)m_blkmgr.QtrOfHandle(hmvdefn);
+
+ // Free referenced sub-objects first (referenced by handles).
+ hdllentrydefn = pmvdefn->Hdllentrydefn();
+ if (hdllentrydefn != HDLLENTRYDEFN_Nil)
+ m_blkmgr.FreeChunk(hdllentrydefn, sizeof(DLLENTRY_DEFN));
+
+ // Work out size of ULONG-length-prefixed doc string and free it.
+ hstDocumentation = pmvdefn->HstDocumentation();
+ if (hstDocumentation != HST_Nil) {
+ uCbSizeStr = *(ULONG *)m_blkmgr.QtrOfHandle(hstDocumentation);
+ m_blkmgr.FreeChunk(hstDocumentation, (UINT)(uCbSizeStr+sizeof(ULONG)));
+ }
+
+ // Free the const value if any.
+ if (pmvdefn->HasConstVal() && !pmvdefn->IsSimpleConst()) {
+ hchunkConstVal = pmvdefn->HchunkConstMbrVal();
+ if (hchunkConstVal != HCHUNK_Nil) {
+ m_blkmgr.FreeChunk(hchunkConstVal,
+ SizeofConstVal((VAR_DEFN *)pmvdefn, hchunkConstVal));
+ }
+ }
+
+ if (!pmvdefn->IsSimpleType()) {
+ // Free (varlen) TYPE_DEFN
+ FreeTypeDefn(pmvdefn->Htdefn());
+ }
+
+
+ // Finally free top-level memory of MBR_VAR_DEFN itself
+ m_blkmgr.FreeChunk(hmvdefn, pmvdefn->HasV2Flags() ?
+ sizeof(MBR_VAR_DEFN):
+ sizeof(MBR_VAR_DEFN) - sizeof(USHORT));
+
+ m_blkmgr.DebCheckState(0);
+}
+
+/***
+*PRIVATE TYPE_DATA::SizeofConstVal - Determine how big a constant is
+*Purpose: Determine how big a constant is, so we can free it.
+*
+*
+*Implementation Notes:
+*
+*Entry:
+* hchunkConstVal - handle to block containing the constant data.
+*
+*Exit:
+*
+*Errors:
+* NONE.
+*
+***********************************************************************/
+UINT TYPE_DATA::SizeofConstVal(VAR_DEFN *qvdefn, HCHUNK hchunkConstVal)
+{
+ UINT cb;
+ BYTE * pbConst;
+ TYPEDESCKIND tdesckind;
+
+ pbConst = m_blkmgr.QtrOfHandle(hchunkConstVal);
+
+ // what is the type?
+ if (qvdefn->IsSimpleType()) {
+ tdesckind = qvdefn->QtdefnOfSimpleType()->Tdesckind();
+ }
+ else {
+ tdesckind = QtdefnOfHtdefn(qvdefn->Htdefn())->Tdesckind();
+ }
+ DebAssert(IsSimpleType(tdesckind), "tdesckind must be simple");
+
+ switch (tdesckind) {
+ case TDESCKIND_R8:
+ case TDESCKIND_Date:
+ case TDESCKIND_Currency:
+ cb = sizeof(double);
+ break;
+
+ case TDESCKIND_String:
+ // string is prefixed by a SHORT indicating string length
+ cb = sizeof(USHORT) + (UINT)*((USHORT *)pbConst);
+ break;
+
+ case TDESCKIND_Value:
+ cb = sizeof(VARIANT);
+ if (((LPVARIANT)pbConst)->vt == VT_BSTR) {
+ // string data is stored after the VARIANT structure.
+ // string is prefixed by a short indicating string length
+ cb += sizeof(USHORT) + (UINT)*((USHORT *)(pbConst + sizeof(VARIANT)));
+ }
+ break;
+
+ default:
+ cb = sizeof(long); // everybody else is just a long
+
+ } // switch
+ return cb;
+}
+
+
+/***
+*PRIVATE TYPE_DATA::FreeFuncDefn - Release FUNC_DEFN memory.
+*Purpose:
+* Release memory for a FUNC_DEFN and its parts.
+*
+*Implementation Notes:
+* Free referenced sub-chunks first (that this DEFN has
+* handles to, then free top-level chunks.
+* Namely, DLLENTRY_DEFN, doc string and FUNC_TYPE_DEFN's
+* list of PARAM_DEFN's (formal param list).
+*
+*Entry:
+* hfdefn - handle to a FUNC_DEFN.
+*
+*Exit:
+*
+*Errors:
+* NONE.
+*
+***********************************************************************/
+
+VOID TYPE_DATA::FreeFuncDefn(HFUNC_DEFN hfdefn)
+{
+ FUNC_DEFN *pfdefn, *qfdefn;
+ HDLLENTRY_DEFN hdllentrydefn;
+ HST hstDocumentation;
+ HPARAM_DEFN hparamdefn;
+ ULONG uCbSizeStr;
+ BOOL fFound = FALSE;
+ HLNAM hlnam;
+ USHORT usSize;
+
+ UINT iArg, cArgs;
+
+ DebAssert(hfdefn != HFUNCDEFN_Nil,
+ "TYPE_DATA::FreeFuncDefn: bad param.");
+
+ pfdefn = (FUNC_DEFN *)m_blkmgr.QtrOfHandle(hfdefn);
+
+
+ // Free referenced sub-objects first (referenced by handles).
+ // The hdllentrydefn and hstDocumentation come from the
+ // MEMBER_DEFN part of the FUNC_DEFN.
+ //
+ if (!(pfdefn->IsVirtual())) {
+ hdllentrydefn = pfdefn->Hdllentrydefn();
+ if (hdllentrydefn != HDLLENTRYDEFN_Nil)
+ ReleaseDllentrydefn(hdllentrydefn);
+ }
+
+ // Work out size of ULONG-length-prefixed doc string and free it.
+ hstDocumentation = pfdefn->HstDocumentation();
+ if (hstDocumentation != HST_Nil) {
+ // if this is a property function then pass the owner ship
+ // some other property (if it exists).
+ if (pfdefn->InvokeKind() != INVOKE_FUNC ) {
+ hlnam = pfdefn->Hlnam();
+ hfdefn = HfdefnFirstMeth();
+ while (hfdefn != HDEFN_Nil) {
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+ if ((qfdefn->InvokeKind() != INVOKE_FUNC) &&
+ (hlnam == qfdefn->Hlnam())) {
+ // Assign the doc string to this function
+
+ qfdefn->SetHstDocumentation(hstDocumentation);
+ // set the flag to indicate that we have assigned the
+ // doc string to some other function. So that we do not
+ // release the doc string.
+ fFound = TRUE;
+
+ } // if
+
+ hfdefn = qfdefn->HdefnNext();
+ }// while
+ } // if
+
+ // we did not assign the string to some other function hence
+ // delete the doc string.
+ if (!fFound) {
+ uCbSizeStr = *(ULONG *)m_blkmgr.QtrOfHandle(hstDocumentation);
+ m_blkmgr.FreeChunk(hstDocumentation, (UINT)(uCbSizeStr+sizeof(ULONG)));
+ }
+ }
+
+ // Now free the parts of the FUNC_TYPE_DEFN.
+
+
+ // free the (embedded) formal param list.
+ hparamdefn = pfdefn->m_ftdefn.m_hdefnFormalFirst;
+ if (hparamdefn != HPARAMDEFN_Nil) { // if any params
+ HPARAM_DEFN hparamdefnCur = hparamdefn; // first array elem
+
+ // We have an array of (OLE) PARAM_DEFNs.
+ cArgs = pfdefn->CArgsUnmunged();
+ for (iArg = 0; iArg < cArgs; iArg++) {
+ // Note: we fake the hparamdefn by adding in sizeof(PARAM_DEFN)
+ // each time through the loop.
+ // Note that the OLE impl of FreeParamDefn doesn't actually
+ // free this quasi-chunk, cos we just have a quasi-handle.
+ //
+ FreeParamDefn(hparamdefnCur);
+ hparamdefnCur += sizeof(PARAM_DEFN);
+ }
+
+ m_blkmgr.FreeChunk(hparamdefn, cArgs * sizeof(PARAM_DEFN));
+ }
+
+ // Now, free the TYPE_DEFN owned by the FUNC_TYPE_DEFN.
+ if (!(pfdefn->m_ftdefn.IsSimpleTypeResult()))
+ FreeTypeDefn(pfdefn->m_ftdefn.HtdefnResult());
+
+ DebAssert(sizeof(FUNC_DEFN) == sizeof(VIRTUAL_FUNC_DEFN), " size changed");
+
+ // Finally free top-level memory of FUNC_DEFN itself
+ // Must check to see whether it's a FUNC_DEFN or a
+ // VIRTUAL_FUNC_DEFN.
+ //
+ usSize = pfdefn->HasV2Flags() ? sizeof(FUNC_DEFN):
+ sizeof(FUNC_DEFN) - sizeof(USHORT) ;
+
+ m_blkmgr.FreeChunk(hfdefn, usSize);
+
+ m_blkmgr.DebCheckState(0);
+}
+
+
+/***
+*PRIVATE TYPE_DATA::FreeParamDefn - Release PARAM_DEFN memory.
+*Purpose:
+* Release memory for a PARAM_DEFN and its parts.
+*
+*Implementation Notes:
+* Free referenced sub-chunks first (that this DEFN has
+* handles to, then free top-level chunks).
+* Namely, doc string and TYPE_DEFN.
+*
+*Entry:
+* hparamdefn - handle to a PARAM_DEFN.
+*
+*Exit:
+*
+*Errors:
+* NONE.
+*
+***********************************************************************/
+
+VOID TYPE_DATA::FreeParamDefn(HPARAM_DEFN hparamdefn)
+{
+ PARAM_DEFN *pparamdefn;
+
+ DebAssert(hparamdefn != HPARAMDEFN_Nil,
+ "TYPE_DATA::FreeParamDefn: bad param.");
+
+ pparamdefn = (PARAM_DEFN *)m_blkmgr.QtrOfHandle(hparamdefn);
+
+ // Free referenced sub-objects first (referenced by handles).
+ if (!pparamdefn->IsSimpleType()) {
+ // Free (varlen) TYPE_DEFN
+ FreeTypeDefn(pparamdefn->Htdefn());
+ }
+
+
+ m_blkmgr.DebCheckState(0);
+}
+
+
+
+
+
+
+/***
+*PUBLIC TYPE_DATA::Write - Serialize an instance.
+*Purpose:
+* Serialize an instance.
+*
+*Implementation Notes:
+* Serialization layout:
+* Handle to method listhead.
+* Handle to datamember listhead.
+* Handle to base listhead.
+* Handle to method listtail.
+* Handle to datamember listtail.
+* Handle to base listtail.
+* Embedded BLKMGR
+*
+* Note that it's ok to save BLKMGR handles: when the
+* the TYPE_DATA is deserialized they are still valid since
+* no relocation is done within the block.
+*
+*Entry:
+* pstrm - Pointer to stream to write to.
+*
+*Exit:
+*
+*Errors:
+* TIPERROR.
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR TYPE_DATA::Write(STREAM *pstrm)
+{
+ TIPERROR err;
+
+ DebAssert(pstrm != NULL, "bad param.");
+
+#if HP_BIGENDIAN
+ // swap bytes for mac
+ SwapbmData(FALSE);
+
+ // swap the binding table
+ m_pdtroot->Pdtmbrs()->Pdtbind()->Pdbindnametbl()->SwapBindDescs();
+#endif // HP_BIGENDIAN
+
+ // Serialize BLK_MGR member.
+ // Save the error because we can't return until we've
+ // swapped back.
+ //
+ err = m_blkmgr.Write(pstrm);
+
+#if HP_BIGENDIAN
+ // swap bytes back
+ SwapbmData(TRUE);
+
+ // swap the binding table
+ m_pdtroot->Pdtmbrs()->Pdtbind()->Pdbindnametbl()->SwapBindDescs();
+#endif // HP_BIGENDIAN
+
+ // Now that we've swapped back, we can return the Write error,
+ // if any.
+ //
+ IfErrRet(err);
+
+ // serialize TYPE_DATA meta-info, namely list counts and heads.
+ IfErrRet(pstrm->WriteUShort(m_cMeth));
+ IfErrRet(pstrm->WriteUShort(m_cDataMember));
+ IfErrRet(pstrm->WriteUShort(m_cBase));
+ IfErrRet(pstrm->WriteUShort(m_cNestedType));
+ IfErrRet(pstrm->WriteUShort(m_hdefnFirstMeth));
+ IfErrRet(pstrm->WriteUShort(m_hdefnFirstDataMbrNestedType));
+ IfErrRet(pstrm->WriteUShort(m_hdefnFirstBase));
+ IfErrRet(pstrm->WriteUShort(m_hdefnLastMeth));
+ IfErrRet(pstrm->WriteUShort(m_hdefnLastDataMbrNestedType));
+ IfErrRet(pstrm->WriteUShort(m_hdefnLastBase));
+ IfErrRet(pstrm->WriteUShort(m_htdefnAlias));
+ IfErrRet(pstrm->WriteUShort(m_hmvdefnPredeclared));
+ IfErrRet(pstrm->WriteULong(m_uHelpContextBase));
+ IfErrRet(pstrm->WriteUShort((USHORT)m_isSimpleTypeAlias));
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC TYPE_DATA::Read - Deserialize an instance.
+*Purpose:
+* Deserialize an instance.
+*
+*Implementation Notes:
+* (See Write for layout).
+*
+*Entry:
+* pstrm - Pointer to stream to read from (IN).
+*
+*Exit:
+*
+*Errors:
+* NONE.
+*
+***********************************************************************/
+
+TIPERROR TYPE_DATA::Read(STREAM *pstrm)
+{
+ USHORT isSimpleTypeAlias;
+ TIPERROR err;
+
+ DebAssert(pstrm != NULL, "bad param.");
+
+ // Deserialize BLK_MGR member.
+ IfErrRet(m_blkmgr.Read(pstrm));
+
+ // serialize TYPE_DATA meta-info, namely list counts and heads.
+ IfErrRet(pstrm->ReadUShort(&m_cMeth));
+ IfErrRet(pstrm->ReadUShort(&m_cDataMember));
+ IfErrRet(pstrm->ReadUShort(&m_cBase));
+ IfErrRet(pstrm->ReadUShort(&m_cNestedType));
+ IfErrRet(pstrm->ReadUShort(&m_hdefnFirstMeth));
+ IfErrRet(pstrm->ReadUShort(&m_hdefnFirstDataMbrNestedType));
+ IfErrRet(pstrm->ReadUShort(&m_hdefnFirstBase));
+ IfErrRet(pstrm->ReadUShort(&m_hdefnLastMeth));
+ IfErrRet(pstrm->ReadUShort(&m_hdefnLastDataMbrNestedType));
+ IfErrRet(pstrm->ReadUShort(&m_hdefnLastBase));
+ IfErrRet(pstrm->ReadUShort(&m_htdefnAlias));
+ IfErrRet(pstrm->ReadUShort(&m_hmvdefnPredeclared));
+ IfErrRet(pstrm->ReadULong(&m_uHelpContextBase));
+ IfErrRet(pstrm->ReadUShort(&isSimpleTypeAlias));
+ m_isSimpleTypeAlias = isSimpleTypeAlias; // update bitfield
+
+ DebAssert(Pdtroot()->CompState() == CS_DECLARED,
+ " Should be in Declared State ");
+
+#if HP_BIGENDIAN
+ // for OLE swap all defns
+ SwapbmData(TRUE);
+#endif // HP_BIGENDIAN
+
+ return TIPERR_None;
+}
+
+
+#if HP_BIGENDIAN
+
+/***
+*PRIVATE TYPE_DATA::SwapbmData
+*Purpose:
+* Swap TYPE_DATA defns for mac serialization (typelib only)
+*
+*Entry:
+* fSwapFirst - do the defns need to be swapped _before_ the links
+* are followed?
+*
+*Exit:
+*
+*Errors:
+* NONE.
+*
+*Implementation Notes:
+* traverses the member, method and base lists of the TYPE_DATA,
+* swapping all DEFNs
+*
+***********************************************************************/
+
+VOID TYPE_DATA::SwapbmData(BOOL fSwapFirst)
+{
+ HMBR_VAR_DEFN hmvdefn;
+ DEFN *qdefn;
+ USHORT usDefnkind;
+ sDEFNKIND defnkind;
+
+
+ // swap the data member MBR_VAR_DEFNs
+ for (hmvdefn = (HMBR_VAR_DEFN)HdefnFirstDataMbrNestedType();
+ hmvdefn != HMBRVARDEFN_Nil;) {
+
+ qdefn = QdefnOfHdefn(hmvdefn);
+
+ // 3 BIT Hack::
+ // Before we can correctly swap the DEFN we need to
+ // know the "kind" of the defn. To find the "kind" we might have to
+ // swap the first byte of the DEFN if the defn is already
+ // swapped (i.e. fSwapFirst == TRUE)
+ //
+ // if we need to swap first then swap defnkind.
+ if (fSwapFirst) {
+ SwapStruct(qdefn, "s");
+ usDefnkind = qdefn->Defnkind();
+ // swap back the first word of the defn.
+ SwapStruct(qdefn, "s");
+ defnkind = (DEFNKIND)usDefnkind;
+ }
+ else {
+ defnkind = qdefn->Defnkind();
+ }
+
+
+ if ((DEFNKIND) defnkind == DK_RecTypeDefn) {
+ hmvdefn = (HMBR_VAR_DEFN)SwapRectypeDefnOfHrtdefn((HVAR_DEFN)hmvdefn,
+ fSwapFirst, TRUE);
+
+ }
+ else {
+
+ DebAssert((DEFNKIND) defnkind == DK_VarDefn ||
+ (DEFNKIND) defnkind == DK_MbrVarDefn , " bad defn kind ");
+
+ hmvdefn = (HMBR_VAR_DEFN)SwapVarDefnOfHvdefn((HVAR_DEFN)hmvdefn,
+ fSwapFirst);
+ }
+ }
+
+ // swap the base list MBR_VAR_DEFNs
+ for(hmvdefn = (HMBR_VAR_DEFN)HvdefnFirstBase();
+ hmvdefn != HMBRVARDEFN_Nil;
+ hmvdefn = (HMBR_VAR_DEFN)SwapVarDefnOfHvdefn((HVAR_DEFN)hmvdefn,
+ fSwapFirst));
+
+ // swap the method FUNC_DEFNs
+ SwapAllFuncDefns(fSwapFirst);
+
+ // swap the predeclared MBR_VAR_DEFN, if any
+ hmvdefn = m_hmvdefnPredeclared;
+ if (hmvdefn != HMBRVARDEFN_Nil) {
+ hmvdefn = (HMBR_VAR_DEFN)SwapVarDefnOfHvdefn((HVAR_DEFN)hmvdefn,
+ fSwapFirst);
+ DebAssert(hmvdefn == HMBRVARDEFN_Nil, ""); // shouldn't be a chain
+ }
+ if (Pdtroot()->Pgdtinfo()->GetTypeKind() == TKIND_ALIAS && !m_isSimpleTypeAlias) {
+ DebAssert(m_htdefnAlias != (sHTYPE_DEFN)HTYPEDEFN_Nil, "");
+ SwapTypeDefnOfHtdefn(m_htdefnAlias, fSwapFirst);
+ }
+}
+
+
+/***
+*PRIVATE TYPE_DATA::SwapAllFuncDefns
+*Purpose:
+* Swap TYPE_DATA funcdefns for mac serialization (typelib only)
+*
+*Entry:
+* fSwapFirst - do the defns need to be swapped _before_ the links
+* are followed?
+*
+*Exit:
+*
+*Errors:
+* NONE.
+*
+*Implementation Notes:
+* traverses the method list of the TYPE_DATA, swapping all FUNC_DEFNs
+*
+***********************************************************************/
+
+VOID TYPE_DATA::SwapAllFuncDefns(BOOL fSwapFirst)
+{
+ HFUNC_DEFN hfdefn;
+
+ for (hfdefn = HfdefnFirstMeth();
+ hfdefn != HFUNCDEFN_Nil;
+ hfdefn = SwapFuncDefnOfHfdefn(hfdefn, fSwapFirst));
+}
+
+
+/***
+*PUBLIC TYPE_DATA::SwapVarDefnOfHvdefn
+*Purpose:
+* Swap a VAR_DEFN (or MBR_VAR_DEFN) for mac serialization
+*
+*Entry:
+* hvdefn - handle to the VAR_DEFN (or MBR_VAR_DEFN)
+* fSwapFirst - do the defns need to be swapped _before_ the links
+* are followed?
+*
+*Exit:
+* returns a handle to the next VAR_DEFN in the list
+*
+*Errors:
+* NONE.
+*
+* HVARDEFN_Nil is invalid input!
+*
+***********************************************************************/
+
+HVAR_DEFN TYPE_DATA::SwapVarDefnOfHvdefn(HVAR_DEFN hvdefn, BOOL fSwapFirst)
+{
+ HVAR_DEFN hvdefnNext;
+ VAR_DEFN *qvdefn;
+ BYTE *pbConst, *pbVariantConst;
+ TYPEDESCKIND tdesckind;
+ HST hstDocumentation;
+ USHORT usDefnkind;
+ BOOL fHasV2Flags;
+
+ DebAssert(hvdefn != HVARDEFN_Nil, "Can't swap HVARDEFN_Nil");
+
+ Lock();
+ qvdefn = QvdefnOfHvdefn(hvdefn);
+
+ if (fSwapFirst) {
+
+ // swap either the MBR_VAR_DEFN or the VAR_DEFN
+
+ // first get & un-swap defnkind so we can figure out which one this is
+ SwapStruct(qvdefn, "s");
+ usDefnkind = qvdefn->Defnkind();
+ fHasV2Flags = qvdefn->HasV2Flags();
+ // swap back the first word of the defn.
+ SwapStruct(qvdefn, "s");
+
+ // can't use IsMemberVarDefn() here, because m_defnkind is swapped
+ if ((DEFNKIND) usDefnkind == DK_MbrVarDefn) {
+ SwapStruct((BYTE *)qvdefn, fHasV2Flags ? MBR_VAR_DEFN_V2_LAYOUT:
+ MBR_VAR_DEFN_LAYOUT);
+ }
+ else {
+
+ // swap the VAR_DEFN structure
+ SwapStruct(qvdefn, VAR_DEFN_LAYOUT);
+ }
+
+ // swap the TYPE_DEFN if necessary
+ if (!qvdefn->IsSimpleType()
+ && qvdefn->Htdefn() != HTYPEDEFN_Nil) {
+ SwapTypeDefnOfHtdefn(qvdefn->Htdefn(), fSwapFirst);
+ }
+ }
+
+ // in this section, we have a defn with the correct byte ordering
+
+ DebAssert(qvdefn->IsVarDefn(),
+ "SwapVarDefn: MUST be a VAR_DEFN or MBR_VAR_DEFN");
+
+ hvdefnNext = qvdefn->HdefnNext();
+
+ // swap the length-prefix of the documentation string, if any
+ if ((hstDocumentation = qvdefn->HstDocumentation()) != HST_Nil)
+ SwapStruct((BYTE *)m_blkmgr.QtrOfHandle(hstDocumentation), "l");
+
+ // swap the help context if it is a HCHUNK guy
+ if (qvdefn->IsMemberVarDefn()) {
+ WORD wHelpContext;
+ HCHUNK hchunk;
+ // if there was some encoded string then check/free any space allocated
+ // for the previous help context.
+ wHelpContext = ((MBR_VAR_DEFN *)qvdefn)->WHelpContext();
+
+ if(IsHchunk(wHelpContext)) {
+ // Get the hchunk
+ hchunk = GetHchunk(wHelpContext);
+
+ // check if the hchunk stored is valid. if all top 15 bits are 1 then
+ // it is HCHUNK_Nil and we do not have to swap it. Otherwise swap the
+ // hchunk's data
+ if (hchunk != 0xfffe) {
+ SwapStruct(m_blkmgr.QtrOfHandle(hchunk), "l");
+ }
+ }
+ }
+
+ // swap the constant if it's not a simple constant
+ if (qvdefn->HasConstVal() && !qvdefn->IsSimpleConst()) {
+ // NOTE: there isn't necessarily a const val to swap
+ // if the module hasn't been compiled.
+ //
+ if ((pbConst = PbConstVal(this, qvdefn)) != NULL) {
+
+ // what is the type?
+ if (qvdefn->IsSimpleType()) {
+ tdesckind = qvdefn->QtdefnOfSimpleType()->Tdesckind();
+ }
+ else {
+ tdesckind = QtdefnOfHtdefn(qvdefn->Htdefn())->Tdesckind();
+ }
+ DebAssert(IsSimpleType(tdesckind), "tdesckind must be simple");
+
+ // do any necessary swapping based on the type
+ switch(tdesckind) {
+
+ case TDESCKIND_Uint: // INT's are I4's on the mac & NT. We know we
+ case TDESCKIND_Int: // aren't dealing with an win16 typelib/project
+ // because I2 constants are stored as simple
+ // constants.
+ case TDESCKIND_HResult:
+ case TDESCKIND_Error:
+ case TDESCKIND_Bool:
+ case TDESCKIND_UI4:
+ case TDESCKIND_I4:
+ case TDESCKIND_R4:
+ SwapStruct(pbConst, "l"); // swap 4 bytes
+ break;
+
+ // strings are prefixed by a SHORT, indicating string length
+ case TDESCKIND_String:
+ SwapStruct(pbConst, "s"); // swap 2 bytes
+ break;
+
+ case TDESCKIND_R8:
+ case TDESCKIND_Date:
+ case TDESCKIND_Currency:
+ // swap 8 bytes
+ Swap8Bytes(pbConst);
+ break;
+
+ case TDESCKIND_Value:
+ if (fSwapFirst) {
+ // swap VARIANT structure
+ SwapStruct(pbConst, VARIANT_LAYOUT);
+ }
+ pbVariantConst = (BYTE *)&((LPVARIANT)pbConst)->iVal;
+
+ // swap more bytes based on variant type
+ switch(((LPVARIANT)pbConst)->vt) {
+ case VT_I2:
+ case VT_BOOL:
+ SwapStruct(pbVariantConst, "s");
+ break;
+
+ case VT_I4:
+ case VT_R4:
+ case VT_ERROR:
+ SwapStruct(pbVariantConst, "l");
+ break;
+
+ case VT_R8:
+ case VT_CY:
+ case VT_DATE:
+ Swap8Bytes(pbVariantConst);
+ break;
+
+ case VT_BSTR:
+ // SHORT string length follows VARIANT structure, so swap it
+ SwapStruct(pbConst + sizeof(VARIANT), "s");
+ break;
+
+ case VT_NULL:
+ // do nothing
+ break;
+
+ default:
+ DebHalt("Invalid constant variant type");
+ break;
+ }
+
+ if (!fSwapFirst) {
+ // swap VARIANT structure
+ SwapStruct(pbConst, VARIANT_LAYOUT);
+ }
+ break;
+
+ default:
+ DebHalt("Unsupported constant type");
+ break;
+
+ }
+ } // if pbConst != NULL
+ } // if hasConstVal
+
+ if (!fSwapFirst) {
+ // swap the TYPE_DEFN if necessary
+ if (!qvdefn->IsSimpleType()
+ && qvdefn->Htdefn() != HTYPEDEFN_Nil) {
+ SwapTypeDefnOfHtdefn(qvdefn->Htdefn(), fSwapFirst);
+ }
+
+ // swap the MBR_VAR_DEFN part, if necessary
+ if (qvdefn->IsMemberVarDefn()) {
+ SwapStruct((BYTE *)qvdefn,
+ qvdefn->HasV2Flags() ? MBR_VAR_DEFN_V2_LAYOUT:
+ MBR_VAR_DEFN_LAYOUT);
+ }
+ else {
+
+ // swap the VAR_DEFN structure
+ SwapStruct(qvdefn, VAR_DEFN_LAYOUT);
+ }
+ }
+
+ Unlock();
+
+ return hvdefnNext;
+}
+
+
+
+/***
+*static Swap8Bytes
+*Purpose:
+* Swap 8 bytes in place
+*
+*Entry:
+* pv - pointer to first byte
+*
+*Exit:
+*
+*Errors:
+* NONE.
+*
+***********************************************************************/
+
+static VOID Swap8Bytes(void * pv)
+{
+ ULONG ulFirst, ulLast, ulTemp;
+
+ ulFirst = *(ULONG *)pv;
+ ulLast = *(ULONG *)((BYTE *)pv + 4);
+
+ // byte swap the first long, and the second long
+ // then switch the longs themselves
+ //
+ ulTemp = ((ulFirst & 0x000000FF) << 24) |
+ ((ulFirst & 0x0000FF00) << 8) |
+ ((ulFirst & 0x00FF0000) >> 8) |
+ (ulFirst >> 24);
+
+ ulFirst = ((ulLast & 0x000000FF) << 24) |
+ ((ulLast & 0x0000FF00) << 8) |
+ ((ulLast & 0x00FF0000) >> 8) |
+ (ulLast >> 24);
+
+ ulLast = ulTemp;
+
+ *(ULONG *)pv = ulFirst;
+ *(ULONG *)((BYTE *)pv + 4) = ulLast;
+}
+
+
+
+
+/***
+*PUBLIC TYPE_DATA::SwapFuncDefnOfHfdefn
+*Purpose:
+* Swap a FUNC_DEFN (or VIRTUAL_FUNC_DEFN) for mac serialization
+*
+*Entry:
+* hfdefn - handle to the FUNC_DEFN (or VIRTUAL_FUNC_DEFN)
+* fSwapFirst - do the defns need to be swapped _before_ the links
+* are followed?
+*
+*Exit:
+* returns a handle to the next FUNC_DEFN in the list
+*
+*Errors:
+* NONE.
+*
+* HFUNCDEF_Nil is invalid input!
+*
+***********************************************************************/
+
+#pragma code_seg( CS_CORE2 )
+HFUNC_DEFN TYPE_DATA::SwapFuncDefnOfHfdefn(HFUNC_DEFN hfdefn, BOOL fSwapFirst)
+{
+ HFUNC_DEFN hfdefnNext;
+ HPARAM_DEFN hparamdefn;
+ PARAM_DEFN *qparamdefn;
+ FUNC_DEFN *qfdefn;
+ PARAM_DEFN *qparamdefnNext;
+ UINT i;
+
+ DebAssert(hfdefn != HFUNCDEFN_Nil, "Can't swap HFUNCDEFN_Nil");
+
+ Lock();
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+
+ if (fSwapFirst) {
+ SwapStruct(qfdefn, FUNC_DEFN_LAYOUT);
+ }
+
+ // In this section, we have a defn with the correct byte ordering
+ DebAssert(qfdefn->IsFuncDefn(),
+ "SwapFuncDefn: MUST be a FUNC_DEFN or VIRTUAL_FUNC_DEFN");
+
+ hfdefnNext = qfdefn->HdefnNext();
+
+ // We do not serialize the length of the encoded string in case of OLE.
+
+ // swap the help context if it is a HCHUNK guy
+ WORD wHelpContext;
+ HCHUNK hchunk;
+ // if there was some encoded string then check/free any space allocated
+ // for the previous help context.
+ wHelpContext = qfdefn->WHelpContext();
+
+ if(IsHchunk(wHelpContext)) {
+ // Get the hchunk
+ hchunk = GetHchunk(wHelpContext);
+
+ // check if the hchunk stored is valid. if all top 15 bits are 1 then
+ // it is HCHUNK_Nil and we do not have to swap it. Otherwise swap the
+ // hchunk's data
+ if (hchunk != 0xfffe) {
+ SwapStruct(m_blkmgr.QtrOfHandle(hchunk), "l");
+ }
+ }
+
+ // if necessary, swap the result TYPE_DEFN
+ //
+ if(!qfdefn->m_ftdefn.IsSimpleTypeResult() &&
+ qfdefn->m_ftdefn.HtdefnResult() != HTYPEDEFN_Nil) {
+ SwapTypeDefnOfHtdefn(qfdefn->m_ftdefn.HtdefnResult(), fSwapFirst);
+ }
+
+ // swap the PARAM_DEFNs
+ hparamdefn = (HPARAM_DEFN)qfdefn->m_ftdefn.m_hdefnFormalFirst;
+
+ // Layout of OB and OLE PARAM_DEFN(s) are different.
+ if (qfdefn->CArgsUnmunged() > 0) {
+ // We have an array of PARAM_DEFNs.
+ qparamdefn = QparamdefnOfHparamdefn(hparamdefn);
+ }
+
+ for (i=0; i < qfdefn->CArgsUnmunged(); i++) {
+
+ DebAssert(qfdefn->CArgsUnmunged(), " # of arg should be > 0");
+
+ if (fSwapFirst) {
+ SwapStruct((BYTE *)qparamdefn, PARAM_DEFN_LAYOUT);
+ }
+
+ // swap the TYPE_DEFN if necessary
+ if (!qparamdefn->IsSimpleType() &&
+ qparamdefn->Htdefn() != HTYPEDEFN_Nil) {
+ SwapTypeDefnOfHtdefn(qparamdefn->Htdefn(), fSwapFirst);
+ }
+
+ qparamdefnNext = qparamdefn->QparamdefnNext();
+
+ if (!fSwapFirst) {
+ SwapStruct((BYTE *)qparamdefn, PARAM_DEFN_LAYOUT);
+ }
+
+ qparamdefn = qparamdefnNext;
+ }
+
+ // Note: DllEntryDefns are swapped by entrymgr and hence we do not have
+ // to do it here.
+
+ // swap the extra V2 flags word if it's present
+ if (qfdefn->HasV2Flags()) {
+ SwapStruct(((BYTE*)qfdefn + sizeof(FUNC_DEFN) - sizeof(USHORT)),
+ FUNC_DEFN_V2FLAGS_LAYOUT);
+ }
+
+ // if it's a VIRTUAL_FUNC_DEFN, swap the non-FUNC_DEFN
+ // part of the structure
+ //
+ if (qfdefn->IsVirtualFuncDefn()) {
+ SwapStruct((BYTE *)qfdefn + sizeof(FUNC_DEFN), VIRTUAL_FUNC_DEFN_LAYOUT);
+ }
+
+ if (!fSwapFirst) {
+ SwapStruct(qfdefn, FUNC_DEFN_LAYOUT);
+ }
+
+ Unlock();
+ return hfdefnNext;
+}
+#pragma code_seg( )
+
+
+
+/***
+*PUBLIC TYPE_DATA::SwapTypeDefnOfHtdefn
+*Purpose:
+* Swap a TYPE_DEFN for mac serialization
+*
+*Implementation Notes:
+* defers to SwapTypeDefnOfQtdefn
+*
+*Entry:
+* htdefn - handle to the TYPE_DEFN
+* fSwapFirst - do the defns need to be swapped _before_ the links
+* are followed?
+*
+*Exit:
+*
+*Errors:
+* NONE.
+*
+* HTYPEDEFN_Nil is invalid input!
+*
+***********************************************************************/
+
+VOID TYPE_DATA::SwapTypeDefnOfHtdefn(HTYPE_DEFN htdefn, BOOL fSwapFirst)
+{
+ DebAssert(htdefn != HTYPEDEFN_Nil, "Can't swap HTYPEDEFN_Nil" );
+
+ Lock();
+ SwapTypeDefnOfQtdefn(QtdefnOfHtdefn(htdefn), fSwapFirst);
+ Unlock();
+}
+
+
+
+/***
+*PRIVATE TYPE_DATA::SwapTypeDefnOfQtdefn
+*Purpose:
+* Swap a TYPE_DEFN for mac serialization
+*
+*Implementation Notes:
+* Does a 'deep swap' of the TYPE_DEFN - possibly recursive.
+* Note that a qointer is passed to this routine -
+* TYPE_DATA must be locked!!! (there really isn't a reason why this
+* routine should be called by anything other than SwapTypeDefnOfHtdefn
+* so this shouldn't be a problem)
+*
+*Entry:
+* qtdefn - qointer to the TYPE_DEFN
+* fSwapFirst - do the defns need to be swapped _before_ the links
+* are followed?
+*
+*Exit:
+*
+*Errors:
+* NONE.
+*
+***********************************************************************/
+
+VOID TYPE_DATA::SwapTypeDefnOfQtdefn(TYPE_DEFN *qtdefn, BOOL fSwapFirst)
+{
+ BYTE * pbFollowing;
+ SAFEARRAY *qad;
+ UINT i;
+
+ pbFollowing = (BYTE *)qtdefn + sizeof(TYPE_DEFN);
+
+ if (fSwapFirst) {
+ // swap the TYPE_DEFN structure
+ SwapStruct(qtdefn, TYPE_DEFN_LAYOUT);
+ }
+
+ // in this section, we have a defn with the correct byte ordering
+
+ // determine if any other swapping has to be done based on
+ // the tdesckind (see defn.hxx)
+ //
+ switch (qtdefn->Tdesckind()) {
+
+ case TDESCKIND_Ptr:
+ // the TYPE_DEFN following specifies the type being pointed to
+ SwapTypeDefnOfQtdefn((TYPE_DEFN *)pbFollowing, fSwapFirst);
+ break;
+
+ case TDESCKIND_UserDefined:
+ // swap the sHIMPTYPE following
+ SwapStruct(pbFollowing, "s");
+ break;
+
+ case TDESCKIND_Carray:
+ case TDESCKIND_BasicArray:
+
+ if (fSwapFirst) {
+ // swap following sHARRAY_DESC
+ SwapStruct(pbFollowing, "s");
+ }
+
+ qad = QarraydescOfHarraydesc(*(sHARRAY_DESC *)pbFollowing);
+
+ // swap array descriptor
+ if (fSwapFirst) {
+ SwapStruct(qad, AD_LAYOUT);
+ }
+ for (i=0; i < qad->cDims; i++) {
+ SwapStruct(&qad->rgsabound[i], DD_LAYOUT);
+ }
+ if (!fSwapFirst) {
+ SwapStruct(qad, AD_LAYOUT);
+ }
+
+ // swap array TYPE_DEFN
+ SwapTypeDefnOfQtdefn((TYPE_DEFN *)(pbFollowing + sizeof(sHARRAY_DESC)),
+ fSwapFirst);
+
+ if (!fSwapFirst) {
+ // swap following sHARRAY_DESC
+ SwapStruct(pbFollowing, "s");
+ }
+ break;
+ }
+
+ if (!fSwapFirst) {
+ // swap the TYPE_DEFN structure
+ SwapStruct(qtdefn, TYPE_DEFN_LAYOUT);
+ }
+}
+
+
+/***
+*PUBLIC TYPE_DATA::SwapRectypeDefnOfHrtdefn
+*Purpose:
+* Swap a RECTYPE_DEFN for mac serialization
+*
+*Entry:
+* hrtdefn - handle to the RECTYPE_DEFN
+* fSwapFirst - do the defns need to be swapped _before_ the links
+* are followed?
+*
+*Exit:
+* returns a handle to the next RECTYPE_DEFN in the list
+*
+*Errors:
+* NONE.
+*
+* HRECTYPEDEFN_Nil is invalid input!
+*
+***********************************************************************/
+
+HRECTYPE_DEFN TYPE_DATA::SwapRectypeDefnOfHrtdefn(HRECTYPE_DEFN hrtdefn,
+ BOOL fSwapFirst,
+ BOOL fSwapVarDefns)
+{
+ RECTYPE_DEFN *qrtdefn;
+ HRECTYPE_DEFN hrtdefnNext;
+ HVAR_DEFN hvdefn;
+
+ DebAssert(hrtdefn != HRECTYPEDEFN_Nil, "Can't swap HRECTYPEDEFN_Nil" );
+
+ Lock();
+ qrtdefn = QrtdefnOfHrtdefn(hrtdefn);
+
+ if (fSwapFirst) {
+ SwapStruct(qrtdefn, RECTYPE_DEFN_LAYOUT);
+
+ // if TYPE_DATA is swapping then swap the contained var defns.
+ if (fSwapVarDefns) {
+ // walk the list of var defns and swap them.
+ // swap the base list MBR_VAR_DEFNs
+ for (hvdefn = (HVAR_DEFN)qrtdefn->HvdefnFirstMember();
+ hvdefn != HVARDEFN_Nil;
+ hvdefn = (HVAR_DEFN)SwapVarDefnOfHvdefn((HVAR_DEFN)hvdefn,
+ fSwapFirst));
+
+ }
+
+ }
+
+ hrtdefnNext = (HRECTYPE_DEFN)qrtdefn->HdefnNext();
+
+ if (!fSwapFirst) {
+
+ // if TYPE_DATA is swapping then swap the contained var defns.
+ if (fSwapVarDefns) {
+ // walk the list of var defns and swap them.
+ // swap the base list MBR_VAR_DEFNs
+ for (hvdefn = (HVAR_DEFN)qrtdefn->HvdefnFirstMember();
+ hvdefn != HVARDEFN_Nil;
+ hvdefn = (HVAR_DEFN)SwapVarDefnOfHvdefn((HVAR_DEFN)hvdefn,
+ fSwapFirst));
+ }
+
+ SwapStruct(qrtdefn, RECTYPE_DEFN_LAYOUT);
+
+ }
+
+ Unlock();
+
+ return hrtdefnNext;
+}
+
+#endif // HP_BIGENDIAN
+
+
+/***
+*PRIVATE TYPE_DATA::Alloc[--]Defn - Allocate a some kind of DEFN
+*Purpose:
+* The following functions all share the same macro
+* template that allocates some sort of structure
+* in this TYPE_DATA's block.
+*
+*Implementation Notes:
+*
+*Entry:
+* Pointer to handle of the structure (OUT).
+*
+*Exit:
+* Produces handle.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+// Here's the macro.
+// It's pretty straightforward.
+// Note the syntax for constructing an instance
+// at a particular location.
+//
+#define ALLOCSTRUCT(type,phandle,fV2) \
+ TIPERROR err; \
+ HCHUNK hchunk; \
+ DebAssert(phandle != NULL, "AllocStruct: phandle is NULL"); \
+ IfErrGo(m_blkmgr.AllocChunk(&hchunk, fV2 ? sizeof(type): (sizeof(type) - sizeof(USHORT)) )); \
+ new (QdefnOfHdefn(hchunk)) type; \
+ *phandle = (sH ## type)hchunk; \
+ return TIPERR_None; \
+Error: \
+ *phandle = (sHCHUNK)HCHUNK_Nil; \
+ return err
+
+TIPERROR TYPE_DATA::AllocMbrVarDefn(sHMBR_VAR_DEFN *phmvdefn, BOOL fV2Flags)
+{
+ ALLOCSTRUCT(MBR_VAR_DEFN,phmvdefn, fV2Flags);
+}
+
+
+TIPERROR TYPE_DATA::AllocFuncDefn(sHFUNC_DEFN *phfdefn, BOOL fV2Flags)
+{
+ ALLOCSTRUCT(FUNC_DEFN,phfdefn, fV2Flags);
+}
+
+TIPERROR TYPE_DATA::AllocVirtualFuncDefn(sHVIRTUAL_FUNC_DEFN *phvfdefn,
+ BOOL fV2Flags)
+{
+ ALLOCSTRUCT(VIRTUAL_FUNC_DEFN,phvfdefn, fV2Flags);
+}
+
+
+
+
+
+/***
+*PRIVATE TYPE_DATA::AllocTypeDefn - Allocate a TYPE_DEFN
+*Purpose:
+* Allocate a TYPE_DEFN.
+*
+*Implementation Notes:
+*
+*Entry:
+* UINT cTypes - number of simple type defns passed in
+* USHORT rgtdesckind - array of tdesckinds
+* (this was TYPEDESCKIND, but a CFront bug forces it to USHORT)
+* sHTYPE_DEFN *phtdefn - pointer to tdefn handle (OUT)
+*
+*Exit:
+* Produces TYPE_DEFN handle.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR TYPE_DATA::AllocTypeDefn(UINT cTypes,
+ TYPEDESCKIND rgtdesckind[],
+ sHTYPE_DEFN *phtdefn)
+{
+ TIPERROR err;
+ HCHUNK hchunk;
+
+ DebAssert(phtdefn != NULL, "AllocTypeDefn: phtdefn is NULL");
+
+ IfErrRet(m_blkmgr.AllocChunk(&hchunk,
+ SizeTypeDefnOfTDescKind(cTypes, rgtdesckind)));
+ *phtdefn = (sHTYPE_DEFN)hchunk;
+ new (QtdefnOfHtdefn(*phtdefn)) TYPE_DEFN;
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+
+
+/***
+*PRIVATE TYPE_DATA::AllocArrayDescriptor - Allocate an array descriptor.
+*Purpose:
+* Allocate an array descriptor.
+*
+*Implementation Notes:
+*
+*Entry:
+* pharraydesc - Pointer to handle of array descriptor (OUT).
+*
+*Exit:
+* Produces array descriptor handle.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+TIPERROR TYPE_DATA::AllocArrayDescriptor(UINT uNDim, sHARRAY_DESC *pharraydesc)
+{
+ ULONG uSize;
+ TIPERROR err;
+ HCHUNK hchunk;
+
+ DebAssert(pharraydesc != NULL, "AllocArrayDescriptor: pharraydesc is NULL");
+
+ uSize = CbSizeArrayDesc(uNDim);
+ IfErrRet(m_blkmgr.AllocChunk(&hchunk, (UINT)uSize));
+ *pharraydesc = (sHARRAY_DESC)hchunk;
+ rtArrayInit( QarraydescOfHarraydesc(*pharraydesc), uNDim );
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+
+
+/***
+*PUBLIC TYPE_DATA::HdefnOfHmember - Map HMEMBER to HDEFN
+*Purpose:
+* Map HMEMBER to HDEFN.
+*
+*Implementation Notes:
+* For OLE the hmember is just the hdefn with the low bit twiddled for
+* functions, except for BASIC and TKIND_DISPATCH which just linear search.
+* The tricky one is for TKIND_INTERFACE, DISPID_VALUE which is zero.
+* For this we cached the hfdefn in m_hfdefnValue. Note that this can't be a
+* hvardefn because TKIND_INTERFACE can't have them.
+*
+*Entry:
+* hmember - Handle of member we want (IN).
+*
+*Exit:
+* *pdefnkind - kind
+* returns hdefn of hmember (returns a VARDEFN or a FUNCDEFN only)
+* HCHUNK_Nil if unsuccessful.
+*
+*Errors:
+* None.
+*
+***********************************************************************/
+
+HDEFN TYPE_DATA::HdefnOfHmember(HMEMBER hmember, UINT *pdefnkind)
+{
+ HDEFN hdefn;
+ DebAssert(hmember != DISPID_UNKNOWN, "which defn do you want?");
+
+ // do linear search on defns
+ // Check variables first.
+ // Let's see if this is a vardefn?
+ //
+ hdefn = (HDEFN) HmvdefnOfHmember(hmember);
+
+ if (hdefn != HDEFN_Nil) {
+ // yes, it's a vardefn
+ DebAssert(QdefnOfHdefn(hdefn)->IsVarDefn(), "Bad defn kind");
+ *pdefnkind = DK_VarDefn;
+ }
+ else {
+ // well, a funcdefn then?
+ hdefn = (HDEFN) HfdefnOfHmember(hmember);
+ if (hdefn != HDEFN_Nil) {
+ *pdefnkind = DK_FuncDefn;
+ }
+ }
+
+ return hdefn;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::HfdefnOfHmember - Map HMEMBER to HFUNC_DEFN
+*Purpose:
+* Map HMEMBER to HFUNC_DEFN.
+*
+*Implementation Notes:
+* Walk funcdefn list searching for matching hmember.
+*
+*Entry:
+* hmember - Handle of function member we want (IN).
+* fInvokekind - The invoke kind of the function we want to bind to.
+* (one of INVOKE_FUNC, INVOKE_PROPGET, INVOKE_PROPPUT,
+* INVOKE_PROPPUTREF).
+* The default value for this parm (if it is omitted)
+* contains all invoke kind(s), which causes us to return
+* the first function with the give hmember (used when
+* we don't care about the invoke kind).
+*
+*Exit:
+* Returns HFUNC_DEFN of FUNC_DEFN describing function or
+* HCHUNK_Nil if unsuccessful.
+*
+*Errors:
+* None.
+*
+***********************************************************************/
+HFUNC_DEFN TYPE_DATA::HfdefnOfHmember(HMEMBER hmember,
+ UINT fInvokekind) const
+{
+ HFUNC_DEFN hfdefn;
+ FUNC_DEFN *pfdefn;
+
+
+ // at least one of the interesting bits must be set
+ DebAssert((fInvokekind & (INVOKE_FUNC | INVOKE_PROPERTYGET | INVOKE_PROPERTYPUT | INVOKE_PROPERTYPUTREF)) != 0, "invalid invoke flags");
+
+ // For ole ITypeInfos where we computed the id, the hmember is just the
+ // hdefn in the loword and a bit set in the hiword for functions.
+ // Special case of the Value parameter of TKIND_INTERFACE
+ //
+ DebAssert(DISPID_VALUE == 0, "dispid value must be 0 else weirdness");
+ if (hmember == DISPID_VALUE) {
+ if (Pdtroot()->Pgdtinfo()->GetTypeKind() == TKIND_INTERFACE) {
+ // get cached defn, if any
+ hfdefn = m_hfdefnValue;
+ if (hfdefn == HDEFN_Nil) {
+ return hfdefn;
+ }
+ goto short_circuit; // for property functions, this will be the
+ // first hfdefn with the given id. So use
+ // our "shortcut" method to skip into the loop
+ }
+ }
+
+
+ hfdefn = m_hdefnFirstMeth;
+ while (hfdefn != HFUNCDEFN_Nil) {
+short_circuit:
+ pfdefn = QfdefnOfHfdefn(hfdefn);
+ if (pfdefn->Hmember() == hmember && pfdefn->InvokeKind() & fInvokekind) {
+ return hfdefn;
+ }
+ hfdefn = pfdefn->HdefnNext();
+ }
+
+ // couldn't find it...
+ return HFUNCDEFN_Nil;
+}
+
+
+
+
+/***
+*PUBLIC TYPE_DATA::HvdefnPredeclared.
+*Purpose:
+* returns the predeclared VAR_DEFN
+*
+*Entry:
+* None.
+*
+*Exit:
+* HVAR_DEFN
+*
+***********************************************************************/
+
+HVAR_DEFN TYPE_DATA::HvdefnPredeclared() const
+{
+ return m_hmvdefnPredeclared;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::SetHvdefnPredeclared.
+*Purpose:
+* Sets the predeclared VAR_DEFN
+* NOTE: lsb reserved to indicate IsSimpleTypeAlias
+*
+*Entry:
+* None.
+*
+*Exit:
+*
+***********************************************************************/
+#pragma code_seg( CS_CORE2 )
+VOID TYPE_DATA::SetHvdefnPredeclared(HVAR_DEFN hvdefnPredeclared)
+{
+ m_hmvdefnPredeclared = (sHMBR_VAR_DEFN)hvdefnPredeclared;
+}
+#pragma code_seg( )
+
+
+
+
+/***
+*PUBLIC TYPE_DATA::HmvdefnOfHmember - Map HMEMBER to HMBRVAR_DEFN
+*Purpose:
+* Map HMEMBER to HMBRVAR_DEFN.
+*
+*Implementation Notes:
+* Walk vardefn list searching for matching hmember.
+*NOTE: only works for OLE typeinfos
+*
+*Entry:
+* hmember - Handle of data member we want (IN).
+*
+*Exit:
+* Returns HMBRVAR_DEFN of MBRVAR_DEFN describing data member or
+* HVARDEFN_Nil if unsuccessful.
+*
+*Errors:
+* None.
+*
+***********************************************************************/
+
+HMBR_VAR_DEFN TYPE_DATA::HmvdefnOfHmember(HMEMBER hmember) const
+{
+ HMBR_VAR_DEFN hmvdefn;
+ MBR_VAR_DEFN *qmvdefn;
+
+ if (hmember == ID_DEFAULTINST) {
+ // special case of the id for the pre-declared identifier.
+ return HvdefnPredeclared();
+ }
+
+
+ hmvdefn = HdefnFirstDataMbrNestedType();
+ while (hmvdefn != HMBRVARDEFN_Nil) {
+ qmvdefn = QmvdefnOfHmvdefn(hmvdefn);
+ DebAssert(qmvdefn->IsMemberVarDefn(), "Bad defn kind");
+ if (qmvdefn->Hmember() == hmember) {
+ break;
+ } else {
+ hmvdefn = qmvdefn->HdefnNext();
+ }
+ }
+
+ return hmvdefn;
+}
+
+
+#if ID_DEBUG
+
+
+
+/***
+*PUBLIC TYPE_DATA::DebCheckState - check TYPE_DATA state
+*Purpose:
+* Check TYPE_DATA state
+*
+*Implementation Notes:
+* Defers to embedded BLK_MGR method.
+*
+*Entry:
+* uLevel Check level.
+*
+*Exit:
+*
+*Errors:
+* Asserts on failures.
+*
+**********************************************************************/
+
+VOID TYPE_DATA::DebCheckState(UINT uLevel) const
+{
+ HDEFN hdefn;
+
+ m_blkmgr.DebCheckState(uLevel);
+
+ // check member lists
+ if (uLevel > 0) {
+ DebAssert((m_hdefnFirstMeth == HDEFN_Nil) ||
+ (m_cMeth == ::Count((TYPE_DATA *)this, m_hdefnFirstMeth)),
+ "bad func list.");
+
+ DebAssert((m_hdefnFirstDataMbrNestedType == HDEFN_Nil) ||
+ ((USHORT)(m_cDataMember + m_cNestedType) ==
+ ::Count((TYPE_DATA *)this, m_hdefnFirstDataMbrNestedType)),
+ "bad var list.");
+
+ DebAssert((m_hdefnFirstBase == HDEFN_Nil) ||
+ (m_cBase == ::Count((TYPE_DATA *)this, m_hdefnFirstBase)),
+ "bad base list.");
+
+ hdefn = m_hdefnFirstMeth;
+ while (hdefn != HDEFN_Nil) {
+ DebCheckDefn(hdefn);
+ hdefn = QdefnOfHdefn(hdefn)->HdefnNext();
+ }
+
+ hdefn = m_hdefnFirstDataMbrNestedType;
+ while (hdefn != HDEFN_Nil) {
+ DebCheckDefn(hdefn);
+ hdefn = QdefnOfHdefn(hdefn)->HdefnNext();
+ }
+
+ hdefn = m_hdefnFirstBase;
+ while (hdefn != HDEFN_Nil) {
+ DebCheckDefn(hdefn);
+ hdefn = QdefnOfHdefn(hdefn)->HdefnNext();
+ }
+ }
+}
+
+
+/***
+*PUBLIC TYPE_DATA::DebCheck*Defn - check TYPE_DATA Defns
+*Purpose:
+* Check TYPE_DATA Defn
+*
+*Implementation Notes:
+* DebCheckDefn should not be called for DLLENTRY_DEFNs, for these
+* DebCheckDllentryDefn should be called directly.
+*
+*Entry:
+* HDEFN handle of defn to check. Note we switch off defnkind.
+*
+*Exit:
+*
+*Errors:
+* Asserts on failures.
+*
+**********************************************************************/
+
+VOID TYPE_DATA::DebCheckVarDefn(HVAR_DEFN hvdefn) const
+{
+ VAR_DEFN *qvdefn;
+
+ qvdefn = QvdefnOfHvdefn(hvdefn);
+
+ DebAssert(qvdefn->IsPublic() || qvdefn->IsPrivate(), "bad access.");
+ if (qvdefn->HasConstVal()) {
+ DebAssert(qvdefn->IsDataMember() ||
+ qvdefn->IsEnumerator(),
+ "only locals, datamembers, enumerators can be constants.");
+ }
+
+ if (qvdefn->IsStatic()) {
+ DebAssert(qvdefn->IsDataMember() ||
+ qvdefn->IsEnumerator(),
+ "only locals, datamembers, enumerators can be static.");
+ }
+}
+
+VOID TYPE_DATA::DebCheckParamDefn(HPARAM_DEFN hparamdefn) const
+{
+}
+
+
+VOID TYPE_DATA::DebCheckMbrVarDefn(HMBR_VAR_DEFN hmvdefn) const
+{
+ DebCheckVarDefn((HVAR_DEFN)hmvdefn); // check the vardefn part
+ // CONSIDER: any more state consistency to check here?
+}
+
+
+VOID TYPE_DATA::DebCheckFuncDefn(HFUNC_DEFN hfdefn) const
+{
+ FUNC_DEFN *qfdefn;
+
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+
+ DebAssert(qfdefn->IsPublic() || qfdefn->IsPrivate(),
+ "should be public or private.");
+ DebCheckFuncTypeDefn(qfdefn->m_ftdefn);
+}
+
+
+VOID TYPE_DATA::DebCheckVirtualFuncDefn(HVIRTUAL_FUNC_DEFN hvfdefn) const
+{
+ DebCheckFuncDefn((HFUNC_DEFN)hvfdefn); // check funcdefn part
+ // CONSIDER: anything else to check?
+}
+
+
+VOID TYPE_DATA::DebCheckFuncTypeDefn(FUNC_TYPE_DEFN ftdefn) const
+{
+}
+
+
+VOID TYPE_DATA::DebCheckRecTypeDefn(HRECTYPE_DEFN hrtdefn) const
+{
+ UINT cMember;
+ RECTYPE_DEFN *qrtdefn = QrtdefnOfHrtdefn(hrtdefn);
+
+ cMember = ::Count((TYPE_DATA *)this, qrtdefn->HvdefnFirstMember());
+ DebAssert(cMember < USHRT_MAX, "bad list.");
+}
+
+
+VOID TYPE_DATA::DebCheckDefn(HDEFN hdefn) const
+{
+ DEFN *qdefn;
+
+ if (hdefn != HDEFN_Nil) {
+ qdefn = QdefnOfHdefn(hdefn);
+ switch (qdefn->Defnkind()) {
+ case DK_VarDefn:
+ DebCheckVarDefn(hdefn);
+ break;
+ case DK_ParamDefn:
+ DebCheckParamDefn(hdefn);
+ break;
+ case DK_MbrVarDefn:
+ DebCheckMbrVarDefn(hdefn);
+ break;
+ case DK_FuncDefn:
+ DebCheckFuncDefn(hdefn);
+ break;
+ case DK_VirtualFuncDefn:
+ DebCheckVirtualFuncDefn(hdefn);
+ break;
+ case DK_RecTypeDefn:
+ DebCheckRecTypeDefn(hdefn);
+ break;
+ default:
+ DebHalt("bad defnkind.");
+ } // switch
+ }
+}
+
+
+#endif // ID_DEBUG
+
+
+/*********************************************************************/
+// These functions have been moved to the end of the file because
+// they are only called by internal clients.
+
+
+/***
+*PRIVATE TYPE_DATA::SizeTypeDefnOfTDescKind - Calculates size of TYPE_DEFN
+*Purpose:
+* Calculates size of a TYPE_DEFN instance. TYPE_DEFN
+* is defined recursively in terms of itself.
+*
+*Implementation Notes:
+* CONSIDER: switching on rel/debug and use default clause
+*
+
+*Entry:
+* cTypes - size of typedesckind array (IN)
+* rgtdesckind - array of typedesckinds (IN)
+*
+*Exit:
+* Returns size of TYPE_DEFN for array of typedesckind.
+*
+*Errors:
+* NONE.
+*
+***********************************************************************/
+
+#pragma code_seg(CS_CREATE)
+UINT TYPE_DATA::SizeTypeDefnOfTDescKind(UINT cTypes,
+ TYPEDESCKIND *rgtdesckind) const
+{
+ UINT cbSizeChunk = 0, uType;
+ TYPEDESCKIND tdesckind;
+
+ for (uType = 0; uType < cTypes; uType++) {
+ tdesckind = rgtdesckind[uType];
+ if (IsSimpleType(tdesckind)) {
+ DebAssert(uType+1 == cTypes, "Only last typedefn can be simple");
+ cbSizeChunk += sizeof(TYPE_DEFN);
+ }
+ else {
+ switch (tdesckind) {
+ case TDESCKIND_Ptr: {
+ cbSizeChunk += sizeof(TYPE_DEFN);
+ break;
+ }
+ case TDESCKIND_Carray:
+ case TDESCKIND_BasicArray: {
+ cbSizeChunk += sizeof(TYPE_DEFN) + sizeof(sHARRAY_DESC);
+ break;
+ }
+ case TDESCKIND_UserDefined: {
+ cbSizeChunk += sizeof(TYPE_DEFN) + sizeof(sHIMPTYPE);
+ break;
+ }
+ default: {
+ DebHalt("TYPE_DATA::SizeTypeDefnOfTDescKind: whoops! bad tdesckind.");
+ break;
+ } // end default
+ } // end switch
+ } // end else
+ } // end for
+
+ return cbSizeChunk;
+}
+#pragma code_seg()
+
+
+/***
+*PRIVATE TYPE_DATA::SizeOfTypeDefn - Calculates size of TYPE_DEFN
+*Purpose:
+* Calculates size of a TYPE_DEFN instance. TYPE_DEFN
+* is defined recursively in terms of itself.
+*
+*Implementation Notes:
+* Note: Can't inline since recursive.
+* CONSIDER: switching on rel/debug and use default clause
+*
+*Entry:
+* htdefn - Handle of TYPE_DEFN (IN)
+*
+*Exit:
+* Returns size of TYPE_DEFN (var len).
+*
+*Errors:
+* NONE.
+*
+***********************************************************************/
+
+UINT TYPE_DATA::SizeOfTypeDefn(HTYPE_DEFN htdefn) const
+{
+ return ((TYPE_DEFN *)m_blkmgr.QtrOfHandle(htdefn))->DefnSize();
+}
+
+UINT TYPE_DEFN::DefnSize()
+{
+ UINT cbSizeChunk;
+ TYPEDESCKIND tdesckind;
+
+ tdesckind = Tdesckind();
+ cbSizeChunk = sizeof(TYPE_DEFN);
+ if (IsSimpleType(tdesckind)) {
+ return cbSizeChunk;
+ }
+ else {
+ switch (tdesckind) {
+ case TDESCKIND_Ptr: {
+ // adjust handle to next contiguous TYPE_DEFN.
+ return cbSizeChunk +
+ ((TYPE_DEFN *)(((BYTE * const)this)+cbSizeChunk))->DefnSize();
+ }
+ case TDESCKIND_Carray:
+ case TDESCKIND_BasicArray: {
+ return cbSizeChunk + sizeof(sHARRAY_DESC) +
+ ((TYPE_DEFN *)(((BYTE * const)this)+cbSizeChunk+sizeof(sHARRAY_DESC)))->DefnSize();
+ }
+ case TDESCKIND_UserDefined: {
+ // NOTE: assumes that the cName attr is 0!
+ // Can't assert here cos don't have TYPE_DEFN.
+ //
+ return cbSizeChunk + sizeof(sHIMPTYPE);
+ }
+ default:
+ DebHalt("TYPE_DEFN::DefnSize: whoops! bad tdesckind.");
+ return 0; // C7 wants return value on all control paths.
+ }
+ }
+}
+
+
+/***
+*PRIVATE TYPE_DATA::MapTypeDefn - Maps TYPE_DEFN to new block
+*Purpose:
+* Walks TYPE_DEFN and maps any owned parts to new chunks.
+* Also returns size of TYPE_DEFN so that caller can map
+* the TYPE_DEFN to a new chunk.
+*
+* IMPORTANT! IMPORTANT! IMPORTANT! IMPORTANT! IMPORTANT! IMPORTANT!
+* IMPORTANT! IMPORTANT! IMPORTANT! IMPORTANT! IMPORTANT! IMPORTANT!
+* IMPORTANT! IMPORTANT! IMPORTANT! IMPORTANT! IMPORTANT! IMPORTANT!
+*
+* Right now the only client that compacts the TYPE_DATA
+* is the BASIC_TYPESRC. This function is only meant for
+* use within BASIC_TYPESRC::Compact. Be careful if you
+* plan to use it for general-purpose TYPE_DATA compaction.
+*
+* IMPORTANT! IMPORTANT! IMPORTANT! IMPORTANT! IMPORTANT! IMPORTANT!
+* IMPORTANT! IMPORTANT! IMPORTANT! IMPORTANT! IMPORTANT! IMPORTANT!
+* IMPORTANT! IMPORTANT! IMPORTANT! IMPORTANT! IMPORTANT! IMPORTANT!
+*
+*Implementation Notes:
+* Works like TYPE_DATA::SizeOfTypeDefn.
+* Recurses for arrays and pointer/ref types.
+*
+*Entry:
+* htdefn - Handle of TYPE_DEFN (IN)
+*
+*Exit:
+* Returns size of TYPE_DEFN (var len).
+*
+*Errors:
+* NONE.
+*
+***********************************************************************/
+
+
+
+/***
+*PUBLIC TYPE_DATA::AllocVardefnPredeclared - Allocs vardefn for predeclared
+*Purpose:
+* Allocs vardefn for predeclared id.
+*
+*Implementation Notes:
+*
+
+*Entry:
+* htdefn - Handle of TYPE_DEFN (IN)
+*
+*Exit:
+* Returns size of TYPE_DEFN (var len).
+*
+*Errors:
+* NONE.
+*
+***********************************************************************/
+
+TIPERROR TYPE_DATA::AllocVardefnPredeclared()
+{
+ MBR_VAR_DEFN *qmvdefnPredeclared;
+ TYPE_DEFN *qtdefnPredeclared;
+ sHTYPE_DEFN htdefnPredeclared;
+ BSTRA bstr;
+ NAMMGR *pnammgr;
+ HLNAM hlnam;
+ TYPEDESCKIND tdesckind;
+ sHIMPTYPE himptypePredeclared;
+ sHMBR_VAR_DEFN hmvdefnPredeclared;
+ TIPERROR err = TIPERR_None;
+
+ // We need to initialize the Var defn for predeclared identifier
+ // Allocate a VAR_DEFN
+ //
+ IfErrRet(AllocMbrVarDefn(&hmvdefnPredeclared, FALSE));
+ SetHvdefnPredeclared(hmvdefnPredeclared);
+
+ // Get the name of the class
+ IfErrGo(TiperrOfHresult(m_pdtroot->Pgdtinfo()->GetDocumentation(
+ -1,
+ (BSTR *)&bstr,
+ NULL,
+ NULL,
+ NULL)));
+
+#if OE_WIN32
+ HRESULT hresult;
+ if ((hresult = ConvertBstrToAInPlace(&bstr)) != NOERROR) {
+ err = TiperrOfHresult(hresult);
+ goto Error;
+ }
+#endif //OE_WIN32
+
+ // Get the hlnam of the name
+ IfErrGo(m_pdtroot->GetNamMgr(&pnammgr));
+ IfErrGo(pnammgr->HlnamOfStr(bstr, &hlnam, FALSE, NULL));
+
+ // Free the BSTR
+ FreeBstrA(bstr);
+
+ qmvdefnPredeclared =
+ (MBR_VAR_DEFN *)QvdefnOfHvdefn(HvdefnPredeclared());
+ qmvdefnPredeclared->SetHlnam(hlnam);
+ qmvdefnPredeclared->SetHasNew(TRUE);
+ qmvdefnPredeclared->SetVkind(VKIND_DataMember);
+ qmvdefnPredeclared->SetHmember((ULONG)ID_DEFAULTINST);
+ qmvdefnPredeclared->SetOVar(HMEMBER_PredeclId);
+ qmvdefnPredeclared->SetIsStatic(TRUE);
+
+ // Alloc a TYPE_DEFN for the predecl'ed var
+ qmvdefnPredeclared->SetIsSimpleType(FALSE);
+ tdesckind = TDESCKIND_UserDefined;
+ IfErrGo(AllocTypeDefn(1, &tdesckind, &htdefnPredeclared));
+
+ // Get a qointer to the TYPE_DEFN and initialize the data members
+ qtdefnPredeclared = QtdefnOfHtdefn(htdefnPredeclared);
+
+ qtdefnPredeclared->SetTdesckind(TDESCKIND_UserDefined);
+ qtdefnPredeclared->SetPtrkind(PTRKIND_Basic);
+
+ // Set the himptype by importing ourselves.
+ // Note we don't want to add a reference!
+ //
+ IfErrGo(m_pimpmgr->RegisterDeclRefDep(m_pdtroot->Pgdtinfo()));
+ himptypePredeclared =
+ m_pimpmgr->GetHimptypeIfExists(m_pdtroot->Pgdtinfo());
+ DebAssert(himptypePredeclared != HIMPTYPE_Nil, "should have existed.");
+
+ // Get a qointer to the TYPE_DEFN and initialize the data members
+ qtdefnPredeclared = QtdefnOfHtdefn(htdefnPredeclared);
+
+ *(qtdefnPredeclared->Qhimptype()) = himptypePredeclared;
+
+ // Update the htdefn field of the vardefn
+ // (Note need to rederef)
+ //
+ QvdefnOfHvdefn(HvdefnPredeclared())->SetHtdefn(htdefnPredeclared);
+ return err;
+
+Error:
+ FreeMbrVarDefn(hmvdefnPredeclared);
+ // Free the BSTR
+ FreeBstrA(bstr);
+ return err;
+}
diff --git a/private/oleauto/src/typelib/tdata2.cxx b/private/oleauto/src/typelib/tdata2.cxx
new file mode 100644
index 000000000..10ce43924
--- /dev/null
+++ b/private/oleauto/src/typelib/tdata2.cxx
@@ -0,0 +1,3651 @@
+/***
+*tdata2.cxx - Type Data part 2
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* TYPEDATA manages the internal representation of a class's members.
+* In particular, it maintains three linked lists of data members,
+* base members and methods respectively.
+* See \silver\doc\ic\dtmbrs.doc for more information.
+*
+*Revision History:
+*
+* [00] 11-Aug-92 stevenl: Broken off from tdata.cxx.
+* [01] 18-Jan-93 w-peterh: implemented AddFuncDesc/ AddVarDesc
+* [02] 02-Feb-93 w-peterh: added IndexOfFuncName
+* [03] 12-Feb-93 w-peterh: bunches of typelib support
+* [04] 02-Mar-93 w-peterh: fix AddVarDesc of const
+* enable EI_OB AddRefTypeInfo and AddImplType
+* [05] 19-Mar-93 w-jeffc: added GetDocumentationOfFuncName
+* [06] 30-Apr-93 w-jeffc: made DEFN data members private
+*
+*Implementation Notes:
+* ST's are implemented as ULONG prefixed.
+*
+*****************************************************************************/
+
+#define TDATA_VTABLE // export blk mgr vtable
+
+#include "silver.hxx"
+#include "xstring.h" // for memcpy
+#include "typelib.hxx"
+#include "tdata.hxx" // no longer includes dtinfo.hxx
+#include "clutil.hxx"
+#include "nammgr.hxx"
+#include "impmgr.hxx"
+#include "entrymgr.hxx"
+#include "exbind.hxx"
+
+#pragma hdrstop(RTPCHNAME)
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+char szOleTdata2Cxx[] = __FILE__;
+#define SZ_FILE_NAME szOleTdata2Cxx
+#else
+static char szTdata2Cxx[] = __FILE__;
+#define SZ_FILE_NAME szTdata2Cxx
+#endif
+#endif
+
+
+// Second bit indicates if the number is negtive.
+#define SetNegativeBit(us, f) \
+ us = f ? (us | 0x0002) : (us & ~0x0002)
+#define IsNegative(us) (us & 0x0002)
+
+// First bit indicates if we stored a hlnam or a number
+#define SetIsNumber(us) (us |= 0x0001)
+#define SetIsHchunk(us) (us &= ~0x0001)
+#define IsHchunk(us) (!(us & 0x0001))
+
+#define AbsDiff(a,b) (a > b ? (a-b) : (b-a))
+#define GetHchunk(us) (us & ~0x0001)
+#define GetDiff(us) (USHORT(us >> 2))
+
+// A helper function for retrieving pointers to consts for both
+// VAR_DEFN and MBR_VAR_DEFNs
+// Returns NULL if no const val exists yet (i.e. the compiler
+// hasn't been called to evaluate a const initializer yet for
+// this variable).
+//
+BYTE *PbConstVal(TYPE_DATA *ptdata, VAR_DEFN *qvdefn)
+{
+ HCHUNK hchunk;
+
+ DebAssert(qvdefn->HasConstVal(), "bad const.");
+ DebAssert(!qvdefn->IsSimpleConst(), "can't be simple.");
+
+ // NOTE: the following could be done with nested conditional
+ // exprs (?:) -- but it got too cryptic.
+ //
+ hchunk = qvdefn->IsMemberVarDefn() ?
+ ((MBR_VAR_DEFN *)qvdefn)->HchunkConstMbrVal() :
+ qvdefn->HchunkConstVal();
+ return (hchunk == HCHUNK_Nil) ? NULL : ptdata->QtrOfHandle(hchunk);
+}
+
+
+#pragma code_seg(CS_CREATE)
+// A helper function for setting const val for both
+// VAR_DEFN and MBR_VAR_DEFNs
+//
+VOID SetHchunkConstVal(VAR_DEFN *qvdefn, HCHUNK hchunk)
+{
+ DebAssert(qvdefn->HasConstVal(), "bad const.");
+ DebAssert(!qvdefn->IsSimpleConst(), "can't be simple.");
+ if (qvdefn->IsMemberVarDefn()) {
+ ((MBR_VAR_DEFN *)qvdefn)->SetHchunkConstMbrVal(hchunk);
+ }
+ else {
+ qvdefn->SetHchunkConstVal(hchunk);
+ }
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_CREATE)
+TIPERROR ValidateMemid(MEMBERID memid)
+{
+ // If the top two bits of the memid are 01, we must verify that the
+ // memid is in the format 010000<inheritence level><16 anything bits>.
+ // Unfortunately, we don't know what the inheritence level is at
+ // this point, so we have to check in DYN_TYPEMEMBERS::AllocHmembers.
+
+ // validate incoming memid -- the top bit is reserved for internal
+ // use (special case allowing of DISPID_UNKNOWN & DISPID_NEWENUM)
+ //
+#ifndef DISPID_COLLECT // temporary until everybody upgrades header files
+#define DISPID_COLLECT (-8)
+#endif
+ if (memid & HMEMBER_ReservedBits) {
+ // NOTE explict casting to a LONG to work around C7 optimizer bug
+ switch ((long)(memid)) {
+ case DISPID_UNKNOWN:
+ case DISPID_NEWENUM:
+ case DISPID_EVALUATE:
+ case DISPID_CONSTRUCTOR:
+ case DISPID_DESTRUCTOR:
+ case DISPID_COLLECT:
+ break;
+
+ default:
+ // Also allow the special range -999 to -500 for the controls folks.
+ // This range will be documented as reserved in the next version.
+ if ((long)memid >= -999 && (long)memid <= -500) {
+ break;
+ }
+ // Also allow the special range 0x80010000 to 0x8001FFFF for Control
+ // containers such as VB4.
+ if (HIWORD(memid) == 0x8001) {
+ break;
+ }
+ return TIPERR_InvalidArg;
+ }
+ }
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+/***
+*PUBLIC TYPE_DATA::HvdefnOfHlnam
+*Purpose:
+* get the hvdefn of an hlnam
+*
+*Entry:
+* hlnam - hlnam to search for
+*
+*Exit:
+* hvdefn of matching variable
+***********************************************************************/
+
+HVAR_DEFN TYPE_DATA::HvdefnOfHlnam(HLNAM hlnam)
+{
+ HVAR_DEFN hvdefn;
+ VAR_DEFN *qvdefn;
+
+ hvdefn = HdefnFirstDataMbrNestedType();
+ while (hvdefn != HVARDEFN_Nil) {
+ qvdefn = QvdefnOfHvdefn(hvdefn);
+ DebAssert(qvdefn->IsVarDefn(), "Bad defn kind");
+ if (qvdefn->Hlnam() == hlnam) {
+ break;
+ }
+ hvdefn = qvdefn->HdefnNext();
+ }
+
+ return hvdefn;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::HfdefnFirstOfHlnam
+*Purpose:
+* get the hfdefn of an hlnam
+*
+*Entry:
+* hlnam - hlnam to search for
+*
+*Exit:
+* hfdefn of matching function
+***********************************************************************/
+
+HFUNC_DEFN TYPE_DATA::HfdefnFirstOfHlnam(HLNAM hlnam,INVOKEKIND *pinvokekind)
+{
+ return HfdefnNextOfHlnam(hlnam, HfdefnFirstAvailMeth(),pinvokekind);
+}
+
+
+/***
+*PUBLIC TYPE_DATA::HfdefnNextOfHlnam
+*Purpose:
+* get the hfdefn of an hlnam
+*
+*Entry:
+* hlnam - hlnam to search for
+* hfdefn -
+*
+*Exit:
+* hfdefn of matching function
+***********************************************************************/
+
+HFUNC_DEFN TYPE_DATA::HfdefnNextOfHlnam(HLNAM hlnam, HFUNC_DEFN hfdefn,INVOKEKIND *pinvokekind)
+{
+ FUNC_DEFN *qfdefn;
+
+ while (hfdefn != HFUNCDEFN_Nil) {
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+ if (qfdefn->Hlnam() == hlnam) {
+ *pinvokekind = qfdefn->InvokeKind();
+ break;
+ }
+ hfdefn = HfdefnNextAvailMeth(hfdefn);
+ }
+
+ return hfdefn;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::HfdefnFirstAvailMeth - First availible method in list.
+*Purpose:
+* Returns first availible method in list of class's methods.
+*
+*Implementation Notes:
+*
+*Entry:
+* None
+*
+*Exit:
+* returns handle to first availible function.
+*
+***********************************************************************/
+
+HFUNC_DEFN TYPE_DATA::HfdefnFirstAvailMeth()
+{
+ // All OLE functions are availilble.
+ return HfdefnFirstMeth();
+}
+
+
+/***
+*PUBLIC TYPE_DATA::GetFuncDescOfHfdefn
+*Purpose:
+* Get FUNC_DESC given a FUNC_DEFN.
+*
+*Entry:
+* hfdefn - handle to FUNC_DEFN (IN).
+* lplpfuncdesc - Returns a pointer to a FUNCDESC that describes
+* the specified function.
+*
+*Exit:
+* *lplpfuncdesc points to a FUNC_DESC or error returned
+***********************************************************************/
+TIPERROR TYPE_DATA::GetFuncDescOfHfdefn(HFUNC_DEFN hfdefn,
+ FUNCDESC **ppfuncdesc)
+{
+ FUNC_DEFN *qfdefn;
+ PARAM_DEFN *qparamdefn;
+ HPARAM_DEFN hparamdefn;
+ FUNCDESC *pfuncdesc;
+ ELEMDESC *pelemdesc;
+ UINT i;
+ TIPERROR err = TIPERR_None;
+ WORD wFlags;
+ UINT cArgs;
+ TYPE_DEFN *qtdefn;
+
+ DebAssert(hfdefn != HFUNCDEFN_Nil, "bad FUNC_DEFN handle.");
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+
+ // Create a FUNCDESC instance.
+ //
+ pfuncdesc = MemNew(FUNCDESC);
+ if (pfuncdesc == NULL) {
+ return TIPERR_OutOfMemory;
+ }
+ ::new (pfuncdesc) FUNCDESC;
+ InitFuncDesc(pfuncdesc);
+
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+
+ // set FUNCKIND
+ // VIRTUAL, PUREVIRTUAL, NONVIRTUAL, STATIC, DISPATCH
+ if (qfdefn->IsVirtual()) {
+ pfuncdesc->funckind =
+ qfdefn->IsPure() ? FUNC_PUREVIRTUAL : FUNC_VIRTUAL;
+ // for FUNC_VIRTUAL, specifies the offset in the virtual function table
+ pfuncdesc->oVft = (SHORT)((VIRTUAL_FUNC_DEFN *)qfdefn)->Ovft();
+ }
+ else {
+ pfuncdesc->oVft = 0;
+ if (qfdefn->IsNonVirtual())
+ pfuncdesc->funckind = FUNC_NONVIRTUAL;
+ else if (qfdefn->IsStatic())
+ pfuncdesc->funckind = FUNC_STATIC;
+ else if (qfdefn->IsDispatch())
+ pfuncdesc->funckind = FUNC_DISPATCH;
+ else DebHalt("Invalid FuncKind");
+ }
+
+ // invocation kind; indicates if this is a property function and if so what kind
+ pfuncdesc->invkind = qfdefn->InvokeKind();
+
+ // CC_MSCPASCAL, CC_MACPASCAL, CC_STDCALL, CC_THISCALL,CC_CDECL
+ pfuncdesc->callconv = (CALLCONV)qfdefn->m_ftdefn.CcUnmunged();
+
+ // count of parameters
+ cArgs = pfuncdesc->cParams = qfdefn->m_ftdefn.CArgsUnmunged();
+
+ // count of optional parameters; see detailed description below
+ pfuncdesc->cParamsOpt = qfdefn->m_ftdefn.CArgsOpt();
+
+//CONSIDER: (size/speed) are we double-initializing any of these fields?
+//CONSIDER: What exactly does InitFuncDesc() above do?
+
+ // scodes (reserved for future use)
+ pfuncdesc->lprgscode = NULL;
+ pfuncdesc->cScodes = 0;
+
+ // idldesc
+ pfuncdesc->elemdescFunc.idldesc.wIDLFlags = 0;
+#if OE_WIN16
+ pfuncdesc->elemdescFunc.idldesc.bstrIDLInfo = NULL;
+#else //OE_WIN16
+ pfuncdesc->elemdescFunc.idldesc.dwReserved = 0;
+#endif //OE_WIN16
+
+ // Set Function Return Type
+ if (qfdefn->IsSub()) {
+ pfuncdesc->elemdescFunc.tdesc.vt = VT_VOID;
+ }
+ else {
+ IfErrGo(AllocTypeDescOfTypeDefn(
+ qfdefn->m_ftdefn.HtdefnResultUnmunged(),
+ qfdefn->m_ftdefn.IsSimpleTypeResultUnmunged(),
+ &(pfuncdesc->elemdescFunc.tdesc)));
+ }
+ // contains the ID, name, and return type of the function
+ pfuncdesc->memid = qfdefn->Hmember();
+
+ // set the func flags
+ if (qfdefn->IsRestricted()) {
+ pfuncdesc->wFuncFlags = (WORD) FUNCFLAG_FRESTRICTED;
+ }
+ else {
+ pfuncdesc->wFuncFlags = 0;
+ }
+ if (qfdefn->HasV2Flags()) {
+ // if the typelib was create using V2 typelib.dll then we store the
+ // flags in the word we added.
+ pfuncdesc->wFuncFlags |= qfdefn->WFuncFlags();
+ }
+
+ // Parameters
+ //
+ if (cArgs > 0) {
+ pelemdesc = (ELEMDESC *)MemAlloc(sizeof(ELEMDESC) * cArgs);
+
+ if (pelemdesc == NULL) {
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+
+ // array containing the ID, name, and return type of the parameters
+ pfuncdesc->lprgelemdescParam = pelemdesc;
+ for (i = 0; i < cArgs; i++) {
+ InitElemDesc(pfuncdesc->lprgelemdescParam + i);
+ }
+
+ hparamdefn = qfdefn->m_ftdefn.m_hdefnFormalFirst;
+
+#if ID_DEBUG & EI_OLE
+ if (qfdefn->CArgs() > 0) {
+ DebAssert(hparamdefn != HPARAMDEFN_Nil,
+ "number vs actual dont match");
+ }
+#endif // ID_DEBUG & EI_OLE
+
+ i = 0;
+ while (i < cArgs) {
+ // In OLE we have an array of PARAM_DEFN(s).
+ // Get the ith PARAM_DEFN
+ //
+ qparamdefn = QparamdefnOfIndex(hparamdefn, i);
+
+
+ // idldesc
+ wFlags = IDLFLAG_NONE;
+ // set the idldesc
+ if (qparamdefn->IsSimpleType()) {
+ qtdefn = qparamdefn->QtdefnOfSimpleType();
+ }
+ else {
+ qtdefn = QtdefnOfHtdefn(qparamdefn->Htdefn());
+ }
+
+ if (qtdefn->IsModeIn() || qtdefn->IsModeInOut()) {
+ wFlags |= (WORD) IDLFLAG_FIN;
+ }
+ if (qtdefn->IsModeOut() || qtdefn->IsModeInOut()) {
+ wFlags |= (WORD) IDLFLAG_FOUT;
+ }
+ if (qtdefn->IsRetval()) {
+ wFlags |= (WORD) IDLFLAG_FRETVAL;
+ }
+ if (qtdefn->IsLCID()) {
+ wFlags |= (WORD) IDLFLAG_FLCID;
+ }
+ pelemdesc[i].idldesc.wIDLFlags = wFlags;
+
+
+#if OE_WIN16
+ pelemdesc[i].idldesc.bstrIDLInfo = NULL;
+#else //OE_WIN16
+ pelemdesc[i].idldesc.dwReserved = 0;
+#endif //OE_WIN16
+
+ // Parameter Type
+ IfErrGo(AllocTypeDescOfTypeDefn(qparamdefn->Htdefn(),
+ qparamdefn->IsSimpleType(),
+ &(pelemdesc[i].tdesc)));
+ i++;
+ } // while param list or array
+
+ } // if parameters
+ else {
+ // no parameters
+ pfuncdesc->lprgelemdescParam = NULL;
+ }
+
+ *ppfuncdesc = pfuncdesc;
+ return err;
+
+Error:
+ FreeFuncDesc(pfuncdesc);
+
+ return err;
+}
+
+
+
+
+
+
+/***
+*PUBLIC TYPE_DATA::GetFuncDesc
+*Purpose:
+* Get the index'th FUNCDESC
+*
+*Entry:
+* index - Index of the function to be returned.
+* The index should be in the range
+* of 0 up to the number of functions in this type -1.
+* lplpfuncdesc - Returns a pointer to a FUNCDESC that describes
+* the specified function.
+*
+*Exit:
+* *lplpfuncdesc points to a FUNCDESC or error returned
+***********************************************************************/
+TIPERROR TYPE_DATA::GetFuncDesc(UINT index,
+ FUNCDESC **ppfuncdesc)
+{
+ FUNC_DEFN *qfdefn;
+ HFUNC_DEFN hfdefn, hfdefnStart;
+ UINT ifdefn, ifdefnStart;
+ TIPERROR err = TIPERR_None;
+
+ if (CAvailMeth() <= index) {
+ return TIPERR_ElementNotFound;
+ }
+
+ // count up to the function indicated
+ // in OLE use the cache if there is one and it's useful.
+ if ((HfdefnLast() != HFUNCDEFN_Nil) &&
+ (index >= UOrdinalHfdefnLast())) {
+ // start from where we stopped last
+ ifdefnStart = UOrdinalHfdefnLast();
+ hfdefnStart = HfdefnLast();
+ }
+ else {
+ ifdefnStart = 0;
+ hfdefnStart = HfdefnFirstMeth();
+ }
+
+ for (ifdefn = ifdefnStart, hfdefn = hfdefnStart;;) {
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+
+ if (index == ifdefn++) {
+ // cache the match in OLE
+ SetUOrdinalHfdefnLast(index);
+ SetHfdefnLast(hfdefn);
+ break;
+ } // if match
+
+ hfdefn = HfdefnNextAvailMeth(hfdefn);
+ } // for
+
+ return GetFuncDescOfHfdefn(hfdefn, ppfuncdesc);
+}
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC TYPE_DATA::AddFuncDesc
+*Purpose:
+* Adds a function/method description to the TypeInfo.
+* The index is used to specify the order of the functions.
+* The first function has an index of zero. If an index is
+* specified that is greater than the number of functions
+* currently in the TypeInfo then an error is returned.
+* Calling this function does not pass ownership of the FUNCDESC
+* structure to the IDynTypeInfo.
+*
+*Entry:
+* index - Index before which function is to be inserted.
+* The index should be in the range
+* of 0 up to the number of functions in this type.
+* pfuncdesc - A pointer to a FUNCDESC that describes
+* the specified function.
+* phfdefn - Pointer to allocated handle (OUT). If NULL then
+* client doesn't care (default).
+*
+*Exit:
+* Status code returned.
+***********************************************************************/
+
+TIPERROR TYPE_DATA::AddFuncDesc(UINT index,
+ FUNCDESC *pfuncdesc,
+ HFUNC_DEFN *phfdefn)
+{
+ sHVIRTUAL_FUNC_DEFN hvfdefn;
+ VIRTUAL_FUNC_DEFN *qvfdefn;
+ sHTYPE_DEFN htdefn;
+ HFUNC_DEFN hfdefnNext;
+ sHFUNC_DEFN hfdefn;
+ FUNC_DEFN *qfdefn;
+ sHDEFN hdefnLast;
+ PARAM_DEFN *qparamdefn;
+ UINT i, cArgs;
+ TIPERROR err;
+ WORD wIDLFlags;
+ TYPE_DEFN *qtdefn;
+ HPARAM_DEFN hparamdefn;
+ BOOL fIsSimpleType;
+ BOOL fV2Flags;
+
+
+ DebAssert(pfuncdesc != NULL,
+ "TYPE_DATA::AddFuncDesc: null FUNCDESC.");
+
+ DebAssert(Pdtroot()->CompState() == CS_UNDECLARED, "Invalid state");
+
+ if (index > CAvailMeth()) {
+ return TIPERR_ElementNotFound;
+ }
+
+ fV2Flags = ((pfuncdesc->wFuncFlags & ~FUNCFLAG_FRESTRICTED) != 0);
+
+ // Now fill in the fields of the FUNC_DEFN to be added
+ // (with the attributes of the input param FUNCDESC).
+ // VIRTUAL, PUREVIRTUAL, NONVIRTUAL, STATIC, DISPATCH
+ switch(pfuncdesc->funckind) {
+ case FUNC_PUREVIRTUAL:
+ case FUNC_VIRTUAL:
+ IfErrRet(AllocVirtualFuncDefn(&hvfdefn, fV2Flags));
+ hfdefn = (HFUNC_DEFN) hvfdefn;
+ qvfdefn = QvfdefnOfHvfdefn(hvfdefn);
+ qfdefn = (FUNC_DEFN *) qvfdefn;
+ qvfdefn->SetFkind(FKIND_Virtual);
+ if (pfuncdesc->funckind == FUNC_PUREVIRTUAL) {
+ qvfdefn->SetIsPure(TRUE); // Default is false
+ }
+ // this is set to -1 so that TKIND_DISPATCH functions
+ // are intialized to some known bogus value
+ // others will be set at layout time w-peterh 17-Feb-93
+ ((VIRTUAL_FUNC_DEFN *)qfdefn)->SetOvft((UINT)-1);
+ break;
+
+ case FUNC_NONVIRTUAL:
+ case FUNC_STATIC:
+ case FUNC_DISPATCH:
+ IfErrRet(AllocFuncDefn(&hfdefn, fV2Flags));
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+ if (pfuncdesc->funckind == FUNC_NONVIRTUAL) {
+ qfdefn->SetFkind(FKIND_NonVirtual);
+ }
+ else if (pfuncdesc->funckind == FUNC_STATIC) {
+ qfdefn->SetFkind(FKIND_Static);
+ }
+ else {
+ qfdefn->SetFkind(FKIND_Dispatch);
+ }
+ break;
+ default:
+ return TIPERR_InvalidArg;
+ }
+
+ // NOTE: All error paths after this point must free the hfdefn!
+
+ // NOTE: There should not be any error between the allocation of the defn
+ // and this call.
+ // set the flag indicating whether we have the V2 flags.
+ qfdefn->SetHasV2Flag(fV2Flags);
+
+ // validate the incoming memid
+ IfErrGo(ValidateMemid(pfuncdesc->memid));
+
+ qfdefn->SetHmember(pfuncdesc->memid);
+
+ // invocation kind; indicates if this is a property function and if so what kind
+ qfdefn->SetInvokeKind(pfuncdesc->invkind);
+ qfdefn->SetHlnam(HLNAM_Nil);
+
+ if (pfuncdesc->wFuncFlags & FUNCFLAG_FRESTRICTED) {
+ qfdefn->SetIsRestricted(TRUE);
+ }
+ if (fV2Flags) {
+ DebAssert(qfdefn->HasV2Flags(), "Bad qfdefn");
+ qfdefn->SetWFuncFlags(pfuncdesc->wFuncFlags);
+ }
+
+
+ // CC_MSCPASCAL, CC_MACPASCAL, CC_STDCALL, CC_THISCALL,CC_CDECL
+ // CC_CDECL is 1
+ DebAssert(pfuncdesc->callconv >= CC_CDECL && pfuncdesc->callconv < CC_MAX, "invalid callconv");
+ qfdefn->m_ftdefn.SetCc(pfuncdesc->callconv);
+ if ((pfuncdesc->cParams > MAX_CARGS) || (pfuncdesc->cParams < 0)){
+ err = TIPERR_OutOfBounds;
+ goto Error;
+ }
+ cArgs = pfuncdesc->cParams;
+
+ if ((pfuncdesc->cParamsOpt > MAX_CARGSOPT) || (pfuncdesc->cParamsOpt < -1)) {
+ err = TIPERR_OutOfBounds;
+ goto Error;
+ }
+ if (pfuncdesc->cParamsOpt == -1) {
+ DebAssert(pfuncdesc->cParams >= 1,
+ "number of optional params can't be more then total");
+ qfdefn->m_ftdefn.SetCArgsOpt(OPTARGS_LIST);
+ }
+ else {
+ DebAssert(pfuncdesc->cParamsOpt <= pfuncdesc->cParams,
+ "number of optional params can't be more then total");
+ qfdefn->m_ftdefn.SetCArgsOpt(pfuncdesc->cParamsOpt);
+ }
+
+ // The following are initted by the constructor:
+ // hstDocumentation, uHelpContext, hdllentrydefn,
+ // access and declkind.
+ //
+ IfErrGo(AllocTypeDefnOfTypeDesc(&(pfuncdesc->elemdescFunc.tdesc),
+ 0,
+ &htdefn,
+ TRUE, // coclasses allowed
+ &fIsSimpleType));
+
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+ qfdefn->m_ftdefn.SetHtdefnResult(htdefn);
+ qfdefn->m_ftdefn.SetIsSimpleTypeResult(fIsSimpleType);
+
+ // parameters
+ hdefnLast = HDEFN_Nil;
+ hparamdefn = HPARAMDEFN_Nil;
+
+ // In OLE allocate enough memory for all the PARAM_DEFN(s).
+ // For OB we allocate one at a time.
+ //
+ // if there are parameters for this function then allocate that array of
+ // of param defn(s).
+ if (cArgs > 0) {
+ IfErrGo(m_blkmgr.AllocChunk(&hparamdefn,
+ cArgs*sizeof(PARAM_DEFN)));
+
+ // construct all the paramdefn's
+ for (i = 0; i < cArgs; i++) {
+ qparamdefn = QparamdefnOfIndex(hparamdefn, i);
+ new (qparamdefn) PARAM_DEFN; // constuct in place
+ }
+ }
+
+ // Dereference the qointer to the funcdefn.
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+ qfdefn->m_ftdefn.m_hdefnFormalFirst = hparamdefn;
+ qfdefn->m_ftdefn.SetCArgs(cArgs); // can now set the cArgs, now that
+ // the paramdefn's are allocated/init'ed
+ // (required by FreeFuncDefn)
+
+ for (i = 0; i < cArgs; i++) {
+ // set parameter type
+ IfErrGo(AllocTypeDefnOfTypeDesc(&(pfuncdesc->lprgelemdescParam[i].tdesc),
+ 0,
+ &htdefn,
+ TRUE, // coclasses allowed
+ &fIsSimpleType));
+
+ // NOTE -- need to set up IsSimpleType AFTER AllocTypeDefnOfTypeDesc,
+ // or else FreeFuncDefn/FreeParamDefn will crap out if
+ // AllocTypeDefnOfTypeDesc failed
+
+ // Get the ith param defn
+ qparamdefn = QparamdefnOfIndex(hparamdefn, i); // rederef
+ qparamdefn->SetHtdefn(htdefn);
+
+ // Determine if type supports "IsSimpleType" optimization.
+ qparamdefn->SetIsSimpleType(fIsSimpleType);
+ qparamdefn->SetHlnam(HLNAM_Nil);
+
+ // Set the param kind.
+ wIDLFlags = pfuncdesc->lprgelemdescParam[i].idldesc.wIDLFlags;
+ DebAssert((wIDLFlags & ~(IDLFLAG_FIN
+ | IDLFLAG_FOUT
+ | IDLFLAG_FRETVAL
+ | IDLFLAG_FLCID
+ )) == 0, "unknown wIDLFLags");
+#if OE_WIN16
+ DebAssert(pfuncdesc->lprgelemdescParam[i].idldesc.bstrIDLInfo == NULL,
+ "bstrIDLInfo must be NULL for future compatibility");
+#else //OE_WIN16
+ DebAssert(pfuncdesc->lprgelemdescParam[i].idldesc.dwReserved == 0,
+ "dwReserved must be 0 for future compatibility");
+#endif //OE_WIN16
+
+ // Get pointer to the TYPE_DEFN.
+ //
+ // if the parameter is a simple type then htdefn is the TYPE_DEFN
+ if (qparamdefn->IsSimpleType()) {
+ qtdefn = qparamdefn->QtdefnOfSimpleType();
+ }
+ else {
+ qtdefn = QtdefnOfHtdefn(htdefn);
+ }
+
+ // Set the paramkind
+ if (wIDLFlags & IDLFLAG_FIN) {
+ if (wIDLFlags & IDLFLAG_FOUT) {
+ qtdefn->SetParamkind(PARAMKIND_InOut);
+ }
+ else {
+ qtdefn->SetParamkind(PARAMKIND_In);
+ }
+ }
+ else {
+ if (wIDLFlags & IDLFLAG_FOUT) {
+ qtdefn->SetParamkind(PARAMKIND_Out);
+ }
+ else {
+ qtdefn->SetParamkind(PARAMKIND_Ignore);
+ }
+ }
+
+ if (wIDLFlags & (IDLFLAG_FRETVAL | IDLFLAG_FLCID)) {
+ TYPE_DEFN * qtdefnResult = QtdefnResultOfHfdefn(hfdefn);
+ DebAssert(qtdefnResult != NULL, "return type should have been set");
+ if (wIDLFlags & IDLFLAG_FRETVAL) {
+ qtdefn->SetIsRetval(TRUE);
+ // note param has RETVAL attr
+ qtdefnResult->SetIsRetval(TRUE);
+ }
+ if (wIDLFlags & IDLFLAG_FLCID) {
+ qtdefn->SetIsLCID(TRUE);
+ // note param has LCID attr
+ qtdefnResult->SetIsLCID(TRUE);
+ }
+ }
+
+ } // for
+
+
+ // insert into list of func_defns if index != ~0
+
+ // check for insert at end of list
+ if (index == CAvailMeth()) {
+ m_hdefnLastMeth = hfdefn;
+ }
+ // check for insert at begining of list
+ if (index == 0) {
+ QfdefnOfHfdefn(hfdefn)->SetHdefnNext(m_hdefnFirstMeth);
+ m_hdefnFirstMeth = hfdefn;
+ }
+ else {
+ hfdefnNext = m_hdefnFirstMeth;
+ qfdefn = QfdefnOfHfdefn(hfdefnNext);
+ while (--index) {
+ hfdefnNext = qfdefn->HdefnNext();
+ qfdefn = QfdefnOfHfdefn(hfdefnNext);
+ } // while
+ QfdefnOfHfdefn(hfdefn)->SetHdefnNext(qfdefn->HdefnNext());
+ qfdefn->SetHdefnNext(hfdefn);
+ }
+
+ m_cMeth++;
+
+
+ // Return the allocated handle if they want it.
+ if (phfdefn != NULL) {
+ *phfdefn = hfdefn;
+ }
+ return err;
+
+Error:
+ FreeFuncDefn(hfdefn);
+ return err;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC TYPE_DATA::GetVarDescOfHvdefn
+*Purpose:
+* Get a VARDESC given a VAR_DEFN
+*
+*Entry:
+* hvdefn - Handle to VAR_DEFN (IN).
+* ppvardesc - Returns a pointer to a VARDESC that describes
+* the specified variable (OUT).
+*
+*Exit:
+* *ppvardesc points to a VARDESC or error returned
+***********************************************************************/
+
+TIPERROR TYPE_DATA::GetVarDescOfHvdefn(HVAR_DEFN hvdefn,
+ VARDESCA **ppvardesc)
+{
+ VAR_DEFN *qvdefn;
+ VARDESCA *pvardesc;
+ TYPEDESCKIND tdesckind;
+ VARIANT *pvariant;
+ UINT cb;
+ BSTR bstr;
+ TIPERROR err = TIPERR_None;
+#if OE_WIN32
+ HRESULT hresult;
+#endif //OE_WIN32
+ TYPE_DEFN *qtdefn;
+ PTRKIND ptrkind;
+
+ DebAssert(hvdefn != HVARDEFN_Nil, "bad VAR_DEFN handle.");
+ // Create a VAR_DESC instance.
+ //
+ pvardesc = MemNew(VARDESCA);
+ if (pvardesc == NULL) {
+ return TIPERR_OutOfMemory;
+ }
+ ::new (pvardesc) VARDESCA;
+
+ InitVarDesc(pvardesc);
+
+ pvardesc->wVarFlags = 0;
+
+ qvdefn = QvdefnOfHvdefn(hvdefn);
+
+ // set varkind
+ if (qvdefn->IsStatic()) {
+ pvardesc->varkind = VAR_STATIC;
+ pvardesc->oInst = NULL; // set oInst/lpvarValue to NULL
+ }
+ else if (qvdefn->HasConstVal()) {
+ pvardesc->varkind = VAR_CONST;
+ // lpvarValue will be set below
+ }
+ else if (qvdefn->IsDispatch()) {
+ pvardesc->varkind = VAR_DISPATCH;
+ pvardesc->oInst = qvdefn->GetOVar();
+ }
+ else {
+ pvardesc->varkind = VAR_PERINSTANCE;
+ pvardesc->oInst = qvdefn->GetOVar();
+ }
+
+ pvardesc->lpstrSchema = NULL; // reserved
+
+ // set ID
+ // Note we don't have virtual functions to work with so we
+ // do the type casting "manually".
+ //
+ DebAssert(qvdefn->IsMemberVarDefn(), "bad defn");
+ pvardesc->memid = ((MBR_VAR_DEFN *)qvdefn)->Hmember();
+
+ // set typedesc
+ IfErrGo(AllocTypeDescOfTypeDefn(qvdefn->Htdefn(),
+ qvdefn->IsSimpleType(),
+ &(pvardesc->elemdescVar.tdesc)));
+
+
+ if (qvdefn->IsReadOnly())
+ pvardesc->wVarFlags = (WORD) VARFLAG_FREADONLY;
+ else
+ pvardesc->wVarFlags = 0;
+
+ // set the var flags
+ if (qvdefn->HasV2Flags()) {
+ DebAssert(qvdefn->IsMemberVarDefn(), "Bad Defn type");
+
+ pvardesc->wVarFlags |= ( ((MBR_VAR_DEFN *)qvdefn)->WVarFlags() );
+ }
+
+ // const value
+ if (qvdefn->HasConstVal()) {
+ if (qvdefn->IsSimpleType()) {
+ qtdefn = qvdefn->QtdefnOfSimpleType();
+ }
+ else {
+ qtdefn = QtdefnOfHtdefn(qvdefn->Htdefn());
+ }
+ tdesckind = qtdefn->Tdesckind();
+ ptrkind = qtdefn->Ptrkind();
+ pvariant = (VARIANT *) MemAlloc(sizeof(VARIANT));
+ if (!pvariant) {
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+ pvariant->vt = (VARTYPE) tdesckind;
+ qvdefn = QvdefnOfHvdefn(hvdefn);
+
+ switch (tdesckind) {
+
+ case VT_INT:
+ case VT_UINT:
+ if (m_pdtroot->Pgdtinfo()->PgtlibOleContaining()->GetSyskind()
+ != SYS_WIN16)
+ goto TagAsI4;
+
+ // these are invalid as variant tags -- must tag variant as an I2
+ case VT_I1:
+ if (ptrkind == PTRKIND_Basic) {
+ goto TagAsString; // char * is a string
+ }
+ case VT_UI1:
+ case VT_UI2:
+ pvariant->vt = VT_I2;
+
+ case VT_I2 : // these are supported as variant tags
+ case VT_BOOL :
+ DebAssert(offsetof(VARIANT, iVal) == offsetof(VARIANT, bool), "Bad offsets in Variant Union");
+ DebAssert(qvdefn->IsSimpleConst(), "Bad vardefn");
+ pvariant->iVal = (qvdefn->IsSimpleConst()) ?
+ qvdefn->GetSConstVal() :
+ *(SHORT *)PbConstVal(this, qvdefn);
+ break;
+
+ // these are invalid as variant tags -- must tag variant as an I4
+ case VT_UI4:
+TagAsI4:
+ pvariant->vt = VT_I4;
+
+ case VT_I4 : // these are supported as variant tags
+ case VT_R4 :
+ case VT_R8 :
+ case VT_CY :
+ case VT_DATE :
+ case VT_ERROR :
+ // allocate chunk for value
+
+ // We cheat here and pass in SYSKIND_CURRENT instead of m_syskind,
+ // because we've only got system-independent data types coming in here.
+ cb = SizeofTdesckind((TYPEDESCKIND) pvariant->vt, SYSKIND_CURRENT);
+
+ // copy chunk into value
+ DebAssert((offsetof(VARIANT, lVal) == offsetof(VARIANT, fltVal)) &&
+ (offsetof(VARIANT, lVal) == offsetof(VARIANT, dblVal)) &&
+ (offsetof(VARIANT, lVal) == offsetof(VARIANT, cyVal)) &&
+ (offsetof(VARIANT, lVal) == offsetof(VARIANT, scode)) &&
+ (offsetof(VARIANT, lVal) == offsetof(VARIANT, date)),
+ "Bad offsets in Variant Union");
+ memcpy(&(pvariant->lVal), PbConstVal(this, qvdefn), cb);
+ break;
+
+ case VT_LPSTR: // const value should also be a bstr
+TagAsString:
+ pvariant->vt = VT_BSTR; // update tag & fall through
+ case VT_BSTR : // TDESCKIND_String
+ cb = (UINT)*(USHORT *)PbConstVal(this, qvdefn);
+ bstr = (BSTR)AllocBstrLenA(NULL, cb);
+ if (!bstr) {
+ MemFree(pvariant);
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+ qvdefn = QvdefnOfHvdefn(hvdefn);
+ memcpy(bstr, PbConstVal(this, qvdefn) + sizeof(USHORT), cb);
+#if OE_WIN32
+ if ((hresult = ConvertBstrToWInPlace(&bstr)) != NOERROR) {
+ FreeBstr(bstr);
+ err = TiperrOfHresult(hresult);
+ goto Error;
+ }
+#endif //OE_WIN32
+ pvariant->bstrVal = bstr;
+ break;
+ case VT_VARIANT :
+ if (!(pvariant->pvarVal = (VARIANT *) MemAlloc(sizeof(VARIANT)))) {
+ err = TIPERR_OutOfMemory;
+ MemFree(pvariant);
+ goto Error;
+ }
+ qvdefn = QvdefnOfHvdefn(hvdefn);
+ memcpy(pvariant->pvarVal,
+ PbConstVal(this, qvdefn),
+ sizeof(VARIANT));
+ DebAssert((pvariant->pvarVal->vt == VT_I2) ||
+ (pvariant->pvarVal->vt == VT_BOOL) ||
+ (pvariant->pvarVal->vt == VT_I4) ||
+ (pvariant->pvarVal->vt == VT_R4) ||
+ (pvariant->pvarVal->vt == VT_R8) ||
+ (pvariant->pvarVal->vt == VT_CY) ||
+ (pvariant->pvarVal->vt == VT_DATE) ||
+ (pvariant->pvarVal->vt == VT_ERROR) ||
+ (pvariant->pvarVal->vt == VT_BSTR),
+ "Invalid vt in variant constant");
+ // CONSIDER: share code with VT_BSTR case above
+ if (pvariant->pvarVal->vt == VT_BSTR) {
+ cb = (UINT)*(USHORT *)(PbConstVal(this, qvdefn) + sizeof(VARIANT));
+ bstr = (BSTR)AllocBstrLenA(NULL, cb);
+ if (!bstr) {
+ MemFree(pvariant->pvarVal);
+ MemFree(pvariant);
+ err = TIPERR_OutOfMemory;
+ goto Error;
+ }
+ qvdefn = QvdefnOfHvdefn(hvdefn);
+ memcpy(bstr,
+ PbConstVal(this, qvdefn) + sizeof(VARIANT) + sizeof(USHORT),
+ cb);
+#if OE_WIN32
+ if ((hresult = ConvertBstrToWInPlace(&bstr)) != NOERROR) {
+ FreeBstr(bstr);
+ err = TiperrOfHresult(hresult);
+ goto Error;
+ }
+#endif //OE_WIN32
+ pvariant->pvarVal->bstrVal = bstr;
+ }
+ break;
+
+ default:
+ DebHalt("Invalid tdesckind");
+ break;
+
+ } // switch
+ pvardesc->lpvarValue = pvariant;
+ }
+
+ // no idl info for variables
+ pvardesc->elemdescVar.idldesc.wIDLFlags = 0;
+#if OE_WIN16
+ pvardesc->elemdescVar.idldesc.bstrIDLInfo = NULL;
+#else //OE_WIN16
+ pvardesc->elemdescVar.idldesc.dwReserved = 0;
+#endif //OE_WIN16
+
+ *ppvardesc = pvardesc;
+
+ return err;
+Error:
+ FreeVarDesc(pvardesc);
+ return err;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::GetVarDesc
+*Purpose:
+* Get the index'th VARDESC
+* NOTE: in OLE uses cache.
+*
+*Entry:
+* index - Index of the variable to be returned.
+* The index should be in the range
+* of 0 up to the number of variables in this type -1.
+* ppvardesc - Returns a pointer to a VARDESC that describes
+* the specified variable.
+*
+*Exit:
+* *ppvardesc points to a VARDESC or error returned
+***********************************************************************/
+TIPERROR TYPE_DATA::GetVarDesc(UINT index,
+ VARDESCA **ppvardesc)
+{
+ HDEFN hdefn;
+ DEFN *qdefn;
+ HVAR_DEFN hvdefn, hdefnStart;
+ UINT ivdefn, ivdefnStart;
+ TIPERROR err = TIPERR_None;
+
+ if (CDataMember() <= index) {
+ return TIPERR_ElementNotFound;
+ }
+
+ // Count up to the variable indicated
+ // Note: must skip over nested types.
+ //
+ // in OLE use the cache if there is one and it's useful.
+ if ((HvdefnLast() != HVARDEFN_Nil) &&
+ (index >= UOrdinalHvdefnLast())) {
+ // start from where we stopped last
+ ivdefnStart = UOrdinalHvdefnLast();
+ hdefnStart = HvdefnLast();
+ }
+ else {
+ ivdefnStart = 0;
+ hdefnStart = HdefnFirstDataMbrNestedType();
+ }
+
+ for (ivdefn = ivdefnStart, hdefn = hdefnStart;;) {
+ qdefn = QdefnOfHdefn(hdefn);
+
+ if (qdefn->IsVarDefn()) {
+ if (index == ivdefn++) {
+ // cache the match in OLE
+ SetUOrdinalHvdefnLast(index);
+ SetHvdefnLast((HVAR_DEFN)hdefn);
+ break;
+ } // if match
+ } // if IsVarDefn
+ // no need to rederef!
+ hdefn = qdefn->HdefnNext();
+ } // for
+ hvdefn = (HVAR_DEFN)hdefn;
+ DebAssert(hvdefn != HVARDEFN_Nil, "bad var list.");
+
+ return GetVarDescOfHvdefn(hvdefn, ppvardesc);
+}
+
+
+/***
+*PUBLIC TYPE_DATA::AllocTypeDescOfTypeDefn()
+*Purpose:
+* Allocs a typedesc from a typedefn
+*
+*Entry:
+* htdefn - handle to the typedefn that we are creating a typedesc for
+* isSimpleType - TRUE if handle is literal TYPE_DEFN
+* ptdesc - ptr typedesc to create
+*
+*Exit:
+* Status code returned.
+***********************************************************************/
+
+TIPERROR TYPE_DATA::AllocTypeDescOfTypeDefn(HTYPE_DEFN htdefn,
+ BOOL isSimpleType,
+ TYPEDESC *ptdesc)
+{
+ TYPE_DEFN *qtdefn;
+ SAFEARRAY *qad;
+ HARRAY_DESC had;
+ UINT i, cDims;
+ sHTYPE_DEFN htdefnActual;
+ TIPERROR err = TIPERR_None;
+
+ DebAssert((htdefn != HTYPEDEFN_Nil) && ptdesc, "Invalid Arguments");
+
+ htdefnActual = (sHTYPE_DEFN)htdefn;
+ qtdefn = isSimpleType ?
+ (TYPE_DEFN *)&htdefnActual :
+ QtdefnOfHtdefn(htdefnActual);
+
+ // Note: can't use IsBasicPtr() accessor here since it'll be true
+ // for objects as well (not what we want).
+ //
+ if (qtdefn->Ptrkind() == PTRKIND_Basic) {
+ // Set the top-level typedesc to be VT_PTR, then alloc another
+ // typedesc and enter the switch statement to handle the base type.
+ //
+ qtdefn->SetPtrkind(PTRKIND_Ignore);
+ ptdesc->vt = VT_PTR;
+ if (!(ptdesc->lptdesc = (TYPEDESC *)MemAlloc(sizeof(TYPEDESC)))) {
+ return TIPERR_OutOfMemory;
+ }
+
+ // Now we recurse: note that we've cleared the PTRKIND above
+ // temporarily to avoid infinite recursion...
+ //
+ if ((err = AllocTypeDescOfTypeDefn(htdefnActual,
+ isSimpleType,
+ ptdesc->lptdesc)) != TIPERR_None) {
+ MemFree(ptdesc->lptdesc);
+ ptdesc->lptdesc = NULL;
+ }
+ qtdefn = isSimpleType ?
+ (TYPE_DEFN *)&htdefnActual :
+ QtdefnOfHtdefn(htdefnActual);
+ qtdefn->SetPtrkind(PTRKIND_Basic);
+ return err;
+ } // if
+
+ switch (qtdefn->Tdesckind()) {
+ case TDESCKIND_Ptr :
+ case TDESCKIND_BasicArray :
+ if (!(ptdesc->lptdesc = (TYPEDESC *)MemAlloc(sizeof(TYPEDESC)))) {
+ return TIPERR_OutOfMemory;
+ }
+ // rederef after MemAlloc
+ DebAssert(!isSimpleType, "can't be simple.");
+ qtdefn = QtdefnOfHtdefn(htdefnActual);
+ if ((err = AllocTypeDescOfTypeDefn(
+ qtdefn->HtdefnFoundation(htdefnActual),
+ isSimpleType,
+ ptdesc->lptdesc)) != TIPERR_None) {
+ MemFree(ptdesc->lptdesc);
+ ptdesc->lptdesc = NULL;
+ return err;
+ }
+ qtdefn = QtdefnOfHtdefn(htdefnActual);
+ break;
+ case TDESCKIND_Carray :
+ had = qtdefn->Harraydesc();
+ qad = QarraydescOfHarraydesc(had);
+ cDims = qad->cDims;
+ if (!(ptdesc->lpadesc = (ARRAYDESC*) MemAlloc(offsetof(ARRAYDESC, rgbounds)
+ + cDims * sizeof(SAFEARRAYBOUND)))) {
+ return TIPERR_OutOfMemory;
+ }
+ // rederef after MemAlloc
+ DebAssert(!isSimpleType, "can't be simple.");
+ qtdefn = QtdefnOfHtdefn(htdefnActual);
+ if ((err = AllocTypeDescOfTypeDefn(
+ qtdefn->HtdefnFoundation(htdefnActual),
+ isSimpleType,
+ &(ptdesc->lpadesc->tdescElem))) != TIPERR_None) {
+ MemFree(ptdesc->lpadesc);
+ ptdesc->lpadesc = NULL;
+ return err;
+ }
+ ptdesc->lpadesc->cDims = cDims;
+ qad = QarraydescOfHarraydesc(had);
+ for (i = 0; i < cDims; i++) {
+ ptdesc->lpadesc->rgbounds[i].cElements = qad->rgsabound[i].cElements;
+ ptdesc->lpadesc->rgbounds[i].lLbound = qad->rgsabound[i].lLbound;
+ }
+ qtdefn = QtdefnOfHtdefn(htdefnActual);
+ break;
+ case TDESCKIND_UserDefined :
+
+ // Make sure the himptype levels have been set.
+ IfErrRet(Pdtroot()->MakeHimptypeLevels());
+
+ qtdefn = QtdefnOfHtdefn(htdefnActual);
+ ptdesc->hreftype = Pdtroot()->HreftypeOfHimptype(qtdefn->Himptype());
+ break;
+ default:
+ // Nothing to do here.. just fall through...
+ break;
+ } // switch
+ ptdesc->vt = (VARTYPE) qtdefn->Tdesckind();
+
+ return TIPERR_None;
+}
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC TYPE_DATA::AllocConstValOfVariant
+*Purpose:
+* Allocate a chunk in the typedata that contains the value of a variant
+*
+*Entry:
+* pvariant - the variant to allocate
+* hvdefn - vardefn to add constant value to
+*
+*Exit:
+* TIPERROR
+***********************************************************************/
+
+TIPERROR TYPE_DATA::AllocConstValOfVariant(VARIANT *pvariant,
+ HVAR_DEFN hvdefn)
+{
+ VAR_DEFN *qvdefn;
+ HCHUNK hchunk;
+ ULONG cb;
+ TIPERROR err;
+ BYTE *pbConstVal;
+ BSTRA bstrValA;
+#if OE_WIN32
+ HRESULT hresult;
+#endif //OE_WIN32
+
+ DebAssert(pvariant && (hvdefn != HVARDEFN_Nil), "Invalid args");
+
+ switch (pvariant->vt) {
+ case VT_I2 :
+ case VT_BOOL :
+ DebAssert(offsetof(VARIANT, iVal) == offsetof(VARIANT, bool), "Bad offsets in Variant Union");
+
+ // don't allocate chunk just insert value
+ qvdefn = QvdefnOfHvdefn(hvdefn);
+ qvdefn->SetSConstVal(pvariant->iVal);
+ qvdefn->SetIsSimpleConst(TRUE);
+ break;
+ case VT_I4 :
+ case VT_R4 :
+ case VT_R8 :
+ case VT_CY :
+ case VT_DATE :
+ case VT_ERROR :
+ // allocate chunk for value
+
+ // We cheat here and pass in SYSKIND_CURRENT instead of m_syskind,
+ // because we've only got system-independent data types coming in here.
+ cb = SizeofTdesckind((TYPEDESCKIND)pvariant->vt, SYSKIND_CURRENT);
+ IfErrRet(m_blkmgr.AllocChunk(&hchunk, (UINT)cb));
+
+ // copy value into chunk
+ DebAssert((offsetof(VARIANT, lVal) == offsetof(VARIANT, fltVal)) &&
+ (offsetof(VARIANT, lVal) == offsetof(VARIANT, dblVal)) &&
+ (offsetof(VARIANT, lVal) == offsetof(VARIANT, cyVal)) &&
+ (offsetof(VARIANT, lVal) == offsetof(VARIANT, date)),
+ "Bad offsets in Variant Union");
+ memcpy(m_blkmgr.QtrOfHandle(hchunk),
+ &(pvariant->lVal),
+ (UINT)cb);
+
+ qvdefn = QvdefnOfHvdefn(hvdefn);
+ SetHchunkConstVal(qvdefn, hchunk); // handles mvdefns as well
+ break;
+ case VT_BSTR :
+#if OE_WIN32
+ IfOleErrRetTiperr(ConvertBstrToA(pvariant->bstrVal, &bstrValA));
+#else //OE_WIN32
+ bstrValA = pvariant->bstrVal;
+#endif //OE_WIN32
+ // allocate chunk for string and length prefix
+ cb = BstrLenA(bstrValA);
+
+ if (cb + sizeof(USHORT) > USHRT_MAX) {
+#if OE_WIN32
+ FreeBstrA(bstrValA);
+#endif //OE_WIN32
+ return TIPERR_OutOfMemory;
+ }
+
+ if ((err = m_blkmgr.AllocChunk(&hchunk, (UINT)cb + sizeof(USHORT))) != TIPERR_None) {
+#if OE_WIN32
+ FreeBstrA(bstrValA);
+#endif //OE_WIN32
+ return err;
+ }
+
+ // copy in string USHORT length prefix and string data
+ pbConstVal = m_blkmgr.QtrOfHandle(hchunk);
+ *((USHORT *)pbConstVal) = (USHORT)cb;
+ memcpy(pbConstVal+sizeof(USHORT),
+ (BYTE*)bstrValA,
+ (UINT)cb);
+#if OE_WIN32
+ FreeBstrA(bstrValA);
+#endif //OE_WIN32
+
+ qvdefn = QvdefnOfHvdefn(hvdefn);
+ SetHchunkConstVal(qvdefn, hchunk); // handles mvdefns as well
+ break;
+ case VT_VARIANT :
+ DebAssert((pvariant->pvarVal->vt == VT_I2) ||
+ (pvariant->pvarVal->vt == VT_BOOL) ||
+ (pvariant->pvarVal->vt == VT_I4) ||
+ (pvariant->pvarVal->vt == VT_R4) ||
+ (pvariant->pvarVal->vt == VT_R8) ||
+ (pvariant->pvarVal->vt == VT_CY) ||
+ (pvariant->pvarVal->vt == VT_DATE) ||
+ (pvariant->pvarVal->vt == VT_ERROR) ||
+ (pvariant->pvarVal->vt == VT_BSTR),
+ "Invalid vt in variant constant");
+
+ // copy in whole variant
+ cb = 0;
+ if (pvariant->pvarVal->vt == VT_BSTR) {
+#if OE_WIN32
+ IfOleErrRetTiperr(ConvertBstrToA(pvariant->pvarVal->bstrVal, &bstrValA));
+#else //OE_WIN32
+ bstrValA = pvariant->pvarVal->bstrVal;
+#endif //OE_WIN32
+ // for string copy in string val and length prefix after variant
+ cb = sizeof(USHORT) + BstrLenA(bstrValA);
+
+ if (cb > USHRT_MAX) {
+#if OE_WIN32
+ FreeBstrA(bstrValA);
+#endif // OE_WIN32
+ return TIPERR_OutOfMemory;
+ }
+ }
+
+ if ((err = m_blkmgr.AllocChunk(&hchunk, (UINT)cb + sizeof(VARIANT))) != TIPERR_None) {
+#if OE_WIN32
+ FreeBstrA(bstrValA);
+#endif //OE_WIN32
+ return err;
+ }
+ pbConstVal = m_blkmgr.QtrOfHandle(hchunk);
+
+ // copy in variant
+ memcpy(pbConstVal, pvariant->pvarVal, sizeof(VARIANT));
+
+ if (pvariant->pvarVal->vt == VT_BSTR) {
+ // if string, copy in length prefix and string data
+ *(USHORT *)(pbConstVal + sizeof(VARIANT)) = (USHORT)(cb - sizeof(USHORT));
+ memcpy(pbConstVal + sizeof(VARIANT),
+ (BYTE*)bstrValA,
+ (UINT)cb - sizeof(USHORT));
+#if FV_UNICODE_OLE
+ FreeBstrA(bstrValA);
+#endif //FV_UNICODE_OLE
+ }
+
+ qvdefn = QvdefnOfHvdefn(hvdefn);
+ SetHchunkConstVal(qvdefn, hchunk); // handles mvdefns as well
+ break;
+ default:
+ DebHalt("Invalid vt in variant");
+ break;
+ } // switch
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC TYPE_DATA::SetTypeDefnAlias()
+*Purpose:
+* Allocs a typedefn for the alias
+*
+*Entry:
+* ptdesc - typedesc to crete typedefn for
+*
+*Exit:
+* Tiperror
+***********************************************************************/
+
+TIPERROR TYPE_DATA::SetTypeDefnAlias(TYPEDESC *ptdesc)
+{
+ TIPERROR err;
+ BOOL fIsSimpleType;
+
+ DebAssert(ptdesc, "Invalid parameter");
+ DebAssert((HTYPE_DEFN)m_htdefnAlias == HTYPEDEFN_Nil,
+ "Alias already Set");
+ // This does all the work we want
+ IfErrRet(AllocTypeDefnOfTypeDesc(ptdesc,
+ 0,
+ &m_htdefnAlias,
+ TRUE, // is an alias/allow coclass
+ &fIsSimpleType));
+
+ SetIsSimpleTypeAlias(fIsSimpleType);
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC TYPE_DATA::AddImplType()
+*Purpose:
+* Adds a base class vardefn to this class
+*
+*Entry:
+* index - where to add this class in the list of bases
+* hreftype - which typeinfo for base
+*
+*Exit:
+* Tiperror
+***********************************************************************/
+
+#pragma code_seg(CS_LAYOUT)
+TIPERROR TYPE_DATA::AddImplType(UINT index, HREFTYPE hreftype)
+{
+ sHMBR_VAR_DEFN hmvdefn;
+ MBR_VAR_DEFN *qmvdefn;
+ HCHUNK hchunk;
+ HTYPE_DEFN htdefn;
+ TYPE_DEFN *qtdefn;
+ TIPERROR err;
+
+ DebAssert(Pdtroot()->CompState() == CS_UNDECLARED, "Invalid state");
+
+ // for V1, we only support appending to the end of the list.
+ // CONSIDER: support arbitrary insertion point like AddFuncDesc/AddVarDesc.
+ if (index != CBase()) {
+ return TIPERR_ElementNotFound;
+ }
+
+ // allocate the var defn
+ IfErrRet(AllocMbrVarDefn(&hmvdefn, FALSE));
+
+ // allocate the type defn for the user defined type
+ IfErrGo(m_blkmgr.AllocChunk(&hchunk, sizeof(TYPE_DEFN) + sizeof(sHIMPTYPE)));
+ htdefn = (HTYPE_DEFN) hchunk;
+ qtdefn = QtdefnOfHtdefn(htdefn);
+ new (qtdefn) TYPE_DEFN;
+
+ qtdefn->SetTdesckind(TDESCKIND_UserDefined);
+
+ // set himptype
+ // CONSIDER: checking the himptype with the impmgr
+ *qtdefn->Qhimptype() = Pdtroot()->HimptypeOfHreftype(hreftype);
+
+ // set the rest of the defns values
+ qmvdefn = QmvdefnOfHmvdefn(hmvdefn);
+ qmvdefn->SetAccess(ACCESS_Public);
+ qmvdefn->SetVkind(VKIND_Base);
+ qmvdefn->SetIsSimpleType(FALSE);
+ qmvdefn->SetHtdefn(htdefn);
+
+ qmvdefn->SetHmember((ULONG)DISPID_UNKNOWN);
+ qmvdefn->SetImplTypeFlags(0); // init flags to 0
+
+
+ AppendMbrVarDefn(hmvdefn);
+ return TIPERR_None;
+Error:
+ FreeMbrVarDefn(hmvdefn);
+ return err;
+}
+#pragma code_seg()
+
+
+
+/***
+*PRIVATE TYPE_DATA::QtdefnOfIndex(index)
+*Purpose:
+* Gets the qtdefn, given an impltype index
+*
+*Entry:
+* index - index of base class of interest
+*
+*Exit:
+* hmvdefn for this guy
+***********************************************************************/
+
+HMBR_VAR_DEFN TYPE_DATA::HmvdefnOfIndex (UINT index)
+{
+ HMBR_VAR_DEFN hmvdefn;
+ MBR_VAR_DEFN *qmvdefn;
+
+ // find correct base in list
+ hmvdefn = m_hdefnFirstBase;
+ while (index > 0) {
+ qmvdefn = QmvdefnOfHmvdefn(hmvdefn);
+ hmvdefn = qmvdefn->HdefnNext();
+ index -= 1;
+ }
+ return hmvdefn;
+}
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC TYPE_DATA::SetImplTypeFlags()
+*Purpose:
+* Sets the impltype flags for a given base class
+*
+*Entry:
+* index - index of base class to set
+* fImplType - flags to set
+*
+*Exit:
+* Tiperror
+***********************************************************************/
+
+TIPERROR TYPE_DATA::SetImplTypeFlags(UINT index, INT fImplType)
+{
+ MBR_VAR_DEFN *qmvdefn;
+
+ if (index >= CBase()) {
+ return TIPERR_ElementNotFound;
+ }
+
+ qmvdefn = QmvdefnOfHmvdefn(HmvdefnOfIndex(index));
+
+ qmvdefn->SetImplTypeFlags((WORD) fImplType);
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC TYPE_DATA::GetImplTypeFlags()
+*Purpose:
+* Gets the impltype flags for a given base class
+*
+*Entry:
+* index - index of base class to get
+* pfImplType - where to put flags
+*
+*Exit:
+* Tiperror
+***********************************************************************/
+
+TIPERROR TYPE_DATA::GetImplTypeFlags(UINT index, INT FAR* pfImplType)
+{
+ MBR_VAR_DEFN *qmvdefn;
+
+ if (index >= CBase()) {
+ return TIPERR_ElementNotFound;
+ }
+
+ qmvdefn = QmvdefnOfHmvdefn(HmvdefnOfIndex(index));
+
+ *pfImplType = (INT)qmvdefn->GetImplTypeFlags();
+
+ return TIPERR_None;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::GetRefTypeOfImplType()
+*Purpose:
+* returns a pointer to a typeinfo for a base class
+*
+*Entry:
+* index - index of base class to get
+*
+*Exit:
+* *pptinfo - pointer to ITypeInfo of base class
+* Tiperror
+***********************************************************************/
+
+TIPERROR TYPE_DATA::GetRefTypeOfImplType(UINT index, HREFTYPE *phreftype)
+{
+ MBR_VAR_DEFN *qmvdefn;
+ HTYPE_DEFN htdefn;
+ TIPERROR err;
+ TYPE_DEFN *qtdefn;
+
+ if (index >= CBase()) {
+ return TIPERR_ElementNotFound;
+ }
+
+ // Make sure all of our levels have been set.
+ IfErrRet(Pdtroot()->MakeHimptypeLevels());
+
+ // get type defn for Himptype
+ qmvdefn = QmvdefnOfHmvdefn(HmvdefnOfIndex(index));
+
+ htdefn = qmvdefn->Htdefn();
+ qtdefn = QtdefnOfHtdefn(htdefn);
+
+ *phreftype = Pdtroot()->HreftypeOfHimptype(qtdefn->HimptypeActual());
+
+ return TIPERR_None;
+}
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC TYPE_DATA::AllocTypeDefnOfTypeDesc()
+*Purpose:
+* Allocs a typedefn from a typedesc
+*
+*Entry:
+* ptdesc - typedesc to crete typedefn for
+* cb - count of bytes required for this typedefn
+* phtdefn - returned handle to the alloced typedefn
+* fAllowCoClass - TRUE if this typedesc can contain a ptr to
+* a coclass.
+*
+*Exit:
+* Status code returned.
+***********************************************************************/
+
+TIPERROR TYPE_DATA::AllocTypeDefnOfTypeDesc(TYPEDESC *ptdesc,
+ UINT cb,
+ sHTYPE_DEFN *phtdefn,
+ BOOL fAllowCoClass,
+ BOOL *pfIsSimpleType)
+{
+ UINT cbNew;
+ UINT i;
+ sHARRAY_DESC had;
+ SAFEARRAY *qad;
+ BYTE *pb;
+
+ HCHUNK hchunk;
+
+ TYPE_DEFN *qtdefn;
+ TYPE_DEFN tdefn;
+ TYPEDESCKIND tdesckind;
+ BOOL isBaseSimple;
+ ITypeInfoA *ptinfo = NULL;
+ TYPEKIND tkind;
+
+ TIPERROR err = TIPERR_None;
+
+ *pfIsSimpleType = FALSE;
+ DebAssert(ptdesc && phtdefn, " Invalid parameters");
+
+ switch (ptdesc->vt) {
+
+ case VT_CARRAY :
+ IfErrRet(AllocArrayDescriptor(ptdesc->lpadesc->cDims, &had));
+ qad = QarraydescOfHarraydesc(had);
+ qad->cDims = ptdesc->lpadesc->cDims;
+ cbNew = sizeof(TYPE_DEFN) + sizeof(sHARRAY_DESC);
+ if ((err = AllocTypeDefnOfTypeDesc(&(ptdesc->lpadesc->tdescElem),
+ cbNew + cb,
+ phtdefn,
+ FALSE, // not an alias
+ &isBaseSimple)) != TIPERR_None) {
+ FreeArrayDescriptor(had);
+ return err;
+ }
+ pb = m_blkmgr.QtrOfHandle(*phtdefn);
+ qtdefn = (TYPE_DEFN *) (pb + cb);
+ new (qtdefn) TYPE_DEFN;
+ qtdefn->SetTdesckind(TDESCKIND_Carray);
+ *((sHARRAY_DESC*)(qtdefn+1)) = (sHARRAY_DESC) had;
+ qad = QarraydescOfHarraydesc(had);
+
+ qad->cbElements = SizeofTdesckind(
+ (TYPEDESCKIND)ptdesc->lpadesc->tdescElem.vt
+ ,m_pdtroot->Pgdtinfo()->PgtlibOleContaining()->GetSyskind()
+ );
+ switch (ptdesc->lpadesc->tdescElem.vt) {
+ case VT_BSTR :
+ qad->fFeatures |= FADF_BSTR;
+ break;
+ case VT_VARIANT :
+ qad->fFeatures |= FADF_VARIANT;
+ break;
+ case VT_DISPATCH :
+ qad->fFeatures |= FADF_DISPATCH;
+ break;
+ case VT_UNKNOWN :
+ qad->fFeatures |= FADF_UNKNOWN;
+ break;
+ default :
+ break;
+ } // switch
+ for (i = 0; i < ptdesc->lpadesc->cDims; i++) {
+ qad->rgsabound[i].cElements = ptdesc->lpadesc->rgbounds[i].cElements;
+ qad->rgsabound[i].lLbound = ptdesc->lpadesc->rgbounds[i].lLbound;
+ }
+ break;
+
+ case VT_SAFEARRAY :
+ IfErrRet(AllocArrayDescriptor(0, &had));
+ qad = QarraydescOfHarraydesc(had);
+ qad->cDims = 0;
+ cbNew = sizeof(TYPE_DEFN) + sizeof(sHARRAY_DESC);
+ // We now need to allocate a TYPE_DEFN for this array's
+ // element type which will be allocated immediately
+ // following the first part.
+ //
+ err = AllocTypeDefnOfTypeDesc(ptdesc->lptdesc, // element typedesc
+ cbNew + cb,
+ phtdefn,
+ fAllowCoClass,
+ &isBaseSimple);
+ if (err != TIPERR_None) {
+ FreeArrayDescriptor(had);
+ return err;
+ }
+ pb = m_blkmgr.QtrOfHandle(*phtdefn);
+ qtdefn = (TYPE_DEFN *) (pb + cb);
+ new (qtdefn) TYPE_DEFN;
+ qtdefn->SetTdesckind(TDESCKIND_BasicArray);
+ qtdefn->SetIsResizable(TRUE);
+ *((sHARRAY_DESC*)(qtdefn+1)) = (sHARRAY_DESC) had;
+ break;
+
+ case VT_PTR :
+ // For BASIC and OLE we always want a PTR to a non-ptr-type
+ // to take up
+ // only two bytes. So, if this PTR points to a non-ptr-type
+ // we set cbNew to zero so that we don't allocate extra space
+ // for the PTR TYPE_DEFN. Instead, we'll set PTRKIND_Basic
+ // on the intrinsic TYPE_DEFN.
+ // And oh by the way we need to remember that this type
+ // is also simple so that we can potentially encode this
+ // TYPE_DEFN in its handle (the famous IsSimpleType optimization).
+ //
+ // In OB, however, we imply a level of indirection with
+ // TDESCKIND_UserDefined so we can pack UDT ** into
+ // one tdefn.
+ //
+ if ((TYPEDESCKIND)ptdesc->lptdesc->vt != TDESCKIND_Ptr
+ ) {
+ cbNew = 0;
+ }
+ else {
+ cbNew = sizeof(TYPE_DEFN);
+ }
+
+ // Create the TYPE_DEFN for the base type. Note that even if
+ // cbNew is zero, we still might alloc space if cb is non-zero.
+ // (Notice that the only memory allocation, if any, happens in
+ // the terminal case of the recursion. At that point, we will
+ // have summed up the total size of the TYPE_DEFN, and we
+ // can just do one alloc and then fill in the parts as we
+ // go back up the stack.)
+ //
+ IfErrRet(AllocTypeDefnOfTypeDesc(ptdesc->lptdesc,
+ cbNew + cb,
+ phtdefn,
+ fAllowCoClass,
+ &isBaseSimple));
+
+
+ // So we've got the base TYPE_DEFN. There are three cases that
+ // we need to handle.
+ // 1) cbNew is nonzero. This means that the base type will
+ // be allocated in the TYPE_DATA's heap.
+ // 2) cbNew is zero, but cb (passed in from above) is nonzero.
+ // Then the base type will be allocated in the TYPE_DATA's heap,
+ // BUT since cbNew is zero, we want to set PTRKIND_BASIC on the
+ // base type instead of creating a new TYPE_DEFN for the PTR.
+ // The other reason that we might want this case is when the
+ // base type has a non-simple TYPEDEFN.
+ // 3) cbNew and cb are zero. In this case, the base type is
+ // actually allocated in *phtdefn that we passed down
+ // recursively. CAREFUL: This means that phtdefn is NOT a
+ // pointer to a handle; it is really a pointer to a TYPE_DEFN.
+ // This is so that intrinsic types (and PTR to intrinsic) only
+ // take up the two bytes of the handle, and don't use space in the
+ // TYPE_DATA's heap. In this case, we have to fake up a pointer
+ // to the TYPE_DEFN and then set PTRKIND_BASIC on it.
+ //
+ if (cbNew) {
+ pb = m_blkmgr.QtrOfHandle(*phtdefn);
+ qtdefn = (TYPE_DEFN *) (pb + cb);
+ new (qtdefn) TYPE_DEFN;
+ qtdefn->SetTdesckind(TDESCKIND_Ptr);
+ qtdefn->SetPtrkind(PTRKIND_Far);
+ }
+ else if (cb || !isBaseSimple) {
+ pb = m_blkmgr.QtrOfHandle(*phtdefn);
+ qtdefn = (TYPE_DEFN *) (pb + cb);
+ qtdefn->SetPtrkind(PTRKIND_Basic);
+ }
+ else {
+ qtdefn = (TYPE_DEFN *) phtdefn;
+ *pfIsSimpleType = TRUE;
+ qtdefn->SetPtrkind(PTRKIND_Basic);
+ }
+ break;
+
+ case VT_USERDEFINED :
+ IfErrRet(Pimpmgr()->GetTypeInfo(
+ Pdtroot()->HimptypeOfHreftype(ptdesc->hreftype),
+ DEP_None,
+ &ptinfo));
+
+ DebAssert(ptinfo != NULL, "null TYPEINFO.");
+
+ ITypeLib *ptlib;
+ UINT index;
+ HRESULT hresult;
+
+ hresult = ptinfo->GetContainingTypeLib(&ptlib, &index);
+
+ if (hresult == NOERROR) {
+ hresult = ptlib->GetTypeInfoType(index, &tkind);
+
+ ptlib->Release();
+ }
+
+ // No longer need this.
+ ptinfo->Release();
+
+ if (hresult != NOERROR) {
+ return TiperrOfHresult(hresult);
+ }
+
+ // Need to give error if the type we're referring to is
+ // TKIND_COCLASS, TKIND_MODULE.
+ //
+ // Those items aren't valid as alias's, or as structure elements,
+ // parameter types, etc -- even pointers to them are no good.
+ //
+ // Note that it's NOT ok to *cast* the typeinfo to a gdtinfo
+ // since this typeinfo could be wrapped.
+ //
+ switch (tkind) {
+ case TKIND_COCLASS:
+ if (fAllowCoClass) {
+ break; // allow alias's to coclass's
+ }
+ case TKIND_MODULE:
+ return TIPERR_TypeMismatch;
+
+ default:
+ break;
+ }
+
+ cbNew = sizeof(TYPE_DEFN) + sizeof(sHIMPTYPE);
+ IfErrRet(m_blkmgr.AllocChunk(&hchunk, cbNew + cb));
+ *phtdefn = (sHTYPE_DEFN) hchunk;
+ pb = m_blkmgr.QtrOfHandle(hchunk);
+ qtdefn = (TYPE_DEFN *) (pb + cb);
+ new (qtdefn) TYPE_DEFN;
+ qtdefn->SetTdesckind(TDESCKIND_UserDefined);
+
+ // set himptype from index
+ *qtdefn->Qhimptype() = Pdtroot()->HimptypeOfHreftype(ptdesc->hreftype);
+ break;
+
+ default :
+ // NOTE: This assert won't work because of things like VT_LPSTR
+ // which can be used in typelib.dll.
+ //
+ // DebAssert(IsSimpleType((TYPEDESCKIND) ptdesc->vt), "must be simple");
+
+ if (cb) {
+ // must allocate block
+ //
+ cbNew = sizeof(TYPE_DEFN);
+ IfErrRet(m_blkmgr.AllocChunk(&hchunk, cbNew + cb));
+ *phtdefn = (sHTYPE_DEFN) hchunk;
+ pb = m_blkmgr.QtrOfHandle(hchunk);
+ qtdefn = (TYPE_DEFN *) (pb + cb);
+ tdesckind = (TYPEDESCKIND)ptdesc->vt;
+ }
+ else {
+ // this is the only type defn, so just use handle as type defn
+ qtdefn = (TYPE_DEFN *)phtdefn;
+ *pfIsSimpleType = TRUE;
+ {
+ tdesckind = (TYPEDESCKIND)ptdesc->vt;
+ }
+ }
+ new (qtdefn) TYPE_DEFN; // construct in place.
+ qtdefn->SetTdesckind(tdesckind); // set the tdesckind finally.
+ break;
+ } // switch
+
+ return TIPERR_None;
+
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC TYPE_DATA::AddVarDesc
+*Purpose:
+* Adds a variable description to the TypeInfo.
+* The index is used to specify the order of the variables.
+* The first variable has an index of zero. If an index is
+* specified that is greater than the number of variables
+* currently in the TypeInfo then an error is returned.
+* Calling this function does not pass ownership of the VARDESC
+* structure to the ICreateTypeInfo.
+*
+*Entry:
+* index - Index before which the variable is to be inserted.
+* The index should be in the range
+* of 0 up to the number of variables in this type.
+* lpvardesc - A pointer to a VARDESC that describes
+* the specified variable.
+* phvdefn - Pointer to allocated handle (OUT). If NULL then
+* client doesn't care (default).
+*
+*Exit:
+* Status code returned.
+***********************************************************************/
+TIPERROR TYPE_DATA::AddVarDesc(UINT index,
+ VARDESCA *pvardesc,
+ HVAR_DEFN *phvdefn)
+{
+ sHMBR_VAR_DEFN hmvdefn;
+ MBR_VAR_DEFN *qmvdefn;
+ sHTYPE_DEFN htdefn;
+ HDEFN hdefn;
+ DEFN *qdefn;
+ BOOL fIsSimpleType;
+ TIPERROR err = TIPERR_None;
+ BOOL fV2Flags;
+
+ DebAssert(pvardesc != NULL,
+ "TYPE_DATA::AddVarDesc: null VARDESC.");
+
+ DebAssert(Pdtroot()->CompState() == CS_UNDECLARED, "Invalid state");
+
+ if (index > CDataMember()) {
+ return TIPERR_ElementNotFound;
+ }
+
+ fV2Flags = ((pvardesc->wVarFlags & ~VARFLAG_FREADONLY) != 0);
+ IfErrRet(AllocMbrVarDefn(&hmvdefn, fV2Flags));
+ qmvdefn = QmvdefnOfHmvdefn(hmvdefn);
+ qmvdefn->SetHasV2Flag(fV2Flags);
+
+
+ IfErrGo(AllocTypeDefnOfTypeDesc(&(pvardesc->elemdescVar.tdesc),
+ 0,
+ &htdefn,
+ TRUE, // coclass allowed
+ &fIsSimpleType));
+
+ qmvdefn = QmvdefnOfHmvdefn(hmvdefn);
+
+
+ qmvdefn->SetAccess(ACCESS_Public);
+ qmvdefn->SetHlnam(HLNAM_Nil);
+ qmvdefn->SetVkind(VKIND_DataMember);
+
+ qmvdefn->SetHtdefn(htdefn);
+ qmvdefn->SetIsSimpleType(fIsSimpleType);
+
+ // Note that we can distinguish between vars and funcs
+ // by looking at the defnkind.
+ //
+ // validate the incoming memid
+ IfErrGo(ValidateMemid(pvardesc->memid));
+
+ if (pvardesc->memid != DISPID_UNKNOWN) {
+ qmvdefn->SetHmember(pvardesc->memid);
+ } else {
+ TYPEKIND tkind = Pdtroot()->Pgdtinfo()->GetTypeKind();
+
+ if (tkind == TKIND_ENUM || tkind == TKIND_ALIAS) {
+ // Neither of these inherit from anybody, so we can use
+ // a nested depth of zero.
+ //
+ qmvdefn->SetHmember(DataHmemberOfOffset(CDataMember(), 0));
+ }
+ else {
+ qmvdefn->SetHmember((ULONG)DISPID_UNKNOWN);
+ }
+ }
+
+
+#if 0
+ // document that these fields are ignored for AddVarDesc. Callers
+ // shouldn't have to initialize this memory if it is going to
+ // alway be ignored (only applies to function parameters).
+ DebAssert(pvardesc->elemdescVar.idldesc.bstrIDLInfo == NULL,
+ "Idldesc must be NULL");
+ DebAssert(pvardesc->elemdescVar.idldesc.wIDLFlags == 0,
+ "idldesc must be empty");
+#endif //0
+
+
+ qmvdefn->SetIsReadOnly((pvardesc->wVarFlags & VARFLAG_FREADONLY) != 0);
+
+ if (fV2Flags) {
+ DebAssert(qmvdefn->HasV2Flags(), "Bad qmvdefn");
+ qmvdefn->SetWVarFlags(pvardesc->wVarFlags & ~VARFLAG_FREADONLY);
+ }
+
+
+ switch(pvardesc->varkind) {
+ case VAR_PERINSTANCE:
+ qmvdefn->SetOVar(0);
+ break;
+ case VAR_STATIC:
+ qmvdefn->SetIsStatic(TRUE);
+ break;
+ case VAR_CONST:
+ qmvdefn->SetHasConstVal(TRUE);
+ if (qmvdefn->IsSimpleType()) {
+ qmvdefn->QtdefnOfSimpleType()->SetIsConst(TRUE);
+ }
+ else {
+ QtdefnOfHvdefn((HVAR_DEFN)hmvdefn)->SetIsConst(TRUE);
+ }
+ IfErrGo(AllocConstValOfVariant(pvardesc->lpvarValue,
+ (HVAR_DEFN) hmvdefn));
+ // memory may have moved, so re-deref
+ qmvdefn = QmvdefnOfHmvdefn(hmvdefn);
+ break;
+ case VAR_DISPATCH:
+ qmvdefn->SetIsDispatch(TRUE);
+ // init to some bogus value since this should never be used
+ qmvdefn->SetOVar((USHORT) ~0);
+ break;
+ default:
+ DebHalt("Unrecognized VarKind");
+ } // switch
+
+ // insert defn into list
+ if (index == CDataMember()) {
+ m_hdefnLastDataMbrNestedType = hmvdefn;
+ }
+ if (index == 0) {
+ qmvdefn->SetHdefnNext(HdefnFirstDataMbrNestedType());
+ m_hdefnFirstDataMbrNestedType = hmvdefn;
+ }
+ else {
+ hdefn = HdefnFirstDataMbrNestedType();
+ qdefn = QdefnOfHdefn(hdefn);
+ DebAssert(qdefn->IsMemberVarDefn(), "bad defn type");
+ while (--index) {
+ hdefn = qdefn->HdefnNext();
+ qdefn = QdefnOfHdefn(hdefn);
+ DebAssert(qdefn->IsMemberVarDefn(), "bad defn type");
+ }
+ qmvdefn->SetHdefnNext(qdefn->HdefnNext());
+ qdefn->SetHdefnNext(hmvdefn);
+ }
+
+ m_cDataMember++;
+
+ // Return the allocated handle if they want it.
+ if (phvdefn != NULL) {
+ *phvdefn = hmvdefn;
+ }
+ return err;
+
+Error:
+ FreeMbrVarDefn(hmvdefn);
+ return err;
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC TYPE_DATA::SetVarName()
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+TIPERROR TYPE_DATA::SetVarName(UINT index, LPSTR szName)
+{
+ HDEFN hdefn;
+ DEFN *qdefn;
+ HLNAM hlnam;
+ TIPERROR err = TIPERR_None;
+ INVOKEKIND invokekind;
+ DebAssert(Pdtroot()->CompState() == CS_UNDECLARED, "Invalid state");
+
+ if (index >= CDataMember()) {
+ return TIPERR_ElementNotFound;
+ }
+
+ IfErrRet(Pnammgr()->HlnamOfStr(szName, &hlnam, FALSE, NULL));
+
+ if (HvdefnOfHlnam(hlnam) != HVARDEFN_Nil) {
+ return TIPERR_AmbiguousName;
+ }
+ if (HfdefnFirstOfHlnam(hlnam,&invokekind) != HFUNCDEFN_Nil) {
+ return TIPERR_AmbiguousName;
+ }
+
+ hdefn = HdefnFirstDataMbrNestedType();
+ qdefn = QdefnOfHdefn(hdefn);
+ DebAssert(qdefn->IsMemberVarDefn(), "bad defn type");
+ while (index > 0) {
+ hdefn = qdefn->HdefnNext();
+ qdefn = QdefnOfHdefn(hdefn);
+ DebAssert(qdefn->IsMemberVarDefn(), "bad defn type");
+ index -= 1;
+ }
+
+ DebAssert(qdefn->Hlnam() == HLNAM_Nil, "Name allready set");
+ qdefn->SetHlnam(hlnam);
+
+ return err;
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC TYPE_DATA::SetFuncAndParamNames()
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+TIPERROR TYPE_DATA::SetFuncAndParamNames(UINT index,
+ LPOLESTR *rgszNames,
+ UINT cNames)
+{
+ HFUNC_DEFN hfdefn;
+
+ DebAssert(Pdtroot()->CompState() == CS_UNDECLARED, "Invalid state");
+
+ if (index >= CAvailMeth()) {
+ return TIPERR_ElementNotFound;
+ }
+
+ hfdefn = HfdefnFirstAvailMeth();
+ while (index > 0) {
+ index -= 1;
+ hfdefn = HfdefnNextAvailMeth(hfdefn);
+ }
+
+ return SetFuncAndParamNamesOfHfdefn(hfdefn, rgszNames, cNames);
+}
+
+/***
+*PUBLIC TYPE_DATA::SetFuncAndParamNamesOfHfdefn()
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+TIPERROR TYPE_DATA::SetFuncAndParamNamesOfHfdefn(HFUNC_DEFN hfdefn,
+ LPOLESTR *rgszNames,
+ UINT cNames)
+{
+ HFUNC_DEFN hfdefnCheck;
+ INVOKEKIND invokekindDummy;
+ FUNC_DEFN *qfdefnCheck;
+
+ FUNC_DEFN *qfdefn;
+ HPARAM_DEFN hparamdefn;
+ PARAM_DEFN *qparamdefn;
+ UINT cParams, i;
+ HLNAM hlnam = HLNAM_Nil;
+ TIPERROR err = TIPERR_None;
+
+ i = 0;
+
+ if (rgszNames[i] != NULL) {
+ IfErrRet(Pnammgr()->HlnamOfStrW(rgszNames[i], &hlnam, FALSE, NULL));
+ }
+
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+
+ // check for name conflict with variables
+ if (hlnam != HLNAM_Nil && HvdefnOfHlnam(hlnam) != HVARDEFN_Nil) {
+ return TIPERR_AmbiguousName;
+ }
+
+ // check for name conflict with function
+ // This will also catch the case of trying to set the name twice.
+ // It will give "duplicate definition" in this case.
+ //
+ if (hlnam != HLNAM_Nil) {
+ hfdefnCheck = HfdefnFirstOfHlnam(hlnam, &invokekindDummy);
+
+ if (hfdefnCheck != HFUNCDEFN_Nil) {
+ if (qfdefn->IsMethod()) {
+ // can't have non property functions with same name
+ return TIPERR_AmbiguousName;
+ } else {
+ // check for matching name and property kind
+ do {
+ qfdefnCheck = QfdefnOfHfdefn(hfdefnCheck);
+ if (qfdefnCheck->IsMethod()) {
+ return TIPERR_AmbiguousName;
+ }
+ if (qfdefnCheck->InvokeKind() == qfdefn->InvokeKind()) {
+ return TIPERR_AmbiguousName;
+ }
+ hfdefnCheck = HfdefnNextOfHlnam(hlnam, qfdefn->HdefnNext(),&invokekindDummy);
+ } while (hfdefnCheck != HFUNCDEFN_Nil);
+ }
+ }
+ }
+
+ // check for the correct number of parameters
+ cParams = qfdefn->CArgsUnmunged();
+
+ // for PUT and PUTREF (i.e. let and set) property functions, the
+ // last parameters name is not set.
+ //
+ if ((UINT)qfdefn->InvokeKind() &
+ ((UINT)INVOKE_PROPERTYPUT |
+ (UINT)INVOKE_PROPERTYPUTREF))
+ cParams--;
+
+ if ((cParams + 1) != cNames) {
+ return TIPERR_ElementNotFound;
+ }
+
+ DebAssert(qfdefn->Hlnam() == HLNAM_Nil, "Name already set");
+
+ if (hlnam != HLNAM_Nil) {
+ qfdefn->SetHlnam(hlnam);
+ }
+
+ i = 1;
+
+ hparamdefn = qfdefn->m_ftdefn.m_hdefnFormalFirst;
+ while(i <= cParams && i < cNames) {
+ hlnam = HLNAM_Nil;
+
+ if (rgszNames[i] != NULL) {
+ IfErrRet(Pnammgr()->HlnamOfStrW(rgszNames[i], &hlnam, FALSE, NULL));
+ }
+
+ // In OLE we have an array of PARAM_DEFN(s).
+ // Get the ith PARAM_DEFN
+ //
+ qparamdefn = QparamdefnOfIndex(hparamdefn, i-1);
+
+ if (hlnam != HLNAM_Nil) {
+ qparamdefn->SetHlnam(hlnam);
+ }
+
+ i++;
+ }
+ return TIPERR_None;
+}
+
+#pragma code_seg()
+
+
+/***
+*PUBLIC TYPE_DATA::GetNames()
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+TIPERROR TYPE_DATA::GetNames(MEMBERID memid,
+ BSTR *rgbstrNames,
+ UINT cNameMax,
+ UINT *lpcName)
+{
+ HDEFN hdefn;
+ HFUNC_DEFN hfdefn;
+ FUNC_DEFN *qfdefn;
+ HPARAM_DEFN hparamdefn;
+ PARAM_DEFN *qparamdefn;
+ UINT defnkind;
+ HVAR_DEFN hvdefn;
+ HLNAM hlnam;
+ UINT cParams, i;
+ UINT uParam;
+ TIPERROR err = TIPERR_None;
+
+ if (cNameMax == 0) {
+ *lpcName = 0;
+ return TIPERR_None;
+ }
+
+ i = 0;
+ // check variables
+ // find var defn
+ hdefn = HdefnOfHmember((HMEMBER) memid, &defnkind);
+
+ if (hdefn != HDEFN_Nil) {
+ if (defnkind == DK_VarDefn || defnkind == DK_MbrVarDefn) {
+ // NOTE: no need to cast to MBR_VAR_DEFN since we can treat
+ // a MBR_VAR_DEFN as a VAR_DEFN for our purposes here.
+ //
+ hvdefn = (HVAR_DEFN) hdefn;
+ hlnam = QvdefnOfHvdefn(hvdefn)->Hlnam();
+
+ if (hlnam != HLNAM_Nil) {
+ IfErrGo(Pnammgr()->BstrWOfHlnam(hlnam, rgbstrNames+i));
+ }
+ else {
+ rgbstrNames[i] = AllocBstr(WIDE(""));
+ }
+
+ i++;
+ }
+ else {
+ DebAssert(defnkind == DK_FuncDefn || defnkind == DK_VirtualFuncDefn,
+ "bad defnkind");
+
+ // NOTE: no need to cast to VIRTUAL_FUNC_DEFN since we can treat
+ // a VIRTUAL_FUNC_DEFN as a FUNC_DEFN for our purposes here.
+ //
+ hfdefn = (HFUNC_DEFN) hdefn;
+
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+
+ // We'd REALLY like to deal only with the PROPERTYGET function
+ // if it exists...so try to get it.
+ //
+ if (!qfdefn->IsPropertyGet()) {
+ HFUNC_DEFN hfdefnGet;
+
+ hfdefnGet = HfdefnOfHmember((HMEMBER)memid, INVOKE_PROPERTYGET);
+
+ if (hfdefnGet != HFUNCDEFN_Nil) {
+ hfdefn = hfdefnGet;
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+ }
+ }
+
+ hlnam = qfdefn->Hlnam();
+
+ if (hlnam != HLNAM_Nil) {
+ IfErrRet(Pnammgr()->BstrWOfHlnam(hlnam, rgbstrNames+i));
+ }
+ else {
+ rgbstrNames[i] = AllocBstr(WIDE(""));
+ }
+
+ i++;
+
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+ cParams = qfdefn->CArgsUnmunged();
+
+ // for PUT and PUTREF (i.e. let and set) property functions, the
+ // last parameters name is ignored
+ if ((UINT)qfdefn->InvokeKind() &
+ ((UINT)INVOKE_PROPERTYPUT |
+ (UINT)INVOKE_PROPERTYPUTREF))
+ cParams--;
+
+ hparamdefn = (HPARAM_DEFN) qfdefn->m_ftdefn.m_hdefnFormalFirst;
+ uParam = 0;
+ while (i < min(cParams + 1, cNameMax)) {
+ // In OLE we have an array of PARAM_DEFN(s).
+ //
+ // Get the (uParam)th PARAM_DEFN
+ qparamdefn = QparamdefnOfIndex(hparamdefn, uParam);
+ uParam++;
+
+ hlnam = qparamdefn->Hlnam();
+
+ if (hlnam != HLNAM_Nil) {
+ IfErrGo(Pnammgr()->BstrWOfHlnam(hlnam, rgbstrNames + i));
+ }
+ else {
+ rgbstrNames[i] = AllocBstr(WIDE(""));
+ }
+
+ i++;
+ } // while
+ } // else
+ }
+ else {
+ return TIPERR_ElementNotFound;
+ }
+ *lpcName = i;
+ return err;
+
+Error:
+ while (i > 0) {
+ i -= 1;
+ FreeBstr(rgbstrNames[i]);
+ rgbstrNames[i] = NULL;
+ }
+ *lpcName = 0;
+
+ return err;
+}
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC TYPE_DATA::GetFuncDefnForDoc()
+*Purpose: Returns the HFUNC_DEFN where the caller can save the doc string
+* or the helpContext.
+*
+*Implementation : Get the FUNC_DEFN for passed in index. If this is a
+* property function then check if there is some other
+* property that is the current owner of the doc string/
+* helpContext. If there is some other owner then return
+* the func_defn of that property.
+*
+*Entry:
+* index : index of the function
+*
+*Exit:
+* FUNC_DEFN : func_defn of the function with the passed in index.
+*
+***********************************************************************/
+
+HFUNC_DEFN TYPE_DATA::GetFuncDefnForDoc(UINT index)
+{
+ HFUNC_DEFN hfdefn = HDEFN_Nil;
+ HFUNC_DEFN hfdefnSearch = HDEFN_Nil;
+ FUNC_DEFN *qfdefn, *qfdefnSearch;
+
+ TIPERROR err = TIPERR_None;
+ HLNAM hlnam;
+
+ if (index >= CAvailMeth()) {
+ return HDEFN_Nil;
+ }
+
+ IfErrGo(HfdefnOfIndex(index, &hfdefn));
+
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+
+ // Search for the owner if this is not the owner
+ if ((qfdefn->HstDocumentation() == HST_Nil) &&
+ (UHelpContextOfEncoding(qfdefn->WHelpContext()) == 0) ) {
+
+ // for property functions walk the list of func_defn and see if there
+ // is some other property(func) who is the owner of the Doc/HelpContext.
+ if (qfdefn->InvokeKind() != INVOKE_FUNC ) {
+ hlnam = qfdefn->Hlnam();
+ hfdefnSearch = HfdefnFirstAvailMeth();
+ while (hfdefnSearch != HDEFN_Nil) {
+ qfdefnSearch = QfdefnOfHfdefn(hfdefnSearch);
+ if ((qfdefnSearch->InvokeKind() != INVOKE_FUNC) &&
+ (hlnam == qfdefnSearch->Hlnam()) &&
+ hfdefn != hfdefnSearch) {
+
+ // Check if the doc string or the help context is set for this
+ // func_defn
+ if ((qfdefnSearch->HstDocumentation() != HST_Nil) ||
+ (UHelpContextOfEncoding(qfdefnSearch->WHelpContext()) != 0) ) {
+ // we found some other owner.
+ break;
+ } // if
+ } // if
+
+ hfdefnSearch = HfdefnNextAvailMeth(hfdefnSearch);
+ }// while
+ } // if
+ } // if
+
+ if (hfdefnSearch != HDEFN_Nil)
+ hfdefn = hfdefnSearch;
+
+
+#if ID_DEBUG
+ // Verify that there is only one owner
+ hfdefnSearch = HfdefnFirstAvailMeth();
+ qfdefnSearch = QfdefnOfHfdefn(hfdefnSearch);
+ if (qfdefn->InvokeKind() != INVOKE_FUNC ) {
+ hlnam = qfdefn->Hlnam();
+
+ hfdefnSearch = HfdefnFirstAvailMeth();
+
+ while (hfdefnSearch != HDEFN_Nil) {
+ qfdefnSearch = QfdefnOfHfdefn(hfdefnSearch);
+ if ((qfdefnSearch->InvokeKind() != INVOKE_FUNC) &&
+ (hlnam == qfdefnSearch->Hlnam()) &&
+ hfdefn != hfdefnSearch) {
+
+ // Check if the doc string or the help context is set for this
+ // func_defn
+ if ((qfdefnSearch->HstDocumentation() != HST_Nil) ||
+ (UHelpContextOfEncoding(qfdefnSearch->WHelpContext()) != 0) ) {
+ DebAssert(hfdefn == hfdefnSearch, " There should be only one owner ");
+ } // if
+ } // if
+
+ hfdefnSearch = qfdefnSearch->HdefnNext();
+ }// while
+ } // if
+
+#endif
+
+ return hfdefn;
+
+
+Error:
+ return HDEFN_Nil;
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC TYPE_DATA::SetFuncDocString()
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+TIPERROR TYPE_DATA::SetFuncDocString(UINT index, LPSTR szDocString)
+{
+ HFUNC_DEFN hfdefn;
+ FUNC_DEFN *qfdefn;
+ TIPERROR err = TIPERR_None;
+
+ HCHUNK hchunk;
+
+
+
+ DebAssert(Pdtroot()->CompState() == CS_UNDECLARED, "Invalid state");
+
+ if (index >= CAvailMeth()) {
+ return TIPERR_ElementNotFound;
+ }
+
+ hfdefn = GetFuncDefnForDoc(index);
+
+ if (hfdefn == HDEFN_Nil) {
+ return TIPERR_ElementNotFound;
+ }
+
+
+ IfErrRet(HchunkOfString(szDocString, &hchunk));
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+
+
+ qfdefn->SetHstDocumentation((HST)hchunk);
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC TYPE_DATA::SetVarDocString()
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+TIPERROR TYPE_DATA::SetVarDocString(UINT index, LPSTR szDocString)
+{
+ HMBR_VAR_DEFN hmvdefn;
+ MBR_VAR_DEFN *qmvdefn;
+ HCHUNK hchunk;
+ TIPERROR err = TIPERR_None;
+
+ DebAssert(Pdtroot()->CompState() == CS_UNDECLARED, "Invalid state");
+
+ if (index >= CDataMember()) {
+ return TIPERR_ElementNotFound;
+ }
+
+ hmvdefn = (HMBR_VAR_DEFN) HdefnFirstDataMbrNestedType();
+ qmvdefn = QmvdefnOfHmvdefn(hmvdefn);
+ DebAssert(qmvdefn->IsMemberVarDefn(), "bad defn type");
+ while (index > 0) {
+ hmvdefn = (HMBR_VAR_DEFN) qmvdefn->HdefnNext();
+ qmvdefn = QmvdefnOfHmvdefn(hmvdefn);
+ DebAssert(qmvdefn->IsMemberVarDefn(), "bad defn type");
+ index -= 1;
+ }
+
+ IfErrRet(HchunkOfString(szDocString, &hchunk));
+ qmvdefn = QmvdefnOfHmvdefn(hmvdefn);
+ qmvdefn->SetHstDocumentation((HST)hchunk);
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC TYPE_DATA::SetFuncHelpContext()
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+TIPERROR TYPE_DATA::SetFuncHelpContext(UINT index, DWORD dwHelpContext)
+{
+ HFUNC_DEFN hfdefn;
+ FUNC_DEFN *qfdefn;
+ TIPERROR err = TIPERR_None;
+ WORD wHelpContextEncoded;
+
+ if (index >= CAvailMeth()) {
+ return TIPERR_ElementNotFound;
+ }
+
+ hfdefn = GetFuncDefnForDoc(index);
+
+ if (hfdefn == HDEFN_Nil) {
+ return TIPERR_ElementNotFound;
+ }
+
+ // For space optimization we store encoded help context(2 bytes).
+ // NOTE: this call allocs memory
+ IfErrRet(GetEncodedHelpContext(dwHelpContext, &wHelpContextEncoded));
+
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+
+
+ qfdefn->SetWHelpContext(wHelpContextEncoded);
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC TYPE_DATA::SetVarHelpContext()
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+TIPERROR TYPE_DATA::SetVarHelpContext(UINT index, DWORD dwHelpContext)
+{
+ HMBR_VAR_DEFN hmvdefn;
+ MBR_VAR_DEFN *qmvdefn;
+ TIPERROR err = TIPERR_None;
+ WORD wHelpContextEncoded;
+
+ DebAssert(Pdtroot()->CompState() == CS_UNDECLARED, "Invalid state");
+
+ if (index >= CDataMember()) {
+ return TIPERR_ElementNotFound;
+ }
+
+ // For optimizing space we store encoded help context in the DEFN
+ // NOTE: this call allocs memory
+ IfErrRet(GetEncodedHelpContext(dwHelpContext, &wHelpContextEncoded));
+
+ hmvdefn = HdefnFirstDataMbrNestedType();
+ qmvdefn = QmvdefnOfHmvdefn(hmvdefn);
+ DebAssert(qmvdefn->IsMemberVarDefn(), "bad defn type");
+ while (index > 0) {
+ hmvdefn = (HMBR_VAR_DEFN) qmvdefn->HdefnNext();
+ qmvdefn = QmvdefnOfHmvdefn(hmvdefn);
+ DebAssert(qmvdefn->IsMemberVarDefn(), "bad defn type");
+ index -= 1;
+ }
+
+ qmvdefn->SetWHelpContext(wHelpContextEncoded);
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC TYPE_DATA::GetDocumentation()
+*Purpose:
+* return the documentation for a func or var
+*
+*Notes:
+* For BASIC modules can not get doc or help for vars/funcs so just
+* return error if asked for
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+
+TIPERROR TYPE_DATA::GetDocumentation(MEMBERID memid,
+ BSTR FAR*lpbstrName,
+ BSTR FAR*lpbstrDocString,
+ DWORD FAR*lpdwHelpContext)
+{
+ HDEFN hdefn;
+ UINT defnkind;
+ HFUNC_DEFN hfdefn;
+ FUNC_DEFN *qfdefn;
+ HMBR_VAR_DEFN hmvdefn;
+ MBR_VAR_DEFN *qmvdefn;
+ HST hst;
+ ULONG uHelpContext;
+ HLNAM hlnam;
+ TIPERROR err = TIPERR_None;
+
+ // check variables
+ // find var defn
+ hdefn = HdefnOfHmember((HMEMBER) memid, &defnkind);
+ if (hdefn != HDEFN_Nil) {
+ if (defnkind == DK_VarDefn) {
+ hmvdefn = (HMBR_VAR_DEFN) hdefn;
+ qmvdefn = QmvdefnOfHmvdefn(hmvdefn);
+ hlnam = qmvdefn->Hlnam();
+ hst = qmvdefn->HstDocumentation();
+ uHelpContext = UHelpContextOfEncoding(qmvdefn->WHelpContext());
+ } else {
+ DebAssert(defnkind == DK_FuncDefn, "bad defnkind");
+ hfdefn = (HFUNC_DEFN) hdefn;
+
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+ hlnam = qfdefn->Hlnam();
+
+ hst = qfdefn->HstDocumentation();
+ uHelpContext = UHelpContextOfEncoding(qfdefn->WHelpContext());
+ }
+ } else {
+ return TIPERR_ElementNotFound;
+ }
+
+ // set return values wanted
+ if (lpbstrName) {
+ IfErrRet(Pnammgr()->BstrWOfHlnam(hlnam, lpbstrName));
+ }
+
+ if (lpbstrDocString) {
+ // get doc string if there is one
+ if (hst != HST_Nil) {
+ IfErrGo(StringOfHchunk(hst, (BSTRA *)lpbstrDocString));
+#if OE_WIN32
+ HRESULT hresult;
+ if ((hresult = ConvertBstrToWInPlace(lpbstrDocString)) != NOERROR) {
+ FreeBstr(*lpbstrDocString);
+ err = TiperrOfHresult(hresult);
+ goto Error;
+ }
+#endif //OE_WIN32
+ } else {
+ *lpbstrDocString = NULL;
+ }
+ }
+ if (lpdwHelpContext) {
+ *lpdwHelpContext = uHelpContext;
+ }
+
+ return TIPERR_None;
+Error:
+ if (lpbstrName) {
+ SysFreeString(*lpbstrName);
+ }
+ return err;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::UHelpContextOfEncoding()
+*Purpose:
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+ULONG TYPE_DATA::UHelpContextOfEncoding(WORD wHelpContext)
+{
+ ULONG uHelpContext;
+ BYTE *pbChunkStr;
+ HCHUNK hchunk;
+ USHORT usDiff;
+
+
+ // check if the encoded help context contains a chunk
+ if(IsHchunk(wHelpContext)) {
+ // Get the hchunk
+ hchunk = GetHchunk(wHelpContext);
+
+ // check if the hchunk stored is valid. if all top 15 bits are 1 then
+ // it is HCHUNK_Nil
+ if (hchunk == 0xfffe) {
+ uHelpContext = 0;
+ }
+ else {
+ // Get the help context stored in the block manager.
+ pbChunkStr = m_blkmgr.QtrOfHandle(hchunk);
+ uHelpContext = *(ULONG *)pbChunkStr;
+ }
+ }
+ else {
+ // get the diff
+ usDiff = GetDiff(wHelpContext);
+ // Calculate the help context
+ if (IsNegative(wHelpContext)) {
+ uHelpContext = m_uHelpContextBase - usDiff;
+ }
+ else {
+ uHelpContext = m_uHelpContextBase + usDiff;
+ }
+
+ }
+
+ return uHelpContext;;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::GetEncodedHelpContext()
+*Purpose: Encodes the help context to a WORD. This is done for space
+* space optimization.
+*
+*IMPLEMENTATION : in the MBR_DEFN we store the difference from the base( the
+* first help context) . The difference can be -ve of +ve #.
+* We only store difference up to 2 to the power of 14.
+* In case the difference is greater than we allocate a
+* chunk of 4 bytes(ULONG) and store the difference there.
+*
+*Entry:
+* None.
+*
+*Exit:
+* None.
+*
+***********************************************************************/
+TIPERROR TYPE_DATA::GetEncodedHelpContext(ULONG uHelpContext, WORD *pwHelpContext)
+{
+ ULONG uDiff;
+ TIPERROR err;
+ HCHUNK hchunk;
+ BYTE *pbChunkStr;
+
+ // if we do not have the base yet then make this the base.
+ if (m_uHelpContextBase == 0) {
+ m_uHelpContextBase = uHelpContext;
+ }
+
+ // if the difference can be stored
+ if ((uDiff = AbsDiff(uHelpContext, m_uHelpContextBase)) <= 0x3fff) {
+ *pwHelpContext = 0;
+ *pwHelpContext |= (((USHORT) uDiff) << 2);
+ // set the flag to indicate that we have stored a number
+ SetIsNumber(*pwHelpContext);
+ // Set if the number is -ve;
+ SetNegativeBit(*pwHelpContext, uHelpContext < m_uHelpContextBase);
+ }
+ else {
+ // Since we cannot store the diff we will allocate a chunk for the long
+ // and store the uHelpContext there.
+ IfErrRet(m_blkmgr.AllocChunk(&hchunk, sizeof(ULONG)));
+ pbChunkStr = m_blkmgr.QtrOfHandle(hchunk);
+ *(ULONG *)pbChunkStr = (ULONG)uHelpContext;
+
+ DebAssert(!(hchunk & 0x0001), " hchunk should be even ");
+ // Store the hchunk.
+ // Note: the lsb will be used to idicate that we are storing a
+ // hchunk
+ //
+ *pwHelpContext = hchunk;
+
+ // Set the bit to indicate that we have stored a hchunk.
+ SetIsHchunk(*pwHelpContext);
+
+ }
+
+ return TIPERR_None;
+}
+
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PRIVATE TYPE_DATA::HchunkOfString - Writes string to chunk.
+*Purpose:
+* Allocates a chunk for string, writes string to chunk and
+* produces handle.
+*
+*Implementation Notes:
+* Stores string as an ST (i.e. a ULONG prefixed buffer).
+*
+*Entry:
+* szStr - string (IN).
+* phchunk - Pointer to handle of chunk for string (OUT).
+*
+*Exit:
+* Produces handle to ST for doc string on heap.
+*
+*Errors:
+* TIPERROR
+*
+***********************************************************************/
+
+TIPERROR TYPE_DATA::HchunkOfString(LPSTR szStr, HCHUNK *phchunk)
+{
+ TIPERROR err;
+
+ DebAssert(phchunk != NULL, "bad param");
+
+ DOCSTR_MGR *pdstrmgr;
+ HST hst;
+
+ // Get the containing typelib.
+ IfErrRet(Pdtroot()->Pgdtinfo()->PgtlibOleContaining()->
+ GetDstrMgr(&pdstrmgr));
+
+ // get the handle for the help string.
+ // Note:- This is a temporary handle. This handle is replaced by
+ // a another handle in UpdateDocStrings().
+ //
+ IfErrRet(pdstrmgr->GetHstOfHelpString(szStr, &hst));
+
+ *phchunk = hst;
+
+ return TIPERR_None;
+}
+#pragma code_seg()
+
+
+/***
+*PUBLIC TYPE_DATA::StringOfHchunk - Reads string from chunk.
+*Purpose:
+* Reads a ULONG-prefixed ST from a chunk and produces a BSTRA.
+*
+*Implementation Notes:
+*
+*Entry:
+* hchunkStr - Handle to chunk containing an ST (IN).
+* plstr - Pointer to a BSTRA (OUT).
+*
+*Exit:
+* Produces BSTRA from chunk on heap.
+*
+*Errors:
+* TIPERR_OutOfMemory
+*
+***********************************************************************/
+
+TIPERROR TYPE_DATA::StringOfHchunk(HCHUNK hchunkStr, BSTRA *plstr)
+{
+ BYTE *pbChunkStr;
+
+ DebAssert(plstr != NULL, "bad param.");
+
+
+ DOCSTR_MGR *pdstrmgr;
+ TIPERROR err;
+
+ // Get the doc string manager.
+ IfErrRet(Pdtroot()->Pgdtinfo()->PgtlibOleContaining()->
+ GetDstrMgr(&pdstrmgr));
+
+ pbChunkStr = m_blkmgr.QtrOfHandle(hchunkStr);
+
+ // Get the decoded Doc string.
+ //
+ IfErrRet(pdstrmgr->GetDecodedDocStrOfHst(pbChunkStr, (BSTR *)plstr));
+#if OE_WIN32
+ IfErrRet(TiperrOfHresult(ConvertBstrToAInPlace(plstr)));
+#endif
+
+ return (*plstr == NULL) ? TIPERR_OutOfMemory : TIPERR_None;
+}
+
+
+
+
+/***
+*TYPE_DATA::GetDynTypeBindOfHvdefn - get type bind of a var defn
+*Purpose:
+* CONSIDER: ilanc 10-Feb-93:
+* this function should vanish -- all clients should
+* use GetTypeComp and GetTypeAttr after having used GetTypeInfoOfHvdefn.
+*
+* Gets the DYN_TYPEBIND associated with a var defn which describes
+* a base member of a class.
+*
+*Entry:
+* hvardefn - VAR_DEFN describing a base member.
+*
+*Exit:
+* returns TIPERROR.
+* *ppdtbind has the DYN_TYPEBIND, or NULL if the base member isn't
+* of class type or doesn't have a DYN_TYPEBIND.
+* *himptype has himptype (in THIS impmgr) of the type. himptype can be NULL.
+*
+***********************************************************************/
+
+TIPERROR TYPE_DATA::GetDynTypeBindOfHvdefn(HVAR_DEFN hvdefn,
+ DYN_TYPEBIND **ppdtbind,
+ HIMPTYPE * phimptype)
+{
+ DEFN_TYPEBIND *pdfntbind;
+ ITypeInfoA * ptinfo;
+ GEN_DTINFO * pgdtinfo;
+
+ BOOL fGetInterface = FALSE;
+
+ TIPERROR err = TIPERR_None;
+
+ *ppdtbind = NULL; // by default, none.
+
+ IfErrRet(GetTypeInfoOfHvdefn(hvdefn, &ptinfo, phimptype));
+
+ // we only support getting the typebind from an ITypeInfo if it's
+ // one of "our" ITypeInfo's (owned by TYPELIB.DLL or VBA.DLL)
+ if (ptinfo->QueryInterface(IID_TYPELIB_GEN_DTINFO,(LPVOID *)&pgdtinfo) != NOERROR)
+ {
+ err = TIPERR_NotYetImplemented; // CONSIDER: better error?
+ }
+ else {
+ err = pgdtinfo->GetDefnTypeBind(&pdfntbind);
+ pgdtinfo->Release();
+ }
+
+ ptinfo->Release();
+
+ if (err)
+ return err;
+
+ // NOTE: this cast will return NULL in the case of failure
+ // which is what we want.
+ //
+ *ppdtbind = (DYN_TYPEBIND *)
+ pdfntbind->QueryProtocol(DYN_TYPEBIND::szProtocolName);
+
+ return err;
+}
+
+
+/***
+*TYPE_DATA::GetTypeInfoOfHvdefn - get type info of a var defn
+*Purpose:
+* Gets the ITypeInfo associated with a var defn which describes
+* a base member of a class.
+*
+*Entry:
+* hvdefn - VAR_DEFN describing a base member.
+*
+*Exit:
+* returns TIPERROR.
+* *pptinfo has the ITypeInfo, or NULL if the base member isn't
+* of class type.
+* *himptype has himptype (in THIS impmgr) of the type. himptype can be NULL.
+*
+***********************************************************************/
+
+TIPERROR TYPE_DATA::GetTypeInfoOfHvdefn(HVAR_DEFN hvdefn,
+ ITypeInfoA **pptinfo,
+ HIMPTYPE *phimptype)
+{
+ VAR_DEFN *qvdefn;
+ TYPE_DEFN *qtdefn;
+ HIMPTYPE himptype;
+ ITypeInfoA *ptinfo;
+ BOOL fGetInterface = FALSE;
+
+ TIPERROR err = TIPERR_None;
+
+ *pptinfo = NULL; // by default, none.
+
+ // Get HIMPTYPE of the base class.
+ qvdefn = QvdefnOfHvdefn(hvdefn);
+
+ DebAssert(!qvdefn->IsSimpleType(), "can't be simple type");
+ qtdefn = QtdefnOfHtdefn(qvdefn->Htdefn());
+ DebAssert(qtdefn->IsUserDefined(), " must derive from user defined type");
+
+ himptype = qtdefn->HimptypeActual();
+
+ // See if we should be getting the interface side of a dual
+ // interface.
+ //
+ if (himptype & 0x1) {
+ fGetInterface = TRUE;
+ himptype &= ~0x1;
+ }
+
+ if (phimptype != NULL)
+ *phimptype = himptype;
+
+ // Try to load the TYPEINFO.
+ err = Pimpmgr()->GetTypeInfo(himptype, DEP_None, &ptinfo);
+ if (err != TIPERR_None) {
+ }
+ else {
+ if (fGetInterface) {
+ ITypeInfoA *ptinfoDisp;
+ TYPEATTR *ptypeattr;
+ TYPEKIND tkind;
+ HREFTYPE hreftype;
+
+ ptinfoDisp = ptinfo;
+
+ IfErrGo(TiperrOfHresult(ptinfoDisp->GetTypeAttr(&ptypeattr)));
+ tkind = ptypeattr->typekind;
+ DebAssert(ptypeattr->wTypeFlags & TYPEFLAG_FDUAL, "Not a dual");
+ ptinfoDisp->ReleaseTypeAttr(ptypeattr);
+
+ if (tkind == TKIND_DISPATCH) {
+ // Get the other interface.
+ IfErrGo(TiperrOfHresult(ptinfoDisp->GetRefTypeOfImplType(
+ (UINT)-1,
+ &hreftype)));
+ IfErrGo(TiperrOfHresult(ptinfoDisp->GetRefTypeInfo(hreftype,
+ &ptinfo)));
+ ptinfoDisp->Release();
+ }
+ }
+ *pptinfo = ptinfo;
+ }
+
+ return err;
+
+Error:
+ ptinfo->Release();
+
+ return err;
+}
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC EquivTypeDefnsIgnoreByRef
+*Purpose:
+* Compares two type defns. For Basic Arrays, the types
+* are the same if the base type of the arrays are the same.
+* Optionally ignores byref vs. byval differences.
+*
+* Two Nil types are considered equivalent.
+*
+*Entry:
+* ptdata1 - TYPE_DATA containing first type defn.
+* fSimple1 - if htdefn1 is a simple type
+* htdefn1 - first type defn
+* ptdata2 - TYPE_DATA containing 2nd type defn.
+* fSimple2 - if htdefn2 is a simple type
+* htdefn2 - second type defn
+* pfEqual -
+*
+*Exit:
+* returns TRUE if the two have the exact same type.
+***********************************************************************/
+
+TIPERROR EquivTypeDefnsIgnoreByRef(TYPE_DATA *ptdata1,
+ BOOL fSimple1,
+ sHTYPE_DEFN htdefn1,
+ TYPE_DATA *ptdata2,
+ BOOL fSimple2,
+ sHTYPE_DEFN htdefn2,
+ WORD wFlags,
+ BOOL *pfEqual,
+ BOOL fIgnoreByRef)
+{
+ TYPE_DEFN *qtdefn1, *qtdefn2;
+
+ // Special case: htdefn==Nil means the same as void.
+ //
+ // CONSIDER: Should we keep this special case?
+ //
+ if (!fSimple1 && htdefn1 == HDEFN_Nil) {
+ fSimple1 = TRUE;
+ htdefn1 = 0; ((TYPE_DEFN *) &htdefn1)->SetTdesckind(TDESCKIND_Void);
+ }
+ if (!fSimple2 && htdefn2 == HDEFN_Nil) {
+ fSimple2 = TRUE;
+ htdefn2 = 0; ((TYPE_DEFN *) &htdefn2)->SetTdesckind(TDESCKIND_Void);
+ }
+
+ // Simple types are encoded in the handle.
+ if (fSimple1)
+ qtdefn1 = (TYPE_DEFN *) &htdefn1;
+ else
+ qtdefn1 = ptdata1->QtdefnOfHtdefn(htdefn1);
+ if (fSimple2)
+ qtdefn2 = (TYPE_DEFN *) &htdefn2;
+ else
+ qtdefn2 = ptdata2->QtdefnOfHtdefn(htdefn2);
+
+ // This loop iterates along the TYPE_DEFN, comparing all
+ // modifier until we hit a terminating TYPE_DEFN.
+ for (;;) {
+ if (fIgnoreByRef == FALSE) {
+ if (*(USHORT *)qtdefn1 != *(USHORT *)qtdefn2) {
+ *pfEqual = FALSE;
+ return TIPERR_None;
+ }
+ }
+ else {
+ // We don't care about PTRKIND_Basic differences
+ // so just compare the tdesckinds
+ //
+ if (qtdefn1->Tdesckind() != qtdefn2->Tdesckind()
+ || (qtdefn1->IsLCID() != qtdefn2->IsLCID())
+ && !(wFlags & FEQUIVIGNORE_HasLcid)
+ ) {
+ if (qtdefn1->Tdesckind() == TDESCKIND_Ptr) {
+ ++qtdefn1; // increment this guy and go around again
+ continue; // this goes around
+ }
+ if (qtdefn2->Tdesckind() == TDESCKIND_Ptr) {
+ ++qtdefn2; // increment this guy and go around again
+ continue; // this goes around
+ }
+ *pfEqual = FALSE;
+ return TIPERR_None;
+ }
+ }
+
+ switch (qtdefn1->Tdesckind()) {
+ case TDESCKIND_Ptr:
+ // followed by another TYPEDEFN
+ ++qtdefn1;
+ ++qtdefn2;
+ break;
+
+ case TDESCKIND_UserDefined:
+ {
+ HIMPTYPE himptype1, himptype2;
+ // Defer to CompareUHimptypes
+ himptype1 = qtdefn1->Himptype();
+ himptype2 = qtdefn2->Himptype();
+
+ return CompareHimptypes(ptdata1,
+ himptype1,
+ ptdata2,
+ himptype2,
+ pfEqual);
+ }
+
+ case TDESCKIND_Carray:
+ case TDESCKIND_BasicArray:
+ // followed by sHARRAY_DESC which we don't need to
+ // compare, then followed by TYPE_DEFN of base type.
+ qtdefn1 = (TYPE_DEFN *) (((BYTE *) qtdefn1) + sizeof(sHARRAY_DESC) +
+ sizeof(TYPE_DEFN));
+ qtdefn2 = (TYPE_DEFN *) (((BYTE *) qtdefn2) + sizeof(sHARRAY_DESC) +
+ sizeof(TYPE_DEFN));
+ break;
+
+ default:
+ DebHalt("unknown or unsupported TDESCKIND");
+#if ID_DEBUG
+ case TDESCKIND_UI1:
+ case TDESCKIND_I1:
+ case TDESCKIND_UI2:
+ case TDESCKIND_I2:
+ case TDESCKIND_UI4:
+ case TDESCKIND_I4:
+ case TDESCKIND_UI8:
+ case TDESCKIND_I8:
+ case TDESCKIND_R4:
+ case TDESCKIND_R8:
+ case TDESCKIND_Void:
+ case TDESCKIND_String:
+ case TDESCKIND_Currency:
+ case TDESCKIND_Value:
+ case TDESCKIND_Object:
+ case TDESCKIND_IUnknown:
+ case TDESCKIND_LPSTR:
+ case TDESCKIND_LPWSTR:
+ case TDESCKIND_Date:
+ case TDESCKIND_Int:
+ case TDESCKIND_Uint:
+ case TDESCKIND_HResult:
+ case TDESCKIND_Bool:
+ case TDESCKIND_Error:
+ case TDESCKIND_Empty:
+ case TDESCKIND_Null:
+#endif //ID_DEBUG
+ // Nothing additional to compare
+ *pfEqual = TRUE;
+ return TIPERR_None;
+
+ } // switch
+ } // for
+
+ DebHalt("I can never get here, even though compiler thinks I could.");
+ return 0;
+}
+#pragma code_seg()
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*PUBLIC EquivTypeDefns - compare two TYPE_DEFNs
+*Purpose:
+* Compares two type defns. For Basic Arrays, the types
+* are the same if the base type of the arrays are the same.
+*
+* Two Nil types are considered equivalent.
+*
+*Entry:
+* ptdata1 - TYPE_DATA containing first type defn.
+* fSimple1 - if htdefn1 is a simple type
+* htdefn1 - first type defn
+* ptdata2 - TYPE_DATA containing 2nd type defn.
+* fSimple2 - if htdefn2 is a simple type
+* htdefn2 - second type defn
+* pfEqual -
+*
+*Exit:
+* returns TRUE if the two have the exact same type.
+***********************************************************************/
+
+TIPERROR EquivTypeDefns(TYPE_DATA *ptdata1, BOOL fSimple1, sHTYPE_DEFN htdefn1,
+ TYPE_DATA *ptdata2, BOOL fSimple2, sHTYPE_DEFN htdefn2,
+ WORD wFlags, BOOL *pfEqual)
+{
+ return EquivTypeDefnsIgnoreByRef(ptdata1,
+ fSimple1,
+ htdefn1,
+ ptdata2,
+ fSimple2,
+ htdefn2,
+ wFlags,
+ pfEqual,
+ FALSE); // byref != byval
+}
+#pragma code_seg()
+
+
+
+
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*Private : SetDllEntryDefn
+*Purpose:
+* returns FUNC_DEFN of index
+*Entry:
+* UINT : index of the func defn to retrun
+*
+*Exit:
+* retruns HFUNC_DEFN for the index passed in .
+*
+**********************************************************************/
+TIPERROR TYPE_DATA::SetDllEntryDefn(UINT index, HDLLENTRY_DEFN hdllentrydefn)
+{
+ TIPERROR err = TIPERR_None;
+ HFUNC_DEFN hfdefn;
+ FUNC_DEFN *qfdefn;
+
+ IfErrRet(HfdefnOfIndex(index, &hfdefn));
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+
+ qfdefn->SetHdllentrydefn(hdllentrydefn);
+
+ return TIPERR_None;
+
+}
+#pragma code_seg()
+
+
+
+
+
+/***
+*Private : HfdefnOfIndex
+*Purpose:
+* returns FUNC_DEFN of index
+*Entry:
+* UINT : index of the func defn to retrun
+*
+*Exit:
+* retruns HFUNC_DEFN for the index passed in .
+*
+**********************************************************************/
+TIPERROR TYPE_DATA::HfdefnOfIndex(UINT index, HFUNC_DEFN *phfdefn)
+{
+ HFUNC_DEFN hfdefn;
+
+ if (index >= CAvailMeth()) {
+ return TIPERR_ElementNotFound;
+ }
+
+ hfdefn = HfdefnFirstAvailMeth();
+ while (index > 0) {
+ index -= 1;
+ hfdefn = HfdefnNextAvailMeth(hfdefn);
+ DebAssert(hfdefn != HFUNCDEFN_Nil, " Bad func defn " );
+ }
+
+ *phfdefn = hfdefn;
+
+ return TIPERR_None;
+}
+
+
+
+
+
+
+
+#pragma code_seg(CS_CREATE)
+/***
+*Public : UpdateDocStrings
+*Purpose:
+* Walks all the fundefn/vardefn and update the handle to the doc string.
+*
+*Entry:
+* None.
+*
+*Exit:
+* TIPERROR (Tiperr_OutOfMemory);
+*
+**********************************************************************/
+TIPERROR TYPE_DATA::UpdateDocStrings()
+{
+ HFUNC_DEFN hfdefn;
+ FUNC_DEFN *qfdefn;
+ HST hst;
+ LPSTR lpstr;
+ UINT uLen;
+ DOCSTR_MGR *pdstrmgr;
+ HCHUNK hchunk;
+ BYTE *qbChunkStr;
+ HMBR_VAR_DEFN hmvdefn;
+ MBR_VAR_DEFN *qmvdefn;
+ TIPERROR err = TIPERR_None;
+
+ // Get the doc string manager
+ IfErrRet(Pdtroot()->Pgdtinfo()->PgtlibOleContaining()->
+ GetDstrMgr(&pdstrmgr));
+
+ // walk all the func defn and store all the encoded strings.
+ hfdefn = HfdefnFirstMeth();
+ while (hfdefn != HFUNCDEFN_Nil) {
+
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+ hst = (HST) qfdefn->HstDocumentation();
+
+ //
+ if (hst != HST_Nil) {
+
+ // ask the doc str manager for the encoded string.
+ IfErrRet(pdstrmgr->GetEncodedDocStrOfHst(hst, &lpstr, &uLen));
+ DebAssert(lpstr != NULL, "");
+
+ // save the encoded string in the blkmgr.
+ IfErrGo(m_blkmgr.AllocChunk(&hchunk, uLen));
+
+ qbChunkStr = m_blkmgr.QtrOfHandle(hchunk);
+ memcpy(qbChunkStr, lpstr, uLen);
+
+ // qfdefn may be invalid by now.
+ qfdefn = QfdefnOfHfdefn(hfdefn);
+ qfdefn->SetHstDocumentation((HST)hchunk);
+
+ // Free the clients memory
+ MemFree(lpstr);
+ }
+
+ // get the next func defn.
+ hfdefn = qfdefn->HdefnNext();
+ }
+
+ DebAssert(hfdefn == HFUNCDEFN_Nil, " Bad func defn " );
+
+ // process each var defn(s)
+ hmvdefn = (HMBR_VAR_DEFN) HdefnFirstDataMbrNestedType();
+
+ while (hmvdefn != HFUNCDEFN_Nil) {
+ qmvdefn = QmvdefnOfHmvdefn(hmvdefn);
+ DebAssert(qmvdefn->IsMemberVarDefn(), "bad defn type");
+
+ hst = (HST) qmvdefn->HstDocumentation();
+
+ //
+ if (hst != HST_Nil) {
+ // ask the doc str manager for the encoded string.
+ IfErrRet(pdstrmgr->GetEncodedDocStrOfHst(hst, &lpstr, &uLen));
+ DebAssert(lpstr != NULL, "");
+
+ // save the encoded string in the blkmgr.
+ IfErrGo(m_blkmgr.AllocChunk(&hchunk, uLen));
+
+ qbChunkStr = m_blkmgr.QtrOfHandle(hchunk);
+ memcpy(qbChunkStr, lpstr, uLen);
+
+ // re deference the qointer.
+ qmvdefn = QmvdefnOfHmvdefn(hmvdefn);
+ qmvdefn->SetHstDocumentation((HST)hchunk);
+
+ // Free the clients memory
+ MemFree(lpstr);
+ }
+
+ hmvdefn = (HMBR_VAR_DEFN) qmvdefn->HdefnNext();
+ }
+
+ return TIPERR_None;
+Error:
+ MemFree(lpstr);
+}
+#pragma code_seg()
+
+
+// methods that want to be inline but cause header file problems if they are.
+//
+/***
+*PUBLIC TYPE_DATA::HtdefnAlias - TypeDefn of alias
+*Purpose:
+* Returns htdefn of tinfos alias
+*
+*Entry:
+* None
+*
+*Exit:
+* Returns htdefn of tinfos alia
+*
+***********************************************************************/
+
+HTYPE_DEFN TYPE_DATA::HtdefnAlias() const
+{
+ DebAssert(m_pdtroot->Pgdtinfo()->GetTypeKind() == TKIND_ALIAS,
+ "should be TKIND_ALIAS");
+ return (HTYPE_DEFN) m_htdefnAlias;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::SetIsSimpleTypeAlias
+*Purpose:
+* Changes simple type state of alias.
+*
+*Entry:
+* isSimpleType
+*
+*Exit:
+*
+***********************************************************************/
+
+VOID TYPE_DATA::SetIsSimpleTypeAlias(BOOL isSimpleType)
+{
+ DebAssert(m_pdtroot->Pgdtinfo()->GetTypeKind() == TKIND_ALIAS,
+ "should be TKIND_ALIAS");
+ m_isSimpleTypeAlias = (USHORT)isSimpleType;
+}
+
+
+/***
+*PUBLIC TYPE_DATA::IsSimpleTypeAlias - TypeDefn of alias
+*Purpose:
+* TRUE if alias typedefn is simple.
+*
+*Entry:
+* None
+*
+*Exit:
+* TRUE if alias typedefn is simple.
+*
+***********************************************************************/
+
+BOOL TYPE_DATA::IsSimpleTypeAlias() const
+{
+ DebAssert(m_pdtroot->Pgdtinfo()->GetTypeKind() == TKIND_ALIAS,
+ "should be TKIND_ALIAS");
+ return (BOOL)m_isSimpleTypeAlias;
+}
diff --git a/private/oleauto/src/typelib/tdesck.hxx b/private/oleauto/src/typelib/tdesck.hxx
new file mode 100644
index 000000000..66f961ec3
--- /dev/null
+++ b/private/oleauto/src/typelib/tdesck.hxx
@@ -0,0 +1,72 @@
+// tdesck.hxx
+// included by cltypes.hxx
+
+// !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+// IMPORTANT: Read this before changing this file
+// !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+
+// As far as I can tell, here are the other files
+// that need updating when tdesck.hxx is changed.
+// They are:
+// clutil.cxx
+//
+// So if you change this file, make sure you update
+// the others. And if you discover any others that
+// need updating, please add them here.
+//
+// 22-Mar-92 stevenl
+//
+
+#ifndef TDESCK_HXX_INCLUDED
+#define TDESCK_HXX_INCLUDED
+
+// enum TYPEDESCKIND - tdesckind
+//
+enum TYPEDESCKIND
+{
+ TDESCKIND_Empty= VT_EMPTY,
+ TDESCKIND_Null= VT_NULL,
+ TDESCKIND_I2= VT_I2,
+ TDESCKIND_I4= VT_I4,
+ TDESCKIND_R4= VT_R4,
+ TDESCKIND_R8= VT_R8,
+ TDESCKIND_Currency= VT_CY,
+ TDESCKIND_Date= VT_DATE,
+ TDESCKIND_String= VT_BSTR,
+ TDESCKIND_Object= VT_DISPATCH,
+ TDESCKIND_Error= VT_ERROR,
+ TDESCKIND_Bool= VT_BOOL,
+ TDESCKIND_Value= VT_VARIANT,
+ TDESCKIND_IUnknown= VT_UNKNOWN,
+
+ TDESCKIND_I1= VT_I1,
+ TDESCKIND_UI1= VT_UI1,
+ TDESCKIND_UI2= VT_UI2,
+ TDESCKIND_UI4= VT_UI4,
+ TDESCKIND_I8= VT_I8,
+ TDESCKIND_UI8= VT_UI8,
+ TDESCKIND_Int= VT_INT,
+ TDESCKIND_Uint= VT_UINT,
+ TDESCKIND_Void= VT_VOID,
+ TDESCKIND_HResult= VT_HRESULT,
+ TDESCKIND_Ptr= VT_PTR,
+ TDESCKIND_BasicArray= VT_SAFEARRAY,
+ TDESCKIND_Carray= VT_CARRAY,
+ TDESCKIND_UserDefined= VT_USERDEFINED,
+ TDESCKIND_LPSTR= VT_LPSTR,
+ TDESCKIND_LPWSTR= VT_LPWSTR,
+
+ TDESCKIND_MAX, // end of enum marker
+
+ TDESCKIND_Filetime= VT_FILETIME,
+ TDESCKIND_Blob= VT_BLOB,
+ TDESCKIND_Stream= VT_STREAM,
+ TDESCKIND_Storage= VT_STORAGE,
+ TDESCKIND_StreamedObj= VT_STREAMED_OBJECT,
+ TDESCKIND_StoredObj= VT_STORED_OBJECT,
+ TDESCKIND_BlobObj= VT_BLOB_OBJECT,
+ TDESCKIND_CF= VT_CF,
+ TDESCKIND_CLSID= VT_CLSID,
+};
+
+#endif // TDESCK_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/tinfo.hxx b/private/oleauto/src/typelib/tinfo.hxx
new file mode 100644
index 000000000..b0d638dd8
--- /dev/null
+++ b/private/oleauto/src/typelib/tinfo.hxx
@@ -0,0 +1,56 @@
+/***
+*tinfo.hxx - TYPEINFO header file
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Protocol for root of all information about a type.
+*
+*Revision History:
+*
+* 03-Jun-91 alanc: Recreated.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#ifndef TINFO_HXX_INCLUDED
+#define TINFO_HXX_INCLUDED
+
+#include "cltypes.hxx"
+
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szTINFO_HXX)
+#define SZ_FILE_NAME g_szTINFO_HXX
+#endif
+
+// UNDONE OA95: This structure should go away.
+
+/***
+*class TYPEINFO - 'ti'
+*Purpose:
+* TYPEINFO Protocol.
+*
+***********************************************************************/
+
+class TYPEINFO : public ITypeInfoA
+{
+public:
+ // TYPEINFO methods
+ virtual TIPERROR EXPORT GetMemberName(HMEMBER hmember, BSTRA *plstrName) = 0;
+ virtual TIPERROR EXPORT GetDynTypeMembers(LPLPDYNTYPEMEMBERS lplpDynTypeMembers) = 0;
+ virtual TIPERROR EXPORT GetDefnTypeBind(LPLPDEFNTBIND pdfntbind) = 0;
+ virtual TIPERROR EXPORT GetTypeFixups(LPLPTYPEFIXUPS lplpTypeFixups) = 0;
+ //virtual TYPEKIND EXPORT GetTypeKind() = 0;
+ virtual TIPERROR EXPORT Reset() = 0;
+
+#ifdef TYPEINFO_VTABLE
+#pragma VTABLE_EXPORT
+#endif
+};
+
+
+#endif // ! TINFO_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/tiperr.h b/private/oleauto/src/typelib/tiperr.h
new file mode 100644
index 000000000..4e05b85f9
--- /dev/null
+++ b/private/oleauto/src/typelib/tiperr.h
@@ -0,0 +1,92 @@
+/***
+*C:\SILVER\D2W32ND\tiperr.h - Defines error code constants
+*
+* THIS FILE IS AUTOMATICALLY GENERATED FROM EB.ERR
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Defines the TIPERR_XXX error codes.
+*
+*****************************************************************************/
+
+#ifndef TIPERR_H_INCLUDED
+#define TIPERR_H_INCLUDED
+
+// Map all of the old TIPERRORs to HRESULTS
+
+#define TIPERR_None NOERROR
+
+#define TIPERR_NotYetImplemented HresultOfScode(E_NOTIMPL)
+#define TIPERR_OutOfMemory HresultOfScode(E_OUTOFMEMORY)
+#define TIPERR_Abort HresultOfScode(E_ABORT)
+#define TIPERR_Unexpected HresultOfScode(E_UNEXPECTED)
+#define TIPERR_InvalidPointer HresultOfScode(E_POINTER)
+#define TIPERR_InvalidHandle HresultOfScode(E_HANDLE)
+#define TIPERR_InvalidArg HresultOfScode(E_INVALIDARG)
+#define TIPERR_NoInterface HresultOfScode(E_NOINTERFACE)
+#define TIPERR_PermissionDenied HresultOfScode(E_ACCESSDENIED)
+
+#define TIPERR_WriteFault HresultOfScode(STG_E_WRITEFAULT)
+#define TIPERR_InsufficientMemory HresultOfScode(STG_E_INSUFFICIENTMEMORY)
+#define TIPERR_NoMoreFiles HresultOfScode(STG_E_NOMOREFILES)
+#define TIPERR_FileShareViolation HresultOfScode(STG_E_SHAREVIOLATION)
+#define TIPERR_FileLockViolation HresultOfScode(STG_E_LOCKVIOLATION)
+#define TIPERR_AbnormalApiExit HresultOfScode(STG_E_ABNORMALAPIEXIT)
+#define TIPERR_InvalidHeader HresultOfScode(STG_E_INVALIDHEADER)
+#define TIPERR_Unknown HresultOfScode(STG_E_UNKNOWN)
+#define TIPERR_InvalidFlag HresultOfScode(STG_E_INVALIDFLAG)
+#define TIPERR_InUse HresultOfScode(STG_E_INUSE)
+#define TIPERR_NotCurrent HresultOfScode(STG_E_NOTCURRENT)
+#define TIPERR_Reverted HresultOfScode(STG_E_REVERTED)
+#define TIPERR_CantSave HresultOfScode(STG_E_CANTSAVE)
+#define TIPERR_BadFunctionId HresultOfScode(STG_E_INVALIDFUNCTION)
+#define TIPERR_FileNotFound HresultOfScode(STG_E_FILENOTFOUND)
+#define TIPERR_PathNotFound HresultOfScode(STG_E_PATHNOTFOUND)
+#define TIPERR_TooManyFiles HresultOfScode(STG_E_TOOMANYOPENFILES)
+#define TIPERR_SeekErr HresultOfScode(STG_E_SEEKERROR)
+#define TIPERR_ReadFault HresultOfScode(STG_E_READFAULT)
+#define TIPERR_NoContainingLib HresultOfScode(STG_E_READFAULT)
+#define TIPERR_BadTypeId HresultOfScode(STG_E_READFAULT)
+#define TIPERR_BadLibId HresultOfScode(STG_E_READFAULT)
+#define TIPERR_Eof HresultOfScode(STG_E_READFAULT)
+#define TIPERR_FileAlreadyExists HresultOfScode(STG_E_FILEALREADYEXISTS)
+#define TIPERR_DiskFull HresultOfScode(STG_E_MEDIUMFULL)
+#define TIPERR_ShareRequired HresultOfScode(STG_E_SHAREREQUIRED)
+#define TIPERR_DLLLoadErr HresultOfScode(TYPE_E_CANTLOADLIBRARY)
+#define TIPERR_CodeResourceNotFound HresultOfScode(TYPE_E_CANTLOADLIBRARY)
+#define TIPERR_CodeResourceLockError HresultOfScode(TYPE_E_CANTLOADLIBRARY)
+#define TIPERR_InvalidOrdinal HresultOfScode(TYPE_E_DLLFUNCTIONNOTFOUND)
+#define TIPERR_InvalidDllFunctionName HresultOfScode(TYPE_E_DLLFUNCTIONNOTFOUND)
+#define TIPERR_TypeMismatch HresultOfScode(TYPE_E_TYPEMISMATCH)
+#define TIPERR_ExpectedFuncNotModule HresultOfScode(TYPE_E_TYPEMISMATCH)
+#define TIPERR_ExpectedFuncNotRecord HresultOfScode(TYPE_E_TYPEMISMATCH)
+#define TIPERR_ExpectedFuncNotProject HresultOfScode(TYPE_E_TYPEMISMATCH)
+#define TIPERR_ExpectedFuncNotVar HresultOfScode(TYPE_E_TYPEMISMATCH)
+#define TIPERR_ExpectedTypeNotProj HresultOfScode(TYPE_E_TYPEMISMATCH)
+#define TIPERR_UnsuitableFuncPropMatch HresultOfScode(TYPE_E_TYPEMISMATCH)
+#define TIPERR_WrongTypeKind HresultOfScode(TYPE_E_WRONGTYPEKIND)
+#define TIPERR_OutOfBounds HresultOfScode(TYPE_E_OUTOFBOUNDS)
+#define TIPERR_IOError HresultOfScode(TYPE_E_IOERROR)
+#define TIPERR_CantCreateTmpFile HresultOfScode(TYPE_E_CANTCREATETMPFILE)
+#define TIPERR_BufferTooSmall HresultOfScode(TYPE_E_BUFFERTOOSMALL)
+#define TIPERR_InvDataRead HresultOfScode(TYPE_E_INVDATAREAD)
+#define TIPERR_UnsupFormat HresultOfScode(TYPE_E_UNSUPFORMAT)
+#define TIPERR_ModNameConflict HresultOfScode(TYPE_E_NAMECONFLICT)
+#define TIPERR_RegistryAccess HresultOfScode(TYPE_E_REGISTRYACCESS)
+#define TIPERR_LibNotRegistered HresultOfScode(TYPE_E_LIBNOTREGISTERED)
+#define TIPERR_UndefinedType HresultOfScode(TYPE_E_UNDEFINEDTYPE)
+#define TIPERR_QualifiedNameDisallowed HresultOfScode(TYPE_E_QUALIFIEDNAMEDISALLOWED)
+#define TIPERR_InvalidState HresultOfScode(TYPE_E_INVALIDSTATE)
+#define TIPERR_ElementNotFound HresultOfScode(TYPE_E_ELEMENTNOTFOUND)
+#define TIPERR_AmbiguousName HresultOfScode(TYPE_E_AMBIGUOUSNAME)
+#define TIPERR_UnknownLcid HresultOfScode(TYPE_E_UNKNOWNLCID)
+#define TIPERR_BadModuleKind HresultOfScode(TYPE_E_BADMODULEKIND)
+#define TIPERR_SizeTooBig HresultOfScode(TYPE_E_SIZETOOBIG)
+#define TIPERR_DuplicateId HresultOfScode(TYPE_E_DUPLICATEID)
+#define TIPERR_InvalidId HresultOfScode(TYPE_E_INVALIDID)
+#define TIPERR_InconsistentPropFuncs HresultOfScode(TYPE_E_INCONSISTENTPROPFUNCS)
+#define TIPERR_CircularType HresultOfScode(TYPE_E_CIRCULARTYPE)
+
+#endif // !TIPERR_H_INCLUDED
diff --git a/private/oleauto/src/typelib/tlibfrag.r b/private/oleauto/src/typelib/tlibfrag.r
new file mode 100644
index 000000000..671f00431
--- /dev/null
+++ b/private/oleauto/src/typelib/tlibfrag.r
@@ -0,0 +1,36 @@
+
+/*
+
+ For PowerPC native Shared Libraries and Applications, make a cfrg resource.
+ For Applications be sure to use kIsApp and not kIsLib.
+ For Shared Libraries be sure to use kIsLib not kIsApp.
+
+ For application plug ins, see the conventions established by the application vendor.
+
+ Making a shared library:
+ Rez -i : Types.r CodeFragmentTypes.r LibIcon.r {Active} -a -o MathLib -t shlb -c cfmg
+ SetFile MathLib -a iB
+
+ Making an application:
+ Rez Types.r CodeFragmentTypes.r {Active} -a -o Application -t APPL
+
+ This example is customized for building an application "MyApp"
+
+ Change all occurences of MyApp to YourApp or YourLib
+ NOTE: ID must be zero.
+ (Sysheap & Locked are no longer required, and not recommended.)
+
+*/
+#include "Types.r"
+#include "CodeFrag.r"
+resource 'cfrg' (0) {
+ {
+ kPowerPC,
+ kFullLib,
+ kNoVersionNum,kNoVersionNum,
+ 0, 0,
+ kIsApp,kOnDiskFlat,kZeroOffset,kWholeFork,
+ TLIB_NAME
+ }
+};
+
diff --git a/private/oleauto/src/typelib/tlibguid.c b/private/oleauto/src/typelib/tlibguid.c
new file mode 100644
index 000000000..170bf447f
--- /dev/null
+++ b/private/oleauto/src/typelib/tlibguid.c
@@ -0,0 +1,69 @@
+/***
+*tlibguid.c
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This module instantiates the data for the TypeInfo related GUIDs
+* that are exported by typelib.dll.
+*
+* Note: the numbers that appear in the DEFINE_OLEGUID macros below
+* *must* match those that appear in the ole supplied header: dispatch.h.
+*
+*
+*Revision History:
+*
+* [00] 13-Feb-92 bradlo: created
+*
+*****************************************************************************/
+
+#include "switches.hxx"
+#include "version.hxx"
+#include "typelib.hxx"
+
+#if OE_MAC
+// HACK to make GUID's be defined in a FAR segment w/o changing the OLE
+// header files (works arounds a Wings bug). Define-away 'const' so that
+// they get put into .fardata like they're supposed to.
+#define const
+#endif
+
+#if BLD_MAC
+#include "silver.hxx"
+#endif //BLD_MAC
+
+//OLE uses _MAC to determine if this is a Mac build
+#if OE_MAC
+# define _MAC
+#endif
+
+// initguid.h requires this.
+#if OE_WIN32
+#define INC_OLE2
+#include <ole2.h>
+#else
+#include <compobj.h>
+#endif
+
+// this redefines the DEFINE_GUID() macro to do allocation.
+//
+#include <initguid.h>
+
+
+#if !FV_UNICODE_OLE && !OE_MACPPC
+// gives dup def warnings when linked with the static ole2di32.lib
+DEFINE_OLEGUID(IID_ITypeInfo, 0x00020401, 0, 0);
+DEFINE_OLEGUID(IID_ITypeLib, 0x00020402, 0, 0);
+DEFINE_OLEGUID(IID_ITypeComp, 0x00020403, 0, 0);
+DEFINE_OLEGUID(IID_ICreateTypeInfo, 0x00020405, 0, 0);
+DEFINE_OLEGUID(IID_ICreateTypeLib, 0x00020406, 0, 0);
+
+DEFINE_OLEGUID(CLSID_PSDispatch, 0x00020420, 0, 0);
+#endif //!FV_UNICODE_OLE
+
+DEFINE_OLEGUID(CLSID_PSRemoteTypeInfo, 0x00020424, 0, 0);
+
+#if OE_MAC
+# undef _MAC
+#endif
diff --git a/private/oleauto/src/typelib/tlibpch.cxx b/private/oleauto/src/typelib/tlibpch.cxx
new file mode 100644
index 000000000..1e7a6ca85
--- /dev/null
+++ b/private/oleauto/src/typelib/tlibpch.cxx
@@ -0,0 +1,178 @@
+// TYPELIB.DLL specific precompiled header
+// 05-Jan-93 ilanc
+// 31-Jan-93 Rajivk: removed typemgr from typelib.dll
+//
+#include "typelib.hxx"
+#include "silver.hxx"
+
+#if OE_MAC
+//
+// We want to include Memory.h, Windows.h and Files.h as they are the
+// most frequently included. The others are files that will be included
+// from Windows.h or Files.h in order of inclusion.
+// These are in order of include frequency, so if you have to cut, cut from
+// the bottom.
+//
+#include <macos\osutils.h>
+#include <macos\segload.h>
+#include <macos\files.h>
+#include <macos\aliases.h>
+#include <macos\memory.h>
+#endif
+
+#include <ctype.h>
+#include <errno.h>
+#include <float.h>
+#include <limits.h>
+#include <malloc.h>
+#include <new.h>
+#include <search.h>
+#include <signal.h>
+#include <stdarg.h>
+#include <stddef.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <sys\types.h>
+#include <sys\locking.h>
+#include <sys\stat.h>
+#include <sys\timeb.h>
+#include <time.h>
+#if !OE_MAC
+#include <conio.h>
+#endif
+#include <io.h>
+
+#ifndef CONVERT_HXX_INCLUDED
+#include "convert.hxx"
+#endif //CONVERT_HXX_INCLUDED
+
+#ifndef NTSTRING_H_INCLUDED
+#include "ntstring.h"
+#endif //NTSTRING_H_INCLUDED
+
+#ifndef BLKDESC32_HXX_INCLUDED
+#include "blkdsc32.hxx"
+#endif
+
+#ifndef BLKMGR_HXX_INCLUDED
+#include "blkmgr.hxx"
+#endif
+
+#ifndef CLTYPES_HXX_INCLUDED
+#include "cltypes.hxx"
+#endif
+#ifndef CLUTIL_HXX_INCLUDED
+#include "clutil.hxx"
+#endif
+#ifndef CTSEG_HXX_INCLUDED
+#include "ctseg.hxx"
+#endif
+#ifndef DBLKMGR_HXX_INCLUDED
+#include "dblkmgr.hxx"
+#endif
+
+#ifndef DEFN_HXX_INCLUDED
+#include "defn.hxx"
+#endif
+#ifndef DFNTBIND_HXX_INCLUDED
+#include "dfntbind.hxx"
+#endif
+#ifndef DFNTCOMP_HXX_INCLUDED
+#include "dfntcomp.hxx"
+#endif
+#ifndef DFSTREAM_HXX_INCLUDED
+#include "dfstream.hxx"
+#endif
+#ifndef DTBIND_HXX_INCLUDED
+#include "dtbind.hxx"
+#endif
+#ifndef DTMBRS_HXX_INCLUDED
+#include "dtmbrs.hxx"
+#endif
+#ifndef DYNTINFO_HXX_INCLUDED
+#include "dyntinfo.hxx"
+#endif
+#ifndef ENTRYMGR_HXX_INCLUDED
+#include "entrymgr.hxx"
+#endif
+#ifndef ERRMAP_HXX_INCLUDED
+#include "errmap.hxx"
+#endif
+#ifndef EXBIND_HXX_INCLUDED
+#include "exbind.hxx"
+#endif
+#ifndef FCNTL_H_INCLUDED
+#include "fcntl.h"
+#endif
+#ifndef GDTINFO_HXX_INCLUDED
+#include "gdtinfo.hxx"
+#endif
+#ifndef GENPROJ_TYPEBIND_HXX_INCLUDED
+#include "gptbind.hxx"
+#endif
+#ifndef GTLIBSTG_HXX_INCLUDED
+#include "gtlibstg.hxx"
+#endif
+#ifndef IMPMGR_HXX_INCLUDED
+#include "impmgr.hxx"
+#endif
+#ifndef MACHINE_HXX_INCLUDED
+#include "machine.hxx"
+#endif
+#ifndef MEM_HXX_INCLUDED
+#include "mem.hxx"
+#endif
+#ifndef NAMMGR_HXX_INCLUDED
+#include "nammgr.hxx"
+#endif
+#if OE_WIN32
+#ifndef OAUTIL_H_INCLUDED
+#include "oautil.h"
+#endif
+#endif // OE_WIN32
+#ifndef OLE_TYPEMGR_HXX_INCLUDED
+#include "oletmgr.hxx"
+#endif
+#ifndef DSTRMGR_HXX_INCLUDED
+#include "dstrmgr.hxx"
+#endif
+#ifndef RTSHEAP_H_INCLUDED
+#include "rtsheap.h"
+#endif
+#ifndef SHARE_H_INCLUDED
+#include "share.h"
+#endif
+#ifndef SHEAPMGR_HXX_INCLUDED
+#include "sheapmgr.hxx"
+#endif
+#ifndef STLTINFO_HXX_INCLUDED
+#include "stltinfo.hxx"
+#endif
+#ifndef STREAM_HXX_INCLUDED
+#include "stream.hxx"
+#endif
+#ifndef TDATA_HXX_INCLUDED
+#include "tdata.hxx"
+#endif
+#ifndef TINFO_HXX_INCLUDED
+#include "tinfo.hxx"
+#endif
+#ifndef TIPERR_H_INCLUDED
+#include "tiperr.h"
+#endif
+#ifndef TLS_H_INCLUDED
+#include "tls.h"
+#endif
+#ifndef TLIBUTIL_HXX_INCLUDED
+#include "tlibutil.hxx"
+#endif
+#ifndef XSTRING_H_INCLUDED
+#include "xstring.h"
+#endif
+#ifndef TYPELIB_H_INCLUDED
+#include "typelib.hxx"
+#endif
+
+#pragma hdrstop(RTPCHNAME)
+
diff --git a/private/oleauto/src/typelib/tlibutil.cxx b/private/oleauto/src/typelib/tlibutil.cxx
new file mode 100644
index 000000000..2dc4a8d25
--- /dev/null
+++ b/private/oleauto/src/typelib/tlibutil.cxx
@@ -0,0 +1,7729 @@
+/***
+*clutil.cxx - Class Lib component-wide utility functions.
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* typelib utility functions
+*
+*Revision History:
+* [00] 24-Jan-93 RajivK: Created
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "typelib.hxx"
+#include "silver.hxx"
+#include <xstring.h>
+#include <time.h>
+#include <ctype.h> // for isspace() et al.
+
+
+#pragma hdrstop(RTPCHNAME)
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+#if OE_MAC
+static char szOleTlibutilCxx[] = __FILE__;
+#define SZ_FILE_NAME szOleTlibutilCxx
+#else
+static char szTlibutilCxx[] = __FILE__;
+#define SZ_FILE_NAME szTlibutilCxx
+#endif
+#endif
+
+
+// forward declarations for DBCS processing
+
+ACHAR MapDBChar(ACHAR xch, LCID lcid);
+unsigned long LHashValOfDBCSName(SYSKIND syskind, LCID lcid, const char FAR* szName);
+
+
+// Define an array for mapping all the characters.
+//
+#pragma code_seg(CS_CP1252)
+ALLOC_CODE(BYTE) g_rgbCodePage1252[256] = {
+ 0 ,
+ 1 ,
+ 2 ,
+ 3 ,
+ 4 ,
+ 5 ,
+ 6 ,
+ 7 ,
+ 8 ,
+ 9 ,
+ 10 ,
+ 11 ,
+ 12 ,
+ 13 ,
+ 14 ,
+ 15 ,
+ 16 ,
+ 17 ,
+ 18 ,
+ 19 ,
+ 20 ,
+ 21 ,
+ 22 ,
+ 23 ,
+ 24 ,
+ 25 ,
+ 26 ,
+ 27 ,
+ 28 ,
+ 29 ,
+ 30 ,
+ 31 ,
+ 32 ,
+ 33 ,
+ 34 ,
+ 35 ,
+ 36 ,
+ 37 ,
+ 38 ,
+ 39 ,
+ 40 ,
+ 41 ,
+ 42 ,
+ 43 ,
+ 44 ,
+ 45 ,
+ 46 ,
+ 0 ,
+ 48 ,
+ 49 ,
+ 50 ,
+ 51 ,
+ 52 ,
+ 53 ,
+ 54 ,
+ 55 ,
+ 56 ,
+ 57 ,
+ 58 ,
+ 59 ,
+ 60 ,
+ 61 ,
+ 62 ,
+ 63 ,
+ 64 ,
+ 65 ,
+ 66 ,
+ 67 ,
+ 68 ,
+ 69 ,
+ 70 ,
+ 71 ,
+ 72 ,
+ 73 ,
+ 74 ,
+ 75 ,
+ 76 ,
+ 77 ,
+ 78 ,
+ 79 ,
+ 80 ,
+ 81 ,
+ 82 ,
+ 83 ,
+ 84 ,
+ 85 ,
+ 86 ,
+ 86 ,
+ 88 ,
+ 85 ,
+ 90 ,
+ 91 ,
+ 92 ,
+ 93 ,
+ 94 ,
+ 95 ,
+ 96 ,
+ 65 ,
+ 66 ,
+ 67 ,
+ 68 ,
+ 69 ,
+ 70 ,
+ 71 ,
+ 72 ,
+ 73 ,
+ 74 ,
+ 75 ,
+ 76 ,
+ 77 ,
+ 78 ,
+ 79 ,
+ 80 ,
+ 81 ,
+ 82 ,
+ 83 ,
+ 84 ,
+ 85 ,
+ 86 ,
+ 86 ,
+ 88 ,
+ 85 ,
+ 90 ,
+ 123 ,
+ 124 ,
+ 125 ,
+ 126 ,
+ 127 ,
+ 127 ,
+ 127 ,
+ 130 ,
+ 70 ,
+ 132 ,
+ 133 ,
+ 134 ,
+ 135 ,
+ 127 ,
+ 137 ,
+ 83 ,
+ 139 ,
+ 140 ,
+ 127 ,
+ 127 ,
+ 127 ,
+ 127 ,
+ 145 ,
+ 146 ,
+ 147 ,
+ 148 ,
+ 149 ,
+ 150 ,
+ 150 ,
+ 152 ,
+ 153 ,
+ 83 ,
+ 155 ,
+ 140 ,
+ 127 ,
+ 127 ,
+ 85 ,
+ 160 ,
+ 161 ,
+ 162 ,
+ 163 ,
+ 164 ,
+ 165 ,
+ 166 ,
+ 167 ,
+ 168 ,
+ 169 ,
+ 65 ,
+ 171 ,
+ 172 ,
+ 150 ,
+ 174 ,
+ 175 ,
+ 176 ,
+ 177 ,
+ 50 ,
+ 51 ,
+ 180 ,
+ 181 ,
+ 182 ,
+ 183 ,
+ 184 ,
+ 49 ,
+ 79 ,
+ 187 ,
+ 188 ,
+ 189 ,
+ 190 ,
+ 191 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 67 ,
+ 69 ,
+ 69 ,
+ 69 ,
+ 69 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 68 ,
+ 78 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 215 ,
+ 79 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 222 ,
+ 223 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 67 ,
+ 69 ,
+ 69 ,
+ 69 ,
+ 69 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 68 ,
+ 78 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 247 ,
+ 79 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 222 ,
+ 85
+};
+#pragma code_seg()
+
+#pragma code_seg(CS_CP10000)
+ALLOC_CODE(BYTE) g_rgbCodePage10000[256] = {
+ 0 ,
+ 1 ,
+ 2 ,
+ 3 ,
+ 4 ,
+ 5 ,
+ 6 ,
+ 7 ,
+ 8 ,
+ 9 ,
+ 10 ,
+ 11 ,
+ 12 ,
+ 13 ,
+ 14 ,
+ 15 ,
+ 16 ,
+ 17 ,
+ 18 ,
+ 19 ,
+ 20 ,
+ 21 ,
+ 22 ,
+ 23 ,
+ 24 ,
+ 25 ,
+ 26 ,
+ 27 ,
+ 28 ,
+ 29 ,
+ 30 ,
+ 31 ,
+ 32 ,
+ 33 ,
+ 34 ,
+ 35 ,
+ 36 ,
+ 37 ,
+ 38 ,
+ 39 ,
+ 40 ,
+ 41 ,
+ 42 ,
+ 43 ,
+ 44 ,
+ 45 ,
+ 46 ,
+ 0 ,
+ 48 ,
+ 49 ,
+ 50 ,
+ 51 ,
+ 52 ,
+ 53 ,
+ 54 ,
+ 55 ,
+ 56 ,
+ 57 ,
+ 58 ,
+ 59 ,
+ 60 ,
+ 61 ,
+ 62 ,
+ 63 ,
+ 64 ,
+ 65 ,
+ 66 ,
+ 67 ,
+ 68 ,
+ 69 ,
+ 70 ,
+ 71 ,
+ 72 ,
+ 73 ,
+ 74 ,
+ 75 ,
+ 76 ,
+ 77 ,
+ 78 ,
+ 79 ,
+ 80 ,
+ 81 ,
+ 82 ,
+ 83 ,
+ 84 ,
+ 85 ,
+ 86 ,
+ 86 ,
+ 88 ,
+ 85 ,
+ 90 ,
+ 91 ,
+ 92 ,
+ 93 ,
+ 94 ,
+ 95 ,
+ 96 ,
+ 65 ,
+ 66 ,
+ 67 ,
+ 68 ,
+ 69 ,
+ 70 ,
+ 71 ,
+ 72 ,
+ 73 ,
+ 74 ,
+ 75 ,
+ 76 ,
+ 77 ,
+ 78 ,
+ 79 ,
+ 80 ,
+ 81 ,
+ 82 ,
+ 83 ,
+ 84 ,
+ 85 ,
+ 86 ,
+ 86 ,
+ 88 ,
+ 85 ,
+ 90 ,
+ 123,
+ 124,
+ 125,
+ 126,
+ 127,
+ 65 ,
+ 65 ,
+ 67 ,
+ 69 ,
+ 78 ,
+ 79 ,
+ 85 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 67 ,
+ 69 ,
+ 69 ,
+ 69 ,
+ 69 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 78 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 160,
+ 161,
+ 162,
+ 163,
+ 164,
+ 165,
+ 166,
+ 167,
+ 168,
+ 169,
+ 170,
+ 171,
+ 172,
+ 173,
+ 65 ,
+ 79 ,
+ 176,
+ 177,
+ 178,
+ 179,
+ 180,
+ 181,
+ 182,
+ 183,
+ 184,
+ 185,
+ 186,
+ 65 ,
+ 79 ,
+ 189,
+ 65 ,
+ 79 ,
+ 192,
+ 193,
+ 194,
+ 195,
+ 70 ,
+ 197,
+ 198,
+ 199,
+ 200,
+ 201,
+ 202,
+ 65 ,
+ 65 ,
+ 79 ,
+ 206,
+ 206,
+ 208,
+ 208,
+ 210,
+ 211,
+ 212,
+ 213,
+ 214,
+ 215,
+ 85 ,
+ 85 ,
+ 218,
+ 219,
+ 220,
+ 221,
+ 63 ,
+ 63 ,
+ 224,
+ 225,
+ 226,
+ 227,
+ 228,
+ 65 ,
+ 69 ,
+ 65 ,
+ 69 ,
+ 69 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 79 ,
+ 79 ,
+ 63 ,
+ 79 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 73 ,
+ 127,
+ 247,
+ 127,
+ 249,
+ 250,
+ 251,
+ 63 ,
+ 253,
+ 254,
+ 127
+};
+#pragma code_seg()
+
+#pragma code_seg(CS_CP1250)
+ALLOC_CODE(BYTE) g_rgbCodePage1250[256] = {
+0 ,
+1 ,
+2 ,
+3 ,
+4 ,
+5 ,
+6 ,
+7 ,
+8 ,
+9 ,
+10 ,
+11 ,
+12 ,
+13 ,
+14 ,
+15 ,
+16 ,
+17 ,
+18 ,
+19 ,
+20 ,
+21 ,
+22 ,
+23 ,
+24 ,
+25 ,
+26 ,
+27 ,
+28 ,
+29 ,
+30 ,
+31 ,
+32 ,
+33 ,
+34 ,
+35 ,
+36 ,
+37 ,
+38 ,
+39 ,
+40 ,
+41 ,
+42 ,
+43 ,
+44 ,
+45 ,
+46 ,
+0 ,
+48 ,
+49 ,
+50 ,
+51 ,
+52 ,
+53 ,
+54 ,
+55 ,
+56 ,
+57 ,
+58 ,
+59 ,
+60 ,
+61 ,
+62 ,
+63 ,
+64 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+91 ,
+92 ,
+93 ,
+94 ,
+95 ,
+96 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+123,
+124,
+125,
+126,
+127,
+127,
+127,
+130,
+127,
+132,
+133,
+134,
+135,
+127,
+137,
+83 ,
+139,
+83 ,
+84 ,
+90 ,
+90 ,
+127,
+145,
+146,
+147,
+148,
+149,
+150,
+150,
+127,
+153,
+83 ,
+155,
+83 ,
+84 ,
+90 ,
+90 ,
+160,
+127,
+162,
+76 ,
+164,
+65 ,
+166,
+167,
+168,
+169,
+83 ,
+171,
+172,
+150,
+174,
+90 ,
+176,
+177,
+178,
+76 ,
+180,
+181,
+182,
+183,
+184,
+65 ,
+83 ,
+187,
+76 ,
+189,
+76 ,
+90 ,
+82 ,
+65 ,
+65 ,
+65 ,
+65 ,
+76 ,
+67 ,
+67 ,
+67 ,
+69 ,
+69 ,
+69 ,
+69 ,
+73 ,
+73 ,
+68 ,
+208,
+78 ,
+78 ,
+79 ,
+79 ,
+79 ,
+79 ,
+215,
+82 ,
+85 ,
+85 ,
+85 ,
+85 ,
+89 ,
+84 ,
+223,
+82 ,
+65 ,
+65 ,
+65 ,
+65 ,
+76 ,
+67 ,
+67 ,
+67 ,
+69 ,
+69 ,
+69 ,
+69 ,
+73 ,
+73 ,
+68 ,
+208,
+78 ,
+78 ,
+79 ,
+79 ,
+79 ,
+79 ,
+247,
+82 ,
+85 ,
+85 ,
+85 ,
+85 ,
+89 ,
+84 ,
+255
+};
+#pragma code_seg()
+
+#pragma code_seg(CS_CP1251)
+ALLOC_CODE(BYTE) g_rgbCodePage1251[256] = {
+0 ,
+1 ,
+2 ,
+3 ,
+4 ,
+5 ,
+6 ,
+7 ,
+8 ,
+9 ,
+10 ,
+11 ,
+12 ,
+13 ,
+14 ,
+15 ,
+16 ,
+17 ,
+18 ,
+19 ,
+20 ,
+21 ,
+22 ,
+23 ,
+24 ,
+25 ,
+26 ,
+27 ,
+28 ,
+29 ,
+30 ,
+31 ,
+32 ,
+33 ,
+34 ,
+35 ,
+36 ,
+37 ,
+38 ,
+39 ,
+40 ,
+41 ,
+42 ,
+43 ,
+44 ,
+45 ,
+46 ,
+0 ,
+48 ,
+49 ,
+50 ,
+51 ,
+52 ,
+53 ,
+54 ,
+55 ,
+56 ,
+57 ,
+58 ,
+59 ,
+60 ,
+61 ,
+62 ,
+63 ,
+64 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+91 ,
+92 ,
+93 ,
+94 ,
+95 ,
+96 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+123,
+124,
+125,
+126,
+127,
+127,
+127,
+130,
+70 ,
+132,
+133,
+134,
+135,
+127,
+137,
+83 ,
+139,
+140,
+127,
+127,
+127,
+127,
+145,
+146,
+147,
+148,
+149,
+150,
+150,
+152,
+153,
+83 ,
+155,
+140,
+127,
+127,
+89 ,
+160,
+161,
+162,
+163,
+164,
+165,
+166,
+167,
+168,
+169,
+65 ,
+171,
+172,
+150,
+174,
+175,
+176,
+177,
+50 ,
+51 ,
+180,
+181,
+182,
+183,
+184,
+49 ,
+79 ,
+187,
+188,
+189,
+190,
+191,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+198,
+67 ,
+69 ,
+69 ,
+69 ,
+69 ,
+73 ,
+73 ,
+73 ,
+73 ,
+208,
+78 ,
+79 ,
+79 ,
+79 ,
+79 ,
+79 ,
+215,
+79 ,
+85 ,
+85 ,
+85 ,
+85 ,
+89 ,
+222,
+223,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+198,
+67 ,
+69 ,
+69 ,
+69 ,
+69 ,
+73 ,
+73 ,
+73 ,
+73 ,
+208,
+78 ,
+79 ,
+79 ,
+79 ,
+79 ,
+79 ,
+247,
+79 ,
+85 ,
+85 ,
+85 ,
+85 ,
+89 ,
+222,
+89
+};
+#pragma code_seg()
+
+#pragma code_seg(CS_CP10029)
+ALLOC_CODE(BYTE) g_rgbCodePage10029[256] = {
+0 ,
+1 ,
+2 ,
+3 ,
+4 ,
+5 ,
+6 ,
+7 ,
+8 ,
+9 ,
+10 ,
+11 ,
+12 ,
+13 ,
+14 ,
+15 ,
+16 ,
+17 ,
+18 ,
+19 ,
+20 ,
+21 ,
+22 ,
+23 ,
+24 ,
+25 ,
+26 ,
+27 ,
+28 ,
+29 ,
+30 ,
+31 ,
+32 ,
+33 ,
+34 ,
+35 ,
+36 ,
+37 ,
+38 ,
+39 ,
+40 ,
+41 ,
+42 ,
+43 ,
+44 ,
+45 ,
+46 ,
+0 ,
+48 ,
+49 ,
+50 ,
+51 ,
+52 ,
+53 ,
+54 ,
+55 ,
+56 ,
+57 ,
+58 ,
+59 ,
+60 ,
+61 ,
+62 ,
+63 ,
+64 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+91 ,
+92 ,
+93 ,
+94 ,
+95 ,
+96 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+123,
+124,
+125,
+126,
+127,
+65 ,
+65 ,
+65 ,
+69 ,
+65 ,
+79 ,
+85 ,
+65 ,
+65 ,
+67 ,
+65 ,
+67 ,
+67 ,
+67 ,
+69 ,
+90 ,
+90 ,
+68 ,
+73 ,
+68 ,
+69 ,
+69 ,
+69 ,
+79 ,
+69 ,
+79 ,
+79 ,
+79 ,
+85 ,
+69 ,
+69 ,
+85 ,
+160,
+161,
+69 ,
+163,
+164,
+165,
+166,
+167,
+168,
+169,
+170,
+69 ,
+172,
+173,
+71 ,
+73 ,
+73 ,
+73 ,
+178,
+179,
+73 ,
+75 ,
+182,
+183,
+76 ,
+76 ,
+76 ,
+76 ,
+76 ,
+76 ,
+76 ,
+78 ,
+78 ,
+78 ,
+194,
+195,
+78 ,
+78 ,
+198,
+199,
+200,
+201,
+202,
+78 ,
+79 ,
+79 ,
+79 ,
+79 ,
+208,
+208,
+210,
+211,
+212,
+213,
+214,
+215,
+79 ,
+82 ,
+82 ,
+82 ,
+220,
+221,
+82 ,
+82 ,
+82 ,
+83 ,
+226,
+227,
+83 ,
+83 ,
+83 ,
+65 ,
+84 ,
+84 ,
+73 ,
+90 ,
+90 ,
+85 ,
+79 ,
+79 ,
+85 ,
+85 ,
+85 ,
+85 ,
+85 ,
+85 ,
+85 ,
+85 ,
+89 ,
+89 ,
+75 ,
+90 ,
+76 ,
+76 ,
+71 ,
+255
+};
+#pragma code_seg()
+
+#pragma code_seg(CS_CP10007)
+ALLOC_CODE(BYTE) g_rgbCodePage10007[256] = {
+0 ,
+1 ,
+2 ,
+3 ,
+4 ,
+5 ,
+6 ,
+7 ,
+8 ,
+9 ,
+10 ,
+11 ,
+12 ,
+13 ,
+14 ,
+15 ,
+16 ,
+17 ,
+18 ,
+19 ,
+20 ,
+21 ,
+22 ,
+23 ,
+24 ,
+25 ,
+26 ,
+27 ,
+28 ,
+29 ,
+30 ,
+31 ,
+32 ,
+33 ,
+34 ,
+35 ,
+36 ,
+37 ,
+38 ,
+39 ,
+40 ,
+41 ,
+42 ,
+43 ,
+44 ,
+45 ,
+46 ,
+0 ,
+48 ,
+49 ,
+50 ,
+51 ,
+52 ,
+53 ,
+54 ,
+55 ,
+56 ,
+57 ,
+58 ,
+59 ,
+60 ,
+61 ,
+62 ,
+63 ,
+64 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+91 ,
+92 ,
+93 ,
+94 ,
+95 ,
+96 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+123,
+124,
+125,
+126,
+127,
+128,
+129,
+130,
+131,
+132,
+133,
+134,
+135,
+136,
+137,
+138,
+139,
+140,
+141,
+142,
+143,
+144,
+145,
+146,
+147,
+148,
+149,
+150,
+151,
+152,
+153,
+154,
+155,
+156,
+157,
+158,
+159,
+160,
+161,
+162,
+163,
+164,
+165,
+166,
+167,
+168,
+169,
+170,
+171,
+171,
+173,
+174,
+174,
+176,
+177,
+178,
+179,
+167,
+181,
+182,
+183,
+184,
+184,
+186,
+186,
+188,
+188,
+190,
+190,
+183,
+193,
+194,
+195,
+70 ,
+197,
+198,
+199,
+200,
+201,
+202,
+203,
+203,
+205,
+205,
+193,
+208,
+208,
+210,
+211,
+212,
+213,
+214,
+215,
+216,
+216,
+218,
+218,
+220,
+221,
+221,
+159,
+128,
+129,
+130,
+131,
+132,
+133,
+134,
+135,
+136,
+137,
+138,
+139,
+140,
+141,
+142,
+143,
+144,
+145,
+146,
+147,
+148,
+149,
+150,
+151,
+152,
+153,
+154,
+155,
+156,
+157,
+158,
+159
+};
+#pragma code_seg()
+
+#pragma code_seg(CS_CPWGREEK)
+ALLOC_CODE(BYTE) g_rgbCodePageWGreek[256] = {
+0 ,
+1 ,
+2 ,
+3 ,
+4 ,
+5 ,
+6 ,
+7 ,
+8 ,
+9 ,
+10 ,
+11 ,
+12 ,
+13 ,
+14 ,
+15 ,
+16 ,
+17 ,
+18 ,
+19 ,
+20 ,
+21 ,
+22 ,
+23 ,
+24 ,
+25 ,
+26 ,
+27 ,
+28 ,
+29 ,
+30 ,
+31 ,
+32 ,
+33 ,
+34 ,
+35 ,
+36 ,
+37 ,
+38 ,
+39 ,
+40 ,
+41 ,
+42 ,
+43 ,
+44 ,
+45 ,
+46 ,
+47 ,
+48 ,
+49 ,
+50 ,
+51 ,
+52 ,
+53 ,
+54 ,
+55 ,
+56 ,
+57 ,
+58 ,
+59 ,
+60 ,
+61 ,
+62 ,
+63 ,
+64 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+91 ,
+92 ,
+93 ,
+94 ,
+95 ,
+96 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+123,
+124,
+125,
+126,
+0 ,
+0 ,
+0 ,
+130,
+70 ,
+132,
+133,
+134,
+135,
+0 ,
+137,
+0 ,
+139,
+0 ,
+0 ,
+0 ,
+0 ,
+0 ,
+145,
+146,
+147,
+148,
+149,
+45 ,
+45 ,
+0 ,
+153,
+0 ,
+155,
+0 ,
+0 ,
+0 ,
+0 ,
+9 ,
+161,
+162,
+163,
+164,
+165,
+166,
+167,
+168,
+169,
+0 ,
+171,
+172,
+45 ,
+174,
+45 ,
+176,
+177,
+50 ,
+51 ,
+180,
+181,
+182,
+183,
+184,
+185,
+186,
+187,
+188,
+189,
+190,
+191,
+186,
+162,
+194,
+195,
+196,
+184,
+198,
+185,
+200,
+186,
+202,
+203,
+204,
+205,
+206,
+188,
+208,
+209,
+0 ,
+211,
+212,
+190,
+214,
+215,
+216,
+191,
+186,
+190,
+162,
+184,
+185,
+186,
+190,
+162,
+194,
+195,
+196,
+184,
+198,
+185,
+200,
+186,
+202,
+203,
+204,
+205,
+206,
+188,
+208,
+209,
+211,
+211,
+212,
+190,
+214,
+215,
+216,
+191,
+186,
+190,
+188,
+190,
+191,
+0
+};
+#pragma code_seg()
+
+#pragma code_seg(CS_CPWICELAND)
+ALLOC_CODE(BYTE) g_rgbCodePageWIceland[256] = {
+0 ,
+1 ,
+2 ,
+3 ,
+4 ,
+5 ,
+6 ,
+7 ,
+8 ,
+9 ,
+10 ,
+11 ,
+12 ,
+13 ,
+14 ,
+15 ,
+16 ,
+17 ,
+18 ,
+19 ,
+20 ,
+21 ,
+22 ,
+23 ,
+24 ,
+25 ,
+26 ,
+27 ,
+28 ,
+29 ,
+30 ,
+31 ,
+32 ,
+33 ,
+34 ,
+35 ,
+36 ,
+37 ,
+38 ,
+39 ,
+40 ,
+41 ,
+42 ,
+43 ,
+44 ,
+45 ,
+46 ,
+47 ,
+48 ,
+49 ,
+50 ,
+51 ,
+52 ,
+53 ,
+54 ,
+55 ,
+56 ,
+57 ,
+58 ,
+59 ,
+60 ,
+61 ,
+62 ,
+63 ,
+64 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+91 ,
+92 ,
+93 ,
+94 ,
+95 ,
+96 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+123,
+124,
+125,
+126,
+0 ,
+0 ,
+0 ,
+130,
+70 ,
+132,
+133,
+134,
+135,
+0 ,
+137,
+83 ,
+139,
+140,
+0 ,
+0 ,
+0 ,
+0 ,
+145,
+146,
+147,
+148,
+149,
+45 ,
+45 ,
+152,
+153,
+83 ,
+155,
+140,
+0 ,
+0 ,
+89 ,
+9 ,
+161,
+162,
+163,
+164,
+165,
+166,
+167,
+168,
+169,
+65 ,
+171,
+172,
+45 ,
+174,
+175,
+176,
+177,
+50 ,
+51 ,
+180,
+181,
+182,
+183,
+184,
+49 ,
+79 ,
+187,
+188,
+189,
+190,
+191,
+65 ,
+193,
+65 ,
+65 ,
+65 ,
+65 ,
+198,
+67 ,
+69 ,
+201,
+69 ,
+69 ,
+73 ,
+205,
+73 ,
+73 ,
+208,
+78 ,
+79 ,
+211,
+79 ,
+79 ,
+214,
+215,
+214,
+85 ,
+218,
+85 ,
+85 ,
+221,
+222,
+223,
+65 ,
+193,
+65 ,
+65 ,
+65 ,
+65 ,
+198,
+67 ,
+69 ,
+201,
+69 ,
+69 ,
+73 ,
+205,
+73 ,
+73 ,
+208,
+78 ,
+79 ,
+211,
+79 ,
+79 ,
+214,
+247,
+214,
+85 ,
+218,
+85 ,
+85 ,
+221,
+222,
+89
+};
+#pragma code_seg()
+
+#pragma code_seg(CS_CPWTURKISH)
+ALLOC_CODE(BYTE) g_rgbCodePageWTurkish[256] = {
+0 ,
+1 ,
+2 ,
+3 ,
+4 ,
+5 ,
+6 ,
+7 ,
+8 ,
+9 ,
+10 ,
+11 ,
+12 ,
+13 ,
+14 ,
+15 ,
+16 ,
+17 ,
+18 ,
+19 ,
+20 ,
+21 ,
+22 ,
+23 ,
+24 ,
+25 ,
+26 ,
+27 ,
+28 ,
+29 ,
+30 ,
+31 ,
+32 ,
+33 ,
+34 ,
+35 ,
+36 ,
+37 ,
+38 ,
+39 ,
+40 ,
+41 ,
+42 ,
+43 ,
+44 ,
+45 ,
+46 ,
+47 ,
+48 ,
+49 ,
+50 ,
+51 ,
+52 ,
+53 ,
+54 ,
+55 ,
+56 ,
+57 ,
+58 ,
+59 ,
+60 ,
+61 ,
+62 ,
+63 ,
+64 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+91 ,
+92 ,
+93 ,
+94 ,
+95 ,
+96 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+123,
+124,
+125,
+126,
+0 ,
+0 ,
+0 ,
+130,
+70 ,
+132,
+133,
+134,
+135,
+0 ,
+137,
+83 ,
+139,
+140,
+0 ,
+0 ,
+0 ,
+0 ,
+145,
+146,
+147,
+148,
+149,
+45 ,
+45 ,
+152,
+153,
+83 ,
+155,
+140,
+0 ,
+0 ,
+89 ,
+9 ,
+161,
+162,
+163,
+164,
+165,
+166,
+167,
+168,
+169,
+65 ,
+171,
+172,
+45 ,
+174,
+175,
+176,
+177,
+50 ,
+51 ,
+180,
+181,
+182,
+183,
+184,
+49 ,
+79 ,
+187,
+188,
+189,
+190,
+191,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+198,
+199,
+69 ,
+69 ,
+69 ,
+69 ,
+73 ,
+73 ,
+73 ,
+73 ,
+208,
+78 ,
+79 ,
+79 ,
+79 ,
+79 ,
+214,
+215,
+79 ,
+85 ,
+85 ,
+85 ,
+220,
+221,
+222,
+223,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+198,
+199,
+69 ,
+69 ,
+69 ,
+69 ,
+73 ,
+73 ,
+73 ,
+73 ,
+208,
+78 ,
+79 ,
+79 ,
+79 ,
+79 ,
+214,
+247,
+79 ,
+85 ,
+85 ,
+85 ,
+220,
+221,
+222,
+89
+};
+#pragma code_seg()
+
+#pragma code_seg(CS_CPWNORWEGIAN)
+ALLOC_CODE(BYTE) g_rgbCodePageWNorwegian[256] = {
+0 ,
+1 ,
+2 ,
+3 ,
+4 ,
+5 ,
+6 ,
+7 ,
+8 ,
+9 ,
+10 ,
+11 ,
+12 ,
+13 ,
+14 ,
+15 ,
+16 ,
+17 ,
+18 ,
+19 ,
+20 ,
+21 ,
+22 ,
+23 ,
+24 ,
+25 ,
+26 ,
+27 ,
+28 ,
+29 ,
+30 ,
+31 ,
+32 ,
+33 ,
+34 ,
+35 ,
+36 ,
+37 ,
+38 ,
+39 ,
+40 ,
+41 ,
+42 ,
+43 ,
+44 ,
+45 ,
+46 ,
+47 ,
+48 ,
+49 ,
+50 ,
+51 ,
+52 ,
+53 ,
+54 ,
+55 ,
+56 ,
+57 ,
+58 ,
+59 ,
+60 ,
+61 ,
+62 ,
+63 ,
+64 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+91 ,
+92 ,
+93 ,
+94 ,
+95 ,
+96 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+123,
+124,
+125,
+126,
+0 ,
+0 ,
+0 ,
+130,
+70 ,
+132,
+133,
+134,
+135,
+0 ,
+137,
+83 ,
+139,
+140,
+0 ,
+0 ,
+0 ,
+0 ,
+145,
+146,
+147,
+148,
+149,
+45 ,
+45 ,
+152,
+153,
+83 ,
+155,
+140,
+0 ,
+0 ,
+89 ,
+9 ,
+161,
+162,
+163,
+164,
+165,
+166,
+167,
+168,
+169,
+65 ,
+171,
+172,
+45 ,
+174,
+175,
+176,
+177,
+50 ,
+51 ,
+180,
+181,
+182,
+183,
+184,
+49 ,
+79 ,
+187,
+188,
+189,
+190,
+191,
+65 ,
+65 ,
+65 ,
+65 ,
+196,
+197,
+196,
+67 ,
+69 ,
+69 ,
+69 ,
+69 ,
+73 ,
+73 ,
+73 ,
+73 ,
+68 ,
+78 ,
+79 ,
+79 ,
+79 ,
+79 ,
+214,
+215,
+214,
+85 ,
+85 ,
+85 ,
+89 ,
+89 ,
+222,
+223,
+65 ,
+65 ,
+65 ,
+65 ,
+196,
+197,
+196,
+67 ,
+69 ,
+69 ,
+69 ,
+69 ,
+73 ,
+73 ,
+73 ,
+73 ,
+68 ,
+78 ,
+79 ,
+79 ,
+79 ,
+79 ,
+214,
+247,
+214,
+85 ,
+85 ,
+85 ,
+89 ,
+89 ,
+222,
+89
+};
+#pragma code_seg()
+
+#pragma code_seg(CS_CPWENGIRELAND)
+ALLOC_CODE(BYTE) g_rgbCodePageWEngIreland[256] = {
+0 ,
+1 ,
+2 ,
+3 ,
+4 ,
+5 ,
+6 ,
+7 ,
+8 ,
+9 ,
+10 ,
+11 ,
+12 ,
+13 ,
+14 ,
+15 ,
+16 ,
+17 ,
+18 ,
+19 ,
+20 ,
+21 ,
+22 ,
+23 ,
+24 ,
+25 ,
+26 ,
+27 ,
+28 ,
+29 ,
+30 ,
+31 ,
+32 ,
+33 ,
+34 ,
+35 ,
+36 ,
+37 ,
+38 ,
+39 ,
+40 ,
+41 ,
+42 ,
+43 ,
+44 ,
+45 ,
+46 ,
+47 ,
+48 ,
+49 ,
+50 ,
+51 ,
+52 ,
+53 ,
+54 ,
+55 ,
+56 ,
+57 ,
+58 ,
+59 ,
+60 ,
+61 ,
+62 ,
+63 ,
+64 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+91 ,
+92 ,
+93 ,
+94 ,
+95 ,
+96 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+123,
+124,
+125,
+126,
+0 ,
+0 ,
+0 ,
+130,
+70 ,
+132,
+133,
+134,
+135,
+0 ,
+137,
+83 ,
+139,
+140,
+0 ,
+0 ,
+0 ,
+0 ,
+145,
+146,
+147,
+148,
+149,
+45 ,
+45 ,
+152,
+153,
+83 ,
+155,
+140,
+0 ,
+0 ,
+89 ,
+9 ,
+161,
+162,
+163,
+164,
+165,
+166,
+167,
+168,
+169,
+65 ,
+171,
+172,
+45 ,
+174,
+175,
+176,
+177,
+50 ,
+51 ,
+180,
+181,
+182,
+183,
+184,
+49 ,
+79 ,
+187,
+188,
+189,
+190,
+191,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+198,
+67 ,
+69 ,
+69 ,
+69 ,
+69 ,
+73 ,
+73 ,
+73 ,
+73 ,
+208,
+78 ,
+79 ,
+79 ,
+79 ,
+79 ,
+79 ,
+215,
+79 ,
+85 ,
+85 ,
+85 ,
+85 ,
+89 ,
+222,
+223,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+198,
+67 ,
+69 ,
+69 ,
+69 ,
+69 ,
+73 ,
+73 ,
+73 ,
+73 ,
+208,
+78 ,
+79 ,
+79 ,
+79 ,
+79 ,
+79 ,
+247,
+79 ,
+85 ,
+85 ,
+85 ,
+85 ,
+89 ,
+222,
+89
+};
+
+#pragma code_seg()
+
+#pragma code_seg(CS_CPMGREEK)
+ALLOC_CODE(BYTE) g_rgbCodePageMGreek[256] = {
+0 ,
+1 ,
+2 ,
+3 ,
+4 ,
+5 ,
+6 ,
+7 ,
+8 ,
+9 ,
+10 ,
+11 ,
+12 ,
+13 ,
+14 ,
+15 ,
+16 ,
+17 ,
+18 ,
+19 ,
+20 ,
+21 ,
+22 ,
+23 ,
+24 ,
+25 ,
+26 ,
+27 ,
+28 ,
+29 ,
+30 ,
+31 ,
+32 ,
+33 ,
+34 ,
+35 ,
+36 ,
+37 ,
+38 ,
+39 ,
+40 ,
+41 ,
+42 ,
+43 ,
+44 ,
+45 ,
+46 ,
+47 ,
+48 ,
+49 ,
+50 ,
+51 ,
+52 ,
+53 ,
+54 ,
+55 ,
+56 ,
+57 ,
+58 ,
+59 ,
+60 ,
+61 ,
+62 ,
+63 ,
+64 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+91 ,
+92 ,
+93 ,
+94 ,
+95 ,
+96 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+123,
+124,
+125,
+126,
+0 ,
+65 ,
+49 ,
+50 ,
+69 ,
+51 ,
+79 ,
+85 ,
+135,
+65 ,
+65 ,
+65 ,
+0 ,
+140,
+67 ,
+69 ,
+69 ,
+69 ,
+69 ,
+146,
+147,
+73 ,
+73 ,
+150,
+151,
+152,
+79 ,
+79 ,
+155,
+63 ,
+85 ,
+85 ,
+85 ,
+160,
+161,
+162,
+163,
+164,
+165,
+166,
+167,
+168,
+169,
+170,
+171,
+172,
+173,
+174,
+175,
+176,
+177,
+178,
+179,
+180,
+181,
+182,
+183,
+184,
+171,
+186,
+187,
+188,
+189,
+190,
+191,
+176,
+193,
+194,
+195,
+196,
+197,
+198,
+199,
+200,
+201,
+9 ,
+189,
+204,
+176,
+182,
+207,
+45 ,
+45 ,
+210,
+211,
+212,
+213,
+214,
+184,
+171,
+195,
+189,
+182,
+184,
+171,
+195,
+191,
+189,
+176,
+181,
+190,
+162,
+182,
+188,
+161,
+184,
+171,
+165,
+186,
+164,
+187,
+193,
+195,
+166,
+191,
+196,
+170,
+198,
+163,
+191,
+170,
+204,
+189,
+183,
+171,
+189,
+171,
+189,
+63
+};
+
+#pragma code_seg()
+
+#pragma code_seg(CS_CPMNORWEGIAN)
+ALLOC_CODE(BYTE) g_rgbCodePageMNorwegian[256] = {
+0 ,
+1 ,
+2 ,
+3 ,
+4 ,
+5 ,
+6 ,
+7 ,
+8 ,
+9 ,
+10 ,
+11 ,
+12 ,
+13 ,
+14 ,
+15 ,
+16 ,
+17 ,
+18 ,
+19 ,
+20 ,
+21 ,
+22 ,
+23 ,
+24 ,
+25 ,
+26 ,
+27 ,
+28 ,
+29 ,
+30 ,
+31 ,
+32 ,
+33 ,
+34 ,
+35 ,
+36 ,
+37 ,
+38 ,
+39 ,
+40 ,
+41 ,
+42 ,
+43 ,
+44 ,
+45 ,
+46 ,
+47 ,
+48 ,
+49 ,
+50 ,
+51 ,
+52 ,
+53 ,
+54 ,
+55 ,
+56 ,
+57 ,
+58 ,
+59 ,
+60 ,
+61 ,
+62 ,
+63 ,
+64 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+91 ,
+92 ,
+93 ,
+94 ,
+95 ,
+96 ,
+65 ,
+66 ,
+67 ,
+68 ,
+69 ,
+70 ,
+71 ,
+72 ,
+73 ,
+74 ,
+75 ,
+76 ,
+77 ,
+78 ,
+79 ,
+80 ,
+81 ,
+82 ,
+83 ,
+84 ,
+85 ,
+86 ,
+87 ,
+88 ,
+89 ,
+90 ,
+123,
+124,
+125,
+126,
+0 ,
+128,
+129,
+67 ,
+69 ,
+78 ,
+133,
+89 ,
+65 ,
+65 ,
+65 ,
+128,
+65 ,
+129,
+67 ,
+69 ,
+69 ,
+69 ,
+69 ,
+73 ,
+73 ,
+73 ,
+73 ,
+78 ,
+79 ,
+79 ,
+79 ,
+133,
+79 ,
+85 ,
+85 ,
+85 ,
+89 ,
+160,
+161,
+162,
+163,
+164,
+165,
+166,
+167,
+168,
+169,
+170,
+171,
+172,
+173,
+128,
+133,
+176,
+177,
+178,
+179,
+180,
+181,
+182,
+183,
+184,
+185,
+186,
+65 ,
+79 ,
+189,
+128,
+133,
+192,
+193,
+194,
+195,
+70 ,
+197,
+198,
+199,
+200,
+201,
+9 ,
+65 ,
+65 ,
+79 ,
+206,
+206,
+45 ,
+45 ,
+210,
+211,
+212,
+213,
+214,
+215,
+89 ,
+89 ,
+218,
+219,
+220,
+221,
+63 ,
+63 ,
+224,
+225,
+226,
+227,
+228,
+65 ,
+69 ,
+65 ,
+69 ,
+69 ,
+73 ,
+73 ,
+73 ,
+73 ,
+79 ,
+79 ,
+63 ,
+79 ,
+85 ,
+85 ,
+85 ,
+73 ,
+0 ,
+247,
+0 ,
+249,
+250,
+251,
+63 ,
+253,
+254,
+0
+};
+
+#pragma code_seg()
+
+#pragma code_seg(CS_CPMENGIRELAND)
+ALLOC_CODE(BYTE) g_rgbCodePageMEngIreland[256] = {
+0 ,
+1 ,
+2 ,
+3 ,
+4 ,
+5 ,
+6 ,
+7 ,
+8 ,
+9 ,
+10 ,
+11 ,
+12 ,
+13 ,
+14 ,
+15 ,
+16 ,
+17 ,
+18 ,
+19 ,
+20 ,
+21 ,
+22 ,
+23 ,
+24 ,
+25 ,
+26 ,
+27 ,
+28 ,
+29 ,
+30 ,
+31 ,
+32 ,
+ 33 ,
+ 34 ,
+ 35 ,
+ 36 ,
+ 37 ,
+ 38 ,
+ 39 ,
+ 40 ,
+ 41 ,
+ 42 ,
+ 43 ,
+ 44 ,
+ 45 ,
+ 46 ,
+ 47 ,
+ 48 ,
+ 49 ,
+ 50 ,
+ 51 ,
+ 52 ,
+ 53 ,
+ 54 ,
+ 55 ,
+ 56 ,
+ 57 ,
+ 58 ,
+ 59 ,
+ 60 ,
+ 61 ,
+ 62 ,
+ 63 ,
+ 64 ,
+ 65 ,
+ 66 ,
+ 67 ,
+ 68 ,
+ 69 ,
+ 70 ,
+ 71 ,
+ 72 ,
+ 73 ,
+ 74 ,
+ 75 ,
+ 76 ,
+ 77 ,
+ 78 ,
+ 79 ,
+ 80 ,
+ 81 ,
+ 82 ,
+ 83 ,
+ 84 ,
+ 85 ,
+ 86 ,
+ 87 ,
+ 88 ,
+ 89 ,
+ 90 ,
+ 91 ,
+ 92 ,
+ 93 ,
+ 94 ,
+ 95 ,
+ 96 ,
+ 65 ,
+ 66 ,
+ 67 ,
+ 68 ,
+ 69 ,
+ 70 ,
+ 71 ,
+ 72 ,
+ 73 ,
+ 74 ,
+ 75 ,
+ 76 ,
+ 77 ,
+ 78 ,
+ 79 ,
+ 80 ,
+ 81 ,
+ 82 ,
+ 83 ,
+ 84 ,
+ 85 ,
+ 86 ,
+ 87 ,
+ 88 ,
+ 89 ,
+ 90 ,
+ 123,
+ 124,
+ 125,
+ 126,
+ 0 ,
+ 65 ,
+ 65 ,
+ 67 ,
+ 69 ,
+ 78 ,
+ 79 ,
+ 85 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 67 ,
+ 69 ,
+ 69 ,
+ 69 ,
+ 69 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 78 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 160,
+ 161,
+ 162,
+ 163,
+ 164,
+ 165,
+ 166,
+ 167,
+ 168,
+ 169,
+ 170,
+ 171,
+ 172,
+ 173,
+ 174,
+ 79 ,
+ 176,
+ 177,
+ 178,
+ 179,
+ 180,
+ 181,
+ 182,
+ 183,
+ 184,
+ 185,
+ 186,
+ 65 ,
+ 79 ,
+ 189,
+ 174,
+ 79 ,
+ 192,
+ 193,
+ 194,
+ 195,
+ 70 ,
+ 197,
+ 198,
+ 199,
+ 200,
+ 201,
+ 9 ,
+ 65 ,
+ 65 ,
+ 79 ,
+ 206,
+ 206,
+ 45 ,
+ 45 ,
+ 210,
+ 211,
+ 212,
+ 213,
+ 214,
+ 215,
+ 89 ,
+ 89 ,
+ 218,
+ 219,
+ 220,
+ 221,
+ 63 ,
+ 63 ,
+ 224,
+ 225,
+ 226,
+ 227,
+ 228,
+ 65 ,
+ 69 ,
+ 65 ,
+ 69 ,
+ 69 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 79 ,
+ 79 ,
+ 63 ,
+ 79 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 73 ,
+ 0 ,
+ 247,
+ 0 ,
+ 249,
+ 250,
+ 251,
+ 63 ,
+ 253,
+ 254,
+ 0
+};
+#pragma code_seg()
+
+// BIDI stuff
+#pragma code_seg(CS_CP1255)
+ALLOC_CODE(BYTE) g_rgbCodePage1255[256] = {
+ 0,
+ 1,
+ 2,
+ 3,
+ 4,
+ 5,
+ 6,
+ 7,
+ 8,
+ 9,
+ 10,
+ 11,
+ 12,
+ 13,
+ 14,
+ 15,
+ 16,
+ 17,
+ 18,
+ 19,
+ 20,
+ 21,
+ 22,
+ 23,
+ 24,
+ 25,
+ 26,
+ 27,
+ 28,
+ 29,
+ 30,
+ 31,
+ 32,
+ 33,
+ 34,
+ 35,
+ 36,
+ 37,
+ 38,
+ 39,
+ 40,
+ 41,
+ 42,
+ 43,
+ 44,
+ 45,
+ 46,
+ 47,
+ 48,
+ 49,
+ 50,
+ 51,
+ 52,
+ 53,
+ 54,
+ 55,
+ 56,
+ 57,
+ 58,
+ 59,
+ 60,
+ 61,
+ 62,
+ 63,
+ 64,
+ 65,
+ 66,
+ 67,
+ 68,
+ 69,
+ 70,
+ 71,
+ 72,
+ 73,
+ 74,
+ 75,
+ 76,
+ 77,
+ 78,
+ 79,
+ 80,
+ 81,
+ 82,
+ 83,
+ 84,
+ 85,
+ 86,
+ 87,
+ 88,
+ 89,
+ 90,
+ 91,
+ 92,
+ 93,
+ 94,
+ 95,
+ 96,
+ 65,
+ 66,
+ 67,
+ 68,
+ 69,
+ 70,
+ 71,
+ 72,
+ 73,
+ 74,
+ 75,
+ 76,
+ 77,
+ 78,
+ 79,
+ 80,
+ 81,
+ 82,
+ 83,
+ 84,
+ 85,
+ 86,
+ 87,
+ 88,
+ 89,
+ 90,
+ 123,
+ 124,
+ 125,
+ 126,
+ 127,
+ 128,
+ 129,
+ 130,
+ 70,
+ 132,
+ 133,
+ 134,
+ 135,
+ 94,
+ 137,
+ 138,
+ 139,
+ 140,
+ 141,
+ 142,
+ 143,
+ 144,
+ 145,
+ 146,
+ 147,
+ 148,
+ 149,
+ 150,
+ 151,
+ 152,
+ 153,
+ 154,
+ 155,
+ 156,
+ 157,
+ 158,
+ 159,
+ 160,
+ 161,
+ 162,
+ 163,
+ 164,
+ 165,
+ 166,
+ 167,
+ 168,
+ 169,
+ 170,
+ 171,
+ 172,
+ 173,
+ 174,
+ 175,
+ 176,
+ 177,
+ 50,
+ 51,
+ 180,
+ 181,
+ 182,
+ 183,
+ 184,
+ 49,
+ 186,
+ 187,
+ 188,
+ 189,
+ 190,
+ 191,
+ 192,
+ 193,
+ 194,
+ 195,
+ 196,
+ 197,
+ 198,
+ 199,
+ 200,
+ 201,
+ 202,
+ 203,
+ 204,
+ 205,
+ 206,
+ 207,
+ 208,
+ 209,
+ 210,
+ 211,
+ 212,
+ 213,
+ 214,
+ 215,
+ 216,
+ 217,
+ 218,
+ 219,
+ 220,
+ 221,
+ 222,
+ 223,
+ 224,
+ 225,
+ 226,
+ 227,
+ 228,
+ 229,
+ 230,
+ 231,
+ 232,
+ 233,
+ 234,
+ 234,
+ 236,
+ 237,
+ 237,
+ 239,
+ 239,
+ 241,
+ 242,
+ 243,
+ 243,
+ 245,
+ 245,
+ 247,
+ 248,
+ 249,
+ 250,
+ 251,
+ 252,
+ 0,
+ 0,
+ 255
+};
+#pragma code_seg()
+
+#pragma code_seg(CS_CP1256)
+ALLOC_CODE(BYTE) g_rgbCodePage1256[256] = {
+ 0,
+ 1,
+ 2,
+ 3,
+ 4,
+ 5,
+ 6,
+ 7,
+ 8,
+ 9,
+ 10,
+ 11,
+ 12,
+ 13,
+ 14,
+ 15,
+ 16,
+ 17,
+ 18,
+ 19,
+ 20,
+ 21,
+ 22,
+ 23,
+ 24,
+ 25,
+ 26,
+ 27,
+ 28,
+ 29,
+ 30,
+ 31,
+ 32,
+ 33,
+ 34,
+ 35,
+ 36,
+ 37,
+ 38,
+ 39,
+ 40,
+ 41,
+ 42,
+ 43,
+ 44,
+ 45,
+ 46,
+ 47,
+ 48,
+ 49,
+ 50,
+ 51,
+ 52,
+ 53,
+ 54,
+ 55,
+ 56,
+ 57,
+ 58,
+ 59,
+ 60,
+ 61,
+ 62,
+ 63,
+ 64,
+ 65,
+ 66,
+ 67,
+ 68,
+ 69,
+ 70,
+ 71,
+ 72,
+ 73,
+ 74,
+ 75,
+ 76,
+ 77,
+ 78,
+ 79,
+ 80,
+ 81,
+ 82,
+ 83,
+ 84,
+ 85,
+ 86,
+ 87,
+ 88,
+ 89,
+ 90,
+ 91,
+ 92,
+ 93,
+ 94,
+ 95,
+ 96,
+ 65,
+ 66,
+ 67,
+ 68,
+ 69,
+ 70,
+ 71,
+ 72,
+ 73,
+ 74,
+ 75,
+ 76,
+ 77,
+ 78,
+ 79,
+ 80,
+ 81,
+ 82,
+ 83,
+ 84,
+ 85,
+ 86,
+ 87,
+ 88,
+ 89,
+ 90,
+ 123,
+ 124,
+ 125,
+ 126,
+ 127,
+ 128,
+ 129,
+ 130,
+ 70,
+ 132,
+ 133,
+ 134,
+ 135,
+ 94,
+ 137,
+ 138,
+ 139,
+ 140,
+ 141,
+ 142,
+ 143,
+ 144,
+ 145,
+ 146,
+ 147,
+ 148,
+ 149,
+ 150,
+ 151,
+ 152,
+ 153,
+ 154,
+ 155,
+ 140,
+ 157,
+ 0,
+ 159,
+ 160,
+ 161,
+ 162,
+ 163,
+ 164,
+ 165,
+ 166,
+ 167,
+ 168,
+ 169,
+ 170,
+ 171,
+ 172,
+ 173,
+ 174,
+ 175,
+ 176,
+ 177,
+ 50,
+ 51,
+ 180,
+ 181,
+ 182,
+ 183,
+ 184,
+ 49,
+ 186,
+ 187,
+ 188,
+ 189,
+ 190,
+ 191,
+ 192,
+ 193,
+ 194,
+ 193,
+ 193,
+ 193,
+ 193,
+ 199,
+ 200,
+ 201,
+ 201,
+ 203,
+ 204,
+ 205,
+ 206,
+ 207,
+ 208,
+ 209,
+ 210,
+ 211,
+ 212,
+ 213,
+ 214,
+ 215,
+ 216,
+ 217,
+ 218,
+ 219,
+ 0,
+ 221,
+ 222,
+ 223,
+ 65,
+ 225,
+ 65,
+ 227,
+ 228,
+ 229,
+ 230,
+ 67,
+ 69,
+ 69,
+ 69,
+ 69,
+ 236,
+ 236,
+ 73,
+ 73,
+ 240,
+ 241,
+ 242,
+ 243,
+ 79,
+ 245,
+ 246,
+ 247,
+ 248,
+ 85,
+ 250,
+ 85,
+ 85,
+ 0,
+ 0,
+ 255
+};
+#pragma code_seg()
+
+#pragma code_seg(CS_CP10004)
+ALLOC_CODE(BYTE) g_rgbCodePage10004[256] = {
+ 0,
+ 1,
+ 2,
+ 3,
+ 4,
+ 5,
+ 6,
+ 7,
+ 8,
+ 9,
+ 10,
+ 11,
+ 12,
+ 13,
+ 14,
+ 15,
+ 16,
+ 17,
+ 18,
+ 19,
+ 20,
+ 21,
+ 22,
+ 23,
+ 24,
+ 25,
+ 26,
+ 27,
+ 28,
+ 29,
+ 30,
+ 31,
+ 32,
+ 33,
+ 34,
+ 35,
+ 36,
+ 37,
+ 38,
+ 39,
+ 40,
+ 41,
+ 42,
+ 43,
+ 44,
+ 45,
+ 46,
+ 47,
+ 48,
+ 49,
+ 50,
+ 51,
+ 52,
+ 53,
+ 54,
+ 55,
+ 56,
+ 57,
+ 58,
+ 59,
+ 60,
+ 61,
+ 62,
+ 63,
+ 64,
+ 65,
+ 66,
+ 67,
+ 68,
+ 69,
+ 70,
+ 71,
+ 72,
+ 73,
+ 74,
+ 75,
+ 76,
+ 77,
+ 78,
+ 79,
+ 80,
+ 81,
+ 82,
+ 83,
+ 84,
+ 85,
+ 86,
+ 87,
+ 88,
+ 89,
+ 90,
+ 91,
+ 92,
+ 93,
+ 94,
+ 95,
+ 96,
+ 65,
+ 66,
+ 67,
+ 68,
+ 69,
+ 70,
+ 71,
+ 72,
+ 73,
+ 74,
+ 75,
+ 76,
+ 77,
+ 78,
+ 79,
+ 80,
+ 81,
+ 82,
+ 83,
+ 84,
+ 85,
+ 86,
+ 87,
+ 88,
+ 89,
+ 90,
+ 123,
+ 124,
+ 125,
+ 126,
+ 127,
+ 65,
+ 129,
+ 67,
+ 69,
+ 78,
+ 79,
+ 85,
+ 65,
+ 65,
+ 65,
+ 65,
+ 139,
+ 140,
+ 67,
+ 69,
+ 69,
+ 69,
+ 69,
+ 73,
+ 147,
+ 73,
+ 73,
+ 78,
+ 79,
+ 152,
+ 79,
+ 79,
+ 155,
+ 85,
+ 85,
+ 85,
+ 85,
+ 160,
+ 161,
+ 162,
+ 163,
+ 164,
+ 165,
+ 166,
+ 167,
+ 168,
+ 169,
+ 170,
+ 171,
+ 172,
+ 173,
+ 174,
+ 175,
+ 176,
+ 177,
+ 178,
+ 179,
+ 180,
+ 181,
+ 182,
+ 183,
+ 184,
+ 185,
+ 186,
+ 187,
+ 188,
+ 189,
+ 190,
+ 191,
+ 192,
+ 193,
+ 194,
+ 193,
+ 193,
+ 193,
+ 193,
+ 199,
+ 200,
+ 201,
+ 201,
+ 203,
+ 204,
+ 205,
+ 206,
+ 207,
+ 208,
+ 209,
+ 210,
+ 211,
+ 212,
+ 213,
+ 214,
+ 215,
+ 216,
+ 217,
+ 218,
+ 219,
+ 220,
+ 221,
+ 222,
+ 223,
+ 0,
+ 225,
+ 226,
+ 227,
+ 228,
+ 229,
+ 230,
+ 231,
+ 232,
+ 233,
+ 233,
+ 235,
+ 236,
+ 237,
+ 238,
+ 239,
+ 240,
+ 241,
+ 242,
+ 243,
+ 244,
+ 245,
+ 246,
+ 247,
+ 248,
+ 249,
+ 250,
+ 251,
+ 252,
+ 253,
+ 254,
+ 255,
+};
+#pragma code_seg()
+
+#pragma code_seg(CS_CP10005)
+ALLOC_CODE(BYTE) g_rgbCodePage10005[256] = {
+ 0,
+ 1,
+ 2,
+ 3,
+ 4,
+ 5,
+ 6,
+ 7,
+ 8,
+ 9,
+ 10,
+ 11,
+ 12,
+ 13,
+ 14,
+ 15,
+ 16,
+ 17,
+ 18,
+ 19,
+ 20,
+ 21,
+ 22,
+ 23,
+ 24,
+ 25,
+ 26,
+ 27,
+ 28,
+ 29,
+ 30,
+ 31,
+ 32,
+ 33,
+ 34,
+ 35,
+ 36,
+ 37,
+ 38,
+ 39,
+ 40,
+ 41,
+ 42,
+ 43,
+ 44,
+ 45,
+ 46,
+ 47,
+ 48,
+ 49,
+ 50,
+ 51,
+ 52,
+ 53,
+ 54,
+ 55,
+ 56,
+ 57,
+ 58,
+ 59,
+ 60,
+ 61,
+ 62,
+ 63,
+ 64,
+ 65,
+ 66,
+ 67,
+ 68,
+ 69,
+ 70,
+ 71,
+ 72,
+ 73,
+ 74,
+ 75,
+ 76,
+ 77,
+ 78,
+ 79,
+ 80,
+ 81,
+ 82,
+ 83,
+ 84,
+ 85,
+ 86,
+ 87,
+ 88,
+ 89,
+ 90,
+ 91,
+ 92,
+ 93,
+ 94,
+ 95,
+ 96,
+ 65,
+ 66,
+ 67,
+ 68,
+ 69,
+ 70,
+ 71,
+ 72,
+ 73,
+ 74,
+ 75,
+ 76,
+ 77,
+ 78,
+ 79,
+ 80,
+ 81,
+ 82,
+ 83,
+ 84,
+ 85,
+ 86,
+ 87,
+ 88,
+ 89,
+ 90,
+ 123,
+ 124,
+ 125,
+ 126,
+ 127,
+ 65,
+ 65,
+ 67,
+ 69,
+ 78,
+ 79,
+ 85,
+ 65,
+ 65,
+ 65,
+ 65,
+ 65,
+ 65,
+ 67,
+ 69,
+ 69,
+ 69,
+ 69,
+ 73,
+ 73,
+ 73,
+ 73,
+ 78,
+ 79,
+ 79,
+ 79,
+ 79,
+ 79,
+ 85,
+ 85,
+ 85,
+ 85,
+ 160,
+ 161,
+ 162,
+ 163,
+ 164,
+ 165,
+ 166,
+ 167,
+ 168,
+ 169,
+ 170,
+ 171,
+ 172,
+ 173,
+ 174,
+ 175,
+ 176,
+ 177,
+ 178,
+ 179,
+ 180,
+ 181,
+ 182,
+ 183,
+ 184,
+ 185,
+ 186,
+ 187,
+ 188,
+ 189,
+ 190,
+ 191,
+ 192,
+ 193,
+ 194,
+ 195,
+ 196,
+ 197,
+ 198,
+ 199,
+ 200,
+ 201,
+ 202,
+ 203,
+ 204,
+ 205,
+ 206,
+ 207,
+ 208,
+ 209,
+ 210,
+ 211,
+ 212,
+ 213,
+ 214,
+ 215,
+ 216,
+ 217,
+ 218,
+ 219,
+ 220,
+ 221,
+ 222,
+ 223,
+ 224,
+ 225,
+ 226,
+ 227,
+ 228,
+ 229,
+ 230,
+ 231,
+ 232,
+ 233,
+ 234,
+ 234,
+ 236,
+ 237,
+ 237,
+ 239,
+ 239,
+ 241,
+ 242,
+ 243,
+ 243,
+ 245,
+ 245,
+ 247,
+ 248,
+ 249,
+ 250,
+ 251,
+ 252,
+ 253,
+ 254,
+ 255,
+};
+#pragma code_seg()
+
+
+
+// This is 2-D table of Code Page Vs. System.
+// To get the address of the mapping table to use; Use
+// pb = g_prgHashTbl[CodePage][Syskind];
+//
+ALLOC_CODE(BYTE *)g_prgHashTbl[15][2] = {
+ {NULL, NULL},
+ {g_rgbCodePage1252, g_rgbCodePage10000}, // English/European
+ {g_rgbCodePage1250, g_rgbCodePage10029},
+ {g_rgbCodePage1251, g_rgbCodePage10007},
+ {NULL, NULL}, // JAPNESE_CP
+ {NULL, NULL}, // KOREAN_CP
+ {NULL, NULL}, // CHINESES_CP
+ {NULL, NULL}, // CHINESET_CP
+
+ // MAC: UNDONE: Tables of Turkish and Icelandic is not available on MAC.
+ {g_rgbCodePageWGreek, g_rgbCodePageMGreek }, // GREEK
+ {g_rgbCodePageWIceland, g_rgbCodePageWIceland }, // ICELANDIC
+ {g_rgbCodePageWTurkish, g_rgbCodePageWTurkish }, // TURKISH
+ {g_rgbCodePageWNorwegian, g_rgbCodePageMNorwegian }, // NORWEIGIAN
+ {g_rgbCodePageWEngIreland, g_rgbCodePageMEngIreland }, // ENGLISH(IRELAND)
+ {g_rgbCodePage1256, g_rgbCodePage10004}, // Arabic
+ {g_rgbCodePage1255, g_rgbCodePage10005} // Hebrew
+};
+
+// Following are the code page "codes" for the dbcs world.
+#define JAPNESE_CP 0x4
+#define KOREAN_CP 0x5
+#define CHINESES_CP 0x6
+#define CHINESET_CP 0x7
+
+#define GREEK_CP 0x8
+#define ICELANDIC_CP 0x9
+#define TURKISH_CP 0xa
+#define NORWEIGIAN_CP 0xb
+#define IRELAND_CP 0xc
+#define ARABIC_CP 0xd
+#define HEBREW_CP 0xe
+
+
+/***
+*PUBLIC LHashValOfName
+*Purpose: This API calculates the hash value depending on the system and
+* the lcid that was passed in.
+*
+*Implementation Notes:
+* Use the table pointed by pbHashTable to map each character in the
+* szName.
+*
+*
+*Entry:
+* xsz: String whose hash value has to be calculated
+*
+*Exit:
+* ULONG : hash value of the passed in string
+*
+* 31 23 19 15 0
+* |-------|---|----|-------------------|
+* |UNUSED |CP |Sys | wHashVal |
+* |_______|___|____|___________________|
+* ^ ^
+* | |
+* CodePageId Encoding bits for System kind
+*
+*
+*
+***********************************************************************/
+#pragma optimize("t", on)
+
+#if OE_WIN32
+STDAPI_(unsigned long) LHashValOfNameSysW(SYSKIND syskind,
+ LCID lcid,
+ LPCOLESTR szName)
+{
+ // NOTE: We only bother to translate the first 255 chars of the name.
+ // NOTE: This should sill get a pretty good hash function, without
+ // NOTE: having burn more stack space, or (worse) alloc & free memory
+ // NOTE: on this call.
+ char szNameA[255+1];
+
+ if (szName == NULL) // can't return E_INVALIDARG here, so just
+ return 0; // don't crash
+
+ // convert szName from Unicode to Ansi.
+ NoAssertRetail (WideCharToMultiByte(CP_ACP,
+ 0,
+ szName,
+ -1,
+ szNameA,
+ 255+1,
+ NULL,
+ NULL) != 0, "");
+ szNameA[255] = '\0'; // ensure null-terminated (in case truncated).
+
+ return LHashValOfNameSysA(syskind, lcid, szNameA);
+}
+#endif //OE_WIN32
+
+STDAPI_(unsigned long) LHashValOfNameSysA(SYSKIND syskind,
+ LCID lcid,
+ const char FAR* szName)
+{
+ ULONG ulHash; // hash value which accumulates hash
+ USHORT uIndex;
+ BYTE *pbHashTable;
+ USHORT usSystem, usCodePage;
+ ULONG uEncoding;
+
+ if (szName == NULL) // can't return E_INVALIDARG here, so just
+ return 0; // don't crash
+
+ // If DBCS then defer to LHashValOfDBCSName
+ if (IsDBCS(lcid))
+ return LHashValOfDBCSName(syskind, lcid, szName);
+
+ // Deternine the hash table that should be used.
+ //
+ // Find the index corresponding to the system passed in.
+ usSystem = (syskind == SYS_MAC) ? 1 : 0;
+
+ // Determine the Code page.
+ if (lcid == 0x409)
+ usCodePage = 1; // English is most likely.
+ else switch (lcid) {
+ default:
+ if (LOBYTE(lcid) == 0x01 || lcid == 0x0429) {
+ usCodePage = ARABIC_CP; break;
+ }
+ usCodePage = 1; break; // default gets US English (1252)
+ case 0x0419:
+ usCodePage = 3; break;
+ case 0x0408:
+ usCodePage = GREEK_CP; break;
+ case 0x040f:
+ usCodePage = ICELANDIC_CP; break;
+ case 0x041f:
+ usCodePage = TURKISH_CP; break;
+ case 0x0814:
+ usCodePage = NORWEIGIAN_CP; break;
+ case 0x1809:
+ usCodePage = IRELAND_CP; break;
+ case 0x040d:
+ usCodePage = HEBREW_CP; break;
+ case 0x0405:
+ case 0x040e:
+ case 0x0415:
+ case 0x041b:
+ usCodePage = 2; break;
+ }
+
+
+
+
+ pbHashTable = g_prgHashTbl[usCodePage][usSystem];
+
+ uEncoding = (ULONG) (((ULONG) ((usCodePage << 4) | usSystem)) << 16);
+
+
+ // Algorithm: compute 32-bit value by multipling by 37 and adding
+ // in the character. Ignore all overflows. Then convert to
+ // a 16-bit number by moding by 65599 (a prime).
+
+ ulHash = 0xDeadBee; // arbitrary starting number
+
+
+ for (;*szName; szName++) {
+
+ // use pbHashTable[] to map characters
+ //
+
+ uIndex = ((BYTE) *szName) & 0x00ff;
+
+ ulHash = ulHash * 37 + pbHashTable[uIndex];
+
+ } // for
+
+ ulHash = ulHash % 65599;
+
+ return (ULONG) (uEncoding | (ulHash & 0x0000FFFF));
+}
+
+
+
+/***
+*LHashValOfDBCSName
+*Purpose: Calculates the hash value for strings from DBCS language.
+*
+*Implementation Notes:
+* Use the table pointed by pbHashTable to map each character in the
+* szName.
+*
+*
+*Entry:
+* xsz: String whose hash value has to be calculated
+*
+*Exit:
+* ULONG : hash value of the passed in string
+*
+*
+***********************************************************************/
+#pragma code_seg(CS_DBCSHASH)
+unsigned long LHashValOfDBCSName(SYSKIND syskind, LCID lcid, const char FAR* szName)
+{
+ ULONG ulHash; // hash value which accumulates hash
+ ACHAR xch;
+ USHORT uIndex;
+ BYTE *pbHashTable;
+ USHORT usSystem, usCodePage;
+ ULONG uEncoding;
+
+ // UNDONE : for MAC
+ //
+ // For DBCS characters < 255, the mapping rules are same as CODE page for
+ // US english.
+ //
+ pbHashTable = g_rgbCodePage1252;
+
+ // Find the index corresponding to the system passed in.
+ usSystem = (syskind == SYS_MAC) ? 1 : 0;
+
+ // Get the code page.
+ switch (PRIMARYLANGID(lcid)) {
+ case LANG_JAPANESE:
+ usCodePage = JAPNESE_CP;
+ break;
+ case LANG_KOREAN:
+ usCodePage = KOREAN_CP;
+ break;
+ case LANG_CHINESE:
+ switch (SUBLANGID(lcid)) {
+ case SUBLANG_CHINESE_TRADITIONAL:
+ usCodePage = CHINESET_CP;
+ break;
+ case SUBLANG_CHINESE_SIMPLIFIED:
+ usCodePage = CHINESES_CP;
+ break;
+ default:
+ // We default to chinese_simplified sub-lang.
+ usCodePage = CHINESES_CP;
+ break;
+ }
+ break;
+ default:
+ DebHalt("bad lcid");
+ }
+
+ uEncoding = (ULONG) (((ULONG) ((usCodePage << 4) | usSystem)) << 16);
+
+ // Algorithm: compute 32-bit value by multipling by 37 and adding
+ // in the character. Ignore all overflows. Then convert to
+ // a 16-bit number by moding by 65599 (a prime).
+
+ ulHash = 0xDeadBee; // arbitrary starting number
+
+ for (; (xch = xpch((LPSTR)szName)) != '\0'; szName = xstrinc(szName)) {
+
+ // use pbHashTable[] to map characters
+ //
+
+ // If the next character is a double byte character then first map it.
+ if ((USHORT)xch > 0xff) {
+ xch = MapDBChar(xch, lcid);
+
+ // process the high byte.
+ // shift the upper byte down to get the index.
+ if (uIndex = (((USHORT) xch & 0xff00) >> 8)) {
+ ulHash = ulHash * 37 + pbHashTable[uIndex];
+ }
+ }
+
+ // process the low byte.
+ uIndex = ((USHORT) xch) & 0x00ff;
+
+ ulHash = ulHash * 37 + pbHashTable[uIndex];
+
+ } // for
+
+ ulHash = ulHash % 65599;
+
+ return (ULONG) (uEncoding | (ulHash & 0x0000FFFF));
+
+}
+#pragma optimize("t", )
+
+
+
+ALLOC_CODE(ACHAR) m_rgJapneseExcepMap[][2] = {
+0x829F, 0x00A7,
+0x82A0, 0x00B1,
+0x82A1, 0x00A8,
+0x82A2, 0x00B2,
+0x82A3, 0x00A9,
+0x82A4, 0x00B3,
+0x82A5, 0x00AA,
+0x82A6, 0x00B4,
+0x82A7, 0x00AB,
+0x82A8, 0x00B5,
+0x82A9, 0x00B6,
+0x82AA, 0xB6DE,
+0x82AB, 0x00B7,
+0x82AC, 0xB7DE,
+0x82AD, 0x00B8,
+0x82AE, 0xB8DE,
+0x82AF, 0x00B9,
+0x82B0, 0xB9DE,
+0x82B1, 0x00BA,
+0x82B2, 0xBADE,
+0x82B3, 0x00BB,
+0x82B4, 0xBBDE,
+0x82B5, 0x00BC,
+0x82B6, 0xBCDE,
+0x82B7, 0x00BD,
+0x82B8, 0xBDDE,
+0x82B9, 0x00BE,
+0x82BA, 0xBEDE,
+0x82BB, 0x00BF,
+0x82BC, 0xBFDE,
+0x82BD, 0x00C0,
+0x82BE, 0xC0DE,
+0x82BF, 0x00C1,
+0x82C0, 0xC1DE,
+0x82C1, 0x00AF,
+0x82C2, 0x00C2,
+0x82C3, 0xC2DE,
+0x82C4, 0x00C3,
+0x82C5, 0xC3DE,
+0x82C6, 0x00C4,
+0x82C7, 0xC4DE,
+0x82C8, 0x00C5,
+0x82C9, 0x00C6,
+0x82CA, 0x00C7,
+0x82CB, 0x00C8,
+0x82CC, 0x00C9,
+0x82CD, 0x00CA,
+0x82CE, 0xCADE,
+0x82CF, 0xCADF,
+0x82D0, 0x00CB,
+0x82D1, 0xCBDE,
+0x82D2, 0xCBDF,
+0x82D3, 0x00CC,
+0x82D4, 0xCCDE,
+0x82D5, 0xCCDF,
+0x82D6, 0x00CD,
+0x82D7, 0xCDDE,
+0x82D8, 0xCDDF,
+0x82D9, 0x00CE,
+0x82DA, 0xCEDE,
+0x82DB, 0xCEDF,
+0x82DC, 0x00CF,
+0x82DD, 0x00D0,
+0x82DE, 0x00D1,
+0x82DF, 0x00D2,
+0x82E0, 0x00D3,
+0x82E1, 0x00AC,
+0x82E2, 0x00D4,
+0x82E3, 0x00AD,
+0x82E4, 0x00D5,
+0x82E5, 0x00AE,
+0x82E6, 0x00D6,
+0x82E7, 0x00D7,
+0x82E8, 0x00D8,
+0x82E9, 0x00D9,
+0x82EA, 0x00DA,
+0x82EB, 0x00DB,
+0x82EC, 0x838E,
+0x82ED, 0x00DC,
+0x82EE, 0x8390,
+0x82EF, 0x8391,
+0x82F0, 0x00A6,
+0x82F1, 0x00DD,
+
+0x8340, 0x00A7,
+0x8341, 0x00B1,
+0x8342, 0x00A8,
+0x8343, 0x00B2,
+0x8344, 0x00A9,
+0x8345, 0x00B3,
+0x8346, 0x00AA,
+0x8347, 0x00B4,
+0x8348, 0x00AB,
+0x8349, 0x00B5,
+0x834A, 0x00B6,
+0x834B, 0xB6DE,
+0x834C, 0x00B7,
+0x834D, 0xB7DE,
+0x834E, 0x00B8,
+0x834F, 0xB8DE,
+0x8350, 0x00B9,
+0x8351, 0xB9DE,
+0x8352, 0x00BA,
+0x8353, 0xBADE,
+0x8354, 0x00BB,
+0x8355, 0xBBDE,
+0x8356, 0x00BC,
+0x8357, 0xBCDE,
+0x8358, 0x00BD,
+0x8359, 0xBDDE,
+0x835A, 0x00BE,
+0x835B, 0xBEDE,
+0x835C, 0x00BF,
+0x835D, 0xBFDE,
+0x835E, 0x00C0,
+0x835F, 0xC0DE,
+0x8360, 0x00C1,
+0x8361, 0xC1DE,
+0x8362, 0x00AF,
+0x8363, 0x00C2,
+0x8364, 0xC2DE,
+0x8365, 0x00C3,
+0x8366, 0xC3DE,
+0x8367, 0x00C4,
+0x8368, 0xC4DE,
+0x8369, 0x00C5,
+0x836A, 0x00C6,
+0x836B, 0x00C7,
+0x836C, 0x00C8,
+0x836D, 0x00C9,
+0x836E, 0x00CA,
+0x836F, 0xCADE,
+0x8370, 0xCADF,
+0x8371, 0x00CB,
+0x8372, 0xCBDE,
+0x8373, 0xCBDF,
+0x8374, 0x00CC,
+0x8375, 0xCCDE,
+0x8376, 0xCCDF,
+0x8377, 0x00CD,
+0x8378, 0xCDDE,
+0x8379, 0xCDDF,
+0x837A, 0x00CE,
+0x837B, 0xCEDE,
+0x837C, 0xCEDF,
+0x837D, 0x00CF,
+0x837E, 0x00D0,
+0x8380, 0x00D1,
+0x8381, 0x00D2,
+0x8382, 0x00D3,
+0x8383, 0x00AC,
+0x8384, 0x00D4,
+0x8385, 0x00AD,
+0x8386, 0x00D5,
+0x8387, 0x00AE,
+0x8388, 0x00D6,
+0x8389, 0x00D7,
+0x838A, 0x00D8,
+0x838B, 0x00D9,
+0x838C, 0x00DA,
+0x838D, 0x00DB,
+0x838E, 0x838E,
+0x838F, 0x00DC,
+0x8390, 0x8390,
+0x8391, 0x8391,
+0x8392, 0x00A6,
+0x8393, 0x00DD,
+0x8394, 0xB3DE,
+0x8395, 0x8395,
+0x8396, 0x8396,
+
+0x824F, 0x30,
+0x8250, 0x31,
+0x8251, 0x32,
+0x8252, 0x33,
+0x8253, 0x34,
+0x8254, 0x35,
+0x8255, 0x36,
+0x8256, 0x37,
+0x8257, 0x38,
+0x8258, 0x39,
+0x8260, 0x41,
+0x8261, 0x42,
+0x8262, 0x43,
+0x8263, 0x44,
+0x8264, 0x45,
+0x8265, 0x46,
+0x8266, 0x47,
+0x8267, 0x48,
+0x8268, 0x49,
+0x8269, 0x4A,
+0x826A, 0x4B,
+0x826B, 0x4C,
+0x826C, 0x4D,
+0x826D, 0x4E,
+0x826E, 0x4F,
+0x826F, 0x50,
+0x8270, 0x51,
+0x8271, 0x52,
+0x8272, 0x53,
+0x8273, 0x54,
+0x8274, 0x55,
+0x8275, 0x56,
+0x8276, 0x57,
+0x8277, 0x58,
+0x8278, 0x59,
+0x8279, 0x5A,
+0x8151, 0x5F,
+0x8281, 0x61,
+0x8282, 0x62,
+0x8283, 0x63,
+0x8284, 0x64,
+0x8285, 0x65,
+0x8286, 0x66,
+0x8287, 0x67,
+0x8288, 0x68,
+0x8289, 0x69,
+0x828A, 0x6A,
+0x828B, 0x6B,
+0x828C, 0x6C,
+0x828D, 0x6D,
+0x828E, 0x6E,
+0x828F, 0x6F,
+0x8290, 0x70,
+0x8291, 0x71,
+0x8292, 0x72,
+0x8293, 0x73,
+0x8294, 0x74,
+0x8295, 0x75,
+0x8296, 0x76,
+0x8297, 0x77,
+0x8298, 0x78,
+0x8299, 0x79,
+0x829A, 0x7A,
+0x0000, 0x00
+};
+
+ALLOC_CODE(ACHAR) m_rgKoreaExcepMap[][2] = {
+0xA3B0, 0x30,
+0xA3B1, 0x31,
+0xA3B2, 0x32,
+0xA3B3, 0x33,
+0xA3B4, 0x34,
+0xA3B5, 0x35,
+0xA3B6, 0x36,
+0xA3B7, 0x37,
+0xA3B8, 0x38,
+0xA3B9, 0x39,
+0xA3C1, 0x41,
+0xA3C2, 0x42,
+0xA3C3, 0x43,
+0xA3C4, 0x44,
+0xA3C5, 0x45,
+0xA3C6, 0x46,
+0xA3C7, 0x47,
+0xA3C8, 0x48,
+0xA3C9, 0x49,
+0xA3CA, 0x4A,
+0xA3CB, 0x4B,
+0xA3CC, 0x4C,
+0xA3CD, 0x4D,
+0xA3CE, 0x4E,
+0xA3CF, 0x4F,
+0xA3D0, 0x50,
+0xA3D1, 0x51,
+0xA3D2, 0x52,
+0xA3D3, 0x53,
+0xA3D4, 0x54,
+0xA3D5, 0x55,
+0xA3D6, 0x56,
+0xA3D7, 0x57,
+0xA3D8, 0x58,
+0xA3D9, 0x59,
+0xA3DA, 0x5A,
+0xA3DF, 0x5F,
+0xA3E1, 0x61,
+0xA3E2, 0x62,
+0xA3E3, 0x63,
+0xA3E4, 0x64,
+0xA3E5, 0x65,
+0xA3E6, 0x66,
+0xA3E7, 0x67,
+0xA3E8, 0x68,
+0xA3E9, 0x69,
+0xA3EA, 0x6A,
+0xA3EB, 0x6B,
+0xA3EC, 0x6C,
+0xA3ED, 0x6D,
+0xA3EE, 0x6E,
+0xA3EF, 0x6F,
+0xA3F0, 0x70,
+0xA3F1, 0x71,
+0xA3F2, 0x72,
+0xA3F3, 0x73,
+0xA3F4, 0x74,
+0xA3F5, 0x75,
+0xA3F6, 0x76,
+0xA3F7, 0x77,
+0xA3F8, 0x78,
+0xA3F9, 0x79,
+0xA3FA, 0x7A,
+0x0000, 0x00
+};
+
+
+ALLOC_CODE(ACHAR) m_rgChinaTExcepMap[][2] = {
+0xA2AF, 0x30,
+0xA2B0, 0x31,
+0xA2B1, 0x32,
+0xA2B2, 0x33,
+0xA2B3, 0x34,
+0xA2B4, 0x35,
+0xA2B5, 0x36,
+0xA2B6, 0x37,
+0xA2B7, 0x38,
+0xA2B8, 0x39,
+0xA2CF, 0x41,
+0xA2D0, 0x42,
+0xA2D1, 0x43,
+0xA2D2, 0x44,
+0xA2D3, 0x45,
+0xA2D4, 0x46,
+0xA2D5, 0x47,
+0xA2D6, 0x48,
+0xA2D7, 0x49,
+0xA2D8, 0x4A,
+0xA2D9, 0x4B,
+0xA2DA, 0x4C,
+0xA2DB, 0x4D,
+0xA2DC, 0x4E,
+0xA2DD, 0x4F,
+0xA2DE, 0x50,
+0xA2DF, 0x51,
+0xA2E0, 0x52,
+0xA2E1, 0x53,
+0xA2E2, 0x54,
+0xA2E3, 0x55,
+0xA2E4, 0x56,
+0xA2E5, 0x57,
+0xA2E6, 0x58,
+0xA2E7, 0x59,
+0xA2E8, 0x5A,
+0xA1C5, 0x5F,
+0xA2E9, 0x61,
+0xA2EA, 0x62,
+0xA2EB, 0x63,
+0xA2EC, 0x64,
+0xA2ED, 0x65,
+0xA2EE, 0x66,
+0xA2EF, 0x67,
+0xA2F0, 0x68,
+0xA2F1, 0x69,
+0xA2F2, 0x6A,
+0xA2F3, 0x6B,
+0xA2F4, 0x6C,
+0xA2F5, 0x6D,
+0xA2F6, 0x6E,
+0xA2F7, 0x6F,
+0xA2F8, 0x70,
+0xA2F9, 0x71,
+0xA2FA, 0x72,
+0xA2FB, 0x73,
+0xA2FC, 0x74,
+0xA2FD, 0x75,
+0xA2FE, 0x76,
+0xA340, 0x77,
+0xA341, 0x78,
+0xA342, 0x79,
+0xA343, 0x7A,
+};
+
+ALLOC_CODE(ACHAR) m_rgChinaSExcepMap[][2] = {
+0xA3B0, 0x30,
+0xA3B1, 0x31,
+0xA3B2, 0x32,
+0xA3B3, 0x33,
+0xA3B4, 0x34,
+0xA3B5, 0x35,
+0xA3B6, 0x36,
+0xA3B7, 0x37,
+0xA3B8, 0x38,
+0xA3B9, 0x39,
+0xA3C1, 0x41,
+0xA3C2, 0x42,
+0xA3C3, 0x43,
+0xA3C4, 0x44,
+0xA3C5, 0x45,
+0xA3C6, 0x46,
+0xA3C7, 0x47,
+0xA3C8, 0x48,
+0xA3C9, 0x49,
+0xA3CA, 0x4A,
+0xA3CB, 0x4B,
+0xA3CC, 0x4C,
+0xA3CD, 0x4D,
+0xA3CE, 0x4E,
+0xA3CF, 0x4F,
+0xA3D0, 0x50,
+0xA3D1, 0x51,
+0xA3D2, 0x52,
+0xA3D3, 0x53,
+0xA3D4, 0x54,
+0xA3D5, 0x55,
+0xA3D6, 0x56,
+0xA3D7, 0x57,
+0xA3D8, 0x58,
+0xA3D9, 0x59,
+0xA3DA, 0x5A,
+0xA3DF, 0x5F,
+0xA3E1, 0x61,
+0xA3E2, 0x62,
+0xA3E3, 0x63,
+0xA3E4, 0x64,
+0xA3E5, 0x65,
+0xA3E6, 0x66,
+0xA3E7, 0x67,
+0xA3E8, 0x68,
+0xA3E9, 0x69,
+0xA3EA, 0x6A,
+0xA3EB, 0x6B,
+0xA3EC, 0x6C,
+0xA3ED, 0x6D,
+0xA3EE, 0x6E,
+0xA3EF, 0x6F,
+0xA3F0, 0x70,
+0xA3F1, 0x71,
+0xA3F2, 0x72,
+0xA3F3, 0x73,
+0xA3F4, 0x74,
+0xA3F5, 0x75,
+0xA3F6, 0x76,
+0xA3F7, 0x77,
+0xA3F8, 0x78,
+0xA3F9, 0x79,
+0xA3FA, 0x7A,
+};
+
+
+/***
+*MapDBChar
+*Purpose: Maps a double byte character to a (1 or 2) single byte character
+*
+*Implementation Notes:
+* Use the exception tables above for the appropriate language.
+*
+*Entry:
+* xch: Character to be mapped
+* lcid: LCID of language in use
+*
+*Exit:
+* returns mapped character
+*
+*CONSIDER: there are some optimizations that could be done here
+*
+***********************************************************************/
+ACHAR MapDBChar(ACHAR xch, LCID lcid)
+{
+ ACHAR * pchException;
+
+ DebAssert(0xff00 & (USHORT)xch, " should a double byte character ");
+
+ // Do language specific mapping.
+ switch (PRIMARYLANGID(lcid)) {
+ case LANG_JAPANESE:
+ // Japan
+ pchException = m_rgJapneseExcepMap[0];
+ break;
+ case LANG_KOREAN:
+ // Korea
+ pchException = m_rgKoreaExcepMap[0];
+ break;
+ case LANG_CHINESE:
+ switch (SUBLANGID(lcid)) {
+ case SUBLANG_CHINESE_TRADITIONAL:
+ // China(T)
+ pchException = m_rgChinaTExcepMap[0];
+ break;
+ case SUBLANG_CHINESE_SIMPLIFIED:
+ // China(S)
+ pchException = m_rgChinaSExcepMap[0];
+ break;
+ default:
+ DebHalt("bad lcid");
+ }
+ break;
+ default:
+ DebHalt("bad lcid");
+ }
+
+ for (; *pchException != 0x0000 && *pchException != xch; pchException += 2);
+ // end of for loop
+
+ if (*pchException == 0x0000)
+ return xch;
+ else
+ return *(pchException+1);
+
+}
+#pragma code_seg()
+
+
+// ***** Start case mapping tables
+
+/////////////////////////////////////////////////////////////////////////
+// The following tables/Code is used to generate the tables for accent and
+// and case insensitive comparision.
+//
+
+
+
+/******
+* 0x0409 // These uses the base table it self.
+* 0x0407,
+* 0x040c,
+* 0x0809,
+* 0x0c09,
+* 0x1009,
+* 0x1409,
+* 0x0413,
+* 0x0813,
+* 0x080c,
+* 0x0c0c,
+* 0x100c,
+* 0x0807,
+* 0x0c07,
+* 0x0410,
+* 0x0810,
+* 0x0416,
+* 0x0816,
+* 0x0419 // Russian(in different code page):
+* // but the comparision table is same as US english.
+*
+* 0x040b, // these uses g_rgbExcepTblWin1035 as execption table
+* 0x041d,
+*
+*
+* 0x0406, // these uses g_rgbExcepTblWin1030 as execption table
+* 0x0414,
+*
+*
+* 0x040a, // these uses g_rgbExcepTblWin1034 as execption table
+* 0x080a,
+* 0x0c0a,
+*
+*
+* These falls in a different Code Page (WIN:1240, MAC:10029)
+* 0x0405, These uses the base table it self.
+*
+* 0x040e,
+*
+* 0x0415,
+*
+* 0x041b,
+***************************************************************************/
+
+// Partial base Tables. The partial tables are used to build the CodePage
+// and sysytem kind dependent base table. We the full blown table when we
+// load the typelib.dll
+//
+
+// In the partial base tables we do not have the first 128 characters.
+// We construct the first 128 characters in the following way:
+// From 0 to 96 we have identity (index == the entry).
+// From 97 to 122 we have 65 to 90 (note this is 'a' to 'z' that naps to 'A' to 'Z').
+// From 123 to 127 we again have identity.
+//
+#pragma code_seg(CS_CORE2)
+ALLOC_CODE(BYTE) g_rgbPartialBaseTbl1252[128] = {
+ 127,
+ 127,
+ 130,
+ 70 ,
+ 132,
+ 133,
+ 134,
+ 135,
+ 127,
+ 137,
+ 83 ,
+ 139,
+ 140,
+ 127,
+ 127,
+ 127,
+ 127,
+ 145,
+ 146,
+ 147,
+ 148,
+ 149,
+ 150,
+ 150,
+ 152,
+ 153,
+ 83 ,
+ 155,
+ 140,
+ 127,
+ 127,
+ 89 ,
+ 160,
+ 161,
+ 162,
+ 163,
+ 164,
+ 165,
+ 166,
+ 167,
+ 168,
+ 169,
+ 65 ,
+ 171,
+ 172,
+ 150,
+ 174,
+ 175,
+ 176,
+ 177,
+ 50 ,
+ 51 ,
+ 180,
+ 181,
+ 182,
+ 183,
+ 184,
+ 49 ,
+ 79 ,
+ 187,
+ 188,
+ 189,
+ 190,
+ 191,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 198,
+ 67 ,
+ 69 ,
+ 69 ,
+ 69 ,
+ 69 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 208,
+ 78 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 215,
+ 79 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 89 ,
+ 222,
+ 223,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 198,
+ 67 ,
+ 69 ,
+ 69 ,
+ 69 ,
+ 69 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 208,
+ 78 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 247,
+ 79 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 89 ,
+ 222,
+ 89
+};
+
+ALLOC_CODE(BYTE) g_rgbPartialBaseTbl1250[128] = {
+ 127,
+ 127,
+ 130,
+ 127,
+ 132,
+ 133,
+ 134,
+ 135,
+ 127,
+ 137,
+ 138,
+ 139,
+ 83 ,
+ 84 ,
+ 142,
+ 90 ,
+ 127,
+ 145,
+ 146,
+ 147,
+ 148,
+ 149,
+ 150,
+ 150,
+ 127,
+ 153,
+ 138,
+ 155,
+ 83 ,
+ 84 ,
+ 142,
+ 90 ,
+ 160,
+ 127,
+ 162,
+ 76 ,
+ 164,
+ 65 ,
+ 166,
+ 167,
+ 168,
+ 169,
+ 83 ,
+ 171,
+ 172,
+ 150,
+ 174,
+ 90 ,
+ 176,
+ 177,
+ 178,
+ 76 ,
+ 180,
+ 181,
+ 182,
+ 183,
+ 184,
+ 65 ,
+ 83 ,
+ 187,
+ 76 ,
+ 189,
+ 76 ,
+ 90 ,
+ 82 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 76 ,
+ 67 ,
+ 67 ,
+ 200,
+ 69 ,
+ 69 ,
+ 69 ,
+ 69 ,
+ 73 ,
+ 73 ,
+ 68 ,
+ 208,
+ 78 ,
+ 78 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 215,
+ 216,
+ 85 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 89 ,
+ 84 ,
+ 223,
+ 82 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 76 ,
+ 67 ,
+ 67 ,
+ 200,
+ 69 ,
+ 69 ,
+ 69 ,
+ 69 ,
+ 73 ,
+ 73 ,
+ 68 ,
+ 208,
+ 78 ,
+ 78 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 247,
+ 216,
+ 85 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 89 ,
+ 84 ,
+ 255
+};
+
+ALLOC_CODE(BYTE) g_rgbPartialBaseTbl10000[128] = {
+ 65 ,
+ 65 ,
+ 67 ,
+ 69 ,
+ 78 ,
+ 79 ,
+ 85 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 67 ,
+ 69 ,
+ 69 ,
+ 69 ,
+ 69 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 78 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 160,
+ 161,
+ 162,
+ 163,
+ 164,
+ 165,
+ 166,
+ 167,
+ 168,
+ 169,
+ 170,
+ 171,
+ 172,
+ 173,
+ 174,
+ 79 ,
+ 176,
+ 177,
+ 178,
+ 179,
+ 180,
+ 181,
+ 182,
+ 183,
+ 184,
+ 185,
+ 186,
+ 65 ,
+ 79 ,
+ 189,
+ 174,
+ 79 ,
+ 192,
+ 193,
+ 194,
+ 195,
+ 70 ,
+ 197,
+ 198,
+ 199,
+ 200,
+ 201,
+ 202,
+ 65 ,
+ 65 ,
+ 79 ,
+ 206,
+ 206,
+ 208,
+ 208,
+ 210,
+ 211,
+ 212,
+ 213,
+ 214,
+ 215,
+ 89 ,
+ 89 ,
+ 218,
+ 219,
+ 220,
+ 221,
+ 63 ,
+ 63 ,
+ 224,
+ 225,
+ 226,
+ 227,
+ 228,
+ 65 ,
+ 69 ,
+ 65 ,
+ 69 ,
+ 69 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 79 ,
+ 79 ,
+ 63 ,
+ 79 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 73 ,
+ 127,
+ 247,
+ 127,
+ 249,
+ 250,
+ 251,
+ 63 ,
+ 253,
+ 254,
+ 127
+
+};
+
+ALLOC_CODE(BYTE) g_rgbPartialBaseTbl10029[128] = {
+ 65 ,
+ 65 ,
+ 65 ,
+ 69 ,
+ 65 ,
+ 79 ,
+ 85 ,
+ 65 ,
+ 65 ,
+ 137,
+ 65 ,
+ 137,
+ 67 ,
+ 67 ,
+ 69 ,
+ 90 ,
+ 90 ,
+ 68 ,
+ 73 ,
+ 68 ,
+ 69 ,
+ 69 ,
+ 69 ,
+ 79 ,
+ 69 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 85 ,
+ 69 ,
+ 69 ,
+ 85 ,
+ 160,
+ 161,
+ 69 ,
+ 163,
+ 164,
+ 165,
+ 166,
+ 167,
+ 168,
+ 169,
+ 170,
+ 69 ,
+ 172,
+ 173,
+ 71 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 178,
+ 179,
+ 73 ,
+ 75 ,
+ 182,
+ 183,
+ 76 ,
+ 76 ,
+ 76 ,
+ 76 ,
+ 76 ,
+ 76 ,
+ 76 ,
+ 78 ,
+ 78 ,
+ 78 ,
+ 194,
+ 195,
+ 78 ,
+ 78 ,
+ 198,
+ 199,
+ 200,
+ 201,
+ 202,
+ 78 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 208,
+ 208,
+ 210,
+ 211,
+ 212,
+ 213,
+ 214,
+ 215,
+ 79 ,
+ 82 ,
+ 82 ,
+ 219,
+ 220,
+ 221,
+ 219,
+ 82 ,
+ 82 ,
+ 225,
+ 226,
+ 227,
+ 225,
+ 83 ,
+ 83 ,
+ 65 ,
+ 84 ,
+ 84 ,
+ 73 ,
+ 235,
+ 235,
+ 85 ,
+ 79 ,
+ 79 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 89 ,
+ 89 ,
+ 75 ,
+ 90 ,
+ 76 ,
+ 76 ,
+ 71 ,
+ 255
+
+
+};
+
+ALLOC_CODE(BYTE) g_rgbPartialBaseTbl10007[128] = {
+ 128,
+ 129,
+ 130,
+ 131,
+ 132,
+ 133,
+ 134,
+ 135,
+ 136,
+ 137,
+ 138,
+ 139,
+ 140,
+ 141,
+ 142,
+ 143,
+ 144,
+ 145,
+ 146,
+ 147,
+ 148,
+ 149,
+ 150,
+ 151,
+ 152,
+ 153,
+ 154,
+ 155,
+ 156,
+ 157,
+ 158,
+ 159,
+ 160,
+ 161,
+ 162,
+ 163,
+ 164,
+ 165,
+ 166,
+ 167,
+ 168,
+ 169,
+ 170,
+ 171,
+ 171,
+ 173,
+ 174,
+ 174,
+ 176,
+ 177,
+ 178,
+ 179,
+ 167,
+ 181,
+ 182,
+ 183,
+ 184,
+ 184,
+ 186,
+ 186,
+ 188,
+ 188,
+ 190,
+ 190,
+ 183,
+ 193,
+ 194,
+ 195,
+ 70 ,
+ 197,
+ 198,
+ 199,
+ 200,
+ 201,
+ 202,
+ 203,
+ 203,
+ 205,
+ 205,
+ 193,
+ 208,
+ 208,
+ 210,
+ 211,
+ 212,
+ 213,
+ 214,
+ 215,
+ 216,
+ 216,
+ 218,
+ 218,
+ 220,
+ 221,
+ 221,
+ 159,
+ 128,
+ 129,
+ 130,
+ 131,
+ 132,
+ 133,
+ 134,
+ 135,
+ 136,
+ 137,
+ 138,
+ 139,
+ 140,
+ 141,
+ 142,
+ 143,
+ 144,
+ 145,
+ 146,
+ 147,
+ 148,
+ 149,
+ 150,
+ 151,
+ 152,
+ 153,
+ 154,
+ 155,
+ 156,
+ 157,
+ 158,
+ 159
+
+};
+
+
+// Now we use g_rgbCodePageWGreek to build the table.
+#if 0
+ALLOC_CODE(BYTE) g_rgbPartialBaseTblWGreek[128] = {
+0 ,
+0 ,
+130,
+70 ,
+132,
+133,
+134,
+135,
+0 ,
+137,
+0 ,
+139,
+0 ,
+0 ,
+0 ,
+0 ,
+0 ,
+145,
+146,
+147,
+148,
+149,
+45 ,
+45 ,
+0 ,
+153,
+0 ,
+155,
+0 ,
+0 ,
+0 ,
+0 ,
+9 ,
+161,
+162,
+163,
+164,
+165,
+166,
+167,
+168,
+169,
+0 ,
+171,
+172,
+45 ,
+174,
+45 ,
+176,
+177,
+50 ,
+51 ,
+180,
+181,
+182,
+183,
+184,
+185,
+186,
+187,
+188,
+189,
+190,
+191,
+186,
+162,
+194,
+195,
+196,
+184,
+198,
+185,
+200,
+186,
+202,
+203,
+204,
+205,
+206,
+188,
+208,
+209,
+0 ,
+211,
+212,
+190,
+214,
+215,
+216,
+191,
+186,
+190,
+162,
+184,
+185,
+186,
+190,
+162,
+194,
+195,
+196,
+184,
+198,
+185,
+200,
+186,
+202,
+203,
+204,
+205,
+206,
+188,
+208,
+209,
+211,
+211,
+212,
+190,
+214,
+215,
+216,
+191,
+186,
+190,
+188,
+190,
+191,
+0
+};
+#endif //0
+
+// Now we use g_rgbCodePageWIceland to build the table.
+#if 0
+ALLOC_CODE(BYTE) g_rgbPartialBaseTblWIceland[128] = {
+0 ,
+0 ,
+130,
+70 ,
+132,
+133,
+134,
+135,
+0 ,
+137,
+83 ,
+139,
+140,
+0 ,
+0 ,
+0 ,
+0 ,
+145,
+146,
+147,
+148,
+149,
+45 ,
+45 ,
+152,
+153,
+83 ,
+155,
+140,
+0 ,
+0 ,
+89 ,
+9 ,
+161,
+162,
+163,
+164,
+165,
+166,
+167,
+168,
+169,
+65 ,
+171,
+172,
+45 ,
+174,
+175,
+176,
+177,
+50 ,
+51 ,
+180,
+181,
+182,
+183,
+184,
+49 ,
+79 ,
+187,
+188,
+189,
+190,
+191,
+65 ,
+193,
+65 ,
+65 ,
+65 ,
+65 ,
+198,
+67 ,
+69 ,
+201,
+69 ,
+69 ,
+73 ,
+205,
+73 ,
+73 ,
+208,
+78 ,
+79 ,
+211,
+79 ,
+79 ,
+214,
+215,
+214,
+85 ,
+218,
+85 ,
+85 ,
+221,
+222,
+223,
+65 ,
+193,
+65 ,
+65 ,
+65 ,
+65 ,
+198,
+67 ,
+69 ,
+201,
+69 ,
+69 ,
+73 ,
+205,
+73 ,
+73 ,
+208,
+78 ,
+79 ,
+211,
+79 ,
+79 ,
+214,
+247,
+214,
+85 ,
+218,
+85 ,
+85 ,
+221,
+222,
+89
+};
+
+#endif //0
+
+
+ALLOC_CODE(BYTE) g_rgbPartialBaseTblWTurkish[128] = {
+0 ,
+0 ,
+130,
+70 ,
+132,
+133,
+134,
+135,
+0 ,
+137,
+83 ,
+139,
+140,
+0 ,
+0 ,
+0 ,
+0 ,
+145,
+146,
+147,
+148,
+149,
+45 ,
+45 ,
+152,
+153,
+83 ,
+155,
+140,
+0 ,
+0 ,
+89 ,
+9 ,
+161,
+162,
+163,
+164,
+165,
+166,
+167,
+168,
+169,
+65 ,
+171,
+172,
+45 ,
+174,
+175,
+176,
+177,
+50 ,
+51 ,
+180,
+181,
+182,
+183,
+184,
+49 ,
+79 ,
+187,
+188,
+189,
+190,
+191,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+198,
+199,
+69 ,
+69 ,
+69 ,
+69 ,
+73 ,
+73 ,
+73 ,
+73 ,
+208,
+78 ,
+79 ,
+79 ,
+79 ,
+79 ,
+214,
+215,
+79 ,
+85 ,
+85 ,
+85 ,
+220,
+221,
+222,
+223,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+198,
+199,
+69 ,
+69 ,
+69 ,
+69 ,
+73 ,
+73 ,
+73 ,
+73 ,
+208,
+78 ,
+79 ,
+79 ,
+79 ,
+79 ,
+214,
+247,
+79 ,
+85 ,
+85 ,
+85 ,
+220,
+221,
+222,
+89
+};
+
+ALLOC_CODE(BYTE) g_rgbPartialBaseTblWNorwegian[128] = {
+0 ,
+0 ,
+130,
+70 ,
+132,
+133,
+134,
+135,
+0 ,
+137,
+83 ,
+139,
+140,
+0 ,
+0 ,
+0 ,
+0 ,
+145,
+146,
+147,
+148,
+149,
+45 ,
+45 ,
+152,
+153,
+83 ,
+155,
+140,
+0 ,
+0 ,
+89 ,
+9 ,
+161,
+162,
+163,
+164,
+165,
+166,
+167,
+168,
+169,
+65 ,
+171,
+172,
+45 ,
+174,
+175,
+176,
+177,
+50 ,
+51 ,
+180,
+181,
+182,
+183,
+184,
+49 ,
+79 ,
+187,
+188,
+189,
+190,
+191,
+65 ,
+65 ,
+65 ,
+65 ,
+196,
+197,
+196,
+67 ,
+69 ,
+69 ,
+69 ,
+69 ,
+73 ,
+73 ,
+73 ,
+73 ,
+68 ,
+78 ,
+79 ,
+79 ,
+79 ,
+79 ,
+214,
+215,
+214,
+85 ,
+85 ,
+85 ,
+89 ,
+89 ,
+222,
+223,
+65 ,
+65 ,
+65 ,
+65 ,
+196,
+197,
+196,
+67 ,
+69 ,
+69 ,
+69 ,
+69 ,
+73 ,
+73 ,
+73 ,
+73 ,
+68 ,
+78 ,
+79 ,
+79 ,
+79 ,
+79 ,
+214,
+247,
+214,
+85 ,
+85 ,
+85 ,
+89 ,
+89 ,
+222,
+89
+};
+
+ALLOC_CODE(BYTE) g_rgbPartialBaseTblWEngIreland[128] = {
+0 ,
+0 ,
+130,
+70 ,
+132,
+133,
+134,
+135,
+0 ,
+137,
+83 ,
+139,
+140,
+0 ,
+0 ,
+0 ,
+0 ,
+145,
+146,
+147,
+148,
+149,
+45 ,
+45 ,
+152,
+153,
+83 ,
+155,
+140,
+0 ,
+0 ,
+89 ,
+9 ,
+161,
+162,
+163,
+164,
+165,
+166,
+167,
+168,
+169,
+65 ,
+171,
+172,
+45 ,
+174,
+175,
+176,
+177,
+50 ,
+51 ,
+180,
+181,
+182,
+183,
+184,
+49 ,
+79 ,
+187,
+188,
+189,
+190,
+191,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+198,
+67 ,
+69 ,
+69 ,
+69 ,
+69 ,
+73 ,
+73 ,
+73 ,
+73 ,
+208,
+78 ,
+79 ,
+79 ,
+79 ,
+79 ,
+79 ,
+215,
+79 ,
+85 ,
+85 ,
+85 ,
+85 ,
+89 ,
+222,
+223,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+65 ,
+198,
+67 ,
+69 ,
+69 ,
+69 ,
+69 ,
+73 ,
+73 ,
+73 ,
+73 ,
+208,
+78 ,
+79 ,
+79 ,
+79 ,
+79 ,
+79 ,
+247,
+79 ,
+85 ,
+85 ,
+85 ,
+85 ,
+89 ,
+222,
+89
+};
+
+
+// Now we use g_rgbCodePageMGreek to build the table.
+#if 0
+ALLOC_CODE(BYTE) g_rgbPartialBaseTblMGreek[128] = {
+65 ,
+49 ,
+50 ,
+69 ,
+51 ,
+79 ,
+85 ,
+135,
+65 ,
+65 ,
+65 ,
+0 ,
+140,
+67 ,
+69 ,
+69 ,
+69 ,
+69 ,
+146,
+147,
+73 ,
+73 ,
+150,
+151,
+152,
+79 ,
+79 ,
+155,
+63 ,
+85 ,
+85 ,
+85 ,
+160,
+161,
+162,
+163,
+164,
+165,
+166,
+167,
+168,
+169,
+170,
+171,
+172,
+173,
+174,
+175,
+176,
+177,
+178,
+179,
+180,
+181,
+182,
+183,
+184,
+171,
+186,
+187,
+188,
+189,
+190,
+191,
+176,
+193,
+194,
+195,
+196,
+197,
+198,
+199,
+200,
+201,
+9 ,
+189,
+204,
+176,
+182,
+207,
+45 ,
+45 ,
+210,
+211,
+212,
+213,
+214,
+184,
+171,
+195,
+189,
+182,
+184,
+171,
+195,
+191,
+189,
+176,
+181,
+190,
+162,
+182,
+188,
+161,
+184,
+171,
+165,
+186,
+164,
+187,
+193,
+195,
+166,
+191,
+196,
+170,
+198,
+163,
+191,
+170,
+204,
+189,
+183,
+171,
+189,
+171,
+189,
+63
+};
+#endif // 0
+
+ALLOC_CODE(BYTE) g_rgbPartialBaseTblMNorwegian[128] = {
+128,
+129,
+67 ,
+69 ,
+78 ,
+133,
+89 ,
+65 ,
+65 ,
+65 ,
+128,
+65 ,
+129,
+67 ,
+69 ,
+69 ,
+69 ,
+69 ,
+73 ,
+73 ,
+73 ,
+73 ,
+78 ,
+79 ,
+79 ,
+79 ,
+133,
+79 ,
+85 ,
+85 ,
+85 ,
+89 ,
+160,
+161,
+162,
+163,
+164,
+165,
+166,
+167,
+168,
+169,
+170,
+171,
+172,
+173,
+128,
+133,
+176,
+177,
+178,
+179,
+180,
+181,
+182,
+183,
+184,
+185,
+186,
+65 ,
+79 ,
+189,
+128,
+133,
+192,
+193,
+194,
+195,
+70 ,
+197,
+198,
+199,
+200,
+201,
+9 ,
+65 ,
+65 ,
+79 ,
+206,
+206,
+45 ,
+45 ,
+210,
+211,
+212,
+213,
+214,
+215,
+89 ,
+89 ,
+218,
+219,
+220,
+221,
+63 ,
+63 ,
+224,
+225,
+226,
+227,
+228,
+65 ,
+69 ,
+65 ,
+69 ,
+69 ,
+73 ,
+73 ,
+73 ,
+73 ,
+79 ,
+79 ,
+63 ,
+79 ,
+85 ,
+85 ,
+85 ,
+73 ,
+0 ,
+247,
+0 ,
+249,
+250,
+251,
+63 ,
+253,
+254,
+0
+};
+
+ALLOC_CODE(BYTE) g_rgbPartialBaseTblMEngIreland[128] = {
+ 65 ,
+ 65 ,
+ 67 ,
+ 69 ,
+ 78 ,
+ 79 ,
+ 85 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 65 ,
+ 67 ,
+ 69 ,
+ 69 ,
+ 69 ,
+ 69 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 78 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 79 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 160,
+ 161,
+ 162,
+ 163,
+ 164,
+ 165,
+ 166,
+ 167,
+ 168,
+ 169,
+ 170,
+ 171,
+ 172,
+ 173,
+ 174,
+ 79 ,
+ 176,
+ 177,
+ 178,
+ 179,
+ 180,
+ 181,
+ 182,
+ 183,
+ 184,
+ 185,
+ 186,
+ 65 ,
+ 79 ,
+ 189,
+ 174,
+ 79 ,
+ 192,
+ 193,
+ 194,
+ 195,
+ 70 ,
+ 197,
+ 198,
+ 199,
+ 200,
+ 201,
+ 9 ,
+ 65 ,
+ 65 ,
+ 79 ,
+ 206,
+ 206,
+ 45 ,
+ 45 ,
+ 210,
+ 211,
+ 212,
+ 213,
+ 214,
+ 215,
+ 89 ,
+ 89 ,
+ 218,
+ 219,
+ 220,
+ 221,
+ 63 ,
+ 63 ,
+ 224,
+ 225,
+ 226,
+ 227,
+ 228,
+ 65 ,
+ 69 ,
+ 65 ,
+ 69 ,
+ 69 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 73 ,
+ 79 ,
+ 79 ,
+ 63 ,
+ 79 ,
+ 85 ,
+ 85 ,
+ 85 ,
+ 73 ,
+ 0 ,
+ 247,
+ 0 ,
+ 249,
+ 250,
+ 251,
+ 63 ,
+ 253,
+ 254,
+ 0
+};
+
+
+
+// Table that is used to generate the base table for each code page for
+// WIN and MAC.
+ALLOC_CODE(BYTE*) g_prgbPartialBaseTbl[11][2] = {
+ // WIN // MAC
+ {NULL, NULL},
+ {g_rgbPartialBaseTbl1252, g_rgbPartialBaseTbl10000},
+ {g_rgbPartialBaseTbl1250, g_rgbPartialBaseTbl10029},
+ {g_rgbPartialBaseTbl1252, g_rgbPartialBaseTbl10007},
+
+ // MAC: UNDONE: Tables of Turkish and Icelandic is not available on MAC.
+// UNDONE: they are now available. Add them.
+ {g_rgbCodePageWGreek+128, g_rgbCodePageMGreek+128 }, // GREEK
+ {g_rgbCodePageWIceland+128, g_rgbCodePageWIceland+128 }, // ICELANDIC
+ {g_rgbPartialBaseTblWTurkish, g_rgbPartialBaseTblWTurkish }, // TURKISH
+ {g_rgbPartialBaseTblWNorwegian, g_rgbPartialBaseTblMNorwegian }, // NORWEIGIAN
+ {g_rgbPartialBaseTblWEngIreland, g_rgbPartialBaseTblMEngIreland }, // ENGLISH(IRELAND)
+ {g_rgbCodePage1256+128, g_rgbCodePage10004+128}, // Arabic
+ {g_rgbCodePage1255+128, g_rgbCodePage10005+128} // Hebrew
+
+};
+
+
+#define GREEK_CP_Partial 0x4
+#define ICELANDIC_CP_Partial 0x5
+#define TURKISH_CP_Partial 0x6
+#define NORWEIGIAN_CP_Partial 0x7
+#define IRELAND_CP_Partial 0x8
+#define ARABIC_CP_Partial 0x9
+#define HEBREW_CP_Partial 0xa
+
+
+ALLOC_CODE(BYTE) g_rgbExcepTblWin1030[][2] = {
+ {196, 196},
+ {197, 197},
+ {198, 196},
+ {208, 68 },
+ {214, 214},
+ {216, 214},
+ {220, 89 },
+ {228, 196},
+ {229, 197},
+ {230, 196},
+ {240, 68 },
+ {246, 214},
+ {248, 214},
+ {252, 89 },
+ {0, 0}
+};
+
+ALLOC_CODE(BYTE) g_rgbExcepTblMac1030[][2] = {
+ {128, 128},
+ {129, 129},
+ {133, 133},
+ {134, 89},
+ {138, 128},
+ {140, 129},
+ {154, 133},
+ {159, 89 },
+ {174, 128},
+ {175, 133},
+ {190, 128},
+ {191, 133},
+ {0, 0}
+};
+
+
+ALLOC_CODE(BYTE) g_rgbExcepTblWin1034[][2] = {
+ {209, 209},
+ {241, 209},
+ {0, 0}
+};
+
+ALLOC_CODE(BYTE) g_rgbExcepTblMac1034[][2] = {
+ {132, 132},
+ {150, 132},
+ {0, 0}
+};
+
+
+ALLOC_CODE(BYTE) g_rgbExcepTblWin1035[][2] = {
+ {87, 86 },
+ {119, 86 },
+ {196, 196},
+ {197, 197},
+ {208, 68 },
+ {214, 214},
+ {216, 214},
+ {220, 89 },
+ {228, 196},
+ {229, 197},
+ {240, 68 },
+ {246, 214},
+ {248, 214},
+ {252, 89 },
+ {0, 0}
+};
+
+
+ALLOC_CODE(BYTE) g_rgbExcepTblMac1035[][2] = {
+ {87, 86 },
+ {119, 86 },
+ {128, 128},
+ {129, 129},
+ {133, 133},
+ {134, 89 },
+ {138, 128},
+ {140, 129},
+ {154, 133},
+ {159, 89 },
+ {175, 133},
+ {191, 133},
+ {0, 0}
+};
+
+
+
+ALLOC_CODE(BYTE) g_rgbExcepTblWin1038[][2] = {
+ {138, 83 },
+ {142, 90 },
+ {154, 83 },
+ {158, 90 },
+ {200, 67 },
+ {213, 213},
+ {214, 213},
+ {216, 82 },
+ {218, 218},
+ {219, 219},
+ {220, 219},
+ {232, 67 },
+ {245, 213},
+ {246, 213},
+ {248, 82 },
+ {250, 218},
+ {251, 219},
+ {252, 219},
+ {0, 0}
+};
+
+
+ALLOC_CODE(BYTE) g_rgbExcepTblMac1038[][2] = {
+ {133, 133},
+ {134, 134},
+ {137, 67 },
+ {139, 67 },
+ {154, 133},
+ {156, 156},
+ {159, 134},
+ {204, 133},
+ {206, 133},
+ {219, 82 },
+ {222, 82 },
+ {225, 83 },
+ {228, 83 },
+ {235, 90 },
+ {236, 90 },
+ {242, 156},
+ {244, 134},
+ {245, 134},
+ {0, 0}
+};
+
+
+ALLOC_CODE(BYTE) g_rgbExcepTblWin1045[][2] = {
+ {138, 83 },
+ {140, 140},
+ {142, 90 },
+ {143, 143},
+ {154, 83 },
+ {156, 140},
+ {158, 90 },
+ {159, 143},
+ {163, 163},
+ {165, 165},
+ {175, 175},
+ {179, 163},
+ {185, 165},
+ {191, 175},
+ {198, 198},
+ {200, 67 },
+ {202, 202},
+ {209, 209},
+ {211, 211},
+ {216, 82 },
+ {230, 198},
+ {232, 67 },
+ {241, 209},
+ {243, 211},
+ {248, 82 },
+ {0, 0}
+};
+
+ALLOC_CODE(BYTE) g_rgbExcepTblMac1045[][2] = {
+ {132, 132},
+ {136, 132},
+ {137, 67 },
+ {139, 67 },
+ {140, 140},
+ {140, 140},
+ {143, 143},
+ {144, 143},
+ {151, 151},
+ {162, 162},
+ {171, 162},
+ {184, 184},
+ {193, 193},
+ {196, 193},
+ {219, 82 },
+ {222, 82 },
+ {225, 83 },
+ {228, 83 },
+ {229, 229},
+ {230, 229},
+ {235, 90 },
+ {236, 90 },
+ {238, 151},
+ {251, 251},
+ {252, 184},
+ {0, 0}
+};
+
+
+ALLOC_CODE(BYTE) g_rgbExcepTblWin1051[][2] = {
+ {196, 196},
+ {212, 212},
+ {228, 196},
+ {244, 212},
+ {0, 0}
+};
+
+ALLOC_CODE(BYTE) g_rgbExcepTblMac1051[][2] = {
+ {138, 138},
+ {153, 153},
+ {239, 153},
+ {0, 0}
+};
+
+ALLOC_CODE(BYTE) g_rgbExcepTblNew[][2] = {
+ {127, 0},
+ {0, 0}
+};
+
+
+struct LcidToExcep {
+ LCID m_lcid;
+ VOID *pvExcepTbl;
+};
+
+// Table containing pointers to the exception table for both windows and
+// Mac platform.
+ALLOC_CODE(struct LcidToExcep) g_rgLcidToExcepTbl[][2] = {
+ // WIN // MAC
+ { {1030, g_rgbExcepTblWin1030}, {1030, g_rgbExcepTblMac1030}, },
+ { {1044, g_rgbExcepTblWin1030}, {1044, g_rgbExcepTblMac1030}, },
+ { {1035, g_rgbExcepTblWin1035}, {1035, g_rgbExcepTblMac1035}, },
+ { {1053, g_rgbExcepTblWin1035}, {1053, g_rgbExcepTblMac1035}, },
+ { {1034, g_rgbExcepTblWin1034}, {1034, g_rgbExcepTblMac1034}, },
+ { {2058, g_rgbExcepTblWin1034}, {2058, g_rgbExcepTblMac1034}, },
+ { {3082, g_rgbExcepTblWin1034}, {3082, g_rgbExcepTblMac1034}, },
+ { {0x403, g_rgbExcepTblWin1034}, {0x403, g_rgbExcepTblMac1034}, },
+ { {1038, g_rgbExcepTblWin1038}, {1038, g_rgbExcepTblMac1038}, },
+ { {1045, g_rgbExcepTblWin1045}, {1045, g_rgbExcepTblMac1045}, },
+ { {1051, g_rgbExcepTblWin1051}, {1051, g_rgbExcepTblMac1051}, },
+
+ { {1032, g_rgbExcepTblNew}, {1032, g_rgbExcepTblNew}, },
+ { {1039, g_rgbExcepTblNew}, {1039, g_rgbExcepTblNew}, },
+ { {1055, g_rgbExcepTblNew}, {1055, g_rgbExcepTblNew}, },
+ { {2068, g_rgbExcepTblNew}, {2068, g_rgbExcepTblNew}, },
+ { {6153, g_rgbExcepTblNew}, {6153, g_rgbExcepTblNew}, },
+
+ { {0, NULL}, {0, NULL} }
+};
+
+
+
+/***
+*VOID GetInsensitiveCompTbl()
+*Purpose: This function returns a table that can be used for accent and case
+* insensitive comparision.
+*IMPLEMENTATION : There are 2 steps to build the table. First build the base
+* table for the code page that contains the passed in lcid.
+* Then see if there is any exception table for that code page.
+* If there is then fix up the exception cases.
+*
+* From 0 to 96 we have identity (index == the entry).
+* From 97 to 122 we have 65 to 90 (note this is 'a' to 'z' that naps to 'A' to 'Z').
+* From 123 to 127 we again have identity.
+*
+*Inputs:
+* lcid : locale for which that table is required.
+* syskind : the system for which the table is required.
+*
+*Outputs:
+* rgchTbl : This table is initialized. This can be used to do accent and
+* case insensitive comparision.
+*
+*
+****************************************************************************/
+VOID GetInsensitiveCompTbl(LCID lcid, SYSKIND syskind, XCHAR *rgchTbl)
+{
+ BYTE *pbPartialTable;
+ // BYTE *pbrgExcepTable[2];
+ BYTE *pbExcepTable;
+ USHORT usSystem, usCodePage;
+ UINT i;
+
+ DebAssert(rgchTbl != NULL, " Bad Argument ");
+
+ // In retail version, return if we have a bad argument.
+ if (rgchTbl == NULL)
+ return;
+
+
+ // Deternine the partail base table to use to get the generate the
+ // base table.
+ //
+ // Find the index corresponding to the system passed in.
+ usSystem = (syskind == SYS_MAC) ? 1 : 0;
+
+ // Determine the Code page.
+ if (lcid == 0x0419) {
+ usCodePage = 3;
+ }
+ else
+ if (lcid == 0x0408) {
+ usCodePage = GREEK_CP_Partial;
+ }
+ else
+ if (lcid == 0x040f) {
+ usCodePage = ICELANDIC_CP_Partial;
+ }
+ else
+ if (lcid == 0x041f) {
+ usCodePage = TURKISH_CP_Partial;
+ }
+ else
+ if (lcid == 0x0814) {
+ usCodePage = NORWEIGIAN_CP_Partial;
+ }
+ else
+ if (lcid == 0x1809) {
+ usCodePage = IRELAND_CP_Partial;
+ }
+ else
+ if (lcid == 0x0405 ||
+ lcid == 0x040e ||
+ lcid == 0x0415 ||
+ lcid == 0x041b) {
+ usCodePage = 2;
+ } else
+ if (lcid == 0x040d) {
+ usCodePage = HEBREW_CP_Partial;
+ } else
+ if (LOBYTE(lcid) == 0x01 || lcid == 0x0429) {
+ usCodePage = ARABIC_CP_Partial;
+ }
+ else {
+ // this is the default. (US english, 1252)
+ usCodePage = 1;
+ }
+
+
+ // Get the partial base table
+ pbPartialTable = g_prgbPartialBaseTbl[usCodePage][usSystem];
+
+ // Generate the table.
+ //
+ // the first 128 characters is identity (except for 90 to 122)
+ for (i=0; i < 128; rgchTbl[i]=i, i++);
+
+ // fix up the characters between 97 and 122 (i. A-Z maps to a-z)
+ for (i=0; i < 26; rgchTbl[97+i] = 'A'+i, i++);
+
+ // Get the top 128 characters from the partial table
+ for (i=0;
+ i < 128;
+ rgchTbl[128+i] = pbPartialTable[i], i++);
+ // end of FOR loop.
+
+ // Now check if the is any exception for this lcid.
+ i = 0;
+ while ((g_rgLcidToExcepTbl[i][usSystem].m_lcid != 0) &&
+ (g_rgLcidToExcepTbl[i][usSystem].m_lcid != lcid)) {
+ i++;
+ }
+
+ // check if there is an exception table for this lcid
+ if (g_rgLcidToExcepTbl[i][usSystem].m_lcid != 0) {
+ // there is an exception table, hence we need to do some more fix up
+ pbExcepTable = (BYTE *)g_rgLcidToExcepTbl[i][usSystem].pvExcepTbl;
+
+ i = 0;
+ while (*(pbExcepTable + 2*i) != 0) {
+ rgchTbl[ (0x00ff & *(pbExcepTable + 2*i)) ] =
+ (0x00ff & *(pbExcepTable + 2*i + 1));
+ i++;
+ } // while
+
+ } // if
+
+ // DONE !!!
+ return;
+}
+#pragma code_seg()
+
+
diff --git a/private/oleauto/src/typelib/tlibutil.hxx b/private/oleauto/src/typelib/tlibutil.hxx
new file mode 100644
index 000000000..3f12f940e
--- /dev/null
+++ b/private/oleauto/src/typelib/tlibutil.hxx
@@ -0,0 +1,40 @@
+/***
+*clutil.hxx - Class Lib component-wide utility functions.
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* typelib utility functions
+*
+*Revision History:
+* [00] 24-Jan-93 RajivK: Created
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#ifndef TLIBUTIL_HXX_INCLUDED
+#define TLIBUTIL_HXX_INCLUDED
+
+#include "typesx.h"
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szTLIBUTIL_HXX)
+#define SZ_FILE_NAME g_szTLIBUTIL_HXX
+#endif
+
+VOID GetInsensitiveCompTbl(LCID lcid, SYSKIND syskind, XCHAR *rgchTbl);
+
+// This table is not used on MAC. On Mac all characters greater than
+// 128 is mapped to 128
+#if !OE_MAC
+// Define an array for mapping characters > 128 (for WIN)
+//
+extern BYTE g_rgbHashTable[];
+#endif
+
+
+
+#endif // ! TLIBUTIL_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/tls.c b/private/oleauto/src/typelib/tls.c
new file mode 100644
index 000000000..9719d335c
--- /dev/null
+++ b/private/oleauto/src/typelib/tls.c
@@ -0,0 +1,340 @@
+/***
+*tls.c - Thread local storage functions for Macintosh, Win16 platforms
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This mimics Win32 Thread-Local-Storage (TLS) functions on non-Win32
+* platforms.
+* For non-preemptive environments, these functions can be used by DLL
+* components that want to maintain a different copy of a struct for
+* every thread (i.e. client application) that uses the DLL. All of the
+* component's per-thread static data can be kept in this struct.
+* When a DLL is initialized, the DLL's LIBMAIN function calls TlsAlloc
+* to allocate an index of type ITLS.
+* Each time a new thread calls a DLL initialization function, that
+* function allocates a struct to store its per-thread static data,
+* and calls TlsSetValue to save a pointer to that per-thread struct.
+* Whenever a context switch may have occurred, e.g. after a call to
+* GetMessage, Yield, etc., the DLL calls TlsGetValue to re-fetch
+* a pointer to the current thread's static struct.
+* When the DLL is about to be unloaded (WEP), it calls TlsFree.
+*
+* ITLS TlsAlloc(void) - allocate 1 slot for each thread
+* void TlsFree(ITLS) - release slot allocated by TlsAlloc
+* BOOL TlsSetValue(ITLS, LPVOID) - set this thread's value for
+* slot ITLS. Unlike Win4 function, this returns FALSE if
+* there's no room for this thread's set of slots.
+* LPVOID TlsGetValue(ITLS) - get value set by TlsSetValue
+*
+* See the Win32 API for more details.
+*
+*Revision History:
+*
+* 11-Mar-92 tomc: Created.
+*
+*****************************************************************************/
+
+
+#include "typelib.hxx"
+#include "silver.hxx"
+
+#include <string.h>
+#include <memory.h>
+#include "tls.h"
+#include "debug.h"
+
+ // This is currently needed to avoid multiply defines on the Mac link.
+ // It assumes that mob.lib necessarily requires mtypelib.lib to link
+ // (DougF assures me that it does). It should be removed when the
+ // typelib becomes a real DLL on the Mac too. -SatishC.
+
+#if ID_DEBUG
+#undef SZ_FILE_NAME
+ASSERTNAME(g_szTLS_C)
+#define SZ_FILE_NAME g_szTLS_C
+#endif
+
+
+// g_rgthread is an array of THREAD structs with one entry per thread.
+// This limits the number of threads that can access the DLL to
+// ITLS_THREADS.
+//
+// CONSIDER: We undoubtably want to change this to be a dynamically
+// grown list. An array was expedient until we know whether
+// this, or something functionally equivalent, may become a
+// part of OLExxx.dll, and thus, whether or not it is ok
+// to depend on OB memory mgmt primitives.
+//
+// Each THREAD instance has another array of pointers.
+// TlsAlloc allocates a slot in this array of pointers for all THREADs.
+// An element of g_rgthread is allocated the 1st time the thread calls
+// TlsSetValue. The element is released when each pointer in the THREAD
+// has been set to NULL by TlsSetValue.
+//
+
+#if OE_WIN16
+#pragma optimize("q",off)
+#endif //OE_WIN16
+
+// g_rgbSlot remembers which slots have been allocated by TlsAlloc.
+// g_rgbSlot[x] is TRUE if slot x has been allocated by TlsAlloc.
+//
+char g_rgbSlot[ITLS_COMPONENTS];
+THREAD g_rgthread[ITLS_THREADS];
+PTHREAD g_pthreadEnd = NULL; // points to first unused THREAD
+
+// The following are used to cache the pointer to the current thread's
+// THREAD instance, speeding up TlsGetValue.
+//
+TID g_tidThreadCache; // cache current thread id
+PTHREAD g_pthreadCache; // pointer to equivalent THREAD instance
+
+// TlsInit is called once 1st time TlsAlloc is called after DLL is loaded.
+// Initializes collection of CDllThread instances.
+//
+#pragma code_seg(CS_INIT)
+#if !OE_MAC
+// UNDONE: linker bug won't allow cross seg call to static func.
+static
+#endif
+void PASCAL TlsInit()
+{
+ int i;
+
+ for(i = 0; i < (sizeof(g_rgthread)/sizeof(g_rgthread[0])); i++) {
+ g_rgthread[i].tid = TID_EMPTY;
+#if ID_DEBUG
+ // Note that in order to be compatible with Win32 TLS, we do
+ // not initialize rgtls. Instead we use rgfSlotUsed to keep
+ // track of TLS usage.
+ {
+ int j;
+ for( j = 0; j < ITLS_COMPONENTS; j++ )
+ g_rgthread[ i ].rgfSlotUsed[ j ] = 0;
+ }
+#endif
+ }
+
+ g_pthreadEnd = (PTHREAD)(&g_rgthread[ITLS_THREADS]);
+ // points 1 byte beyond end of g_rgthread
+
+ memset(g_rgbSlot, 0, ITLS_COMPONENTS);
+ g_tidThreadCache = TID_EMPTY;
+}
+#pragma code_seg()
+
+
+// Allocate a slot for storing per-thread pointers.
+// Called when a client DLL's LIBMAIN is initializing the DLL.
+//
+#pragma code_seg(CS_INIT)
+ITLS PASCAL EXPORT TlsAlloc()
+{
+ ITLS itls;
+
+ if (g_pthreadEnd == NULL) {
+ // 1st time this has been called.
+ TlsInit();
+ }
+
+ for (itls = 0; itls < ITLS_COMPONENTS; itls++) {
+ if (g_rgbSlot[itls] == 0) {
+ g_rgbSlot[itls] = 1;
+ return itls;
+ }
+ }
+ return ITLS_EMPTY; // no slot available
+}
+#pragma code_seg()
+
+
+// Release a slot allocated by TlsAlloc.
+//
+#pragma code_seg(CS_CORE)
+void PASCAL EXPORT TlsFree(ITLS itls)
+{
+ if (itls != ITLS_EMPTY) {
+ DebAssert(g_pthreadEnd != NULL, "TlsAlloc must be called 1st.");
+ DebAssert(itls < ITLS_COMPONENTS, "TlsFree err1");
+ DebAssert(g_rgbSlot[itls] != 0, "TlsFree err2");
+#if ID_DEBUG
+ {
+ int i;
+ for( i = 0; i < ITLS_THREADS; i++ )
+ g_rgthread[ i ].rgfSlotUsed[ itls ] = 0;
+ }
+#endif
+ g_rgbSlot[itls] = 0;
+ }
+}
+#pragma code_seg()
+
+
+// TlsSetValue stores a pointer for this thread in a slot allocated by
+// TlsAlloc. It isn't called frequently, and thus, need not be super fast.
+// It doesn't depend on or affect the cache maintained by TlsGetValue.
+// This allocates a THREAD entry for this thread if necessary.
+// Unlike the WIN32 version, it return FALSE if it wasn't possible to
+// allocate a THREAD instance.
+// Otherwise, set the itls slot for this thread to pvParam and return TRUE;
+//
+#pragma code_seg(CS_INIT)
+BOOL PASCAL EXPORT TlsSetValue(ITLS itls, LPVOID pvParam)
+{
+ TID tid;
+ PTHREAD pthread, pthreadFree;
+ LPVOID * ppv;
+#if ID_DEBUG
+ PID pidTmp;
+#endif //ID_DEBUG
+
+ tid = GETTID(&tid); // tid = caller's SS
+
+ DebAssert(tid != TID_EMPTY, "");
+ DebAssert(itls < ITLS_COMPONENTS, "TlsSetValue err1");
+ DebAssert(g_rgbSlot[itls] != 0, "TlsSetValue err2");
+
+ // search for thread's tid field
+
+ pthreadFree = NULL;
+ for (pthread = g_rgthread; pthread < g_pthreadEnd; pthread++) {
+ if (pthread->tid == tid) {
+#if ID_DEBUG
+ GETPID(pidTmp);
+ DebAssert(ISEQUALPID(pidTmp, pthread->pid), "bad pid");
+#endif //ID_DEBUG
+ goto SetValue; // found it -- set the value
+ }
+ if ((pthreadFree == NULL) &&
+ (pthread->tid == TID_EMPTY)) {
+ // remember 1st free thread
+ pthreadFree = pthread;
+ }
+ }
+ if (pthreadFree == NULL)
+ return FALSE; // no free slots available for this thread
+
+ // allocate a new THREAD instance
+ pthread = pthreadFree;
+ GETPID(pthread->pid);
+
+SetValue:
+ pthread->rgtls[itls] = pvParam;
+
+ // WARNING: setting of tid must be AFTER the data value is set (directly
+ // above). This is required for the interrupt-driven break check,
+ // which assumes the data is valid if the tid is non-empty.
+ //
+ pthread->tid = tid;
+
+#if ID_DEBUG
+ pthread->rgfSlotUsed[ itls ] = -1;
+#endif
+ if (pvParam != NULL)
+ return TRUE;
+
+ // See if all of this thread's slots are NULL.
+ // If so, release resources occupied by the thread.
+
+ for (ppv = &pthread->rgtls[0];
+ ppv < &pthread->rgtls[ITLS_COMPONENTS];
+ ppv++) {
+ if (*ppv != NULL)
+ return TRUE; // at least one slot is still in use by this thread
+ }
+
+ // This thread's last field is NULL - release the thread, flush cache
+
+ pthread->tid = TID_EMPTY;
+ g_tidThreadCache = TID_EMPTY;
+ return TRUE;
+}
+#pragma code_seg()
+
+
+// Retrieve a value stored by TlsSetValue - must be fast.
+//
+#pragma code_seg(CS_INIT)
+LPVOID PASCAL EXPORT TlsGetValue(ITLS itls)
+{
+ PTHREAD pthread;
+ TID tid;
+#if ID_DEBUG
+ PID pidTmp;
+#endif //ID_DEBUG
+
+ tid = GETTID(&tid); // tid = caller's SS
+
+ DebAssert(tid != TID_EMPTY, "");
+ DebAssert(itls < ITLS_COMPONENTS, "TlsGetValue err1");
+ DebAssert(g_rgbSlot[itls] != 0, "TlsGetValue err2");
+
+ if (g_tidThreadCache == tid) {
+#if ID_DEBUG
+ GETPID(pidTmp);
+ DebAssert(ISEQUALPID(pidTmp, g_pthreadCache->pid), "bad pid");
+#endif //ID_DEBUG
+ return g_pthreadCache->rgtls[itls];
+ }
+
+ // cache doesn't contain desired value
+ // search for thread's tid field
+
+ for (pthread = g_rgthread; pthread < g_pthreadEnd; pthread++) {
+ if (pthread->tid == tid) {
+#if ID_DEBUG
+ GETPID(pidTmp);
+ DebAssert(ISEQUALPID(pidTmp, pthread->pid), "bad pid");
+#endif //ID_DEBUG
+ g_tidThreadCache = tid;
+ g_pthreadCache = pthread;
+ return pthread->rgtls[itls];
+ }
+ }
+
+ // thread not found.
+ // value must be NULL since TlsSetValue hasn't been called.
+ //
+ return NULL;
+}
+#pragma code_seg()
+
+#pragma code_seg(CS_QUERY)
+// Clean out thread data that we know to be obsolete (leftover from a task
+// that UAE'd or didn't cleanup after itself correctly).
+//
+void TlsCleanupDeadTasks()
+{
+ PTHREAD pthread;
+ TID tid;
+ PID pid;
+
+ tid = GETTID(&tid); // tid = caller's SS
+ GETPID(pid); // pid = caller's process id
+
+ DebAssert(tid != TID_EMPTY, "");
+
+ // search for thread's tid field
+
+ for (pthread = g_rgthread; pthread < g_pthreadEnd; pthread++) {
+ // if we find an entry with our own SS, but a different process id,
+ // then it must be a process that has terminated without cleaning up
+ // after itself. So we wipe out it's entry now.
+ if (pthread->tid == tid && !ISEQUALPID(pthread->pid, pid)) {
+
+ // This thread's entry contains obsolete data, since the thread has
+ // terminated, and the memory pointed to by our structures is either
+ // gone, or in use by somebody else.
+
+ // Pretend this thread did TlsSetValue(itls, NULL) on all it's itls's,
+ // to put us back into a stable state.
+ memset (pthread->rgtls, 0, ITLS_COMPONENTS * sizeof(LPVOID));
+ pthread->tid = TID_EMPTY;
+ g_tidThreadCache = TID_EMPTY;
+ break;
+ }
+ }
+}
+#pragma code_seg()
diff --git a/private/oleauto/src/typelib/tls.h b/private/oleauto/src/typelib/tls.h
new file mode 100644
index 000000000..dcaa43efb
--- /dev/null
+++ b/private/oleauto/src/typelib/tls.h
@@ -0,0 +1,175 @@
+/***
+*tls.h - Defines Win16/Mac interface for Thread-Local-Storage functions.
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file defines the interface to functions for Thread-Local-Storage.
+* They allow DLL functions to easily maintain per-app static data.
+* These functions mimic Win32 Thread-Local-Storage (TLS) functions on
+* non-Win32 platforms. For more info, see the Win32 definitions for:
+* TlsAlloc, TlsFree, TlsSetValue, TlsGetValue.
+*
+* For non-preemptive environments, these functions can be used by DLL
+* components that want to maintain a different copy of a struct for
+* every thread (i.e. client application) that uses the DLL. All of the
+* component's per-thread static data can be kept in this struct.
+* When a DLL is initialized, the DLL's LIBMAIN function calls TlsAlloc
+* to allocate an index of type ITLS.
+* Each time a new thread calls a DLL initialization function, that
+* function allocates a struct to store its per-thread static data,
+* and calls TlsSetValue to save a pointer to that per-thread struct.
+* Whenever a context switch may have occurred, e.g. after a call to
+* GetMessage, Yield, etc., the DLL calls TlsGetValue to re-fetch
+* a pointer to the current thread's static struct.
+* When the DLL is about to be unloaded (WEP), it calls TlsFree.
+*
+* ITLS TlsAlloc(void) - allocate 1 slot for each thread
+* void TlsFree(ITLS) - release slot allocated by TlsAlloc
+* BOOL TlsSetValue(ITLS, LPVOID) - set this thread's value for
+* slot ITLS. Unlike Win4 function, this returns FALSE if
+* there's no room for this thread's set of slots.
+* LPVOID TlsGetValue(ITLS) - get value set by TlsSetValue
+*
+* See the Win32 API for more details.
+*
+*
+*****************************************************************************/
+#ifndef TLS_H_INCLUDED
+#define TLS_H_INCLUDED
+
+
+#if OE_WIN32
+ typedef DWORD TID; //Thread Id
+ typedef DWORD ITLS; //index to a thread-local-storage slot.
+ #define TID_EMPTY 0xFFFFFFFF
+ #define ITLS_EMPTY 0xFFFFFFFF
+#else //OE_WIN32
+#if HP_I286
+ typedef WORD TID; //Thread Id - SS register on Win16
+#else //HP_I286
+ typedef DWORD TID; //Thread Id - A5 register on Mac
+#endif //HP_I286
+ typedef WORD ITLS; //index to a thread-local-storage slot.
+#if OE_MAC68K
+ typedef ProcessSerialNumber PID; // process id (from GetCurrentProcess)
+#define ISEQUALPID(a, b) \
+ (a.highLongOfPSN == b.highLongOfPSN && a.lowLongOfPSN == b.lowLongOfPSN)
+#else //OE_MAC68K
+ typedef DWORD PID; //process id (from CoGetCurrentProcess)
+#define ISEQUALPID(a, b) (a == b)
+#endif //OE_MAC68K
+ #define TID_EMPTY 0xFFFF
+ #define ITLS_EMPTY 0xFFFF //impossible ITLS value
+ #define PID_EMPTY 0xFFFFFFFF //impossible PID value
+#endif //OE_WIN32
+
+#if !(OE_MAC && !OE_DLL)
+
+#define ITLS_COMPONENTS 2 // only 2 are used in typelib.dll
+ // Number of per-thread components,
+ // i.e. number of times TlsAlloc can be called.
+#define ITLS_THREADS 50
+
+#else //EI_OLE
+
+#if OE_MAC
+#define ITLS_COMPONENTS 8 // CONSIDER: tune this constant
+#define ITLS_THREADS 1 // Statically linked, cannot have more than 1
+#else //OE_MAC
+#define ITLS_COMPONENTS 8 // CONSIDER: tune this constant
+#define ITLS_THREADS 20
+#endif
+#endif //EI_OLE
+ // Number of threads supported
+
+// One instance of THREAD per thread that calls TlsSetValue(<non-null>)
+typedef struct {
+ TID tid; // thread id
+#if !OE_WIN32
+ PID pid; // process id (from CoGetCurrentProcess)
+#endif //!OE_WIN32
+ LPVOID rgtls[ITLS_COMPONENTS]; // per-thread component pointers
+#if ID_DEBUG
+ CHAR rgfSlotUsed[ ITLS_COMPONENTS ];
+ //Used in debug mode to validate Tls calls.
+#endif
+} THREAD;
+typedef THREAD *PTHREAD;
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#if !OE_WIN32
+ //These functions only need to be defined on non-Win32 platforms
+ ITLS FAR PASCAL EXPORT TlsAlloc(void);
+ void FAR PASCAL EXPORT TlsFree(ITLS itls);
+ LPVOID FAR PASCAL EXPORT TlsGetValue(ITLS itls);
+ BOOL FAR PASCAL EXPORT TlsSetValue(ITLS itls, LPVOID);
+
+ // not in the "offical" TLS API, but we need this to be able to invalidate
+ // entries in our task list for ill-behaved apps.
+ void FAR TlsCleanupDeadTasks(void);
+
+//
+// GETTID, GETPID
+//
+
+#if OE_MAC68K
+
+static const LPLONG pCurrentA5 = (LPLONG)(0x904);
+#define GETTID(x) *pCurrentA5
+
+#define GETPID(dest) (GetCurrentProcess(&dest))
+
+#elif OE_MACPPC
+
+// Note: Mac/PPC has per-process data and only one thread
+#define GETTID(x) ((TID)1)
+#define GETPID(dest) (dest = (PID)1)
+
+#else
+
+#define GETTID(x) (__segment)(x)
+#define GETPID(dest) (dest = CoGetCurrentProcess())
+
+#endif
+
+
+#ifdef __cplusplus
+//TlsCache is useful in non-preemptive environments for caching
+//a particular pointer stored with TlsSetValue for the current thread.
+//
+//Sample usage:
+// //Assume we want to maintain a static instance of X for every thread.
+// ITLS g_itlsPx; //index to per-thread slot allocated by TlsAlloc
+// TID g_tidPxCache; //cache current thread id
+// PEBTHREAD g_pxCache; //pointer to current thread's instance of X
+// :
+// TlsCache(g_itlsPx, (LPVOID *)&g_pxCache, &g_tidPxCache);
+// //update g_pxCache and g_tidPxCache if caller is different
+// //thread than the last time this was called.
+//
+
+inline void TlsCache(ITLS itls, LPVOID *ppvCache, TID * ptidCache)
+{
+ TID tid;
+
+ tid = GETTID(&tid); //tid = caller's SS
+ if (tid != *ptidCache) {
+ //caller's thread is different than *ptidCache - update cache
+ *ppvCache = TlsGetValue(itls);
+ *ptidCache = tid;
+ }
+}
+#endif //__cplusplus
+
+#endif //OE_WIN32
+
+#ifdef __cplusplus
+}
+#endif //__cplusplus
+
+#endif //TLS_H_INCLUDED
diff --git a/private/oleauto/src/typelib/tmpguid.c b/private/oleauto/src/typelib/tmpguid.c
new file mode 100644
index 000000000..f5c091898
--- /dev/null
+++ b/private/oleauto/src/typelib/tmpguid.c
@@ -0,0 +1,104 @@
+/***
+*tmpguid.c
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file is intended for the misc instantiation of guids
+* from other components (Ole2 for example) that are not available
+* for some reason, or that we dont want to pull in from somewhere
+* else (for example, as imported data from a dll that we otherwise
+* don't use).
+*
+* Guids that are part of OB, or that name things internal to OB
+* should be declared in obguid.h, and thereby instantiated by
+* obguid.c
+*
+* This file should probably be called miscguid.c.
+*
+*
+*Revision History:
+*
+* [00] 27-Dec-92 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#include "switches.hxx"
+#include "version.hxx"
+
+#if OE_MAC
+// HACK to make GUID's be defined in a FAR segment w/o changing the OLE
+// header files (works arounds a Wings bug). Define-away 'const' so that
+// they get put into .fardata like they're supposed to.
+#define const
+#endif
+
+#include "silver.hxx"
+
+//OLE uses _MAC to determine if this is a Mac build
+#if OE_MAC
+# define _MAC
+#endif
+
+// initguid.h requires this.
+#if OE_WIN32
+#define INC_OLE2
+#include <ole2.h>
+#else
+#include <compobj.h>
+#endif
+
+// this redefines the DEFINE_GUID() macro to do allocation.
+//
+#include <initguid.h>
+
+
+#if !OE_MACPPC // already defined in dispiid.c for the PPC
+// The following guid is not yet available in the Automation Dll(s).
+//
+DEFINE_GUID(IID_IErrorInfo,
+ 0xC093F1A0L,0x1827,0x101B,0x99,0xA1,0x08,0x00,0x2B,0x2B,0xD1,0x19);
+#endif //OE_MACPPC
+
+// The following Connection Point related GUIDs are not instantiated
+// by any of the Ole2 dlls (yet).
+// These definitions are cut out of ole2ctlid.h, which was picked
+// up from the CDK beta on 11/23/93.
+//
+DEFINE_GUID(IID_IProvideClassInfo,
+ 0xB196B283,0xBAB4,0x101A,0xB6,0x9C,0x00,0xAA,0x00,0x34,0x1D,0x07);
+DEFINE_GUID(IID_IConnectionPointContainer,
+ 0xB196B284,0xBAB4,0x101A,0xB6,0x9C,0x00,0xAA,0x00,0x34,0x1D,0x07);
+DEFINE_GUID(IID_IEnumConnectionPoints,
+ 0xB196B285,0xBAB4,0x101A,0xB6,0x9C,0x00,0xAA,0x00,0x34,0x1D,0x07);
+DEFINE_GUID(IID_IConnectionPoint,
+ 0xB196B286,0xBAB4,0x101A,0xB6,0x9C,0x00,0xAA,0x00,0x34,0x1D,0x07);
+DEFINE_GUID(IID_IEnumConnections,
+ 0xB196B287,0xBAB4,0x101A,0xB6,0x9C,0x00,0xAA,0x00,0x34,0x1D,0x07);
+//
+// Interface IDs for licensing interfaces
+DEFINE_GUID(IID_IClassFactory2,
+ 0xB196B28F,0xBAB4,0x101A,0xB6,0x9C,0x00,0xAA,0x00,0x34,0x1D,0x07);
+
+
+
+// IIDs on PPC & 68k Mac:
+#if OE_MAC
+DEFINE_OLEGUID(IID_ILockBytes, 0x0000000aL, 0, 0);
+DEFINE_OLEGUID(IID_IPersistFile, 0x0000010bL, 0, 0);
+DEFINE_OLEGUID(IID_IStorage, 0x0000000bL, 0, 0);
+#endif
+
+// IIDs on 68k Mac only:
+#if OE_MAC68K
+DEFINE_OLEGUID(IID_IDispatch, 0x00020400, 0, 0);
+DEFINE_OLEGUID(IID_IEnumVARIANT, 0x00020404, 0, 0);
+DEFINE_OLEGUID(IID_IUnknown, 0x00000000, 0, 0);
+DEFINE_OLEGUID(IID_IStream, 0x0000000cL, 0, 0);
+DEFINE_GUID(GUID_NULL, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0);
+#endif
+
+
diff --git a/private/oleauto/src/typelib/typelib.def b/private/oleauto/src/typelib/typelib.def
new file mode 100644
index 000000000..d69ea95bd
--- /dev/null
+++ b/private/oleauto/src/typelib/typelib.def
@@ -0,0 +1,74 @@
+;pull in OE_WIN16, OE_WIN32, and OE_MAC switches
+#include "switches.hxx"
+
+#if OE_WIN32
+LIBRARY TYPLIB32
+#endif
+#if OE_WIN16 || OE_MACPPC
+LIBRARY TYPELIB
+#endif //OE_WIN16
+
+DESCRIPTION 'OLE Automation Type Information Interfaces'
+
+#if !OE_MACPPC
+EXETYPE WINDOWS
+CODE MOVEABLE DISCARDABLE
+#if OE_WIN32
+DATA MULTIPLE MOVEABLE PRELOAD
+#else //OE_WIN32
+DATA SINGLE MOVEABLE PRELOAD
+#endif //OE_WIN32
+
+PROTMODE
+HEAPSIZE 512
+
+SEGMENTS
+ _TEXT PRELOAD
+#if OE_WIN16
+ TlibQuery PRELOAD
+ WEP_TEXT PRELOAD
+ TlibCreate //[bb]this doesn't need to be listed here anymore
+
+#endif
+#endif // !OE_MACPPC
+; Please try to keep the following list in alphabetical order,
+; but retain ordinal values from version to version.
+;
+EXPORTS
+#if OE_MAC
+ CreateTypeLib @1
+ LoadTypeLib @2
+ LoadRegTypeLib @3
+ RegisterTypeLib @4
+ QueryPathOfRegTypeLib @5
+ LHashValOfNameSys @6
+ LoadTypeLibFSp @7
+ RegisterTypeLibFolder @8
+ QueryTypeLibFolder @9
+ IID_ICreateTypeInfo @10
+ IID_ICreateTypeLib @11
+ IID_ITypeComp @12
+ IID_ITypeInfo @13
+ IID_ITypeLib @14
+
+#else
+ CreateTypeLib@12 @2
+ LoadTypeLib@8 @3
+ LoadRegTypeLib@20 @11
+ RegisterTypeLib@12 @10
+ QueryPathOfRegTypeLib@20 @14
+#if OE_WIN16
+ WEP@4 @1 RESIDENTNAME
+#endif
+ LHashValOfNameSys@12 @4
+ _IID_ICreateTypeInfo @5
+ _IID_ICreateTypeLib @6
+ _IID_ITypeComp @7
+ _IID_ITypeInfo @8
+ _IID_ITypeLib @9
+#endif
+
+ ; New API's for OA94
+ OaBuildVersion@0 @15
+
+ ; Highest ordinal in use is @15, next is @16
diff --git a/private/oleauto/src/typelib/typelib.hxx b/private/oleauto/src/typelib/typelib.hxx
new file mode 100644
index 000000000..df638ce2b
--- /dev/null
+++ b/private/oleauto/src/typelib/typelib.hxx
@@ -0,0 +1,336 @@
+/***
+*typelib.hxx
+*
+* Copyright (C) 1990, Microsoft Corporation
+*
+*Purpose:
+* This file defines newNames for the function defined in MAC typelib.
+*
+*
+*Revision History:
+*
+* 29-Mar-93 Rajivk: File created.
+*
+*******************************************************************************/
+
+#ifndef TYPELIB_HXX_INCLUDED
+#define TYPELIB_HXX_INCLUDED
+
+#include "switches.hxx"
+#include "version.hxx"
+
+#if OE_MAC68K
+#if !OE_DLL
+#define OLENAMES_MUNGE_FOR_STATIC
+#include "olenames.h"
+#endif //!OE_DLL
+#endif //EI_OB
+
+#define GenericTypeLibOLE OGTOLE
+#define STL_TYPEINFO OSTL_TI
+#define CDefnTypeComp ODfnTCmp
+#define REC_TYPEINFO OREC_TI
+#define CreateTypeInfo OCreateTI
+#define GetRefTypeInfo OGtRfTI
+#define GetBestLcidMatch OGetBestLcidMatch
+#define g_mempool Og_mempool
+#if ID_DEBUG
+#define GetMemPool OGetMemPool
+#define FreeMemPool OFreeMemPool
+#define MemPoolSize OMemPoolSize
+#endif //ID_DEBUG
+#if OE_MAC
+#define g_rgLcidToExcepTbl Og_rgLcidToExcepTbl
+#define g_rgbExcepTblMac1051 Og_rgbExcepTblMac1051
+#define g_rgbExcepTblWin1051 Og_rgbExcepTblWin1051
+#define g_rgbExcepTblMac1045 Og_rgbExcepTblMac1045
+#define g_rgbExcepTblWin1045 Og_rgbExcepTblWin1045
+#define g_rgbExcepTblMac1038 Og_rgbExcepTblMac1038
+#define g_rgbExcepTblWin1038 Og_rgbExcepTblWin1038
+#define g_rgbExcepTblMac1035 Og_rgbExcepTblMac1035
+#define g_rgbExcepTblWin1035 Og_rgbExcepTblWin1035
+#define g_rgbExcepTblMac1034 Og_rgbExcepTblMac1034
+#define g_rgbExcepTblWin1034 Og_rgbExcepTblWin1034
+#define g_rgbExcepTblMac1030 Og_rgbExcepTblMac1030
+#define g_rgbExcepTblWin1030 Og_rgbExcepTblWin1030
+#define g_prgbPartialBaseTbl Og_prgbPartialBaseTbl
+#define g_rgbPartialBaseTbl10007 Og_rgbPartialBaseTbl10007
+#define g_rgbPartialBaseTbl10029 Og_rgbPartialBaseTbl10029
+#define g_rgbPartialBaseTbl10000 Og_rgbPartialBaseTbl10000
+#define g_rgbPartialBaseTbl1250 Og_rgbPartialBaseTbl1250
+#define g_rgbPartialBaseTbl1252 Og_rgbPartialBaseTbl1252
+
+#define GetInsensitiveCompTbl OGetInsensitiveCompTbl
+#define g_presetlib Og_presetlib
+#define BINDINFO OBINDINFO
+#define IMPTYPE OIMPTYPE
+#define PROPERTY_NODE OPROPERTY_NODE
+#define SHEAPMGR_LIST OSHEAPMGR_LIST
+#define SHEAP_WRAPPER OSHEAP_WRAPPER
+#define VAROFS OVAROFS
+#define VBASEPOS OVBASEPOS
+#define VMETHOFS OVMETHOFS
+#define VMETHPOS OVMETHPOS
+#define PROPERTY_NODE OPROPERTY_NODE
+#define SHEAP_WRAPPER OSHEAP_WRAPPER
+#define YAPAXI OYAPAXI
+#define YAPAXIPAX OYAPAXIPAX
+#define YAXPAX OYAXPAX
+#define PROPERTY_NODE OPROPERTY_NODE
+#define NAME_CACHE ONAME_CACHE
+#define DataMemberHmemberOfOffset ODataMemberHmemberOfOffset
+#define DllFuncHmemberOfOffset ODllFuncHmemberOfOffset
+#define HashOfHgnam OHashOfHgnam
+#define IsDataMember OIsDataMember
+#define IsMatchOfVisibility OIsMatchOfVisibility
+#define IsPropertyGet OIsPropertyGet
+#define IsPropertyLet OIsPropertyLet
+#define IsPropertySet OIsPropertySet
+#define PropkindOfInvokekind OPropkindOfInvokekind
+#define SizeofTdesckind OSizeofTdesckind
+#define XszAddXChar OXszAddXChar
+#define XszCat OXszCat
+#define XszDup OXszDup
+#define XszFind OXszFind
+#define XszFindOneOf OXszFindOneOf
+#define XszLeft OXszLeft
+#define g_fTdataSwap Og_fTdataSwap
+#define XszMid OXszMid
+#define UB_IMPTYPE OUB_IMPTYPE
+#define GetLStrOfSz OGetLStrOfSz
+#define LStrAlloc OLStrAlloc
+#define LStrFree OLStrFree
+#define LStrOfBuf OLStrOfBuf
+#define LStrOfSz OLStrOfSz
+#define LStrSize OLStrSize
+#define OB_SER_TYPE_ENTRY OOB_SER_TYPE_ENTRY
+#define OB_TYPE_ENTRY OOB_TYPE_ENTRY
+#define ELEMPROP OELEMPROP
+#define REFLIB OREFLIB
+#define SER_TYPE_ENTRY OSER_TYPE_ENTRY
+#define TYPE_ENTRY OTYPE_ENTRY
+#define DYN_TYPEROOT ODYN_TYPEROOT
+#define GEN_DTINFO OGEN_DTINFO
+#define COMPILETIME_SEG OCOMPILETIME_SEG
+#define BIND_DESC OBIND_DESC
+#define EXBIND OEXBIND
+#define TYPE_DATA OTYPE_DATA
+#define ENTRYMGR OENTRYMGR
+#define NAMMGR ONAMMGR
+#define DYNTYPEINFO ODYNTYPEINFO
+#define DYN_TYPEMEMBERS ODYN_TYPEMEMBERS
+#define DYN_TYPEBIND ODYN_TYPEBIND
+#define BINDNAME_TABLE OBINDNAME_TABLE
+#define DYN_BINDNAME_TABLE ODYN_BINDNAME_TABLE
+#define IMPMGR OIMPMGR
+#define BLK_MGR OBLK_MGR
+#define GENPROJ_TYPEBIND OGENPROJ_TYPEBIND
+#define DEFN_TYPEBIND ODEFN_TYPEBIND
+#define GENPROJ_BINDNAME_TABLE OGENPROJ_BINDNAME_TABLE
+#define _Mem O_Mem
+#define STREAM OSTREAM
+#define SHEAP_MGR OSHEAP_MGR
+#define BLK_DESC OBLK_DESC
+#define DOCFILE_STREAM ODOCFILE_STREAM
+#define IMPMGR OIMPMGR
+#define IMPMGR OIMPMGR
+#define IMPMGR OIMPMGR
+#define DEFN ODEFN
+#define MEMBER_DEFN OMEMBER_DEFN
+#define VAR_DEFN OVAR_DEFN
+#define MBR_VAR_DEFN OMBR_VAR_DEFN
+#define RECTYPE_DEFN ORECTYPE_DEFN
+#define TYPE_DEFN OTYPE_DEFN
+#define FUNC_DEFN OFUNC_DEFN
+#define VIRTUAL_FUNC_DEFN OVIRTUAL_FUNC_DEFN
+#define FUNC_TYPE_DEFN OFUNC_TYPE_DEFN
+#define PARAM_DEFN OPARAM_DEFN
+#define DLLENTRY_DEFN ODLLENTRY_DEFN
+
+#define OpenTypeLibKey OOpenTypeLibKey
+#define CloseTypeLibKey OCloseTypeLibKey
+#define GetLibIdKind OGetLibIdKind
+
+#undef GETSCODE
+#define GETSCODE OGETSCODE
+#define REPORTRESULT OREPORTRESULT
+#define CkVt OCkVt
+#define g_pOBZone Og_pOBZone
+#define HsysAlloc OHsysAlloc
+#define HsysReallocHsys OHsysReallocHsys
+#define PvLockHsys OPvLockHsys
+#define PvDerefHsys OPvDerefHsys
+#define FreeHsys OFreeHsys
+#define UnlockHsys OUnlockHsys
+#define BchSizeBlockHsys OBchSizeBlockHsys
+#define SheapTerm OSheapTerm
+#define HbpAllocHh OHbpAllocHh
+#define HbpReallocHhHbp OHbpReallocHhHbp
+#define FreeHhHbp OFreeHhHbp
+#define BcSizeBlockHhHbp OBcSizeBlockHhHbp
+#define BcHeapCompactHh OBcHeapCompactHh
+#define PvDerefHhHbp OPvDerefHhHbp
+#define PvLockHhHbp OPvLockHhHbp
+#define UnlockHhHbp OUnlockHhHbp
+#define IsSheapEmpty OIsSheapEmpty
+#define rtReallocMem OrtReallocMem
+#define rtFreeMem OrtFreeMem
+#define rtSizeMem OrtSizeMem
+#define rtDerefMem OrtDerefMem
+#define rtLockMem OrtLockMem
+#define rtUnlockMem OrtUnlockMem
+#define rtTermMem OrtTermMem
+#define GetNewIndex OGetNewIndex
+#define CbSizeArrayDesc OCbSizeArrayDesc
+#define rtArrayInit OAD_Init
+#define MakeRelativePath OMakeRelativePath
+#define MakeAbsolutePath OMakeAbsolutePath
+#define SplitGuidLibId OSplitGuidLibId
+#define GetPathOfLibId OGetPathOfLibId
+#define MakeAbsoluteLibId OMakeAbsoluteLibId
+#define DBM_cbSizeHandleTableInitial ODBM_cbSizeHandleTableInitial
+#define DYN_BLK_MGR ODYN_BLK_MGR
+#define IndexOfParam OIndexOfParam
+#define g_fHeapChk Og_fHeapChk
+#define g_fSheapShakingOn Og_fSheapShakingOn
+#define g_fValidSheapmgrList Og_fValidSheapmgrList
+#define g_itlsSheapmgr Og_itlsSheapmgr
+#define rtDim OrtDim
+#define rtAllocMem OrtAllocMem
+#define SheapInit OSheapInit
+#define rtSheapMgrInit OrtSheapMgrInit
+#define DebPrintf ODebPrintf
+#define DebAssertFailed ODebAssertFailed
+#define DebHalted ODebHalted
+#if ID_DEBUG
+#define DebExamineHeap ODebExamineHeap
+#endif //ID_DEBUG
+#define DebAddInstTable_ ODebAddInstTable_
+#define DebRemInstTable_ ODebRemInstTable_
+#define DebErrorNow_ ODebErrorNow_
+#define LoadRegTypeLibOfSzGuid OLoadRegTypeLibOfSzGuid
+#define GetRegInfoForTypeLibOfSzGuid OGetRegInfoForTypeLibOfSzGuid
+#define cbSizeBitmap OcbSizeBitmap
+#define cbSizeInitial OcbSizeInitial
+#define g_cbHeapAllocd Og_cbHeapAllocd
+#define g_cbHeapAllocdMax Og_cbHeapAllocdMax
+#define MemAlloc OMemAlloc
+#define MemZalloc OMemZalloc
+#define MemRealloc OMemRealloc
+#define MemFree OMemFree
+#define MemSize OMemSize
+#define CreateXsz OCreateXsz
+#define ErrCopy OErrCopy
+#define SwapShortArray OSwapShortArray
+#define SwapLongArray OSwapLongArray
+#define SwapStruct OSwapStruct
+#define SwapStructArray OSwapStructArray
+#define g_rgusErrorMap Og_rgusErrorMap
+
+#if 0
+#define OleerrOfTiperr OOleerrOfTiperr
+#define TiperrOfOleerr OTiperrOfOleerr
+#define HresultOfTiperr OHresultOfTiperr
+#define TiperrOfHresult OTiperrOfHresult
+#define TiperrToHresult OTiperrToHresult
+#define HresultToTiperr OHresultToTiperr
+#define LookupHresultOfTiperr OLookupHresultOfTiperr
+#define LookupTiperrOfHresult OLookupTiperrOfHresult
+#endif //0
+
+#define IsTypeBasicIntrinsic OIsTypeBasicIntrinsic
+#define OffsetOfHmember OOffsetOfHmember
+#define ReleaseLibrary OReleaseLibrary
+#define ReleaseDllEntries OReleaseDllEntries
+#define g_rgrgcbSizeType Og_rgrgcbSizeType
+#define g_rgrgcbAlignment Og_rgrgcbAlignment
+#define VtValidInVariant OVtValidInVariant
+#define VtValidInVariantArg OVtValidInVariantArg
+#define IsIntegerType OIsIntegerType
+#define ReadTextLine OIsIntegerType
+#define WriteTextString OWriteTextString
+#define WriteTextULong OWriteTextULong
+#define WriteTextSpaces OWriteTextSpaces
+#define GetTimeStamp OGetTimeStamp
+#define LibIdFromDocItem OLibIdFromDocItem
+#define LibIdFromPath OLibIdFromPath
+#define SzLibIdLocalTypeIdOfTypeId OSzLibIdLocalTypeIdOfTypeId
+#define SzTypeIdHmemberOfFunctionId OSzTypeIdHmemberOfFunctionId
+#define SplitLocalTypeId OSplitLocalTypeId
+#define MakeEmbeddedTypeId OMakeEmbeddedTypeId
+#define IsTypeMembersEqual OIsTypeMembersEqual
+#define IsSimpleType OIsSimpleType
+#define GetDllEntryOfDynInfo OGetDllEntryOfDynInfo
+#define GetDllEntryOfDataInfo OGetDllEntryOfDataInfo
+#define HashSz OHashSz
+#define HashSzTerm OHashSzTerm
+#define Countd OCountd
+#define RegisterErrorOfHdefn ORegisterErrorOfHdefn
+#define GetLStrOfHChunk OGetLStrOfHChunk
+#define GetLStrOfHsz OGetLStrOfHsz
+#define GetExecutingProject OGetExecutingProject
+#define RoundDownPower2 ORoundDownPower2
+#define GetFunctionIdOfExbind OGetFunctionIdOfExbind
+#define CompareUDTs OCompareUDTs
+#define CompareHimptypes OCompareHimptypes
+#define ConvertString OConvertString
+#define GetRegLibOfLibId OGetRegLibOfLibId
+#define GetTypelibOfLibId OGetTypelibOfLibId
+#define DebShowState ODebShowState
+#define TypeDescOfTypeDefn OTypeDescOfTypeDefn
+#define BstrOfHlnam OBstrOfHlnam
+#define GetTypeKindOfITypeInfo OGetTypeKindOfITypeInfo
+#define InitTypeDesc OInitTypeDesc
+#define InitIdlDesc OInitIdlDesc
+#define InitElemDesc OInitElemDesc
+#define InitVarDesc OInitVarDesc
+#define InitFuncDesc OInitFuncDesc
+#define ClearTypeDesc OClearTypeDesc
+#define ClearIdlDesc OClearIdlDesc
+#define ClearArrayDesc OClearArrayDesc
+#define ClearElemDesc OClearElemDesc
+#define FreeVarDesc OFreeVarDesc
+#define FreeFuncDesc OFreeFuncDesc
+#define FreeTypeDesc OFreeTypeDesc
+#define FreeArrayDesc OFreeArrayDesc
+#define CopyArrayDesc OCopyArrayDesc
+#define CopyTypeDesc OCopyTypeDesc
+#define GetLibIdOfRegLib OGetLibIdOfRegLib
+#define GetLibIdOfTypeLib OGetLibIdOfTypeLib
+#define GetTypeInfoOfTypeId OGetTypeInfoOfTypeId
+#define StringFromGuid OStringFromGuid
+#define GetRegInfoForTypeLib OGetRegInfoForTypeLib
+#define BM_cbSizeBitmap OBM_cbSizeBitmap
+#define BM_cbSizeInitial OBM_cbSizeInitial
+#define VerifyLcid OVerifyLcid
+#define IsEuroLang OIsEuroLang
+#define StrGetNewLcid OStrGetNewLcid
+#define LcStrEqi OLcStrEqi
+#define CopyBstrAInternal OCopyBstrAInternal
+#define QuickSortIndex OQuickSortIndex
+#define SwapElementIndex OSwapElementIndex
+#define MacFileSearch OMacFileSearch
+#define GetPathFromFSSpec OGetPathFromFSSpec
+#define GetFSSpecOfAliasPath OGetFSSpecOfAliasPath
+#define GetPathFromAlias OGetPathFromAlias
+#define GetAliasFromPath OGetAliasFromPath
+#define GetRegisteredPath OGetRegisteredPath
+
+#if !OE_MACPPC
+#define CLSID_GenericTypeLibOLE OCLSID_GenericTypeLibOLE
+#endif
+
+#define IID_TYPEINFO OIID_TYPEINFO
+#define IID_DYNTYPEINFO OIID_DYNTYPEINFO
+#define IID_CDefnTypeComp OIID_CDefnTypeComp
+#define IID_TYPELIB_GEN_DTINFO OIID_TYPELIB_GEN_DTINFO
+#define GetPathEnd OGetPathEnd
+#define IsolateFilename OIsolateFilename
+#define g_rgcbAlignment Og_rgcbAlignment
+#define IsFilenameEqual OIsFilenameEqual
+
+#endif // OE_MAC
+
+
+
+#endif // !TYPELIB_HXX_INCLUDED
diff --git a/private/oleauto/src/typelib/typelib.rc b/private/oleauto/src/typelib/typelib.rc
new file mode 100644
index 000000000..a8122fe51
--- /dev/null
+++ b/private/oleauto/src/typelib/typelib.rc
@@ -0,0 +1,131 @@
+/***
+*typelib.rc - Resource file for typelib.DLL
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file in the resource file for typelib.DLL that is compiled and
+* added to the file. String resources are included in this file
+* via an include statement, since these are automatically generated.
+*
+*Revision History:
+*
+* [01] 24-Feb-93 dougf: Added version information.
+* [00] 04-Jan-93 ilanc: Created --
+*
+*****************************************************************************/
+
+// This includes WINDOWS.H, and all the OB switches, like ID_DEBUG, etc.
+#include "obwin.hxx"
+#include <ver.h>
+
+#include "verstamp.h"
+
+#ifndef OLEMINORVERS
+// win16 typelib.dll for Daytona will require a special build. Oh well.
+#define OLEMINORVERS 02 // assume OLE 2.02
+#endif //!OLEMINORVERS
+
+// for OLE, we want the major version # to be 2
+#undef rmj
+#define rmj 2
+#undef rmm
+#define rmm OLEMINORVERS // want version # to be 2.OLEMINORVERS.xxxx
+// keep 'rup' the same as OB's version number for simplicity
+
+// WARNING: Similar code exists in tlibutil.cxx in the implementation of
+// WARNING: OaBuildVersion -- keep the two versions in ssync!
+
+/* Define the version string with more preprocessor magic */
+#define STRING(x) #x
+#define VERSTRINGX(maj,min,rev) STRING(maj ## . ## min ## . ## rev ## \0)
+#define VERSTRING VERSTRINGX(rmj,rmm,rup)
+
+/* Version information */
+VS_VERSION_INFO VERSIONINFO
+//FILEVERSION rmj,rmm,rup,0
+//PRODUCTVERSION rmj,rmm,rup,0
+
+#if 0
+
+// WARNING: Similar code exists in tlibutil.cxx in the implementation of
+// WARNING: OaBuildVersion -- keep the two versions in ssync!
+
+// Version 2.01.0100.14 (non-dbcs enabled) was shipped with the OLE 2.01 CD
+// Version 2.01.0100.15 (non-dbcs enabled) is to be shipped with Excel 5.0
+// Version 2.01.0100.35 (dbcs enabled) was shipped with Excel 5.0J
+FILEVERSION 2,rmm,0100,0
+PRODUCTVERSION 2,rmm,0100,0
+#else //0
+
+// WARNING: Similar code exists in tlibutil.cxx in the implementation of
+// WARNING: OaBuildVersion -- keep the two versions in ssync!
+
+// Use VBA's verstamp.h to get the file versions for now.
+FILEVERSION 2,rmm,rup,01
+PRODUCTVERSION 2,rmm,rup,01
+#endif //0
+FILEFLAGSMASK VS_FFI_FILEFLAGSMASK
+
+#if 0
+#define BETAFLAG VS_FF_PRERELEASE
+#else //1
+#define BETAFLAG 0L
+#endif //1
+
+#if ID_DEBUG
+FILEFLAGS VS_FF_DEBUG | BETAFLAG
+#else // !ID_DEBUG
+FILEFLAGS BETAFLAG
+#endif // !ID_DEBUG
+
+#if (OLEMINORVERS == 02)
+// re-distributable 16-bit DLL
+FILEOS VOS_DOS_WINDOWS16
+#else
+FILEOS VOS_DOS_WINDOWS32
+// non-re-distributable 16-bit DLL (shipped with the OS)
+#endif
+
+FILETYPE VFT_DLL
+FILESUBTYPE 0
+
+BEGIN
+ BLOCK "StringFileInfo"
+ BEGIN
+ BLOCK "040904E4"
+ BEGIN
+#if (OLEMINORVERS == 02)
+// re-distributable 16-bit DLL
+ VALUE "CompanyName", "Microsoft Corporation\0"
+ VALUE "FileDescription", "OLE Automation Type Information Interfaces\0"
+ VALUE "FileVersion", "2.02\0"
+ VALUE "InternalName", "TYPELIB.DLL\0"
+ VALUE "LegalCopyright", "Copyright \251 Microsoft Corp. 1993-1995\0"
+ VALUE "LegalTrademarks", "Microsoft\256 is a registered trademark of Microsoft Corporation. Windows(TM) is a trademark of Microsoft Corporation.\0"
+ VALUE "ProductName", "Microsoft OLE 2.02 for Windows\0"
+ VALUE "ProductVersion", "2.02\0"
+ VALUE "Comments", "Windows OLE DLLs\0"
+#else
+// non-re-distributable 16-bit DLL (shipped with the OS)
+ VALUE "CompanyName", "Microsoft Corporation\0"
+ VALUE "FileDescription", "OLE 2.1 16/32 Interoperability Library\0"
+ VALUE "FileVersion", "2.1\0"
+ VALUE "InternalName", "TYPELIB.DLL\0"
+ VALUE "LegalCopyright", "Copyright \251 Microsoft Corp. 1993-1995\0"
+ VALUE "LegalTrademarks", "Microsoft\256 is a registered trademark of Microsoft Corporation. Windows(TM) is a trademark of Microsoft Corporation.\0"
+ VALUE "ProductName", "Microsoft OLE 2.1 16/32 Interoperability for Windows NT\0"
+ VALUE "ProductVersion", "2.1\0"
+ VALUE "Comments", "Windows NT OLE 16/32 Interoperability DLLs\0"
+#endif
+ END
+
+ END
+
+ BLOCK "VarFileInfo"
+ BEGIN
+ VALUE "Translation", 0x409, 1252
+ END
+END
+
diff --git a/private/oleauto/src/typelib/types.h b/private/oleauto/src/typelib/types.h
new file mode 100644
index 000000000..4cf71d516
--- /dev/null
+++ b/private/oleauto/src/typelib/types.h
@@ -0,0 +1,342 @@
+/***
+*types.h - Common types used by Silver
+*
+* Copyright (C) 1990, Microsoft Corporation
+*
+*Purpose:
+* This include file defines the basic types used by Silver, and the basic
+* constants. The file is designed to be both C and C++ compatible.
+*
+* Note that types depended upon by externally-released include files
+* should be defined in typesx.h. types.h just defines types referenced
+* by internal source files.
+*
+* Note that this file is included before the compile switches, so
+* it should not contain any conditional compilations.
+*
+*Revision History:
+*
+* 15-AUG-90 petergo: File created.
+* 05-Feb-91 ilanc: Added VOID (wow!!!!)
+* 05-Mar-91 petergo: removed INTRINSIC_KIND, now TDKIND in cltypes.hxx
+* 07-Mar-91 petergo: changed WCHAR to a normal character due
+* to AFX limitations/bugs. Add HCHUNK, HCHUNK_Nil.
+* 12-Mar-91 petergo: re-changed WCHAR; AFX bug fixed.
+* 30-May-91 alanc: use windows type names
+* 06-Jun-91 ilanc: Undef stuff we typedef or redefine.
+* 14-Jun-91 petergo: Added Unicode XCHAR/XSZ
+* 25-Jun-91 petergo: Fix WINDOWS.H handling of WORD.
+* 11-Nov-91 satishc: Added BASIC_TRUE and BASIC_FALSE constants.
+* 15-Nov-91 satishc: Added SINGLE and DOUBLE types
+* 14-Apr-92 martinc: defined BOOL as short for OE_MAC (as in WLM)
+* 01-Jun-92 tomc: moved types depended upon by externally-released
+* headers to typesx.h. types.h defines types used by
+* internal source files.
+* 17-Mar-93 w-jeffc: moved defns of PASCAL, CDECL, etc from typesx.h
+* 23-Mar-93 w-jeffc: added EBCALL
+* 11-Apr-93 kazusy: added DBCS stuff.
+* 30-Apr-93 w-jeffc: added sBOOL
+* 04-Apr-94 jeffrob: Mac/PowerPC support
+*
+*Implementation Notes:
+*
+* In order to coexist peacefully, we must follow the following rules
+* for #include order:
+*
+* 1. First must come all non-Silver #includes
+* 2. Then must come silver.hxx
+* 3. Then comes the Silver include files (in any order)
+*
+* In order to promote 16/32 bit portability, two versions of each
+* data type are defined. The type name without an 's' prefix denotes
+* the efficient version of the type, typically used for locals, formals
+* and return values. The type name with an 's' prefix denotes the
+* short version of the type, typically used as member variables.
+* This applies only to new types, not BOOL, USHORT, etc.
+*
+*******************************************************************************/
+
+#ifndef TYPES_HXX_INCLUDED
+#define TYPES_HXX_INCLUDED
+
+#include "switches.hxx"
+#include "version.hxx"
+
+// OS2DEF.h typedef's BOOL to be unsigned short and we want it to be int.
+// We use #define to textually replace BOOL definitions to int when
+// OS2DEF.h is included. This must be defined before typesx.h is included.
+#ifdef OS2_INCLUDED
+#define BOOL int
+#endif
+
+// do this to pickup up the same definition as used in typesx.h
+#undef FAR
+#define FAR EBFAR
+
+//
+// internal definitions
+//
+
+#if OE_MAC68K
+
+ #define UNALIGNED
+
+#ifdef PASCAL
+ #undef PASCAL
+#endif
+
+ #define PASCAL
+
+ #define CDECL _cdecl
+ #pragma message("CDECL defined to be _cdecl")
+
+ #define EXPORT
+ #define HUGE
+
+ #define ENCALL CDECL
+ #define EXMCALL CDECL
+ #define RTCALL _pascal
+ #define ENTMPLT _pascal
+
+#endif // OE_MAC68K
+
+
+#if OE_MACPPC
+
+ #define UNALIGNED
+
+#ifndef PASCAL
+ #define PASCAL _stdcall
+#endif
+
+#ifndef CDECL
+ #define CDECL _cdecl
+ #pragma message("CDECL defined to be _cdecl")
+#endif
+
+ #define EXPORT
+ #define HUGE
+
+ #define ENCALL _stdcall
+ #define EXMCALL _stdcall
+ #define RTCALL _stdcall
+ #define ENTMPLT _stdcall
+
+#endif // OE_MACPPC
+
+
+#if OE_WIN32
+#ifndef PASCAL
+ #define PASCAL __stdcall
+#endif
+
+#ifndef CDECL
+ #define CDECL __cdecl
+#endif
+
+#ifndef HUGE
+ #define HUGE
+#endif
+
+#ifndef EXPORT
+ #define EXPORT _export
+#endif
+
+#ifndef CALLBACK
+ #define CALLBACK __stdcall
+#endif
+
+ #define ENCALL __stdcall
+ #define EXMCALL __stdcall
+ #define RTCALL __stdcall
+ #define ENTMPLT __stdcall
+
+#ifdef _H2INC
+ // The version we have only understands 1 underscore on the following:
+ #define __stdcall _stdcall
+ #define __cdecl _cdecl
+#endif
+
+#endif // OE_WIN32
+
+
+#if OE_WIN16
+
+ #define UNALIGNED
+
+#ifndef PASCAL
+ #define PASCAL _pascal
+#endif
+
+#ifndef CDECL
+ #define CDECL _cdecl
+#endif
+
+#ifndef HUGE
+ #define HUGE _huge
+#endif
+
+#ifndef EXPORT
+ # define EXPORT _export
+#endif
+
+#ifndef CALLBACK
+ # define CALLBACK FAR PASCAL
+#endif
+
+ #define ENCALL PASCAL
+ #define EXMCALL CDECL
+ #define RTCALL PASCAL
+ #define ENTMPLT PASCAL
+
+#endif
+
+#include "typesx.h"
+
+
+typedef LPVOID * LPLPVOID;
+
+// platform dependent type
+
+typedef float SINGLE; // sng
+typedef double DOUBLE; // dbl
+
+// Synonyms included for compatability with existing code
+//typedef WORD USHORT; // u
+//typedef DWORD ULONG; // ul
+#if OE_WIN32
+typedef char * SZ; // sz
+typedef const char * SZ_CONST; // sz
+#else
+typedef char FAR * SZ; // sz
+typedef const char FAR * SZ_CONST; // sz
+#endif
+
+// Type which is enough size to keep a character.
+typedef unsigned short ACHAR;
+
+// Extended char and string types for Unicode
+#if FV_UNICODE
+typedef unsigned short XCHAR;
+#else // !FV_UNICODE
+typedef char XCHAR;
+#endif //!FV_UNICODE
+#if OE_WIN32
+typedef XCHAR * XSZ;
+typedef const XCHAR * XSZ_CONST;
+#else
+typedef XCHAR FAR * XSZ;
+typedef const XCHAR FAR * XSZ_CONST;
+#endif
+
+typedef unsigned short WCHAR;
+
+typedef XSZ LPSTR;
+typedef XSZ_CONST LPSTR_CONST;
+
+
+/* Fundamental types of Silver. */
+typedef UINT STRID; /* string id; hungarian = strid */
+typedef UINT ERR; /* an error code */
+typedef UINT HCHUNK; /* a memory chunk */
+typedef ULONG HCHUNK32; /* a 32bit memory chunk */
+
+typedef USHORT sSTRID;
+typedef USHORT sERR;
+typedef USHORT sHCHUNK;
+typedef USHORT sTIPERROR;
+typedef USHORT sEBERR;
+typedef USHORT sBOOL;
+typedef ULONG sHCHUNK32;
+
+/* constants that go with these fundemental types */
+#define HCHUNK_Nil (0xFFFF)
+#define HCHUNK32_Nil (0xFFFFFFFF)
+
+// ENUMPAD is used to pad enums in a structure when a
+// 16-bit compiler is used for 32-bit code (hxxtoinc on Mac).
+#ifndef ID_INT_IS_LONG
+#define ENUMPAD(x) // don't pad enums to Long
+#endif
+
+/* By default everything is far. If you want near stuff on a Intel 16-bit
+ * processor, then the following are used.
+ */
+#if HP_16BIT
+
+#define NEARCODE near
+#define NEARDATA near
+
+#else /* !HP_16BITS */
+
+#define NEARCODE
+#define NEARDATA
+
+#endif /* !HP_16BITS */
+
+#if EI_VBARUN_VB && HP_16BIT
+ #define FARDATA_EXE far
+#else
+ #define FARDATA_EXE
+#endif
+
+
+#include "segnames.h"
+
+
+/* The BASIC boolean constants. Only BASIC_TRUE is different, but I added
+ BASIC_FALSE for uniformity */
+
+#define BASIC_TRUE -1
+
+#define BASIC_FALSE 0
+
+
+#if OE_MAC
+#define huge
+#define _far
+#endif
+
+/* This should be identical to the definition of HOSTCALLBACK in typesx.h,
+ * except that the EXPORT keyword is removed.
+ */
+#undef HOSTCALLBACK
+#undef EBAPI
+#undef EBCALL
+
+#if OE_MAC68K
+ #define HOSTCALLBACK _cdecl
+ #define EBCALL _pascal
+ #define EBAPI _cdecl
+
+#elif OE_MACPPC
+ #define HOSTCALLBACK
+ #define EBCALL
+ #define EBAPI
+
+#elif OE_WIN16
+ #define HOSTCALLBACK _far _cdecl
+ #define EBCALL _pascal
+ #define EBAPI _far _pascal _export
+
+#elif OE_WIN32
+ #define HOSTCALLBACK __stdcall
+ #define EBCALL __stdcall
+ #define EBAPI __stdcall
+
+#endif // OE_WIN32
+
+
+#ifndef _INC_WINDOWS
+ typedef DWORD COLORREF;
+#endif
+
+// this defines a macro which on Win32 builds gives UNICODE string literals
+// and character literals, but on Win16 and Mac, gives ANSI literals
+#if OE_WIN32
+#define WIDE(x) L##x
+#else //!OE_WIN32
+#define WIDE(x) x
+#endif //!OE_WIN32
+
+#endif /* !TYPES_HXX_INCLUDED */
diff --git a/private/oleauto/src/typelib/typesx.h b/private/oleauto/src/typelib/typesx.h
new file mode 100644
index 000000000..1f19a0d70
--- /dev/null
+++ b/private/oleauto/src/typelib/typesx.h
@@ -0,0 +1,190 @@
+/***
+*typesx.h - Public common types used by Silver
+*
+* Copyright (C) 1992, Microsoft Corporation
+*
+*Purpose:
+* This include file defines the basic types used by Silver,
+* that are referenced by header files that are released to
+* other groups.
+* The file is designed to be both C and C++ compatible.
+*
+* It depends on the switches documented in switches.h
+*
+*Revision History:
+*
+* 29-Apr-92 tomc: File created.
+* 17-Mar-93 w-jeffc: removed all references to PASCAL, FAR, CDECL, etc
+* 23-Mar-93 w-jeffc: added EBCALL
+*
+*******************************************************************************/
+
+#ifndef TYPESX_H_INCLUDED
+#define TYPESX_H_INCLUDED
+
+#if OE_WIN16
+ #define EBFAR _far
+#else
+ #define EBFAR
+#endif
+
+// Host* function calling convention
+#undef HOSTCALLBACK
+#undef EBAPI
+#undef EBLIBAPI
+#undef EBCALL
+
+
+#if OE_MAC68K
+ #define HOSTCALLBACK _cdecl
+ #define EBCALL _pascal
+ #define EBAPI _cdecl
+ #define EBLIBAPI _cdecl
+
+#elif OE_MACPPC
+ #define HOSTCALLBACK
+ #define EBCALL
+ #define EBAPI
+ #define EBLIBAPI
+
+#elif OE_WIN16
+ #define HOSTCALLBACK _far _cdecl _export
+ #define EBCALL _pascal _export
+ #define EBAPI _far _pascal
+ #define EBLIBAPI _cdecl
+
+#elif OE_WIN32
+ #define HOSTCALLBACK __stdcall
+ #define EBCALL __stdcall
+ #define EBAPI __stdcall
+ #define EBLIBAPI __stdcall
+
+#endif // OE_WIN32
+
+
+// INT is needed due to hxxtoinc dependency inside windows decl section.
+// UINT is needed for 16-bit tools to build 32-bit targets.
+#ifndef ID_INT_IS_LONG
+#ifndef _H2INC
+ #undef INT
+ typedef int INT; // n
+#else
+#ifndef INT
+ #define INT int // INT is reserved in MASM
+#endif
+#if !HP_16BIT
+ // NOTE!: the following definitions are here to allow a 16bit
+ // hosted h2inc to generate correct offsets for a 32bit target.
+ #define ID_INT_IS_LONG
+ typedef unsigned long UINT; // un
+#endif
+#endif
+#endif
+
+#if OE_WIN32
+# ifdef _WINDOWS_
+# define _INC_WINDOWS
+# endif
+#endif
+
+#ifndef _INC_WINDOWS
+ // Standard types defined by windows.
+
+ #define VOID void
+
+ typedef VOID EBFAR * LPVOID;
+ typedef int EBFAR * LPINT; // pn
+ typedef long LONG; // l
+ typedef LONG EBFAR * LPLONG; // ul
+ typedef unsigned char BYTE; // b
+ typedef BYTE EBFAR * LPBYTE; // pb
+ typedef char EBFAR * LPSTR; // sz
+ typedef const char EBFAR * LPCSTR; // sz
+ typedef unsigned short WORD; // w
+ typedef WORD EBFAR * LPWORD; // pw
+ typedef unsigned long DWORD; // dw
+ typedef DWORD EBFAR * LPDWORD; // pdw
+#ifndef ID_INT_IS_LONG
+ typedef unsigned int UINT; // un
+#endif
+
+#if OE_WIN32
+ typedef VOID * HANDLE; // h
+#endif
+
+#if OE_WIN16
+ typedef UINT HANDLE; // h
+#endif
+
+#if OE_WIN
+ typedef HANDLE HDC; // hdc
+#endif
+
+#if OE_WIN
+ typedef HANDLE HCURSOR; // hcrs
+ typedef HANDLE HFONT; // hfont
+ typedef HANDLE HBRUSH; // hbr
+ typedef HANDLE HINSTANCE; // hInst
+ typedef UINT WPARAM; // wparam
+ typedef long LPARAM; // lparam
+#endif
+
+
+#ifndef BOOL
+ // WLM wants this signed, hxxtoinc cannot use 'int'.
+ typedef INT BOOL;
+#endif
+
+#if OE_WIN16
+ typedef unsigned int HWND;
+#endif
+
+#if OE_WIN32
+ typedef HANDLE HWND;
+#endif
+
+#if OE_MAC
+ // leave HWND undefined. This is picked up in macport.hxx (defined as WindowPtr)
+#endif
+
+ typedef BOOL EBFAR * LPBOOL; // pf, pis, pwas, pcan
+
+#endif // _INC_WINDOWS
+
+
+ // Types not defined by Windows:
+#undef CHAR
+typedef char CHAR; // ch
+typedef CHAR EBFAR * LPCHAR; // pch
+
+#undef SHORT
+typedef short SHORT; // s
+typedef SHORT EBFAR * LPSHORT; // ps
+
+typedef WORD USHORT; // u
+typedef DWORD ULONG; // ul
+
+typedef UINT EBFAR * LPUINT; // pun
+
+#undef NULL
+#define NULL 0
+
+#undef TRUE
+#define TRUE 1
+
+#undef FALSE
+#define FALSE 0
+
+#define TIPERROR HRESULT
+#define EBERR HRESULT
+
+// Types defined by OLE.
+#ifndef _OLE2_H_
+typedef long SCODE;
+#endif // _OLE2_H_
+
+#define VTABLE_EXPORT
+#define VTABLE_IMPORT
+
+
+#endif //TYPESX_H_INCLUDED
diff --git a/private/oleauto/src/typelib/validate.h b/private/oleauto/src/typelib/validate.h
new file mode 100644
index 000000000..602325a54
--- /dev/null
+++ b/private/oleauto/src/typelib/validate.h
@@ -0,0 +1,71 @@
+/***
+*validate.h
+*
+* Copyright (C) 1994, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Some pointer/interface validation routines.
+*
+*Revision History:
+*
+* [00] 23-Mar-94 bradlo: Created.
+*
+*Implementation Notes:
+*
+*****************************************************************************/
+
+#ifndef VALIDATE_H_INCLUDED
+#define VALIDATE_H_INCLUDED
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+BOOL FIsBadReadPtr(const void FAR* pv, UINT cb);
+BOOL FIsBadWritePtr(void FAR* pv, UINT cb);
+BOOL FIsBadCodePtr(void FAR* pv);
+BOOL FIsBadStringPtr(void FAR* psz, UINT cchMax);
+BOOL FIsBadInterface(void FAR* pv, UINT cMethods);
+
+HRESULT __inline
+ValidateReadPtr(const void FAR* pv, UINT cb)
+{
+ return FIsBadReadPtr(pv, cb)
+ ? HresultOfScode(E_INVALIDARG) : NOERROR;
+}
+
+HRESULT __inline
+ValidateWritePtr(void FAR* pv, UINT cb)
+{
+ return FIsBadWritePtr(pv, cb)
+ ? HresultOfScode(E_INVALIDARG) : NOERROR;
+}
+
+HRESULT __inline
+ValidateCodePtr(void FAR* pv)
+{
+ return FIsBadCodePtr(pv)
+ ? HresultOfScode(E_INVALIDARG) : NOERROR;
+}
+
+HRESULT __inline
+ValidateStringPtr(void FAR* pv, UINT cchMax)
+{
+ return FIsBadStringPtr(pv, cchMax)
+ ? HresultOfScode(E_INVALIDARG) : NOERROR;
+}
+
+HRESULT __inline
+ValidateInterface(void FAR* pv, UINT cMethods)
+{
+ return FIsBadInterface(pv, cMethods)
+ ? HresultOfScode(E_INVALIDARG) : NOERROR;
+}
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif // VALIDATE_H_INCLUDED
+
diff --git a/private/oleauto/src/typelib/version.hxx b/private/oleauto/src/typelib/version.hxx
new file mode 100644
index 000000000..94a5a5f8d
--- /dev/null
+++ b/private/oleauto/src/typelib/version.hxx
@@ -0,0 +1,67 @@
+/***
+*version.hxx - Local overriding of switches
+*
+* Copyright (C) 1990, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file is included immediately after switches.h.
+* This file is a hand assembled collection of all version.hxxs.
+* ID_DEBUG was taken out from this file and should be passed on CL
+* command line to the compiler.
+*
+*Revision History:
+*
+* [00] 02-Aug-94 t-issacl: Created
+*
+*****************************************************************************/
+
+#ifndef VERSION_HXX_INCLUDED
+#define VERSION_HXX_INCLUDED
+
+#define BLD_FEVER 1
+
+#ifdef WIN16
+#define BLD_WIN16 1
+#endif
+
+#if defined (WIN16) && !ID_DEBUG
+// special case for rwin16
+// don't include these #pragmas when running RC
+#ifndef RC_INVOKED
+#pragma message ("rwin16 building with inline_depth(10)")
+#pragma inline_depth(10)
+#endif //RC_INVOKED
+#endif
+
+
+#ifdef WIN32
+#define BLD_WIN32 1
+#endif
+
+
+#if defined (_MIPS_) || defined (_ALPHA_) || defined (_PPC_)
+#define OE_RISC 1
+#endif //DWIN32 mips
+
+
+#ifdef MACPPC
+#define BLD_MAC 1
+#define OE_RISC 1
+#define HE_WIN32 1 // Host is Win32
+#define USESROUTINEDESCRIPTORS 1 // For PPC routine descriptors
+
+// PowerPC currently uses the same yahu tool to convert MPW headers.
+#define __sysapi
+#define pascal _stdcall
+#define _pascal _stdcall
+#define __pascal _stdcall
+#endif //MACPPC
+
+
+#ifdef MAC
+#define BLD_MAC 1
+#endif //MAC
+
+
+#endif
diff --git a/private/oleauto/src/typelib/wep.c b/private/oleauto/src/typelib/wep.c
new file mode 100644
index 000000000..b8c40150f
--- /dev/null
+++ b/private/oleauto/src/typelib/wep.c
@@ -0,0 +1,144 @@
+/***
+*wep.c - Generic DLL termination code.
+*
+* Copyright (C) 1992, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* Contains the initialization and termination functions.
+* This is linked with DLLs (e.g. tls.dll and bind.dll) that don't
+* need to take any action at DLL termination time. It is included
+* simply to keep debug versions of windows from complaining that
+* a WEP entry point cannot be found.
+*
+*Revision History:
+*
+* [00] 24-Jun-92 tomc: Created.
+*
+*****************************************************************************/
+
+#include "switches.hxx"
+#if OE_WIN32
+#include "silver.hxx"
+#else
+#include "version.hxx"
+#include "types.h"
+#endif
+#include <stdlib.h> // for size_t
+#include "mbstring.h"
+
+
+/***
+*LibMain - Main entrypoint into TYPELIB.DLL
+*Purpose:
+* Called just before DLL is unloaded.
+*
+*Entry:
+* hinst - instance of the DLL
+* wDataSeg - value of the DS register
+* cbHeapSize - heap size as specified in the .DEF file
+* lpszCmdLine - ptr to command-line information
+*
+*Exit:
+* returns 1 to indicate success.
+*
+*Notes:
+*
+******************************************************************************/
+int PASCAL __export LibMain(HANDLE hinst, WORD wDataSeg, WORD cbHeapSize,
+ LPSTR lpszCmdLine)
+{
+ InitMbString();
+
+ return 1;
+}
+
+
+/***
+*WEP - Windows Exit Procedure
+*Purpose:
+* Called just before DLL is unloaded.
+*
+*Entry:
+* nExitType- Specifies whether all of Windows is shutting down or only the
+* individual library. This parameter can be either WEP_FREE_DLL or
+* WEP_SYSTEM_EXIT.
+*
+*Exit:
+* returns 1 to indicate success.
+*
+*Notes:
+*
+* UNDONE: Ensure this function is in a FIXED segment.
+*
+* For Windows version 3.1, WEP is called on the stack of the application that
+* is terminating. This enables WEP to call Windows functions. In Windows
+* version 3.0, however, WEP is called on a KERNEL stack that is too small to
+* process most calls to Windows functions. These calls, including calls to
+* global-memory functions, should be avoided in a WEP function for Windows
+* 3.0. Calls to MS-DOS functions go through a KERNEL intercept and can also
+* overflow the stack in Windows 3.0. There is no general reason to free memory
+* from the global heap in a WEP function, because the kernel frees this kind
+* of memory automatically.
+*
+* In some low-memory conditions, WEP can be called before the library
+* initialization function is called and before the library's DGROUP
+* data-segment group has been created. A WEP function that relies on the
+* library initialization function should verify that the initialization
+* function has been called. Also, WEP functions that rely on the validity of
+* DGROUP should check for this. The following procedure is recommended for
+* dynamic-link libraries in Windows 3.0; for Windows 3.1, only step 3 is
+* necessary.
+*
+* 1 Verify that the data segment is present by using a lar instruction and
+* checking the present bit. This will indicate whether DS has been loaded.
+* (The DS register always contains a valid selector.)
+*
+* 2 Set a flag in the data segment when the library initialization is
+* performed. Once the WEP function has verified that the data segment
+* exists, it should test this flag to determine whether initialization has
+* occurred.
+*
+* 3 Declare WEP in the EXPORTS section of the module-definition file for the
+* DLL. Following is an example declaration:
+*
+* WEP @1 RESIDENTNAME
+*
+* The keyword RESIDENTNAME makes the name of the function (WEP) resident at
+* all times. (It is not necessary to use the ordinal reference 1.) The name
+* listed in the LIBRARY statement of the module-definition file must be in
+* uppercase letters and must match the name of the DLL file.
+*
+* Windows calls the WEP function by name when it is ready to remove the DLL.
+* Under low-memory conditions, it is possible for the DLL's nonresident-name
+* table to be discarded from memory. If this occurs, Windows must load the
+* table to determine whether a WEP function was declared for the DLL. Under
+* low-memory conditions, this method could fail, causing a fatal exit. Using
+* the RESIDENTNAME option forces Windows to keep the name entry for WEP in
+* memory whenever the DLL is in use.
+*
+* In Windows 3.0, WEP must be placed in a fixed code segment. If it is placed
+* instead in a discardable segment, under low-memory conditions Windows must
+* load the WEP segment from disk so that the WEP function can be called before
+* the DLL is discarded. Under certain low-memory conditions, attempting to
+* load the segment containing WEP can cause a fatal exit. When WEP is in a
+* fixed segment, this situation cannot occur. (Because fixed DLL code is also
+* page-locked, you should minimize the amount of fixed code.)
+*
+* If a DLL is explicitly loaded by calling the LoadLibrary function, its WEP
+* function is called when the DLL is freed by a call to the FreeLibrary
+* function. (The FreeLibrary function should not be called from within a WEP
+* function.) If the DLL is implicitly loaded, WEP is also called, but some
+* debugging applications will indicate that the application has been
+* terminated before WEP is called.
+*
+* The WEP functions of dependent DLLs can be called in any order. This order
+* depends on the order in which the usage counts for the DLLs reach zero.
+*
+******************************************************************************/
+#pragma optimize("q",off)
+
+int PASCAL _WEP(int nExitType)
+{
+ return 1;
+}
diff --git a/private/oleauto/src/typelib/xstring.h b/private/oleauto/src/typelib/xstring.h
new file mode 100644
index 000000000..c303f9101
--- /dev/null
+++ b/private/oleauto/src/typelib/xstring.h
@@ -0,0 +1,60 @@
+/***
+*xstring.h - Multi-byte/Unicode string handling stub.
+*
+* Copyright (C) 1991, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file is a an include file containing macros and declarations
+* defining string handling functions so we can build SBCS/Kanji/Unicode
+* versions from the same source.
+*
+*Revision History:
+*
+* [00] 14-Jun-91 petergo: Created.
+* [01] 27-Feb-93 kazusy: Added DBCS version.
+* move non standard function to xutil.h
+*
+*Implementation Notes:
+* See \silver\doc\codestd\codestd.doc for info on these.
+* See the International handbook for background info.
+*
+*****************************************************************************/
+
+#ifndef XSTRING_H_INCLUDED
+#define XSTRING_H_INCLUDED
+
+#include <string.h>
+#include "mbstring.h" //[01]
+#include <stdlib.h>
+
+#if FV_UNICODE
+#error UNICODE support not available!
+#endif // FV_UNICODE
+
+
+#define xstrcpy(d,s) (char *)strcpy( (char *)(d), (const char *)(s) )
+#define xstrcat(d,s) (char *)strcat( (char *)(d), (const char *)(s) )
+#define xstrchr(p,c) (char *)_mbschr( (const unsigned char *)(p), c)
+#define xstrrchr(p,c) (char *)_mbsrchr( (const unsigned char *)(p), c)
+#define xstrcmp(s1,s2) _mbscmp( (const unsigned char *)(s1), (const unsigned char *)(s2) )
+
+#define xstrlen strlen
+#define xstrclen(s) _mbslen( (const unsigned char *)(s) ) // character length
+#define xstrblen strlen // byte length
+#define xstrblen0(s) (strlen(s)+1) // byte length w/ terminator
+#define xstrncpy(d,s,c) (char *)_mbsnbcpy( (unsigned char *)(d), (const unsigned char *)(s), c )
+#define xstrncmp(s1,s2,c) _mbsncmp( (const unsigned char *)(s1), (const unsigned char *)(s2), c )
+
+#define xstricmp(s1,s2) _mbsicmp( (const unsigned char *)(s1), (const unsigned char *)(s2) )
+
+#define xtoupper toupper
+#define xtolower tolower
+#define xstrupr strupr
+
+#define xatoi atoi
+#define xltoa ltoa // not DBCS-dependent
+#define xitoa itoa // not DBCS-dependent
+
+
+#endif // XSTRING_H_INCLUDED
diff --git a/private/oleauto/src/typelib/xutil.h b/private/oleauto/src/typelib/xutil.h
new file mode 100644
index 000000000..499e1f363
--- /dev/null
+++ b/private/oleauto/src/typelib/xutil.h
@@ -0,0 +1,196 @@
+/***
+*xutil.h - Multi-byte/Unicode string handling stub.
+*
+* Copyright (C) 1993, Microsoft Corporation. All Rights Reserved.
+* Information Contained Herein Is Proprietary and Confidential.
+*
+*Purpose:
+* This file is a an include file containing macros and declarations
+* defining string handling functions so we can build SBCS/MBCS/Unicode
+* versions from the same source.
+*
+*Revision History:
+*
+* [01] 08-Mar-93 kazusy: Created.
+*
+*Implementation Notes:
+* See \silver\doc\codestd\codestd.doc for info on these.
+* See the International handbook for background info.
+*
+*****************************************************************************/
+
+#ifndef XUTIL_H_INCLUDED
+#define XUTIL_H_INCLUDED
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+
+extern char g_rgchLeadByteTable[256]; // defined in mbstring.c
+#define xislead(c) g_rgchLeadByteTable[(BYTE)c]
+
+
+/****************************************************************************
+* xgetc - DBCS version
+*
+* Returns a character from a string. If the character is composed of a DBCS
+* lead byte followed by '\0' (an illegal character), '\0' is returned.
+*
+****************************************************************************/
+unsigned short __inline xgetc(char *p)
+{
+ unsigned short c;
+
+ if (xislead((unsigned char)(c = (*(unsigned char*)p++)))) {
+ if (*p == '\0') {
+ c = '\0';
+ } else {
+ c *= 256;
+ c += (unsigned short)*(unsigned char *)p;
+ }
+ }
+ return c;
+}
+
+/****************************************************************************
+* xgetincc - DBCS version
+*
+* Returns a character from a string and updates the string pointer to the
+* start of the next character.. If the character is composed of a DBCS
+* lead byte followed by '\0' (an illegal character), '\0' is returned and the
+* string pointer points to the '\0' byte.
+*
+****************************************************************************/
+unsigned short __inline xgetincc(unsigned char **p)
+{
+ unsigned char *q = *p;
+ unsigned short c = 0;
+
+ if (xislead((unsigned char)(c = *q++))) {
+ if (*q == '\0') {
+ c = '\0';
+ } else {
+ c *= 256;
+ c += (unsigned short)*q++;
+ }
+ }
+ *p = q;
+ return c;
+}
+
+/****************************************************************************
+* xputc - DBCS version
+*
+* Writes a character into a string without moving the string pointer.
+* Note that no checking is done to verify that the high byte of the character
+* is a valid lead byte: if the character has a high byte, then two bytes are
+* written. If the character has a high byte==0, then one byte is written.
+*
+****************************************************************************/
+void __inline xputc(unsigned char *p, unsigned short c)
+{
+ if (c >= 256)
+ *p++ = (unsigned char)(c >> 8);
+ *p = (unsigned char)c;
+}
+
+/****************************************************************************
+* xputincc - DBCS version
+*
+* Writes a character into a string and moves the string pointer to the
+* byte following the character just written. Note that no checking is done
+* to verify that the high byte of the character is a valid lead byte: if
+* the character has a high byte, then two bytes are written. If the
+* character has a high byte==0, then one byte is written.
+*
+****************************************************************************/
+void __inline xputincc(unsigned char **p, unsigned short c)
+{
+ unsigned char *q = *p;
+
+ if (c >= 256)
+ *q++ = (unsigned char)(c >> 8);
+ *q++ = (unsigned char)c;
+ *p = q;
+}
+
+/****************************************************************************
+* xincc - DBCS version
+*
+* Moves the string pointer to the beginning of the next character. If the
+* character is compose of a DBCS lead byte followed by a '\0', move the
+* pointer so that it points at the '\0', not the byte beyond the end of
+* the string.
+*
+****************************************************************************/
+void __inline xincc(unsigned char **p)
+{
+ unsigned char *q = *p;
+
+ if (xislead(*q) && *q++ == '\0')
+ q--;
+ q++;
+ *p = q;
+}
+
+/****************************************************************************
+* xsizc - DBCS version
+*
+* Returns the size of a character in bytes.
+*
+****************************************************************************/
+#define xsizc(c) ( (unsigned short)(c) >= 256 ? 2 : 1 )
+
+/***
+* xstrinc - DBCS version
+*
+* Returns a pointer to the next character in a string.
+********************************************************************/
+#define xstrinc(p) (xislead(*p) ? p+2 : p+1)
+
+/****
+* xstrdec(s,p)
+*
+* Returns a pointer to a previous character in a string
+***********************************************************************/
+#if !OE_WIN32
+XCHAR *xstrdec(XCHAR *pxchStart,XCHAR *pxch);
+#endif
+
+/***
+*XCHAR *PxchFindPrevCharOrBeginOfChar(XSZ xszStart, XCHAR *pxchCur)
+*Purpose:
+* This finds the first character in the string xszStart which
+* begins at an address lower than pxchCur. This is used
+* to move backwards in a string possibly containing double
+* byte characters.
+*
+* Unlike xstrdec, this may be called in the case where
+* pxchCur may point into the middle of a character. (If
+* pxchCur does happen to point into the middle of a character,
+* then this returns a pointer to the beginning of that character.
+* (Hence the long name for this function.))
+*
+* If you are sure that pxchCur doesn't point into the middle
+* of a double byte character, you should call xstrdec.
+*
+***********************************************************************/
+#if 0
+XCHAR *PxchFindPrevCharOrBeginOfChar(XCHAR *pxchFirst, XCHAR *pxchCur);
+#endif
+
+
+
+/***
+* xpch - DBCS and non-DBCS
+* // CONSIDER - replace uses of xpch with xgetc
+***********************************************************************/
+#define xpch(p) xgetc(p)
+
+#ifdef __cplusplus
+}
+#endif
+
+
+#endif // XUTIL_H_INCLUDED